1 /* Copyright (c) 2012-2016, The Linux Foundation. All rights reserved. 2 * 3 * Redistribution and use in source and binary forms, with or without 4 * modification, are permitted provided that the following conditions are 5 * met: 6 * * Redistributions of source code must retain the above copyright 7 * notice, this list of conditions and the following disclaimer. 8 * * Redistributions in binary form must reproduce the above 9 * copyright notice, this list of conditions and the following 10 * disclaimer in the documentation and/or other materials provided 11 * with the distribution. 12 * * Neither the name of The Linux Foundation nor the names of its 13 * contributors may be used to endorse or promote products derived 14 * from this software without specific prior written permission. 15 * 16 * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED 17 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 18 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT 19 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS 20 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 21 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 22 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR 23 * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 24 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE 25 * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN 26 * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 * 28 */ 29 30 // To remove 31 #include <cutils/properties.h> 32 33 // System dependencies 34 #include <pthread.h> 35 #include <errno.h> 36 #include <fcntl.h> 37 #include <stdlib.h> 38 #include <linux/media.h> 39 #include <media/msm_cam_sensor.h> 40 #include <dlfcn.h> 41 42 #define IOCTL_H <SYSTEM_HEADER_PREFIX/ioctl.h> 43 #include IOCTL_H 44 45 // Camera dependencies 46 #include "mm_camera_dbg.h" 47 #include "mm_camera_interface.h" 48 #include "mm_camera.h" 49 50 static pthread_mutex_t g_intf_lock = PTHREAD_MUTEX_INITIALIZER; 51 52 static mm_camera_ctrl_t g_cam_ctrl; 53 54 static pthread_mutex_t g_handler_lock = PTHREAD_MUTEX_INITIALIZER; 55 static uint16_t g_handler_history_count = 0; /* history count for handler */ 56 57 #define CAM_SENSOR_TYPE_MASK (1U<<24) // 24th (starting from 0) bit tells its a MAIN or AUX camera 58 #define CAM_SENSOR_FORMAT_MASK (1U<<25) // 25th(starting from 0) bit tells its YUV sensor or not 59 60 /*=========================================================================== 61 * FUNCTION : mm_camera_util_generate_handler 62 * 63 * DESCRIPTION: utility function to generate handler for camera/channel/stream 64 * 65 * PARAMETERS : 66 * @index: index of the object to have handler 67 * 68 * RETURN : uint32_t type of handle that uniquely identify the object 69 *==========================================================================*/ 70 uint32_t mm_camera_util_generate_handler(uint8_t index) 71 { 72 uint32_t handler = 0; 73 pthread_mutex_lock(&g_handler_lock); 74 g_handler_history_count++; 75 if (0 == g_handler_history_count) { 76 g_handler_history_count++; 77 } 78 handler = g_handler_history_count; 79 handler = (handler<<8) | index; 80 pthread_mutex_unlock(&g_handler_lock); 81 return handler; 82 } 83 84 /*=========================================================================== 85 * FUNCTION : mm_camera_util_get_index_by_handler 86 * 87 * DESCRIPTION: utility function to get index from handle 88 * 89 * PARAMETERS : 90 * @handler: object handle 91 * 92 * RETURN : uint8_t type of index derived from handle 93 *==========================================================================*/ 94 uint8_t mm_camera_util_get_index_by_handler(uint32_t handler) 95 { 96 return (handler&0x000000ff); 97 } 98 99 /*=========================================================================== 100 * FUNCTION : mm_camera_util_get_dev_name 101 * 102 * DESCRIPTION: utility function to get device name from camera handle 103 * 104 * PARAMETERS : 105 * @cam_handle: camera handle 106 * 107 * RETURN : char ptr to the device name stored in global variable 108 * NOTE : caller should not free the char ptr 109 *==========================================================================*/ 110 const char *mm_camera_util_get_dev_name(uint32_t cam_handle) 111 { 112 char *dev_name = NULL; 113 uint8_t cam_idx = mm_camera_util_get_index_by_handler(cam_handle); 114 if(cam_idx < MM_CAMERA_MAX_NUM_SENSORS) { 115 dev_name = g_cam_ctrl.video_dev_name[cam_idx]; 116 } 117 return dev_name; 118 } 119 120 /*=========================================================================== 121 * FUNCTION : mm_camera_util_get_camera_by_handler 122 * 123 * DESCRIPTION: utility function to get camera object from camera handle 124 * 125 * PARAMETERS : 126 * @cam_handle: camera handle 127 * 128 * RETURN : ptr to the camera object stored in global variable 129 * NOTE : caller should not free the camera object ptr 130 *==========================================================================*/ 131 mm_camera_obj_t* mm_camera_util_get_camera_by_handler(uint32_t cam_handle) 132 { 133 mm_camera_obj_t *cam_obj = NULL; 134 uint8_t cam_idx = mm_camera_util_get_index_by_handler(cam_handle); 135 136 if (cam_idx < MM_CAMERA_MAX_NUM_SENSORS && 137 (NULL != g_cam_ctrl.cam_obj[cam_idx]) && 138 (cam_handle == g_cam_ctrl.cam_obj[cam_idx]->my_hdl)) { 139 cam_obj = g_cam_ctrl.cam_obj[cam_idx]; 140 } 141 return cam_obj; 142 } 143 144 /*=========================================================================== 145 * FUNCTION : mm_camera_util_get_camera_by_session_id 146 * 147 * DESCRIPTION: utility function to get camera object from camera sessionID 148 * 149 * PARAMETERS : 150 * @session_id: sessionid for which cam obj mapped 151 * 152 * RETURN : ptr to the camera object stored in global variable 153 * NOTE : caller should not free the camera object ptr 154 *==========================================================================*/ 155 mm_camera_obj_t* mm_camera_util_get_camera_by_session_id(uint32_t session_id) 156 { 157 int cam_idx = 0; 158 mm_camera_obj_t *cam_obj = NULL; 159 for (cam_idx = 0; cam_idx < MM_CAMERA_MAX_NUM_SENSORS; cam_idx++) { 160 if ((NULL != g_cam_ctrl.cam_obj[cam_idx]) && 161 (session_id == (uint32_t)g_cam_ctrl.cam_obj[cam_idx]->sessionid)) { 162 LOGD("session id:%d match idx:%d\n", session_id, cam_idx); 163 cam_obj = g_cam_ctrl.cam_obj[cam_idx]; 164 } 165 } 166 return cam_obj; 167 } 168 169 /*=========================================================================== 170 * FUNCTION : mm_camera_intf_query_capability 171 * 172 * DESCRIPTION: query camera capability 173 * 174 * PARAMETERS : 175 * @camera_handle: camera handle 176 * 177 * RETURN : int32_t type of status 178 * 0 -- success 179 * -1 -- failure 180 *==========================================================================*/ 181 static int32_t mm_camera_intf_query_capability(uint32_t camera_handle) 182 { 183 int32_t rc = -1; 184 mm_camera_obj_t * my_obj = NULL; 185 186 LOGD("E: camera_handler = %d ", camera_handle); 187 188 pthread_mutex_lock(&g_intf_lock); 189 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 190 191 if(my_obj) { 192 pthread_mutex_lock(&my_obj->cam_lock); 193 pthread_mutex_unlock(&g_intf_lock); 194 rc = mm_camera_query_capability(my_obj); 195 } else { 196 pthread_mutex_unlock(&g_intf_lock); 197 } 198 LOGD("X rc = %d", rc); 199 return rc; 200 } 201 202 /*=========================================================================== 203 * FUNCTION : mm_camera_intf_set_parms 204 * 205 * DESCRIPTION: set parameters per camera 206 * 207 * PARAMETERS : 208 * @camera_handle: camera handle 209 * @parms : ptr to a param struct to be set to server 210 * 211 * RETURN : int32_t type of status 212 * 0 -- success 213 * -1 -- failure 214 * NOTE : Assume the parms struct buf is already mapped to server via 215 * domain socket. Corresponding fields of parameters to be set 216 * are already filled in by upper layer caller. 217 *==========================================================================*/ 218 static int32_t mm_camera_intf_set_parms(uint32_t camera_handle, 219 parm_buffer_t *parms) 220 { 221 int32_t rc = -1; 222 mm_camera_obj_t * my_obj = NULL; 223 224 pthread_mutex_lock(&g_intf_lock); 225 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 226 227 if(my_obj) { 228 pthread_mutex_lock(&my_obj->cam_lock); 229 pthread_mutex_unlock(&g_intf_lock); 230 rc = mm_camera_set_parms(my_obj, parms); 231 } else { 232 pthread_mutex_unlock(&g_intf_lock); 233 } 234 return rc; 235 } 236 237 /*=========================================================================== 238 * FUNCTION : mm_camera_intf_get_parms 239 * 240 * DESCRIPTION: get parameters per camera 241 * 242 * PARAMETERS : 243 * @camera_handle: camera handle 244 * @parms : ptr to a param struct to be get from server 245 * 246 * RETURN : int32_t type of status 247 * 0 -- success 248 * -1 -- failure 249 * NOTE : Assume the parms struct buf is already mapped to server via 250 * domain socket. Parameters to be get from server are already 251 * filled in by upper layer caller. After this call, corresponding 252 * fields of requested parameters will be filled in by server with 253 * detailed information. 254 *==========================================================================*/ 255 static int32_t mm_camera_intf_get_parms(uint32_t camera_handle, 256 parm_buffer_t *parms) 257 { 258 int32_t rc = -1; 259 mm_camera_obj_t * my_obj = NULL; 260 261 pthread_mutex_lock(&g_intf_lock); 262 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 263 264 if(my_obj) { 265 pthread_mutex_lock(&my_obj->cam_lock); 266 pthread_mutex_unlock(&g_intf_lock); 267 rc = mm_camera_get_parms(my_obj, parms); 268 } else { 269 pthread_mutex_unlock(&g_intf_lock); 270 } 271 return rc; 272 } 273 274 /*=========================================================================== 275 * FUNCTION : mm_camera_intf_do_auto_focus 276 * 277 * DESCRIPTION: performing auto focus 278 * 279 * PARAMETERS : 280 * @camera_handle: camera handle 281 * 282 * RETURN : int32_t type of status 283 * 0 -- success 284 * -1 -- failure 285 * NOTE : if this call success, we will always assume there will 286 * be an auto_focus event following up. 287 *==========================================================================*/ 288 static int32_t mm_camera_intf_do_auto_focus(uint32_t camera_handle) 289 { 290 int32_t rc = -1; 291 mm_camera_obj_t * my_obj = NULL; 292 293 pthread_mutex_lock(&g_intf_lock); 294 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 295 296 if(my_obj) { 297 pthread_mutex_lock(&my_obj->cam_lock); 298 pthread_mutex_unlock(&g_intf_lock); 299 rc = mm_camera_do_auto_focus(my_obj); 300 } else { 301 pthread_mutex_unlock(&g_intf_lock); 302 } 303 return rc; 304 } 305 306 /*=========================================================================== 307 * FUNCTION : mm_camera_intf_cancel_auto_focus 308 * 309 * DESCRIPTION: cancel auto focus 310 * 311 * PARAMETERS : 312 * @camera_handle: camera handle 313 * 314 * RETURN : int32_t type of status 315 * 0 -- success 316 * -1 -- failure 317 *==========================================================================*/ 318 static int32_t mm_camera_intf_cancel_auto_focus(uint32_t camera_handle) 319 { 320 int32_t rc = -1; 321 mm_camera_obj_t * my_obj = NULL; 322 323 pthread_mutex_lock(&g_intf_lock); 324 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 325 326 if(my_obj) { 327 pthread_mutex_lock(&my_obj->cam_lock); 328 pthread_mutex_unlock(&g_intf_lock); 329 rc = mm_camera_cancel_auto_focus(my_obj); 330 } else { 331 pthread_mutex_unlock(&g_intf_lock); 332 } 333 return rc; 334 } 335 336 /*=========================================================================== 337 * FUNCTION : mm_camera_intf_prepare_snapshot 338 * 339 * DESCRIPTION: prepare hardware for snapshot 340 * 341 * PARAMETERS : 342 * @camera_handle: camera handle 343 * @do_af_flag : flag indicating if AF is needed 344 * 345 * RETURN : int32_t type of status 346 * 0 -- success 347 * -1 -- failure 348 *==========================================================================*/ 349 static int32_t mm_camera_intf_prepare_snapshot(uint32_t camera_handle, 350 int32_t do_af_flag) 351 { 352 int32_t rc = -1; 353 mm_camera_obj_t * my_obj = NULL; 354 355 pthread_mutex_lock(&g_intf_lock); 356 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 357 358 if(my_obj) { 359 pthread_mutex_lock(&my_obj->cam_lock); 360 pthread_mutex_unlock(&g_intf_lock); 361 rc = mm_camera_prepare_snapshot(my_obj, do_af_flag); 362 } else { 363 pthread_mutex_unlock(&g_intf_lock); 364 } 365 return rc; 366 } 367 368 /*=========================================================================== 369 * FUNCTION : mm_camera_intf_flush 370 * 371 * DESCRIPTION: flush the current camera state and buffers 372 * 373 * PARAMETERS : 374 * @camera_handle: camera handle 375 * 376 * RETURN : int32_t type of status 377 * 0 -- success 378 * -1 -- failure 379 *==========================================================================*/ 380 static int32_t mm_camera_intf_flush(uint32_t camera_handle) 381 { 382 int32_t rc = -1; 383 mm_camera_obj_t * my_obj = NULL; 384 385 pthread_mutex_lock(&g_intf_lock); 386 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 387 388 if(my_obj) { 389 pthread_mutex_lock(&my_obj->cam_lock); 390 pthread_mutex_unlock(&g_intf_lock); 391 rc = mm_camera_flush(my_obj); 392 } else { 393 pthread_mutex_unlock(&g_intf_lock); 394 } 395 return rc; 396 } 397 398 /*=========================================================================== 399 * FUNCTION : mm_camera_intf_close 400 * 401 * DESCRIPTION: close a camera by its handle 402 * 403 * PARAMETERS : 404 * @camera_handle: camera handle 405 * 406 * RETURN : int32_t type of status 407 * 0 -- success 408 * -1 -- failure 409 *==========================================================================*/ 410 static int32_t mm_camera_intf_close(uint32_t camera_handle) 411 { 412 int32_t rc = -1; 413 uint8_t cam_idx = camera_handle & 0x00ff; 414 mm_camera_obj_t * my_obj = NULL; 415 416 LOGD("E: camera_handler = %d ", camera_handle); 417 418 pthread_mutex_lock(&g_intf_lock); 419 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 420 421 if (my_obj){ 422 my_obj->ref_count--; 423 424 if(my_obj->ref_count > 0) { 425 /* still have reference to obj, return here */ 426 LOGD("ref_count=%d\n", my_obj->ref_count); 427 pthread_mutex_unlock(&g_intf_lock); 428 rc = 0; 429 } else { 430 /* need close camera here as no other reference 431 * first empty g_cam_ctrl's referent to cam_obj */ 432 g_cam_ctrl.cam_obj[cam_idx] = NULL; 433 434 pthread_mutex_lock(&my_obj->cam_lock); 435 pthread_mutex_unlock(&g_intf_lock); 436 rc = mm_camera_close(my_obj); 437 pthread_mutex_destroy(&my_obj->cam_lock); 438 free(my_obj); 439 } 440 } else { 441 pthread_mutex_unlock(&g_intf_lock); 442 } 443 444 return rc; 445 } 446 447 /*=========================================================================== 448 * FUNCTION : mm_camera_intf_add_channel 449 * 450 * DESCRIPTION: add a channel 451 * 452 * PARAMETERS : 453 * @camera_handle: camera handle 454 * @attr : bundle attribute of the channel if needed 455 * @channel_cb : callback function for bundle data notify 456 * @userdata : user data ptr 457 * 458 * RETURN : uint32_t type of channel handle 459 * 0 -- invalid channel handle, meaning the op failed 460 * >0 -- successfully added a channel with a valid handle 461 * NOTE : if no bundle data notify is needed, meaning each stream in the 462 * channel will have its own stream data notify callback, then 463 * attr, channel_cb, and userdata can be NULL. In this case, 464 * no matching logic will be performed in channel for the bundling. 465 *==========================================================================*/ 466 static uint32_t mm_camera_intf_add_channel(uint32_t camera_handle, 467 mm_camera_channel_attr_t *attr, 468 mm_camera_buf_notify_t channel_cb, 469 void *userdata) 470 { 471 uint32_t ch_id = 0; 472 mm_camera_obj_t * my_obj = NULL; 473 474 LOGD("E camera_handler = %d", camera_handle); 475 pthread_mutex_lock(&g_intf_lock); 476 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 477 478 if(my_obj) { 479 pthread_mutex_lock(&my_obj->cam_lock); 480 pthread_mutex_unlock(&g_intf_lock); 481 ch_id = mm_camera_add_channel(my_obj, attr, channel_cb, userdata); 482 } else { 483 pthread_mutex_unlock(&g_intf_lock); 484 } 485 LOGD("X ch_id = %d", ch_id); 486 return ch_id; 487 } 488 489 /*=========================================================================== 490 * FUNCTION : mm_camera_intf_del_channel 491 * 492 * DESCRIPTION: delete a channel by its handle 493 * 494 * PARAMETERS : 495 * @camera_handle: camera handle 496 * @ch_id : channel handle 497 * 498 * RETURN : int32_t type of status 499 * 0 -- success 500 * -1 -- failure 501 * NOTE : all streams in the channel should be stopped already before 502 * this channel can be deleted. 503 *==========================================================================*/ 504 static int32_t mm_camera_intf_del_channel(uint32_t camera_handle, 505 uint32_t ch_id) 506 { 507 int32_t rc = -1; 508 mm_camera_obj_t * my_obj = NULL; 509 510 LOGD("E ch_id = %d", ch_id); 511 pthread_mutex_lock(&g_intf_lock); 512 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 513 514 if(my_obj) { 515 pthread_mutex_lock(&my_obj->cam_lock); 516 pthread_mutex_unlock(&g_intf_lock); 517 rc = mm_camera_del_channel(my_obj, ch_id); 518 } else { 519 pthread_mutex_unlock(&g_intf_lock); 520 } 521 LOGD("X"); 522 return rc; 523 } 524 525 /*=========================================================================== 526 * FUNCTION : mm_camera_intf_get_bundle_info 527 * 528 * DESCRIPTION: query bundle info of the channel 529 * 530 * PARAMETERS : 531 * @camera_handle: camera handle 532 * @ch_id : channel handle 533 * @bundle_info : bundle info to be filled in 534 * 535 * RETURN : int32_t type of status 536 * 0 -- success 537 * -1 -- failure 538 * NOTE : all streams in the channel should be stopped already before 539 * this channel can be deleted. 540 *==========================================================================*/ 541 static int32_t mm_camera_intf_get_bundle_info(uint32_t camera_handle, 542 uint32_t ch_id, 543 cam_bundle_config_t *bundle_info) 544 { 545 int32_t rc = -1; 546 mm_camera_obj_t * my_obj = NULL; 547 548 LOGD("E ch_id = %d", ch_id); 549 pthread_mutex_lock(&g_intf_lock); 550 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 551 552 if(my_obj) { 553 pthread_mutex_lock(&my_obj->cam_lock); 554 pthread_mutex_unlock(&g_intf_lock); 555 rc = mm_camera_get_bundle_info(my_obj, ch_id, bundle_info); 556 } else { 557 pthread_mutex_unlock(&g_intf_lock); 558 } 559 LOGD("X"); 560 return rc; 561 } 562 563 /*=========================================================================== 564 * FUNCTION : mm_camera_intf_register_event_notify 565 * 566 * DESCRIPTION: register for event notify 567 * 568 * PARAMETERS : 569 * @camera_handle: camera handle 570 * @evt_cb : callback for event notify 571 * @user_data : user data ptr 572 * 573 * RETURN : int32_t type of status 574 * 0 -- success 575 * -1 -- failure 576 *==========================================================================*/ 577 static int32_t mm_camera_intf_register_event_notify(uint32_t camera_handle, 578 mm_camera_event_notify_t evt_cb, 579 void * user_data) 580 { 581 int32_t rc = -1; 582 mm_camera_obj_t * my_obj = NULL; 583 584 LOGD("E "); 585 pthread_mutex_lock(&g_intf_lock); 586 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 587 588 if(my_obj) { 589 pthread_mutex_lock(&my_obj->cam_lock); 590 pthread_mutex_unlock(&g_intf_lock); 591 rc = mm_camera_register_event_notify(my_obj, evt_cb, user_data); 592 } else { 593 pthread_mutex_unlock(&g_intf_lock); 594 } 595 LOGD("E rc = %d", rc); 596 return rc; 597 } 598 599 /*=========================================================================== 600 * FUNCTION : mm_camera_intf_qbuf 601 * 602 * DESCRIPTION: enqueue buffer back to kernel 603 * 604 * PARAMETERS : 605 * @camera_handle: camera handle 606 * @ch_id : channel handle 607 * @buf : buf ptr to be enqueued 608 * 609 * RETURN : int32_t type of status 610 * 0 -- success 611 * -1 -- failure 612 *==========================================================================*/ 613 static int32_t mm_camera_intf_qbuf(uint32_t camera_handle, 614 uint32_t ch_id, 615 mm_camera_buf_def_t *buf) 616 { 617 int32_t rc = -1; 618 mm_camera_obj_t * my_obj = NULL; 619 620 pthread_mutex_lock(&g_intf_lock); 621 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 622 623 if(my_obj) { 624 pthread_mutex_lock(&my_obj->cam_lock); 625 pthread_mutex_unlock(&g_intf_lock); 626 rc = mm_camera_qbuf(my_obj, ch_id, buf); 627 } else { 628 pthread_mutex_unlock(&g_intf_lock); 629 } 630 LOGD("X evt_type = %d",rc); 631 return rc; 632 } 633 634 /*=========================================================================== 635 * FUNCTION : mm_camera_intf_qbuf 636 * 637 * DESCRIPTION: enqueue buffer back to kernel 638 * 639 * PARAMETERS : 640 * @camera_handle: camera handle 641 * @ch_id : channel handle 642 * @buf : buf ptr to be enqueued 643 * 644 * RETURN : int32_t type of status 645 * 0 -- success 646 * -1 -- failure 647 *==========================================================================*/ 648 static int32_t mm_camera_intf_cancel_buf(uint32_t camera_handle, uint32_t ch_id, uint32_t stream_id, 649 uint32_t buf_idx) 650 { 651 int32_t rc = -1; 652 mm_camera_obj_t * my_obj = NULL; 653 654 pthread_mutex_lock(&g_intf_lock); 655 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 656 657 if(my_obj) { 658 pthread_mutex_lock(&my_obj->cam_lock); 659 pthread_mutex_unlock(&g_intf_lock); 660 rc = mm_camera_cancel_buf(my_obj, ch_id, stream_id, buf_idx); 661 } else { 662 pthread_mutex_unlock(&g_intf_lock); 663 } 664 LOGD("X evt_type = %d",rc); 665 return rc; 666 } 667 668 669 /*=========================================================================== 670 * FUNCTION : mm_camera_intf_get_queued_buf_count 671 * 672 * DESCRIPTION: returns the queued buffer count 673 * 674 * PARAMETERS : 675 * @camera_handle: camera handle 676 * @ch_id : channel handle 677 * @stream_id : stream id 678 * 679 * RETURN : int32_t - queued buffer count 680 * 681 *==========================================================================*/ 682 static int32_t mm_camera_intf_get_queued_buf_count(uint32_t camera_handle, 683 uint32_t ch_id, uint32_t stream_id) 684 { 685 int32_t rc = -1; 686 mm_camera_obj_t * my_obj = NULL; 687 688 pthread_mutex_lock(&g_intf_lock); 689 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 690 691 if(my_obj) { 692 pthread_mutex_lock(&my_obj->cam_lock); 693 pthread_mutex_unlock(&g_intf_lock); 694 rc = mm_camera_get_queued_buf_count(my_obj, ch_id, stream_id); 695 } else { 696 pthread_mutex_unlock(&g_intf_lock); 697 } 698 LOGD("X queued buffer count = %d",rc); 699 return rc; 700 } 701 702 /*=========================================================================== 703 * FUNCTION : mm_camera_intf_link_stream 704 * 705 * DESCRIPTION: link a stream into a new channel 706 * 707 * PARAMETERS : 708 * @camera_handle: camera handle 709 * @ch_id : channel handle 710 * @stream_id : stream id 711 * @linked_ch_id : channel in which the stream will be linked 712 * 713 * RETURN : int32_t type of stream handle 714 * 0 -- invalid stream handle, meaning the op failed 715 * >0 -- successfully linked a stream with a valid handle 716 *==========================================================================*/ 717 static int32_t mm_camera_intf_link_stream(uint32_t camera_handle, 718 uint32_t ch_id, 719 uint32_t stream_id, 720 uint32_t linked_ch_id) 721 { 722 uint32_t id = 0; 723 mm_camera_obj_t * my_obj = NULL; 724 725 LOGD("E handle = %u ch_id = %u", 726 camera_handle, ch_id); 727 728 pthread_mutex_lock(&g_intf_lock); 729 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 730 731 if(my_obj) { 732 pthread_mutex_lock(&my_obj->cam_lock); 733 pthread_mutex_unlock(&g_intf_lock); 734 id = mm_camera_link_stream(my_obj, ch_id, stream_id, linked_ch_id); 735 } else { 736 pthread_mutex_unlock(&g_intf_lock); 737 } 738 739 LOGD("X stream_id = %u", stream_id); 740 return (int32_t)id; 741 } 742 743 /*=========================================================================== 744 * FUNCTION : mm_camera_intf_add_stream 745 * 746 * DESCRIPTION: add a stream into a channel 747 * 748 * PARAMETERS : 749 * @camera_handle: camera handle 750 * @ch_id : channel handle 751 * 752 * RETURN : uint32_t type of stream handle 753 * 0 -- invalid stream handle, meaning the op failed 754 * >0 -- successfully added a stream with a valid handle 755 *==========================================================================*/ 756 static uint32_t mm_camera_intf_add_stream(uint32_t camera_handle, 757 uint32_t ch_id) 758 { 759 uint32_t stream_id = 0; 760 mm_camera_obj_t * my_obj = NULL; 761 762 LOGD("E handle = %d ch_id = %d", 763 camera_handle, ch_id); 764 765 pthread_mutex_lock(&g_intf_lock); 766 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 767 768 if(my_obj) { 769 pthread_mutex_lock(&my_obj->cam_lock); 770 pthread_mutex_unlock(&g_intf_lock); 771 stream_id = mm_camera_add_stream(my_obj, ch_id); 772 } else { 773 pthread_mutex_unlock(&g_intf_lock); 774 } 775 LOGD("X stream_id = %d", stream_id); 776 return stream_id; 777 } 778 779 /*=========================================================================== 780 * FUNCTION : mm_camera_intf_del_stream 781 * 782 * DESCRIPTION: delete a stream by its handle 783 * 784 * PARAMETERS : 785 * @camera_handle: camera handle 786 * @ch_id : channel handle 787 * @stream_id : stream handle 788 * 789 * RETURN : int32_t type of status 790 * 0 -- success 791 * -1 -- failure 792 * NOTE : stream should be stopped already before it can be deleted. 793 *==========================================================================*/ 794 static int32_t mm_camera_intf_del_stream(uint32_t camera_handle, 795 uint32_t ch_id, 796 uint32_t stream_id) 797 { 798 int32_t rc = -1; 799 mm_camera_obj_t * my_obj = NULL; 800 801 LOGD("E handle = %d ch_id = %d stream_id = %d", 802 camera_handle, ch_id, stream_id); 803 804 pthread_mutex_lock(&g_intf_lock); 805 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 806 807 if(my_obj) { 808 pthread_mutex_lock(&my_obj->cam_lock); 809 pthread_mutex_unlock(&g_intf_lock); 810 rc = mm_camera_del_stream(my_obj, ch_id, stream_id); 811 } else { 812 pthread_mutex_unlock(&g_intf_lock); 813 } 814 LOGD("X rc = %d", rc); 815 return rc; 816 } 817 818 /*=========================================================================== 819 * FUNCTION : mm_camera_intf_config_stream 820 * 821 * DESCRIPTION: configure a stream 822 * 823 * PARAMETERS : 824 * @camera_handle: camera handle 825 * @ch_id : channel handle 826 * @stream_id : stream handle 827 * @config : stream configuration 828 * 829 * RETURN : int32_t type of status 830 * 0 -- success 831 * -1 -- failure 832 *==========================================================================*/ 833 static int32_t mm_camera_intf_config_stream(uint32_t camera_handle, 834 uint32_t ch_id, 835 uint32_t stream_id, 836 mm_camera_stream_config_t *config) 837 { 838 int32_t rc = -1; 839 mm_camera_obj_t * my_obj = NULL; 840 841 LOGD("E handle = %d, ch_id = %d,stream_id = %d", 842 camera_handle, ch_id, stream_id); 843 844 pthread_mutex_lock(&g_intf_lock); 845 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 846 847 LOGD("mm_camera_intf_config_stream stream_id = %d",stream_id); 848 849 if(my_obj) { 850 pthread_mutex_lock(&my_obj->cam_lock); 851 pthread_mutex_unlock(&g_intf_lock); 852 rc = mm_camera_config_stream(my_obj, ch_id, stream_id, config); 853 } else { 854 pthread_mutex_unlock(&g_intf_lock); 855 } 856 LOGD("X rc = %d", rc); 857 return rc; 858 } 859 860 /*=========================================================================== 861 * FUNCTION : mm_camera_intf_start_channel 862 * 863 * DESCRIPTION: start a channel, which will start all streams in the channel 864 * 865 * PARAMETERS : 866 * @camera_handle: camera handle 867 * @ch_id : channel handle 868 * 869 * RETURN : int32_t type of status 870 * 0 -- success 871 * -1 -- failure 872 *==========================================================================*/ 873 static int32_t mm_camera_intf_start_channel(uint32_t camera_handle, 874 uint32_t ch_id) 875 { 876 int32_t rc = -1; 877 mm_camera_obj_t * my_obj = NULL; 878 879 pthread_mutex_lock(&g_intf_lock); 880 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 881 882 if(my_obj) { 883 pthread_mutex_lock(&my_obj->cam_lock); 884 pthread_mutex_unlock(&g_intf_lock); 885 rc = mm_camera_start_channel(my_obj, ch_id); 886 } else { 887 pthread_mutex_unlock(&g_intf_lock); 888 } 889 LOGD("X rc = %d", rc); 890 return rc; 891 } 892 893 /*=========================================================================== 894 * FUNCTION : mm_camera_intf_stop_channel 895 * 896 * DESCRIPTION: stop a channel, which will stop all streams in the channel 897 * 898 * PARAMETERS : 899 * @camera_handle: camera handle 900 * @ch_id : channel handle 901 * 902 * RETURN : int32_t type of status 903 * 0 -- success 904 * -1 -- failure 905 *==========================================================================*/ 906 static int32_t mm_camera_intf_stop_channel(uint32_t camera_handle, 907 uint32_t ch_id) 908 { 909 int32_t rc = -1; 910 mm_camera_obj_t * my_obj = NULL; 911 912 pthread_mutex_lock(&g_intf_lock); 913 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 914 915 if(my_obj) { 916 pthread_mutex_lock(&my_obj->cam_lock); 917 pthread_mutex_unlock(&g_intf_lock); 918 rc = mm_camera_stop_channel(my_obj, ch_id); 919 } else { 920 pthread_mutex_unlock(&g_intf_lock); 921 } 922 LOGD("X rc = %d", rc); 923 return rc; 924 } 925 926 /*=========================================================================== 927 * FUNCTION : mm_camera_intf_request_super_buf 928 * 929 * DESCRIPTION: for burst mode in bundle, reuqest certain amount of matched 930 * frames from superbuf queue 931 * 932 * PARAMETERS : 933 * @camera_handle: camera handle 934 * @ch_id : channel handle 935 * @buf : request buffer info 936 * 937 * RETURN : int32_t type of status 938 * 0 -- success 939 * -1 -- failure 940 *==========================================================================*/ 941 static int32_t mm_camera_intf_request_super_buf(uint32_t camera_handle, 942 uint32_t ch_id, mm_camera_req_buf_t *buf) 943 { 944 int32_t rc = -1; 945 LOGD("E camera_handler = %d,ch_id = %d", 946 camera_handle, ch_id); 947 mm_camera_obj_t * my_obj = NULL; 948 949 pthread_mutex_lock(&g_intf_lock); 950 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 951 952 if(my_obj && buf) { 953 pthread_mutex_lock(&my_obj->cam_lock); 954 pthread_mutex_unlock(&g_intf_lock); 955 rc = mm_camera_request_super_buf (my_obj, ch_id, buf); 956 } else { 957 pthread_mutex_unlock(&g_intf_lock); 958 } 959 LOGD("X rc = %d", rc); 960 return rc; 961 } 962 963 /*=========================================================================== 964 * FUNCTION : mm_camera_intf_cancel_super_buf_request 965 * 966 * DESCRIPTION: for burst mode in bundle, cancel the reuqest for certain amount 967 * of matched frames from superbuf queue 968 * 969 * PARAMETERS : 970 * @camera_handle: camera handle 971 * @ch_id : channel handle 972 * 973 * RETURN : int32_t type of status 974 * 0 -- success 975 * -1 -- failure 976 *==========================================================================*/ 977 static int32_t mm_camera_intf_cancel_super_buf_request(uint32_t camera_handle, 978 uint32_t ch_id) 979 { 980 int32_t rc = -1; 981 mm_camera_obj_t * my_obj = NULL; 982 983 LOGD("E camera_handler = %d,ch_id = %d", 984 camera_handle, ch_id); 985 pthread_mutex_lock(&g_intf_lock); 986 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 987 988 if(my_obj) { 989 pthread_mutex_lock(&my_obj->cam_lock); 990 pthread_mutex_unlock(&g_intf_lock); 991 rc = mm_camera_cancel_super_buf_request(my_obj, ch_id); 992 } else { 993 pthread_mutex_unlock(&g_intf_lock); 994 } 995 LOGD("X rc = %d", rc); 996 return rc; 997 } 998 999 /*=========================================================================== 1000 * FUNCTION : mm_camera_intf_flush_super_buf_queue 1001 * 1002 * DESCRIPTION: flush out all frames in the superbuf queue 1003 * 1004 * PARAMETERS : 1005 * @camera_handle: camera handle 1006 * @ch_id : channel handle 1007 * @frame_idx : frame index 1008 * 1009 * RETURN : int32_t type of status 1010 * 0 -- success 1011 * -1 -- failure 1012 *==========================================================================*/ 1013 static int32_t mm_camera_intf_flush_super_buf_queue(uint32_t camera_handle, 1014 uint32_t ch_id, uint32_t frame_idx) 1015 { 1016 int32_t rc = -1; 1017 mm_camera_obj_t * my_obj = NULL; 1018 1019 LOGD("E camera_handler = %d,ch_id = %d", 1020 camera_handle, ch_id); 1021 pthread_mutex_lock(&g_intf_lock); 1022 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 1023 1024 if(my_obj) { 1025 pthread_mutex_lock(&my_obj->cam_lock); 1026 pthread_mutex_unlock(&g_intf_lock); 1027 rc = mm_camera_flush_super_buf_queue(my_obj, ch_id, frame_idx); 1028 } else { 1029 pthread_mutex_unlock(&g_intf_lock); 1030 } 1031 LOGD("X rc = %d", rc); 1032 return rc; 1033 } 1034 1035 /*=========================================================================== 1036 * FUNCTION : mm_camera_intf_start_zsl_snapshot 1037 * 1038 * DESCRIPTION: Starts zsl snapshot 1039 * 1040 * PARAMETERS : 1041 * @camera_handle: camera handle 1042 * @ch_id : channel handle 1043 * 1044 * RETURN : int32_t type of status 1045 * 0 -- success 1046 * -1 -- failure 1047 *==========================================================================*/ 1048 static int32_t mm_camera_intf_start_zsl_snapshot(uint32_t camera_handle, 1049 uint32_t ch_id) 1050 { 1051 int32_t rc = -1; 1052 mm_camera_obj_t * my_obj = NULL; 1053 1054 LOGD("E camera_handler = %d,ch_id = %d", 1055 camera_handle, ch_id); 1056 pthread_mutex_lock(&g_intf_lock); 1057 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 1058 1059 if(my_obj) { 1060 pthread_mutex_lock(&my_obj->cam_lock); 1061 pthread_mutex_unlock(&g_intf_lock); 1062 rc = mm_camera_start_zsl_snapshot_ch(my_obj, ch_id); 1063 } else { 1064 pthread_mutex_unlock(&g_intf_lock); 1065 } 1066 LOGD("X rc = %d", rc); 1067 return rc; 1068 } 1069 1070 /*=========================================================================== 1071 * FUNCTION : mm_camera_intf_stop_zsl_snapshot 1072 * 1073 * DESCRIPTION: Stops zsl snapshot 1074 * 1075 * PARAMETERS : 1076 * @camera_handle: camera handle 1077 * @ch_id : channel handle 1078 * 1079 * RETURN : int32_t type of status 1080 * 0 -- success 1081 * -1 -- failure 1082 *==========================================================================*/ 1083 static int32_t mm_camera_intf_stop_zsl_snapshot(uint32_t camera_handle, 1084 uint32_t ch_id) 1085 { 1086 int32_t rc = -1; 1087 mm_camera_obj_t * my_obj = NULL; 1088 1089 LOGD("E camera_handler = %d,ch_id = %d", 1090 camera_handle, ch_id); 1091 pthread_mutex_lock(&g_intf_lock); 1092 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 1093 1094 if(my_obj) { 1095 pthread_mutex_lock(&my_obj->cam_lock); 1096 pthread_mutex_unlock(&g_intf_lock); 1097 rc = mm_camera_stop_zsl_snapshot_ch(my_obj, ch_id); 1098 } else { 1099 pthread_mutex_unlock(&g_intf_lock); 1100 } 1101 LOGD("X rc = %d", rc); 1102 return rc; 1103 } 1104 1105 /*=========================================================================== 1106 * FUNCTION : mm_camera_intf_configure_notify_mode 1107 * 1108 * DESCRIPTION: Configures channel notification mode 1109 * 1110 * PARAMETERS : 1111 * @camera_handle: camera handle 1112 * @ch_id : channel handle 1113 * @notify_mode : notification mode 1114 * 1115 * RETURN : int32_t type of status 1116 * 0 -- success 1117 * -1 -- failure 1118 *==========================================================================*/ 1119 static int32_t mm_camera_intf_configure_notify_mode(uint32_t camera_handle, 1120 uint32_t ch_id, 1121 mm_camera_super_buf_notify_mode_t notify_mode) 1122 { 1123 int32_t rc = -1; 1124 mm_camera_obj_t * my_obj = NULL; 1125 1126 LOGD("E camera_handler = %d,ch_id = %d", 1127 camera_handle, ch_id); 1128 pthread_mutex_lock(&g_intf_lock); 1129 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 1130 1131 if(my_obj) { 1132 pthread_mutex_lock(&my_obj->cam_lock); 1133 pthread_mutex_unlock(&g_intf_lock); 1134 rc = mm_camera_config_channel_notify(my_obj, ch_id, notify_mode); 1135 } else { 1136 pthread_mutex_unlock(&g_intf_lock); 1137 } 1138 LOGD("X rc = %d", rc); 1139 return rc; 1140 } 1141 1142 /*=========================================================================== 1143 * FUNCTION : mm_camera_intf_map_buf 1144 * 1145 * DESCRIPTION: mapping camera buffer via domain socket to server 1146 * 1147 * PARAMETERS : 1148 * @camera_handle: camera handle 1149 * @buf_type : type of buffer to be mapped. could be following values: 1150 * CAM_MAPPING_BUF_TYPE_CAPABILITY 1151 * CAM_MAPPING_BUF_TYPE_SETPARM_BUF 1152 * CAM_MAPPING_BUF_TYPE_GETPARM_BUF 1153 * @fd : file descriptor of the buffer 1154 * @size : size of the buffer 1155 * 1156 * RETURN : int32_t type of status 1157 * 0 -- success 1158 * -1 -- failure 1159 *==========================================================================*/ 1160 static int32_t mm_camera_intf_map_buf(uint32_t camera_handle, 1161 uint8_t buf_type, int fd, size_t size, void *buffer) 1162 { 1163 int32_t rc = -1; 1164 mm_camera_obj_t * my_obj = NULL; 1165 1166 pthread_mutex_lock(&g_intf_lock); 1167 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 1168 1169 if(my_obj) { 1170 pthread_mutex_lock(&my_obj->cam_lock); 1171 pthread_mutex_unlock(&g_intf_lock); 1172 rc = mm_camera_map_buf(my_obj, buf_type, fd, size, buffer); 1173 } else { 1174 pthread_mutex_unlock(&g_intf_lock); 1175 } 1176 return rc; 1177 } 1178 1179 /*=========================================================================== 1180 * FUNCTION : mm_camera_intf_map_bufs 1181 * 1182 * DESCRIPTION: mapping camera buffer via domain socket to server 1183 * 1184 * PARAMETERS : 1185 * @camera_handle: camera handle 1186 * @buf_type : type of buffer to be mapped. could be following values: 1187 * CAM_MAPPING_BUF_TYPE_CAPABILITY 1188 * CAM_MAPPING_BUF_TYPE_SETPARM_BUF 1189 * CAM_MAPPING_BUF_TYPE_GETPARM_BUF 1190 * 1191 * RETURN : int32_t type of status 1192 * 0 -- success 1193 * -1 -- failure 1194 *==========================================================================*/ 1195 static int32_t mm_camera_intf_map_bufs(uint32_t camera_handle, 1196 const cam_buf_map_type_list *buf_map_list) 1197 { 1198 int32_t rc = -1; 1199 mm_camera_obj_t * my_obj = NULL; 1200 1201 pthread_mutex_lock(&g_intf_lock); 1202 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 1203 1204 if(my_obj) { 1205 pthread_mutex_lock(&my_obj->cam_lock); 1206 pthread_mutex_unlock(&g_intf_lock); 1207 rc = mm_camera_map_bufs(my_obj, buf_map_list); 1208 } else { 1209 pthread_mutex_unlock(&g_intf_lock); 1210 } 1211 return rc; 1212 } 1213 1214 /*=========================================================================== 1215 * FUNCTION : mm_camera_intf_unmap_buf 1216 * 1217 * DESCRIPTION: unmapping camera buffer via domain socket to server 1218 * 1219 * PARAMETERS : 1220 * @camera_handle: camera handle 1221 * @buf_type : type of buffer to be unmapped. could be following values: 1222 * CAM_MAPPING_BUF_TYPE_CAPABILITY 1223 * CAM_MAPPING_BUF_TYPE_SETPARM_BUF 1224 * CAM_MAPPING_BUF_TYPE_GETPARM_BUF 1225 * 1226 * RETURN : int32_t type of status 1227 * 0 -- success 1228 * -1 -- failure 1229 *==========================================================================*/ 1230 static int32_t mm_camera_intf_unmap_buf(uint32_t camera_handle, 1231 uint8_t buf_type) 1232 { 1233 int32_t rc = -1; 1234 mm_camera_obj_t * my_obj = NULL; 1235 1236 pthread_mutex_lock(&g_intf_lock); 1237 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 1238 1239 if(my_obj) { 1240 pthread_mutex_lock(&my_obj->cam_lock); 1241 pthread_mutex_unlock(&g_intf_lock); 1242 rc = mm_camera_unmap_buf(my_obj, buf_type); 1243 } else { 1244 pthread_mutex_unlock(&g_intf_lock); 1245 } 1246 return rc; 1247 } 1248 1249 /*=========================================================================== 1250 * FUNCTION : mm_camera_intf_set_stream_parms 1251 * 1252 * DESCRIPTION: set parameters per stream 1253 * 1254 * PARAMETERS : 1255 * @camera_handle: camera handle 1256 * @ch_id : channel handle 1257 * @s_id : stream handle 1258 * @parms : ptr to a param struct to be set to server 1259 * 1260 * RETURN : int32_t type of status 1261 * 0 -- success 1262 * -1 -- failure 1263 * NOTE : Assume the parms struct buf is already mapped to server via 1264 * domain socket. Corresponding fields of parameters to be set 1265 * are already filled in by upper layer caller. 1266 *==========================================================================*/ 1267 static int32_t mm_camera_intf_set_stream_parms(uint32_t camera_handle, 1268 uint32_t ch_id, 1269 uint32_t s_id, 1270 cam_stream_parm_buffer_t *parms) 1271 { 1272 int32_t rc = -1; 1273 mm_camera_obj_t * my_obj = NULL; 1274 1275 pthread_mutex_lock(&g_intf_lock); 1276 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 1277 1278 LOGD("E camera_handle = %d,ch_id = %d,s_id = %d", 1279 camera_handle, ch_id, s_id); 1280 1281 if(my_obj) { 1282 pthread_mutex_lock(&my_obj->cam_lock); 1283 pthread_mutex_unlock(&g_intf_lock); 1284 rc = mm_camera_set_stream_parms(my_obj, ch_id, s_id, parms); 1285 }else{ 1286 pthread_mutex_unlock(&g_intf_lock); 1287 } 1288 LOGD("X rc = %d", rc); 1289 return rc; 1290 } 1291 1292 /*=========================================================================== 1293 * FUNCTION : mm_camera_intf_get_stream_parms 1294 * 1295 * DESCRIPTION: get parameters per stream 1296 * 1297 * PARAMETERS : 1298 * @camera_handle: camera handle 1299 * @ch_id : channel handle 1300 * @s_id : stream handle 1301 * @parms : ptr to a param struct to be get from server 1302 * 1303 * RETURN : int32_t type of status 1304 * 0 -- success 1305 * -1 -- failure 1306 * NOTE : Assume the parms struct buf is already mapped to server via 1307 * domain socket. Parameters to be get from server are already 1308 * filled in by upper layer caller. After this call, corresponding 1309 * fields of requested parameters will be filled in by server with 1310 * detailed information. 1311 *==========================================================================*/ 1312 static int32_t mm_camera_intf_get_stream_parms(uint32_t camera_handle, 1313 uint32_t ch_id, 1314 uint32_t s_id, 1315 cam_stream_parm_buffer_t *parms) 1316 { 1317 int32_t rc = -1; 1318 mm_camera_obj_t * my_obj = NULL; 1319 1320 pthread_mutex_lock(&g_intf_lock); 1321 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 1322 1323 LOGD("E camera_handle = %d,ch_id = %d,s_id = %d", 1324 camera_handle, ch_id, s_id); 1325 1326 if(my_obj) { 1327 pthread_mutex_lock(&my_obj->cam_lock); 1328 pthread_mutex_unlock(&g_intf_lock); 1329 rc = mm_camera_get_stream_parms(my_obj, ch_id, s_id, parms); 1330 }else{ 1331 pthread_mutex_unlock(&g_intf_lock); 1332 } 1333 1334 LOGD("X rc = %d", rc); 1335 return rc; 1336 } 1337 1338 /*=========================================================================== 1339 * FUNCTION : mm_camera_intf_map_stream_buf 1340 * 1341 * DESCRIPTION: mapping stream buffer via domain socket to server 1342 * 1343 * PARAMETERS : 1344 * @camera_handle: camera handle 1345 * @ch_id : channel handle 1346 * @s_id : stream handle 1347 * @buf_type : type of buffer to be mapped. could be following values: 1348 * CAM_MAPPING_BUF_TYPE_STREAM_BUF 1349 * CAM_MAPPING_BUF_TYPE_STREAM_INFO 1350 * CAM_MAPPING_BUF_TYPE_OFFLINE_INPUT_BUF 1351 * @buf_idx : index of buffer within the stream buffers, only valid if 1352 * buf_type is CAM_MAPPING_BUF_TYPE_STREAM_BUF or 1353 * CAM_MAPPING_BUF_TYPE_OFFLINE_INPUT_BUF 1354 * @plane_idx : plane index. If all planes share the same fd, 1355 * plane_idx = -1; otherwise, plean_idx is the 1356 * index to plane (0..num_of_planes) 1357 * @fd : file descriptor of the buffer 1358 * @size : size of the buffer 1359 * 1360 * RETURN : int32_t type of status 1361 * 0 -- success 1362 * -1 -- failure 1363 *==========================================================================*/ 1364 static int32_t mm_camera_intf_map_stream_buf(uint32_t camera_handle, 1365 uint32_t ch_id, uint32_t stream_id, uint8_t buf_type, 1366 uint32_t buf_idx, int32_t plane_idx, int fd, 1367 size_t size, void *buffer) 1368 { 1369 int32_t rc = -1; 1370 mm_camera_obj_t * my_obj = NULL; 1371 1372 pthread_mutex_lock(&g_intf_lock); 1373 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 1374 1375 LOGD("E camera_handle = %d, ch_id = %d, s_id = %d, buf_idx = %d, plane_idx = %d", 1376 camera_handle, ch_id, stream_id, buf_idx, plane_idx); 1377 1378 if(my_obj) { 1379 pthread_mutex_lock(&my_obj->cam_lock); 1380 pthread_mutex_unlock(&g_intf_lock); 1381 rc = mm_camera_map_stream_buf(my_obj, ch_id, stream_id, 1382 buf_type, buf_idx, plane_idx, 1383 fd, size, buffer); 1384 }else{ 1385 pthread_mutex_unlock(&g_intf_lock); 1386 } 1387 1388 LOGD("X rc = %d", rc); 1389 return rc; 1390 } 1391 1392 /*=========================================================================== 1393 * FUNCTION : mm_camera_intf_map_stream_bufs 1394 * 1395 * DESCRIPTION: mapping stream buffers via domain socket to server 1396 * 1397 * PARAMETERS : 1398 * @camera_handle: camera handle 1399 * @ch_id : channel handle 1400 * @buf_map_list : list of buffers to be mapped 1401 * 1402 * RETURN : int32_t type of status 1403 * 0 -- success 1404 * -1 -- failure 1405 *==========================================================================*/ 1406 static int32_t mm_camera_intf_map_stream_bufs(uint32_t camera_handle, 1407 uint32_t ch_id, 1408 const cam_buf_map_type_list *buf_map_list) 1409 { 1410 int32_t rc = -1; 1411 mm_camera_obj_t * my_obj = NULL; 1412 1413 pthread_mutex_lock(&g_intf_lock); 1414 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 1415 1416 LOGD("E camera_handle = %d, ch_id = %d", 1417 camera_handle, ch_id); 1418 1419 if(my_obj) { 1420 pthread_mutex_lock(&my_obj->cam_lock); 1421 pthread_mutex_unlock(&g_intf_lock); 1422 rc = mm_camera_map_stream_bufs(my_obj, ch_id, buf_map_list); 1423 }else{ 1424 pthread_mutex_unlock(&g_intf_lock); 1425 } 1426 1427 LOGD("X rc = %d", rc); 1428 return rc; 1429 } 1430 1431 /*=========================================================================== 1432 * FUNCTION : mm_camera_intf_unmap_stream_buf 1433 * 1434 * DESCRIPTION: unmapping stream buffer via domain socket to server 1435 * 1436 * PARAMETERS : 1437 * @camera_handle: camera handle 1438 * @ch_id : channel handle 1439 * @s_id : stream handle 1440 * @buf_type : type of buffer to be unmapped. could be following values: 1441 * CAM_MAPPING_BUF_TYPE_STREAM_BUF 1442 * CAM_MAPPING_BUF_TYPE_STREAM_INFO 1443 * CAM_MAPPING_BUF_TYPE_OFFLINE_INPUT_BUF 1444 * @buf_idx : index of buffer within the stream buffers, only valid if 1445 * buf_type is CAM_MAPPING_BUF_TYPE_STREAM_BUF or 1446 * CAM_MAPPING_BUF_TYPE_OFFLINE_INPUT_BUF 1447 * @plane_idx : plane index. If all planes share the same fd, 1448 * plane_idx = -1; otherwise, plean_idx is the 1449 * index to plane (0..num_of_planes) 1450 * 1451 * RETURN : int32_t type of status 1452 * 0 -- success 1453 * -1 -- failure 1454 *==========================================================================*/ 1455 static int32_t mm_camera_intf_unmap_stream_buf(uint32_t camera_handle, 1456 uint32_t ch_id, 1457 uint32_t stream_id, 1458 uint8_t buf_type, 1459 uint32_t buf_idx, 1460 int32_t plane_idx) 1461 { 1462 int32_t rc = -1; 1463 mm_camera_obj_t * my_obj = NULL; 1464 1465 pthread_mutex_lock(&g_intf_lock); 1466 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 1467 1468 LOGD("E camera_handle = %d, ch_id = %d, s_id = %d, buf_idx = %d, plane_idx = %d", 1469 camera_handle, ch_id, stream_id, buf_idx, plane_idx); 1470 1471 if(my_obj) { 1472 pthread_mutex_lock(&my_obj->cam_lock); 1473 pthread_mutex_unlock(&g_intf_lock); 1474 rc = mm_camera_unmap_stream_buf(my_obj, ch_id, stream_id, 1475 buf_type, buf_idx, plane_idx); 1476 }else{ 1477 pthread_mutex_unlock(&g_intf_lock); 1478 } 1479 1480 LOGD("X rc = %d", rc); 1481 return rc; 1482 } 1483 1484 /*=========================================================================== 1485 * FUNCTION : mm_camera_intf_get_session_id 1486 * 1487 * DESCRIPTION: retrieve the session ID from the kernel for this HWI instance 1488 * 1489 * PARAMETERS : 1490 * @camera_handle: camera handle 1491 * @sessionid: session id to be retrieved from server 1492 * 1493 * RETURN : int32_t type of status 1494 * 0 -- success 1495 * -1 -- failure 1496 * NOTE : if this call succeeds, we will get a valid session id. 1497 *==========================================================================*/ 1498 static int32_t mm_camera_intf_get_session_id(uint32_t camera_handle, 1499 uint32_t* sessionid) 1500 { 1501 int32_t rc = -1; 1502 mm_camera_obj_t * my_obj = NULL; 1503 1504 pthread_mutex_lock(&g_intf_lock); 1505 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 1506 1507 if(my_obj) { 1508 pthread_mutex_lock(&my_obj->cam_lock); 1509 pthread_mutex_unlock(&g_intf_lock); 1510 *sessionid = my_obj->sessionid; 1511 pthread_mutex_unlock(&my_obj->cam_lock); 1512 rc = 0; 1513 } else { 1514 pthread_mutex_unlock(&g_intf_lock); 1515 } 1516 return rc; 1517 } 1518 1519 /*=========================================================================== 1520 * FUNCTION : mm_camera_intf_sync_related_sensors 1521 * 1522 * DESCRIPTION: retrieve the session ID from the kernel for this HWI instance 1523 * 1524 * PARAMETERS : 1525 * @camera_handle: camera handle 1526 * @related_cam_info: pointer to the related cam info to be sent to the server 1527 * 1528 * RETURN : int32_t type of status 1529 * 0 -- success 1530 * -1 -- failure 1531 * NOTE : if this call succeeds, we will get linking established in back end 1532 *==========================================================================*/ 1533 static int32_t mm_camera_intf_sync_related_sensors(uint32_t camera_handle, 1534 cam_sync_related_sensors_event_info_t* related_cam_info) 1535 { 1536 int32_t rc = -1; 1537 mm_camera_obj_t * my_obj = NULL; 1538 1539 pthread_mutex_lock(&g_intf_lock); 1540 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 1541 1542 if(my_obj) { 1543 pthread_mutex_lock(&my_obj->cam_lock); 1544 pthread_mutex_unlock(&g_intf_lock); 1545 rc = mm_camera_sync_related_sensors(my_obj, related_cam_info); 1546 } else { 1547 pthread_mutex_unlock(&g_intf_lock); 1548 } 1549 return rc; 1550 } 1551 1552 /*=========================================================================== 1553 * FUNCTION : get_sensor_info 1554 * 1555 * DESCRIPTION: get sensor info like facing(back/front) and mount angle 1556 * 1557 * PARAMETERS : 1558 * 1559 * RETURN : 1560 *==========================================================================*/ 1561 void get_sensor_info() 1562 { 1563 int rc = 0; 1564 int dev_fd = -1; 1565 struct media_device_info mdev_info; 1566 int num_media_devices = 0; 1567 size_t num_cameras = 0; 1568 1569 LOGD("E"); 1570 while (1) { 1571 char dev_name[32]; 1572 snprintf(dev_name, sizeof(dev_name), "/dev/media%d", num_media_devices); 1573 dev_fd = open(dev_name, O_RDWR | O_NONBLOCK); 1574 if (dev_fd < 0) { 1575 LOGD("Done discovering media devices\n"); 1576 break; 1577 } 1578 num_media_devices++; 1579 memset(&mdev_info, 0, sizeof(mdev_info)); 1580 rc = ioctl(dev_fd, MEDIA_IOC_DEVICE_INFO, &mdev_info); 1581 if (rc < 0) { 1582 LOGE("Error: ioctl media_dev failed: %s\n", strerror(errno)); 1583 close(dev_fd); 1584 dev_fd = -1; 1585 num_cameras = 0; 1586 break; 1587 } 1588 1589 if(strncmp(mdev_info.model, MSM_CONFIGURATION_NAME, sizeof(mdev_info.model)) != 0) { 1590 close(dev_fd); 1591 dev_fd = -1; 1592 continue; 1593 } 1594 1595 unsigned int num_entities = 1; 1596 while (1) { 1597 struct media_entity_desc entity; 1598 uint32_t temp; 1599 uint32_t mount_angle; 1600 uint32_t facing; 1601 int32_t type = 0; 1602 uint8_t is_yuv; 1603 1604 memset(&entity, 0, sizeof(entity)); 1605 entity.id = num_entities++; 1606 rc = ioctl(dev_fd, MEDIA_IOC_ENUM_ENTITIES, &entity); 1607 if (rc < 0) { 1608 LOGD("Done enumerating media entities\n"); 1609 rc = 0; 1610 break; 1611 } 1612 if(entity.type == MEDIA_ENT_T_V4L2_SUBDEV && 1613 entity.group_id == MSM_CAMERA_SUBDEV_SENSOR) { 1614 temp = entity.flags >> 8; 1615 mount_angle = (temp & 0xFF) * 90; 1616 facing = (temp & 0xFF00) >> 8; 1617 type = ((entity.flags & CAM_SENSOR_TYPE_MASK) ? 1618 CAM_TYPE_AUX:CAM_TYPE_MAIN); 1619 is_yuv = ((entity.flags & CAM_SENSOR_FORMAT_MASK) ? 1620 CAM_SENSOR_YUV:CAM_SENSOR_RAW); 1621 LOGL("index = %u flag = %x mount_angle = %u " 1622 "facing = %u type: %u is_yuv = %u\n", 1623 (unsigned int)num_cameras, (unsigned int)temp, 1624 (unsigned int)mount_angle, (unsigned int)facing, 1625 (unsigned int)type, (uint8_t)is_yuv); 1626 g_cam_ctrl.info[num_cameras].facing = (int)facing; 1627 g_cam_ctrl.info[num_cameras].orientation = (int)mount_angle; 1628 g_cam_ctrl.cam_type[num_cameras] = type; 1629 g_cam_ctrl.is_yuv[num_cameras] = is_yuv; 1630 LOGD("dev_info[id=%zu,name='%s']\n", 1631 num_cameras, g_cam_ctrl.video_dev_name[num_cameras]); 1632 num_cameras++; 1633 continue; 1634 } 1635 } 1636 close(dev_fd); 1637 dev_fd = -1; 1638 } 1639 1640 LOGD("num_cameras=%d\n", g_cam_ctrl.num_cam); 1641 return; 1642 } 1643 1644 /*=========================================================================== 1645 * FUNCTION : sort_camera_info 1646 * 1647 * DESCRIPTION: sort camera info to keep back cameras idx is smaller than front cameras idx 1648 * 1649 * PARAMETERS : number of cameras 1650 * 1651 * RETURN : 1652 *==========================================================================*/ 1653 void sort_camera_info(int num_cam) 1654 { 1655 int idx = 0, i; 1656 int8_t is_dual_cam = 0, is_aux_cam_exposed = 0; 1657 char prop[PROPERTY_VALUE_MAX]; 1658 struct camera_info temp_info[MM_CAMERA_MAX_NUM_SENSORS]; 1659 cam_sync_type_t temp_type[MM_CAMERA_MAX_NUM_SENSORS]; 1660 cam_sync_mode_t temp_mode[MM_CAMERA_MAX_NUM_SENSORS]; 1661 uint8_t temp_is_yuv[MM_CAMERA_MAX_NUM_SENSORS]; 1662 char temp_dev_name[MM_CAMERA_MAX_NUM_SENSORS][MM_CAMERA_DEV_NAME_LEN]; 1663 1664 memset(temp_info, 0, sizeof(temp_info)); 1665 memset(temp_dev_name, 0, sizeof(temp_dev_name)); 1666 memset(temp_type, 0, sizeof(temp_type)); 1667 memset(temp_mode, 0, sizeof(temp_mode)); 1668 memset(temp_is_yuv, 0, sizeof(temp_is_yuv)); 1669 1670 // Signifies whether system has to enable dual camera mode 1671 memset(prop, 0, sizeof(prop)); 1672 property_get("persist.camera.dual.camera", prop, "0"); 1673 is_dual_cam = atoi(prop); 1674 1675 // Signifies whether AUX camera has to be exposed as physical camera 1676 memset(prop, 0, sizeof(prop)); 1677 property_get("persist.camera.aux.camera", prop, "0"); 1678 is_aux_cam_exposed = atoi(prop); 1679 LOGI("dualCamera:%d auxCamera %d", 1680 is_dual_cam, is_aux_cam_exposed); 1681 1682 /* 1683 1. If dual camera is enabled, dont hide any camera here. Further logic to handle AUX 1684 cameras is handled in setupLogicalCameras(). 1685 2. If dual camera is not enabled, hide Front camera if AUX camera property is set. 1686 In such case, application will see only back MAIN and back AUX cameras. 1687 3. TODO: Need to revisit this logic if front AUX is available. 1688 */ 1689 1690 /* firstly save the main back cameras info*/ 1691 for (i = 0; i < num_cam; i++) { 1692 if ((g_cam_ctrl.info[i].facing == CAMERA_FACING_BACK) && 1693 (g_cam_ctrl.cam_type[i] == CAM_TYPE_MAIN)) { 1694 temp_info[idx] = g_cam_ctrl.info[i]; 1695 temp_type[idx] = g_cam_ctrl.cam_type[i]; 1696 temp_mode[idx] = g_cam_ctrl.cam_mode[i]; 1697 temp_is_yuv[idx] = g_cam_ctrl.is_yuv[i]; 1698 LOGD("Found Back Main Camera: i: %d idx: %d", i, idx); 1699 memcpy(temp_dev_name[idx++],g_cam_ctrl.video_dev_name[i], 1700 MM_CAMERA_DEV_NAME_LEN); 1701 } 1702 } 1703 1704 /* save the aux back cameras info*/ 1705 if (is_dual_cam || is_aux_cam_exposed) { 1706 for (i = 0; i < num_cam; i++) { 1707 if ((g_cam_ctrl.info[i].facing == CAMERA_FACING_BACK) && 1708 (g_cam_ctrl.cam_type[i] == CAM_TYPE_AUX)) { 1709 temp_info[idx] = g_cam_ctrl.info[i]; 1710 temp_type[idx] = g_cam_ctrl.cam_type[i]; 1711 temp_mode[idx] = g_cam_ctrl.cam_mode[i]; 1712 temp_is_yuv[idx] = g_cam_ctrl.is_yuv[i]; 1713 LOGD("Found Back Aux Camera: i: %d idx: %d", i, idx); 1714 memcpy(temp_dev_name[idx++],g_cam_ctrl.video_dev_name[i], 1715 MM_CAMERA_DEV_NAME_LEN); 1716 } 1717 } 1718 } 1719 1720 if (is_dual_cam || !is_aux_cam_exposed) { 1721 /* then save the front cameras info*/ 1722 for (i = 0; i < num_cam; i++) { 1723 if ((g_cam_ctrl.info[i].facing == CAMERA_FACING_FRONT) && 1724 (g_cam_ctrl.cam_type[i] == CAM_TYPE_MAIN)) { 1725 temp_info[idx] = g_cam_ctrl.info[i]; 1726 temp_type[idx] = g_cam_ctrl.cam_type[i]; 1727 temp_mode[idx] = g_cam_ctrl.cam_mode[i]; 1728 temp_is_yuv[idx] = g_cam_ctrl.is_yuv[i]; 1729 LOGD("Found Front Main Camera: i: %d idx: %d", i, idx); 1730 memcpy(temp_dev_name[idx++],g_cam_ctrl.video_dev_name[i], 1731 MM_CAMERA_DEV_NAME_LEN); 1732 } 1733 } 1734 } 1735 1736 //TODO: Need to revisit this logic if front AUX is available. 1737 /* save the aux front cameras info*/ 1738 for (i = 0; i < num_cam; i++) { 1739 if ((g_cam_ctrl.info[i].facing == CAMERA_FACING_FRONT) && 1740 (g_cam_ctrl.cam_type[i] == CAM_TYPE_AUX)) { 1741 temp_info[idx] = g_cam_ctrl.info[i]; 1742 temp_type[idx] = g_cam_ctrl.cam_type[i]; 1743 temp_mode[idx] = g_cam_ctrl.cam_mode[i]; 1744 temp_is_yuv[idx] = g_cam_ctrl.is_yuv[i]; 1745 LOGD("Found Front Aux Camera: i: %d idx: %d", i, idx); 1746 memcpy(temp_dev_name[idx++],g_cam_ctrl.video_dev_name[i], 1747 MM_CAMERA_DEV_NAME_LEN); 1748 } 1749 } 1750 1751 if (idx <= num_cam) { 1752 memcpy(g_cam_ctrl.info, temp_info, sizeof(temp_info)); 1753 memcpy(g_cam_ctrl.cam_type, temp_type, sizeof(temp_type)); 1754 memcpy(g_cam_ctrl.cam_mode, temp_mode, sizeof(temp_mode)); 1755 memcpy(g_cam_ctrl.is_yuv, temp_is_yuv, sizeof(temp_is_yuv)); 1756 memcpy(g_cam_ctrl.video_dev_name, temp_dev_name, sizeof(temp_dev_name)); 1757 //Set num cam based on the cameras exposed finally via dual/aux properties. 1758 g_cam_ctrl.num_cam = idx; 1759 for (i = 0; i < idx; i++) { 1760 LOGI("Camera id: %d facing: %d, type: %d is_yuv: %d", 1761 i, g_cam_ctrl.info[i].facing, g_cam_ctrl.cam_type[i], g_cam_ctrl.is_yuv[i]); 1762 } 1763 } 1764 LOGI("Number of cameras %d sorted %d", num_cam, idx); 1765 return; 1766 } 1767 1768 /*=========================================================================== 1769 * FUNCTION : get_num_of_cameras 1770 * 1771 * DESCRIPTION: get number of cameras 1772 * 1773 * PARAMETERS : 1774 * 1775 * RETURN : number of cameras supported 1776 *==========================================================================*/ 1777 uint8_t get_num_of_cameras() 1778 { 1779 int rc = 0; 1780 int dev_fd = -1; 1781 struct media_device_info mdev_info; 1782 int num_media_devices = 0; 1783 int8_t num_cameras = 0; 1784 char subdev_name[32]; 1785 char prop[PROPERTY_VALUE_MAX]; 1786 #ifdef DAEMON_PRESENT 1787 int32_t sd_fd = -1; 1788 struct sensor_init_cfg_data cfg; 1789 #endif 1790 1791 LOGD("E"); 1792 1793 property_get("vold.decrypt", prop, "0"); 1794 int decrypt = atoi(prop); 1795 if (decrypt == 1) 1796 return 0; 1797 pthread_mutex_lock(&g_intf_lock); 1798 1799 memset (&g_cam_ctrl, 0, sizeof (g_cam_ctrl)); 1800 #ifndef DAEMON_PRESENT 1801 if (mm_camera_load_shim_lib() < 0) { 1802 LOGE ("Failed to module shim library"); 1803 return 0; 1804 } 1805 #endif /* DAEMON_PRESENT */ 1806 1807 while (1) { 1808 uint32_t num_entities = 1U; 1809 char dev_name[32]; 1810 1811 snprintf(dev_name, sizeof(dev_name), "/dev/media%d", num_media_devices); 1812 dev_fd = open(dev_name, O_RDWR | O_NONBLOCK); 1813 if (dev_fd < 0) { 1814 LOGD("Done discovering media devices\n"); 1815 break; 1816 } 1817 num_media_devices++; 1818 rc = ioctl(dev_fd, MEDIA_IOC_DEVICE_INFO, &mdev_info); 1819 if (rc < 0) { 1820 LOGE("Error: ioctl media_dev failed: %s\n", strerror(errno)); 1821 close(dev_fd); 1822 dev_fd = -1; 1823 break; 1824 } 1825 1826 if (strncmp(mdev_info.model, MSM_CONFIGURATION_NAME, 1827 sizeof(mdev_info.model)) != 0) { 1828 close(dev_fd); 1829 dev_fd = -1; 1830 continue; 1831 } 1832 1833 while (1) { 1834 struct media_entity_desc entity; 1835 memset(&entity, 0, sizeof(entity)); 1836 entity.id = num_entities++; 1837 LOGD("entity id %d", entity.id); 1838 rc = ioctl(dev_fd, MEDIA_IOC_ENUM_ENTITIES, &entity); 1839 if (rc < 0) { 1840 LOGD("Done enumerating media entities"); 1841 rc = 0; 1842 break; 1843 } 1844 LOGD("entity name %s type %d group id %d", 1845 entity.name, entity.type, entity.group_id); 1846 if (entity.type == MEDIA_ENT_T_V4L2_SUBDEV && 1847 entity.group_id == MSM_CAMERA_SUBDEV_SENSOR_INIT) { 1848 snprintf(subdev_name, sizeof(dev_name), "/dev/%s", entity.name); 1849 break; 1850 } 1851 } 1852 close(dev_fd); 1853 dev_fd = -1; 1854 } 1855 1856 #ifdef DAEMON_PRESENT 1857 /* Open sensor_init subdev */ 1858 sd_fd = open(subdev_name, O_RDWR); 1859 if (sd_fd < 0) { 1860 LOGE("Open sensor_init subdev failed"); 1861 return FALSE; 1862 } 1863 1864 cfg.cfgtype = CFG_SINIT_PROBE_WAIT_DONE; 1865 cfg.cfg.setting = NULL; 1866 if (ioctl(sd_fd, VIDIOC_MSM_SENSOR_INIT_CFG, &cfg) < 0) { 1867 LOGE("failed"); 1868 } 1869 close(sd_fd); 1870 #endif 1871 1872 1873 num_media_devices = 0; 1874 while (1) { 1875 uint32_t num_entities = 1U; 1876 char dev_name[32]; 1877 1878 snprintf(dev_name, sizeof(dev_name), "/dev/media%d", num_media_devices); 1879 dev_fd = open(dev_name, O_RDWR | O_NONBLOCK); 1880 if (dev_fd < 0) { 1881 LOGD("Done discovering media devices: %s\n", strerror(errno)); 1882 break; 1883 } 1884 num_media_devices++; 1885 memset(&mdev_info, 0, sizeof(mdev_info)); 1886 rc = ioctl(dev_fd, MEDIA_IOC_DEVICE_INFO, &mdev_info); 1887 if (rc < 0) { 1888 LOGE("Error: ioctl media_dev failed: %s\n", strerror(errno)); 1889 close(dev_fd); 1890 dev_fd = -1; 1891 num_cameras = 0; 1892 break; 1893 } 1894 1895 if(strncmp(mdev_info.model, MSM_CAMERA_NAME, sizeof(mdev_info.model)) != 0) { 1896 close(dev_fd); 1897 dev_fd = -1; 1898 continue; 1899 } 1900 1901 while (1) { 1902 struct media_entity_desc entity; 1903 memset(&entity, 0, sizeof(entity)); 1904 entity.id = num_entities++; 1905 rc = ioctl(dev_fd, MEDIA_IOC_ENUM_ENTITIES, &entity); 1906 if (rc < 0) { 1907 LOGD("Done enumerating media entities\n"); 1908 rc = 0; 1909 break; 1910 } 1911 if(entity.type == MEDIA_ENT_T_DEVNODE_V4L && entity.group_id == QCAMERA_VNODE_GROUP_ID) { 1912 strlcpy(g_cam_ctrl.video_dev_name[num_cameras], 1913 entity.name, sizeof(entity.name)); 1914 LOGI("dev_info[id=%d,name='%s']\n", 1915 (int)num_cameras, g_cam_ctrl.video_dev_name[num_cameras]); 1916 num_cameras++; 1917 break; 1918 } 1919 } 1920 close(dev_fd); 1921 dev_fd = -1; 1922 if (num_cameras >= MM_CAMERA_MAX_NUM_SENSORS) { 1923 LOGW("Maximum number of camera reached %d", num_cameras); 1924 break; 1925 } 1926 } 1927 g_cam_ctrl.num_cam = num_cameras; 1928 1929 get_sensor_info(); 1930 sort_camera_info(g_cam_ctrl.num_cam); 1931 /* unlock the mutex */ 1932 pthread_mutex_unlock(&g_intf_lock); 1933 LOGI("num_cameras=%d\n", (int)g_cam_ctrl.num_cam); 1934 return(uint8_t)g_cam_ctrl.num_cam; 1935 } 1936 1937 /*=========================================================================== 1938 * FUNCTION : mm_camera_intf_process_advanced_capture 1939 * 1940 * DESCRIPTION: Configures channel advanced capture mode 1941 * 1942 * PARAMETERS : 1943 * @camera_handle: camera handle 1944 * @type : advanced capture type 1945 * @ch_id : channel handle 1946 * @trigger : 1 for start and 0 for cancel/stop 1947 * @value : input capture configaration 1948 * 1949 * RETURN : int32_t type of status 1950 * 0 -- success 1951 * -1 -- failure 1952 *==========================================================================*/ 1953 static int32_t mm_camera_intf_process_advanced_capture(uint32_t camera_handle, 1954 uint32_t ch_id, mm_camera_advanced_capture_t type, 1955 int8_t trigger, void *in_value) 1956 { 1957 int32_t rc = -1; 1958 mm_camera_obj_t * my_obj = NULL; 1959 1960 LOGD("E camera_handler = %d,ch_id = %d", 1961 camera_handle, ch_id); 1962 pthread_mutex_lock(&g_intf_lock); 1963 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 1964 1965 if(my_obj) { 1966 pthread_mutex_lock(&my_obj->cam_lock); 1967 pthread_mutex_unlock(&g_intf_lock); 1968 rc = mm_camera_channel_advanced_capture(my_obj, ch_id, type, 1969 (uint32_t)trigger, in_value); 1970 } else { 1971 pthread_mutex_unlock(&g_intf_lock); 1972 } 1973 LOGD("X "); 1974 return rc; 1975 } 1976 1977 /*=========================================================================== 1978 * FUNCTION : mm_camera_intf_register_stream_buf_cb 1979 * 1980 * DESCRIPTION: Register special callback for stream buffer 1981 * 1982 * PARAMETERS : 1983 * @camera_handle: camera handle 1984 * @ch_id : channel handle 1985 * @stream_id : stream handle 1986 * @buf_cb : callback function 1987 * @buf_type :SYNC/ASYNC 1988 * @userdata : userdata pointer 1989 * 1990 * RETURN : int32_t type of status 1991 * 0 -- success 1992 * 1 -- failure 1993 *==========================================================================*/ 1994 static int32_t mm_camera_intf_register_stream_buf_cb(uint32_t camera_handle, 1995 uint32_t ch_id, uint32_t stream_id, mm_camera_buf_notify_t buf_cb, 1996 mm_camera_stream_cb_type cb_type, void *userdata) 1997 { 1998 int32_t rc = 0; 1999 mm_camera_obj_t * my_obj = NULL; 2000 2001 LOGD("E handle = %u ch_id = %u", 2002 camera_handle, ch_id); 2003 2004 pthread_mutex_lock(&g_intf_lock); 2005 my_obj = mm_camera_util_get_camera_by_handler(camera_handle); 2006 2007 if(my_obj) { 2008 pthread_mutex_lock(&my_obj->cam_lock); 2009 pthread_mutex_unlock(&g_intf_lock); 2010 rc = mm_camera_reg_stream_buf_cb(my_obj, ch_id, stream_id, 2011 buf_cb, cb_type, userdata); 2012 } else { 2013 pthread_mutex_unlock(&g_intf_lock); 2014 } 2015 return (int32_t)rc; 2016 } 2017 2018 struct camera_info *get_cam_info(uint32_t camera_id, cam_sync_type_t *pCamType) 2019 { 2020 *pCamType = g_cam_ctrl.cam_type[camera_id]; 2021 return &g_cam_ctrl.info[camera_id]; 2022 } 2023 2024 uint8_t is_yuv_sensor(uint32_t camera_id) 2025 { 2026 return g_cam_ctrl.is_yuv[camera_id]; 2027 } 2028 2029 /* camera ops v-table */ 2030 static mm_camera_ops_t mm_camera_ops = { 2031 .query_capability = mm_camera_intf_query_capability, 2032 .register_event_notify = mm_camera_intf_register_event_notify, 2033 .close_camera = mm_camera_intf_close, 2034 .set_parms = mm_camera_intf_set_parms, 2035 .get_parms = mm_camera_intf_get_parms, 2036 .do_auto_focus = mm_camera_intf_do_auto_focus, 2037 .cancel_auto_focus = mm_camera_intf_cancel_auto_focus, 2038 .prepare_snapshot = mm_camera_intf_prepare_snapshot, 2039 .start_zsl_snapshot = mm_camera_intf_start_zsl_snapshot, 2040 .stop_zsl_snapshot = mm_camera_intf_stop_zsl_snapshot, 2041 .map_buf = mm_camera_intf_map_buf, 2042 .map_bufs = mm_camera_intf_map_bufs, 2043 .unmap_buf = mm_camera_intf_unmap_buf, 2044 .add_channel = mm_camera_intf_add_channel, 2045 .delete_channel = mm_camera_intf_del_channel, 2046 .get_bundle_info = mm_camera_intf_get_bundle_info, 2047 .add_stream = mm_camera_intf_add_stream, 2048 .link_stream = mm_camera_intf_link_stream, 2049 .delete_stream = mm_camera_intf_del_stream, 2050 .config_stream = mm_camera_intf_config_stream, 2051 .qbuf = mm_camera_intf_qbuf, 2052 .cancel_buffer = mm_camera_intf_cancel_buf, 2053 .get_queued_buf_count = mm_camera_intf_get_queued_buf_count, 2054 .map_stream_buf = mm_camera_intf_map_stream_buf, 2055 .map_stream_bufs = mm_camera_intf_map_stream_bufs, 2056 .unmap_stream_buf = mm_camera_intf_unmap_stream_buf, 2057 .set_stream_parms = mm_camera_intf_set_stream_parms, 2058 .get_stream_parms = mm_camera_intf_get_stream_parms, 2059 .start_channel = mm_camera_intf_start_channel, 2060 .stop_channel = mm_camera_intf_stop_channel, 2061 .request_super_buf = mm_camera_intf_request_super_buf, 2062 .cancel_super_buf_request = mm_camera_intf_cancel_super_buf_request, 2063 .flush_super_buf_queue = mm_camera_intf_flush_super_buf_queue, 2064 .configure_notify_mode = mm_camera_intf_configure_notify_mode, 2065 .process_advanced_capture = mm_camera_intf_process_advanced_capture, 2066 .get_session_id = mm_camera_intf_get_session_id, 2067 .sync_related_sensors = mm_camera_intf_sync_related_sensors, 2068 .flush = mm_camera_intf_flush, 2069 .register_stream_buf_cb = mm_camera_intf_register_stream_buf_cb 2070 }; 2071 2072 /*=========================================================================== 2073 * FUNCTION : camera_open 2074 * 2075 * DESCRIPTION: open a camera by camera index 2076 * 2077 * PARAMETERS : 2078 * @camera_idx : camera index. should within range of 0 to num_of_cameras 2079 * @camera_vtbl : ptr to a virtual table containing camera handle and operation table. 2080 * 2081 * RETURN : int32_t type of status 2082 * 0 -- success 2083 * non-zero error code -- failure 2084 *==========================================================================*/ 2085 int32_t camera_open(uint8_t camera_idx, mm_camera_vtbl_t **camera_vtbl) 2086 { 2087 int32_t rc = 0; 2088 mm_camera_obj_t *cam_obj = NULL; 2089 2090 #ifdef QCAMERA_REDEFINE_LOG 2091 mm_camera_set_dbg_log_properties(); 2092 #endif 2093 2094 LOGD("E camera_idx = %d\n", camera_idx); 2095 if (camera_idx >= g_cam_ctrl.num_cam) { 2096 LOGE("Invalid camera_idx (%d)", camera_idx); 2097 return -EINVAL; 2098 } 2099 2100 pthread_mutex_lock(&g_intf_lock); 2101 /* opened already */ 2102 if(NULL != g_cam_ctrl.cam_obj[camera_idx]) { 2103 /* Add reference */ 2104 g_cam_ctrl.cam_obj[camera_idx]->ref_count++; 2105 pthread_mutex_unlock(&g_intf_lock); 2106 LOGD("opened alreadyn"); 2107 *camera_vtbl = &g_cam_ctrl.cam_obj[camera_idx]->vtbl; 2108 return rc; 2109 } 2110 2111 cam_obj = (mm_camera_obj_t *)malloc(sizeof(mm_camera_obj_t)); 2112 if(NULL == cam_obj) { 2113 pthread_mutex_unlock(&g_intf_lock); 2114 LOGE("no mem"); 2115 return -EINVAL; 2116 } 2117 2118 /* initialize camera obj */ 2119 memset(cam_obj, 0, sizeof(mm_camera_obj_t)); 2120 cam_obj->ctrl_fd = -1; 2121 cam_obj->ds_fd = -1; 2122 cam_obj->ref_count++; 2123 cam_obj->my_hdl = mm_camera_util_generate_handler(camera_idx); 2124 cam_obj->vtbl.camera_handle = cam_obj->my_hdl; /* set handler */ 2125 cam_obj->vtbl.ops = &mm_camera_ops; 2126 pthread_mutex_init(&cam_obj->cam_lock, NULL); 2127 /* unlock global interface lock, if not, in dual camera use case, 2128 * current open will block operation of another opened camera obj*/ 2129 pthread_mutex_lock(&cam_obj->cam_lock); 2130 pthread_mutex_unlock(&g_intf_lock); 2131 2132 rc = mm_camera_open(cam_obj); 2133 2134 pthread_mutex_lock(&g_intf_lock); 2135 if (rc != 0) { 2136 LOGE("mm_camera_open err = %d", rc); 2137 pthread_mutex_destroy(&cam_obj->cam_lock); 2138 g_cam_ctrl.cam_obj[camera_idx] = NULL; 2139 free(cam_obj); 2140 cam_obj = NULL; 2141 pthread_mutex_unlock(&g_intf_lock); 2142 *camera_vtbl = NULL; 2143 return rc; 2144 } else { 2145 LOGD("Open succeded\n"); 2146 g_cam_ctrl.cam_obj[camera_idx] = cam_obj; 2147 pthread_mutex_unlock(&g_intf_lock); 2148 *camera_vtbl = &cam_obj->vtbl; 2149 return 0; 2150 } 2151 } 2152 2153 /*=========================================================================== 2154 * FUNCTION : mm_camera_load_shim_lib 2155 * 2156 * DESCRIPTION: Load shim layer library 2157 * 2158 * PARAMETERS : 2159 * 2160 * RETURN : status of load shim library 2161 *==========================================================================*/ 2162 int32_t mm_camera_load_shim_lib() 2163 { 2164 const char* error = NULL; 2165 void *qdaemon_lib = NULL; 2166 2167 LOGD("E"); 2168 qdaemon_lib = dlopen(SHIMLAYER_LIB, RTLD_NOW); 2169 if (!qdaemon_lib) { 2170 error = dlerror(); 2171 LOGE("dlopen failed with error %s", error ? error : ""); 2172 return -1; 2173 } 2174 2175 *(void **)&mm_camera_shim_module_init = 2176 dlsym(qdaemon_lib, "mct_shimlayer_process_module_init"); 2177 if (!mm_camera_shim_module_init) { 2178 error = dlerror(); 2179 LOGE("dlsym failed with error code %s", error ? error: ""); 2180 dlclose(qdaemon_lib); 2181 return -1; 2182 } 2183 2184 return mm_camera_shim_module_init(&g_cam_ctrl.cam_shim_ops); 2185 } 2186 2187 /*=========================================================================== 2188 * FUNCTION : mm_camera_module_open_session 2189 * 2190 * DESCRIPTION: wrapper function to call shim layer API to open session. 2191 * 2192 * PARAMETERS : 2193 * @sessionid : sessionID to open session 2194 * @evt_cb : Event callback function 2195 * 2196 * RETURN : int32_t type of status 2197 * 0 -- success 2198 * non-zero error code -- failure 2199 *==========================================================================*/ 2200 cam_status_t mm_camera_module_open_session(int sessionid, 2201 mm_camera_shim_event_handler_func evt_cb) 2202 { 2203 cam_status_t rc = -1; 2204 if(g_cam_ctrl.cam_shim_ops.mm_camera_shim_open_session) { 2205 rc = g_cam_ctrl.cam_shim_ops.mm_camera_shim_open_session( 2206 sessionid, evt_cb); 2207 } 2208 return rc; 2209 } 2210 2211 /*=========================================================================== 2212 * FUNCTION : mm_camera_module_close_session 2213 * 2214 * DESCRIPTION: wrapper function to call shim layer API to close session 2215 * 2216 * PARAMETERS : 2217 * @sessionid : sessionID to open session 2218 * 2219 * RETURN : int32_t type of status 2220 * 0 -- success 2221 * non-zero error code -- failure 2222 *==========================================================================*/ 2223 int32_t mm_camera_module_close_session(int session) 2224 { 2225 int32_t rc = -1; 2226 if(g_cam_ctrl.cam_shim_ops.mm_camera_shim_close_session) { 2227 rc = g_cam_ctrl.cam_shim_ops.mm_camera_shim_close_session(session); 2228 } 2229 return rc; 2230 } 2231 2232 /*=========================================================================== 2233 * FUNCTION : mm_camera_module_open_session 2234 * 2235 * DESCRIPTION: wrapper function to call shim layer API 2236 * 2237 * PARAMETERS : 2238 * @sessionid : sessionID to open session 2239 * @evt_cb : Event callback function 2240 * 2241 * RETURN : int32_t type of status 2242 * 0 -- success 2243 * non-zero error code -- failure 2244 *==========================================================================*/ 2245 int32_t mm_camera_module_send_cmd(cam_shim_packet_t *event) 2246 { 2247 int32_t rc = -1; 2248 if(g_cam_ctrl.cam_shim_ops.mm_camera_shim_send_cmd) { 2249 rc = g_cam_ctrl.cam_shim_ops.mm_camera_shim_send_cmd(event); 2250 } 2251 return rc; 2252 } 2253 2254 /*=========================================================================== 2255 * FUNCTION : mm_camera_module_event_handler 2256 * 2257 * DESCRIPTION: call back function for shim layer 2258 * 2259 * PARAMETERS : 2260 * 2261 * RETURN : status of call back function 2262 *==========================================================================*/ 2263 int mm_camera_module_event_handler(uint32_t session_id, cam_event_t *event) 2264 { 2265 if (!event) { 2266 LOGE("null event"); 2267 return FALSE; 2268 } 2269 mm_camera_event_t evt; 2270 2271 LOGD("session_id:%d, cmd:0x%x", session_id, event->server_event_type); 2272 memset(&evt, 0, sizeof(mm_camera_event_t)); 2273 2274 evt = *event; 2275 mm_camera_obj_t *my_obj = 2276 mm_camera_util_get_camera_by_session_id(session_id); 2277 if (!my_obj) { 2278 LOGE("my_obj:%p", my_obj); 2279 return FALSE; 2280 } 2281 switch( evt.server_event_type) { 2282 case CAM_EVENT_TYPE_DAEMON_PULL_REQ: 2283 case CAM_EVENT_TYPE_CAC_DONE: 2284 case CAM_EVENT_TYPE_DAEMON_DIED: 2285 case CAM_EVENT_TYPE_INT_TAKE_JPEG: 2286 case CAM_EVENT_TYPE_INT_TAKE_RAW: 2287 mm_camera_enqueue_evt(my_obj, &evt); 2288 break; 2289 default: 2290 LOGE("cmd:%x from shim layer is not handled", evt.server_event_type); 2291 break; 2292 } 2293 return TRUE; 2294 } 2295 2296