1 /* Copyright (c) 2015-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 #define LOG_TAG "QCameraMuxer" 31 32 // System dependencies 33 #include <fcntl.h> 34 #include <stdio.h> 35 #include <stdlib.h> 36 #include <utils/Errors.h> 37 #define STAT_H <SYSTEM_HEADER_PREFIX/stat.h> 38 #include STAT_H 39 40 // Camera dependencies 41 #include "QCameraMuxer.h" 42 #include "QCamera2HWI.h" 43 #include "QCamera3HWI.h" 44 45 extern "C" { 46 #include "mm_camera_dbg.h" 47 } 48 49 /* Muxer implementation */ 50 using namespace android; 51 namespace qcamera { 52 53 QCameraMuxer *gMuxer = NULL; 54 55 //Error Check Macros 56 #define CHECK_MUXER() \ 57 if (!gMuxer) { \ 58 LOGE("Error getting muxer "); \ 59 return; \ 60 } \ 61 62 #define CHECK_MUXER_ERROR() \ 63 if (!gMuxer) { \ 64 LOGE("Error getting muxer "); \ 65 return -ENODEV; \ 66 } \ 67 68 #define CHECK_CAMERA(pCam) \ 69 if (!pCam) { \ 70 LOGE("Error getting physical camera"); \ 71 return; \ 72 } \ 73 74 #define CHECK_CAMERA_ERROR(pCam) \ 75 if (!pCam) { \ 76 LOGE("Error getting physical camera"); \ 77 return -ENODEV; \ 78 } \ 79 80 #define CHECK_HWI(hwi) \ 81 if (!hwi) { \ 82 LOGE("Error !! HWI not found!!"); \ 83 return; \ 84 } \ 85 86 #define CHECK_HWI_ERROR(hwi) \ 87 if (!hwi) { \ 88 LOGE("Error !! HWI not found!!"); \ 89 return -ENODEV; \ 90 } \ 91 92 93 /*=========================================================================== 94 * FUNCTION : getCameraMuxer 95 * 96 * DESCRIPTION : Creates Camera Muxer if not created 97 * 98 * PARAMETERS: 99 * @pMuxer : Pointer to retrieve Camera Muxer 100 * @num_of_cameras : Number of Physical Cameras on device 101 * 102 * RETURN : NONE 103 *==========================================================================*/ 104 void QCameraMuxer::getCameraMuxer( 105 QCameraMuxer** pMuxer, uint32_t num_of_cameras) 106 { 107 *pMuxer = NULL; 108 if (!gMuxer) { 109 gMuxer = new QCameraMuxer(num_of_cameras); 110 } 111 CHECK_MUXER(); 112 *pMuxer = gMuxer; 113 LOGH("gMuxer: %p ", gMuxer); 114 return; 115 } 116 117 /*=========================================================================== 118 * FUNCTION : QCameraMuxer 119 * 120 * DESCRIPTION : QCameraMuxer Constructor 121 * 122 * PARAMETERS: 123 * @num_of_cameras : Number of Physical Cameras on device 124 * 125 *==========================================================================*/ 126 QCameraMuxer::QCameraMuxer(uint32_t num_of_cameras) 127 : mJpegClientHandle(0), 128 m_pPhyCamera(NULL), 129 m_pLogicalCamera(NULL), 130 m_pCallbacks(NULL), 131 m_bAuxCameraExposed(FALSE), 132 m_nPhyCameras(num_of_cameras), 133 m_nLogicalCameras(0), 134 m_MainJpegQ(releaseJpegInfo, this), 135 m_AuxJpegQ(releaseJpegInfo, this), 136 m_pRelCamMpoJpeg(NULL), 137 m_pMpoCallbackCookie(NULL), 138 m_pJpegCallbackCookie(NULL), 139 m_bDumpImages(FALSE), 140 m_bMpoEnabled(TRUE), 141 m_bFrameSyncEnabled(FALSE), 142 m_bRecordingHintInternallySet(FALSE) 143 { 144 setupLogicalCameras(); 145 memset(&mJpegOps, 0, sizeof(mJpegOps)); 146 memset(&mJpegMpoOps, 0, sizeof(mJpegMpoOps)); 147 memset(&mGetMemoryCb, 0, sizeof(mGetMemoryCb)); 148 memset(&mDataCb, 0, sizeof(mDataCb)); 149 150 // initialize mutex for MPO composition 151 pthread_mutex_init(&m_JpegLock, NULL); 152 // launch MPO composition thread 153 m_ComposeMpoTh.launch(composeMpoRoutine, this); 154 155 //Check whether dual camera images need to be dumped 156 char prop[PROPERTY_VALUE_MAX]; 157 property_get("persist.camera.dual.camera.dump", prop, "0"); 158 m_bDumpImages = atoi(prop); 159 LOGH("dualCamera dump images:%d ", m_bDumpImages); 160 } 161 162 /*=========================================================================== 163 * FUNCTION : ~QCameraMuxer 164 * 165 * DESCRIPTION : QCameraMuxer Desctructor 166 * 167 *==========================================================================*/ 168 QCameraMuxer::~QCameraMuxer() { 169 if (m_pLogicalCamera) { 170 delete [] m_pLogicalCamera; 171 m_pLogicalCamera = NULL; 172 } 173 if (m_pPhyCamera) { 174 delete [] m_pPhyCamera; 175 m_pPhyCamera = NULL; 176 } 177 178 if (NULL != m_pRelCamMpoJpeg) { 179 m_pRelCamMpoJpeg->release(m_pRelCamMpoJpeg); 180 m_pRelCamMpoJpeg = NULL; 181 } 182 // flush Jpeg Queues 183 m_MainJpegQ.flush(); 184 m_AuxJpegQ.flush(); 185 186 // stop and exit MPO composition thread 187 m_ComposeMpoTh.sendCmd(CAMERA_CMD_TYPE_STOP_DATA_PROC, TRUE, FALSE); 188 m_ComposeMpoTh.exit(); 189 190 pthread_mutex_destroy(&m_JpegLock); 191 } 192 193 /*=========================================================================== 194 * FUNCTION : get_number_of_cameras 195 * 196 * DESCRIPTION : Provide number of Logical Cameras 197 * 198 * RETURN : Number of logical Cameras 199 *==========================================================================*/ 200 int QCameraMuxer::get_number_of_cameras() 201 { 202 return gMuxer->getNumberOfCameras(); 203 } 204 205 /*=========================================================================== 206 * FUNCTION : get_camera_info 207 * 208 * DESCRIPTION : get logical camera info 209 * 210 * PARAMETERS: 211 * @camera_id : Logical Camera ID 212 * @info : Logical Main Camera Info 213 * 214 * RETURN : 215 * NO_ERROR : success 216 * ENODEV : Camera not found 217 * other: non-zero failure code 218 *==========================================================================*/ 219 int QCameraMuxer::get_camera_info(int camera_id, struct camera_info *info) 220 { 221 int rc = NO_ERROR; 222 LOGH("E"); 223 cam_sync_type_t type; 224 if ((camera_id < 0) || (camera_id >= gMuxer->getNumberOfCameras())) { 225 LOGE("Camera id %d not found!", camera_id); 226 return -ENODEV; 227 } 228 if(info) { 229 rc = gMuxer->getCameraInfo(camera_id, info, &type); 230 } 231 LOGH("X, rc: %d", rc); 232 return rc; 233 } 234 235 236 /*=========================================================================== 237 * FUNCTION : set_callbacks 238 * 239 * DESCRIPTION : Not Implemented 240 * 241 * PARAMETERS: 242 * @callbacks : Camera Module Callbacks 243 * 244 * RETURN : 245 * NO_ERROR : success 246 * other: non-zero failure code 247 *==========================================================================*/ 248 int QCameraMuxer::set_callbacks(__unused const camera_module_callbacks_t *callbacks) 249 { 250 // Not implemented 251 return NO_ERROR; 252 } 253 254 /*=========================================================================== 255 * FUNCTION : camera_device_open 256 * 257 * DESCRIPTION: static function to open a camera device by its ID 258 * 259 * PARAMETERS : 260 * @modue: hw module 261 * @id : camera ID 262 * @hw_device : ptr to struct storing camera hardware device info 263 * 264 * RETURN : 265 * NO_ERROR : success 266 * BAD_VALUE : Invalid Camera ID 267 * other: non-zero failure code 268 *==========================================================================*/ 269 int QCameraMuxer::camera_device_open( 270 __unused const struct hw_module_t *module, const char *id, 271 struct hw_device_t **hw_device) 272 { 273 int rc = NO_ERROR; 274 LOGH("id= %d",atoi(id)); 275 if (!id) { 276 LOGE("Invalid camera id"); 277 return BAD_VALUE; 278 } 279 280 rc = gMuxer->cameraDeviceOpen(atoi(id), hw_device); 281 LOGH("id= %d, rc: %d", atoi(id), rc); 282 return rc; 283 } 284 285 /*=========================================================================== 286 * FUNCTION : open_legacy 287 * 288 * DESCRIPTION: static function to open a camera device by its ID 289 * 290 * PARAMETERS : 291 * @modue: hw module 292 * @id : camera ID 293 * @halVersion: hal version 294 * @hw_device : ptr to struct storing camera hardware device info 295 * 296 * RETURN : 297 * NO_ERROR : success 298 * BAD_VALUE : Invalid Camera ID 299 * other: non-zero failure code 300 *==========================================================================*/ 301 int QCameraMuxer::open_legacy(__unused const struct hw_module_t* module, 302 const char* id, __unused uint32_t halVersion, struct hw_device_t** hw_device) 303 { 304 int rc = NO_ERROR; 305 LOGH("id= %d", atoi(id)); 306 if (!id) { 307 LOGE("Invalid camera id"); 308 return BAD_VALUE; 309 } 310 311 rc = gMuxer->cameraDeviceOpen(atoi(id), hw_device); 312 LOGH("id= %d, rc: %d", atoi(id), rc); 313 return rc; 314 } 315 316 /*=========================================================================== 317 * FUNCTION : set_preview_window 318 * 319 * DESCRIPTION: Set Preview window for main camera 320 * 321 * PARAMETERS : 322 * @device : camera hardware device info 323 * @window: Preview window ops 324 * 325 * RETURN : 326 * NO_ERROR : success 327 * other: non-zero failure code 328 *==========================================================================*/ 329 int QCameraMuxer::set_preview_window(struct camera_device * device, 330 struct preview_stream_ops *window) 331 { 332 int rc = NO_ERROR; 333 CHECK_MUXER_ERROR(); 334 qcamera_physical_descriptor_t *pCam = NULL; 335 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 336 CHECK_CAMERA_ERROR(cam); 337 338 for (uint32_t i = 0; i < cam->numCameras; i++) { 339 pCam = gMuxer->getPhysicalCamera(cam, i); 340 CHECK_CAMERA_ERROR(pCam); 341 342 // Set preview window only for primary camera 343 if (pCam->mode == CAM_MODE_PRIMARY) { 344 QCamera2HardwareInterface *hwi = pCam->hwi; 345 CHECK_HWI_ERROR(hwi); 346 rc = hwi->set_preview_window(pCam->dev, window); 347 if (rc != NO_ERROR) { 348 LOGE("Error!! setting preview window"); 349 return rc; 350 } 351 break; 352 } 353 } 354 return rc; 355 } 356 357 /*=========================================================================== 358 * FUNCTION : set_callBacks 359 * 360 * DESCRIPTION: Set Framework callbacks to notify various frame data asynchronously 361 * 362 * PARAMETERS : 363 * @device : camera hardware device info 364 * @notify_cb: Notification callback 365 * @data_cb: data callback 366 * @data_cb_timestamp: data timestamp callback 367 * @get_memory: callback to obtain memory 368 * @user : userdata 369 * 370 * RETURN : None 371 *==========================================================================*/ 372 void QCameraMuxer::set_callBacks(struct camera_device * device, 373 camera_notify_callback notify_cb, 374 camera_data_callback data_cb, 375 camera_data_timestamp_callback data_cb_timestamp, 376 camera_request_memory get_memory, 377 void *user) 378 { 379 LOGH("E"); 380 CHECK_MUXER(); 381 int rc = NO_ERROR; 382 qcamera_physical_descriptor_t *pCam = NULL; 383 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 384 CHECK_CAMERA(cam); 385 386 // Set callbacks to HWI 387 for (uint32_t i = 0; i < cam->numCameras; i++) { 388 pCam = gMuxer->getPhysicalCamera(cam, i); 389 CHECK_CAMERA(pCam); 390 391 QCamera2HardwareInterface *hwi = pCam->hwi; 392 CHECK_HWI(hwi); 393 394 hwi->set_CallBacks(pCam->dev, notify_cb, data_cb, data_cb_timestamp, 395 get_memory, user); 396 397 // Set JPG callbacks 398 // sending the physical camera description with the Jpeg callback 399 // this will be retrieved in callbacks to get the cam instance 400 // delivering JPEGs 401 hwi->setJpegCallBacks(jpeg_data_callback, (void*)pCam); 402 403 if (pCam->mode == CAM_MODE_PRIMARY) { 404 rc = gMuxer->setMainJpegCallbackCookie((void*)(pCam)); 405 if(rc != NO_ERROR) { 406 LOGW("Error setting Jpeg callback cookie"); 407 } 408 } 409 } 410 // Store callback in Muxer to send data callbacks 411 rc = gMuxer->setDataCallback(data_cb); 412 if(rc != NO_ERROR) { 413 LOGW("Error setting data callback"); 414 } 415 // memory callback stored to allocate memory for MPO buffer 416 rc = gMuxer->setMemoryCallback(get_memory); 417 if(rc != NO_ERROR) { 418 LOGW("Error setting memory callback"); 419 } 420 // actual user callback cookie is saved in Muxer 421 // this will be used to deliver final MPO callback to the framework 422 rc = gMuxer->setMpoCallbackCookie(user); 423 if(rc != NO_ERROR) { 424 LOGW("Error setting mpo cookie"); 425 } 426 427 LOGH("X"); 428 429 } 430 431 /*=========================================================================== 432 * FUNCTION : enable_msg_type 433 * 434 * DESCRIPTION: Enable msg_type to send callbacks 435 * 436 * PARAMETERS : 437 * @device : camera hardware device info 438 * @msg_type: callback Message type to be enabled 439 * 440 * RETURN : None 441 *==========================================================================*/ 442 void QCameraMuxer::enable_msg_type(struct camera_device * device, int32_t msg_type) 443 { 444 LOGH("E"); 445 CHECK_MUXER(); 446 qcamera_physical_descriptor_t *pCam = NULL; 447 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 448 CHECK_CAMERA(cam); 449 450 for (uint32_t i = 0; i < cam->numCameras; i++) { 451 pCam = gMuxer->getPhysicalCamera(cam, i); 452 CHECK_CAMERA(pCam); 453 QCamera2HardwareInterface *hwi = pCam->hwi; 454 CHECK_HWI(hwi); 455 hwi->enable_msg_type(pCam->dev, msg_type); 456 } 457 LOGH("X"); 458 } 459 460 /*=========================================================================== 461 * FUNCTION : disable_msg_type 462 * 463 * DESCRIPTION: disable msg_type to send callbacks 464 * 465 * PARAMETERS : 466 * @device : camera hardware device info 467 * @msg_type: callback Message type to be disabled 468 * 469 * RETURN : None 470 *==========================================================================*/ 471 void QCameraMuxer::disable_msg_type(struct camera_device * device, int32_t msg_type) 472 { 473 LOGH("E"); 474 CHECK_MUXER(); 475 qcamera_physical_descriptor_t *pCam = NULL; 476 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 477 CHECK_CAMERA(cam); 478 479 for (uint32_t i = 0; i < cam->numCameras; i++) { 480 pCam = gMuxer->getPhysicalCamera(cam, i); 481 CHECK_CAMERA(pCam); 482 QCamera2HardwareInterface *hwi = pCam->hwi; 483 CHECK_HWI(hwi); 484 hwi->disable_msg_type(pCam->dev, msg_type); 485 } 486 LOGH("X"); 487 } 488 489 /*=========================================================================== 490 * FUNCTION : msg_type_enabled 491 * 492 * DESCRIPTION: Check if message type enabled 493 * 494 * PARAMETERS : 495 * @device : camera hardware device info 496 * @msg_type: message type 497 * 498 * RETURN : true/false 499 *==========================================================================*/ 500 int QCameraMuxer::msg_type_enabled(struct camera_device * device, int32_t msg_type) 501 { 502 LOGH("E"); 503 CHECK_MUXER_ERROR(); 504 qcamera_physical_descriptor_t *pCam = NULL; 505 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 506 CHECK_CAMERA_ERROR(cam); 507 508 for (uint32_t i = 0; i < cam->numCameras; i++) { 509 pCam = gMuxer->getPhysicalCamera(cam, i); 510 CHECK_CAMERA_ERROR(pCam); 511 512 QCamera2HardwareInterface *hwi = pCam->hwi; 513 CHECK_HWI_ERROR(hwi); 514 515 if (pCam->mode == CAM_MODE_PRIMARY) { 516 return hwi->msg_type_enabled(pCam->dev, msg_type); 517 } 518 } 519 LOGH("X"); 520 return false; 521 } 522 523 /*=========================================================================== 524 * FUNCTION : start_preview 525 * 526 * DESCRIPTION: Starts logical camera preview 527 * 528 * PARAMETERS : 529 * @device : camera hardware device info 530 * 531 * RETURN : 532 * NO_ERROR : success 533 * other: non-zero failure code 534 *==========================================================================*/ 535 int QCameraMuxer::start_preview(struct camera_device * device) 536 { 537 LOGH("E"); 538 CHECK_MUXER_ERROR(); 539 int rc = NO_ERROR; 540 qcamera_physical_descriptor_t *pCam = NULL; 541 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 542 CHECK_CAMERA_ERROR(cam); 543 544 // prepare preview first for all cameras 545 for (uint32_t i = 0; i < cam->numCameras; i++) { 546 pCam = gMuxer->getPhysicalCamera(cam, i); 547 CHECK_CAMERA_ERROR(pCam); 548 549 QCamera2HardwareInterface *hwi = pCam->hwi; 550 CHECK_HWI_ERROR(hwi); 551 552 rc = hwi->prepare_preview(pCam->dev); 553 if (rc != NO_ERROR) { 554 LOGE("Error preparing preview !! "); 555 return rc; 556 } 557 } 558 559 if (cam->numCameras > 1) { 560 uint sessionId = 0; 561 // Set up sync for camera sessions 562 for (uint32_t i = 0; i < cam->numCameras; i++) { 563 pCam = gMuxer->getPhysicalCamera(cam, i); 564 CHECK_CAMERA_ERROR(pCam); 565 566 QCamera2HardwareInterface *hwi = pCam->hwi; 567 CHECK_HWI_ERROR(hwi); 568 569 if(pCam->mode == CAM_MODE_PRIMARY) { 570 // bundle primary cam with all aux cameras 571 for (uint32_t j = 0; j < cam->numCameras; j++) { 572 if (j == cam->nPrimaryPhyCamIndex) { 573 continue; 574 } 575 sessionId = cam->sId[j]; 576 LOGH("Related cam id: %d, server id: %d sync ON" 577 " related session_id %d", 578 cam->pId[i], cam->sId[i], sessionId); 579 rc = hwi->bundleRelatedCameras(true, sessionId); 580 if (rc != NO_ERROR) { 581 LOGE("Error Bundling physical cameras !! "); 582 return rc; 583 } 584 } 585 } 586 587 if (pCam->mode == CAM_MODE_SECONDARY) { 588 // bundle all aux cam with primary cams 589 sessionId = cam->sId[cam->nPrimaryPhyCamIndex]; 590 LOGH("Related cam id: %d, server id: %d sync ON" 591 " related session_id %d", 592 cam->pId[i], cam->sId[i], sessionId); 593 rc = hwi->bundleRelatedCameras(true, sessionId); 594 if (rc != NO_ERROR) { 595 LOGE("Error Bundling physical cameras !! "); 596 return rc; 597 } 598 } 599 } 600 601 // Remember Sync is ON 602 cam->bSyncOn = true; 603 } 604 // Start Preview for all cameras 605 for (uint32_t i = 0; i < cam->numCameras; i++) { 606 pCam = gMuxer->getPhysicalCamera(cam, i); 607 CHECK_CAMERA_ERROR(pCam); 608 609 QCamera2HardwareInterface *hwi = pCam->hwi; 610 CHECK_HWI_ERROR(hwi); 611 rc = hwi->start_preview(pCam->dev); 612 if (rc != NO_ERROR) { 613 LOGE("Error starting preview !! "); 614 return rc; 615 } 616 } 617 LOGH("X"); 618 return rc; 619 } 620 621 /*=========================================================================== 622 * FUNCTION : stop_preview 623 * 624 * DESCRIPTION: Stops logical camera preview 625 * 626 * PARAMETERS : 627 * @device : camera hardware device info 628 * 629 * RETURN : None 630 *==========================================================================*/ 631 void QCameraMuxer::stop_preview(struct camera_device * device) 632 { 633 LOGH("E"); 634 CHECK_MUXER(); 635 qcamera_physical_descriptor_t *pCam = NULL; 636 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 637 CHECK_CAMERA(cam); 638 639 for (uint32_t i = 0; i < cam->numCameras; i++) { 640 pCam = gMuxer->getPhysicalCamera(cam, i); 641 CHECK_CAMERA(pCam); 642 643 QCamera2HardwareInterface *hwi = pCam->hwi; 644 CHECK_HWI(hwi); 645 646 QCamera2HardwareInterface::stop_preview(pCam->dev); 647 } 648 649 //Flush JPEG Queues. Nodes in Main and Aux JPEGQ are not valid after preview stopped. 650 gMuxer->m_MainJpegQ.flush(); 651 gMuxer->m_AuxJpegQ.flush(); 652 LOGH(" X"); 653 } 654 655 /*=========================================================================== 656 * FUNCTION : preview_enabled 657 * 658 * DESCRIPTION: Checks preview enabled 659 * 660 * PARAMETERS : 661 * @device : camera hardware device info 662 * 663 * RETURN : true/false 664 *==========================================================================*/ 665 int QCameraMuxer::preview_enabled(struct camera_device * device) 666 { 667 LOGH("E"); 668 CHECK_MUXER_ERROR(); 669 qcamera_physical_descriptor_t *pCam = NULL; 670 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 671 CHECK_CAMERA_ERROR(cam); 672 673 for (uint32_t i = 0; i < cam->numCameras; i++) { 674 pCam = gMuxer->getPhysicalCamera(cam, i); 675 CHECK_CAMERA_ERROR(pCam); 676 677 QCamera2HardwareInterface *hwi = pCam->hwi; 678 CHECK_HWI_ERROR(hwi); 679 680 if (pCam->mode == CAM_MODE_PRIMARY) { 681 return hwi->preview_enabled(pCam->dev); 682 } 683 } 684 LOGH("X"); 685 return false; 686 } 687 688 /*=========================================================================== 689 * FUNCTION : store_meta_data_in_buffers 690 * 691 * DESCRIPTION: Stores metadata in buffers 692 * 693 * PARAMETERS : 694 * @device : camera hardware device info 695 * @enable: Enable/disable metadata 696 * 697 * RETURN : 698 * NO_ERROR : success 699 * other: non-zero failure code 700 *==========================================================================*/ 701 int QCameraMuxer::store_meta_data_in_buffers(struct camera_device * device, int enable) 702 { 703 LOGH("E"); 704 CHECK_MUXER_ERROR(); 705 int rc = NO_ERROR; 706 qcamera_physical_descriptor_t *pCam = NULL; 707 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 708 CHECK_CAMERA_ERROR(cam); 709 710 for (uint32_t i = 0; i < cam->numCameras; i++) { 711 pCam = gMuxer->getPhysicalCamera(cam, i); 712 CHECK_CAMERA_ERROR(pCam); 713 714 QCamera2HardwareInterface *hwi = pCam->hwi; 715 CHECK_HWI_ERROR(hwi); 716 717 rc = hwi->store_meta_data_in_buffers(pCam->dev, enable); 718 if (rc != NO_ERROR) { 719 LOGE("Error storing metat data !! "); 720 return rc; 721 } 722 } 723 LOGH("X"); 724 return rc; 725 } 726 727 /*=========================================================================== 728 * FUNCTION : start_recording 729 * 730 * DESCRIPTION: Starts recording on camcorder 731 * 732 * PARAMETERS : 733 * @device : camera hardware device info 734 * 735 * RETURN : 736 * NO_ERROR : success 737 * other: non-zero failure code 738 *==========================================================================*/ 739 int QCameraMuxer::start_recording(struct camera_device * device) 740 { 741 LOGH("E"); 742 CHECK_MUXER_ERROR(); 743 int rc = NO_ERROR; 744 bool previewRestartNeeded = false; 745 qcamera_physical_descriptor_t *pCam = NULL; 746 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 747 CHECK_CAMERA_ERROR(cam); 748 749 // In cases where recording hint is not set, hwi->start_recording will 750 // internally restart the preview. 751 // To take the preview restart control in muxer, 752 // 1. call pre_start_recording first 753 for (uint32_t i = 0; i < cam->numCameras; i++) { 754 pCam = gMuxer->getPhysicalCamera(cam, i); 755 CHECK_CAMERA_ERROR(pCam); 756 757 QCamera2HardwareInterface *hwi = pCam->hwi; 758 CHECK_HWI_ERROR(hwi); 759 760 rc = hwi->pre_start_recording(pCam->dev); 761 if (rc != NO_ERROR) { 762 LOGE("Error preparing recording start!! "); 763 return rc; 764 } 765 } 766 767 // 2. Check if preview restart is needed. Check all cameras. 768 for (uint32_t i = 0; i < cam->numCameras; i++) { 769 pCam = gMuxer->getPhysicalCamera(cam, i); 770 CHECK_CAMERA_ERROR(pCam); 771 772 QCamera2HardwareInterface *hwi = pCam->hwi; 773 CHECK_HWI_ERROR(hwi); 774 775 if (hwi->isPreviewRestartNeeded()) { 776 previewRestartNeeded = hwi->isPreviewRestartNeeded(); 777 break; 778 } 779 } 780 781 if (previewRestartNeeded) { 782 // 3. if preview restart needed. stop the preview first 783 for (uint32_t i = 0; i < cam->numCameras; i++) { 784 pCam = gMuxer->getPhysicalCamera(cam, i); 785 CHECK_CAMERA_ERROR(pCam); 786 787 QCamera2HardwareInterface *hwi = pCam->hwi; 788 CHECK_HWI_ERROR(hwi); 789 790 rc = hwi->restart_stop_preview(pCam->dev); 791 if (rc != NO_ERROR) { 792 LOGE("Error in restart stop preview!! "); 793 return rc; 794 } 795 } 796 797 //4. Update the recording hint value to TRUE 798 for (uint32_t i = 0; i < cam->numCameras; i++) { 799 pCam = gMuxer->getPhysicalCamera(cam, i); 800 CHECK_CAMERA_ERROR(pCam); 801 802 QCamera2HardwareInterface *hwi = pCam->hwi; 803 CHECK_HWI_ERROR(hwi); 804 805 rc = hwi->setRecordingHintValue(TRUE); 806 if (rc != NO_ERROR) { 807 LOGE("Error in setting recording hint value!! "); 808 return rc; 809 } 810 gMuxer->m_bRecordingHintInternallySet = TRUE; 811 } 812 813 // 5. start the preview 814 for (uint32_t i = 0; i < cam->numCameras; i++) { 815 pCam = gMuxer->getPhysicalCamera(cam, i); 816 CHECK_CAMERA_ERROR(pCam); 817 818 QCamera2HardwareInterface *hwi = pCam->hwi; 819 CHECK_HWI_ERROR(hwi); 820 821 rc = hwi->restart_start_preview(pCam->dev); 822 if (rc != NO_ERROR) { 823 LOGE("Error in restart start preview!! "); 824 return rc; 825 } 826 } 827 } 828 829 for (uint32_t i = 0; i < cam->numCameras; i++) { 830 pCam = gMuxer->getPhysicalCamera(cam, i); 831 CHECK_CAMERA_ERROR(pCam); 832 833 QCamera2HardwareInterface *hwi = pCam->hwi; 834 CHECK_HWI_ERROR(hwi); 835 836 if (pCam->mode == CAM_MODE_PRIMARY) { 837 rc = hwi->start_recording(pCam->dev); 838 if (rc != NO_ERROR) { 839 LOGE("Error starting recording!! "); 840 } 841 break; 842 } 843 } 844 LOGH("X"); 845 return rc; 846 } 847 848 /*=========================================================================== 849 * FUNCTION : stop_recording 850 * 851 * DESCRIPTION: Stops recording on camcorder 852 * 853 * PARAMETERS : 854 * @device : camera hardware device info 855 * 856 * RETURN : None 857 *==========================================================================*/ 858 void QCameraMuxer::stop_recording(struct camera_device * device) 859 { 860 861 int rc = NO_ERROR; 862 LOGH("E"); 863 864 CHECK_MUXER(); 865 qcamera_physical_descriptor_t *pCam = NULL; 866 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 867 CHECK_CAMERA(cam); 868 869 for (uint32_t i = 0; i < cam->numCameras; i++) { 870 pCam = gMuxer->getPhysicalCamera(cam, i); 871 CHECK_CAMERA(pCam); 872 873 QCamera2HardwareInterface *hwi = pCam->hwi; 874 CHECK_HWI(hwi); 875 876 if (pCam->mode == CAM_MODE_PRIMARY) { 877 QCamera2HardwareInterface::stop_recording(pCam->dev); 878 break; 879 } 880 } 881 882 // If recording hint is set internally to TRUE, 883 // we need to set it to FALSE. 884 // preview restart is needed in between 885 if (gMuxer->m_bRecordingHintInternallySet) { 886 // stop the preview first 887 for (uint32_t i = 0; i < cam->numCameras; i++) { 888 pCam = gMuxer->getPhysicalCamera(cam, i); 889 CHECK_CAMERA(pCam); 890 891 QCamera2HardwareInterface *hwi = pCam->hwi; 892 CHECK_HWI(hwi); 893 894 rc = hwi->restart_stop_preview(pCam->dev); 895 if (rc != NO_ERROR) { 896 LOGE("Error in restart stop preview!! "); 897 return; 898 } 899 } 900 901 // Update the recording hint value to FALSE 902 for (uint32_t i = 0; i < cam->numCameras; i++) { 903 pCam = gMuxer->getPhysicalCamera(cam, i); 904 CHECK_CAMERA(pCam); 905 906 QCamera2HardwareInterface *hwi = pCam->hwi; 907 CHECK_HWI(hwi); 908 909 rc = hwi->setRecordingHintValue(FALSE); 910 if (rc != NO_ERROR) { 911 LOGE("Error in setting recording hint value!! "); 912 return; 913 } 914 gMuxer->m_bRecordingHintInternallySet = FALSE; 915 } 916 917 // start the preview 918 for (uint32_t i = 0; i < cam->numCameras; i++) { 919 pCam = gMuxer->getPhysicalCamera(cam, i); 920 CHECK_CAMERA(pCam); 921 922 QCamera2HardwareInterface *hwi = pCam->hwi; 923 CHECK_HWI(hwi); 924 925 rc = hwi->restart_start_preview(pCam->dev); 926 if (rc != NO_ERROR) { 927 LOGE("Error in restart start preview!! "); 928 return; 929 } 930 } 931 } 932 LOGH("X"); 933 } 934 935 /*=========================================================================== 936 * FUNCTION : recording_enabled 937 * 938 * DESCRIPTION: Checks for recording enabled 939 * 940 * PARAMETERS : 941 * @device : camera hardware device info 942 * 943 * RETURN : true/false 944 *==========================================================================*/ 945 int QCameraMuxer::recording_enabled(struct camera_device * device) 946 { 947 LOGH("E"); 948 CHECK_MUXER_ERROR(); 949 qcamera_physical_descriptor_t *pCam = NULL; 950 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 951 CHECK_CAMERA_ERROR(cam); 952 953 for (uint32_t i = 0; i < cam->numCameras; i++) { 954 pCam = gMuxer->getPhysicalCamera(cam, i); 955 CHECK_CAMERA_ERROR(pCam); 956 957 QCamera2HardwareInterface *hwi = pCam->hwi; 958 CHECK_HWI_ERROR(hwi); 959 960 if (pCam->mode == CAM_MODE_PRIMARY) { 961 return hwi->recording_enabled(pCam->dev); 962 } 963 } 964 LOGH("X"); 965 return false; 966 } 967 968 /*=========================================================================== 969 * FUNCTION : release_recording_frame 970 * 971 * DESCRIPTION: Release the recording frame 972 * 973 * PARAMETERS : 974 * @device : camera hardware device info 975 * @opaque: Frame to be released 976 * 977 * RETURN : None 978 *==========================================================================*/ 979 void QCameraMuxer::release_recording_frame(struct camera_device * device, 980 const void *opaque) 981 { 982 LOGH("E"); 983 CHECK_MUXER(); 984 qcamera_physical_descriptor_t *pCam = NULL; 985 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 986 CHECK_CAMERA(cam); 987 988 for (uint32_t i = 0; i < cam->numCameras; i++) { 989 pCam = gMuxer->getPhysicalCamera(cam, i); 990 CHECK_CAMERA(pCam); 991 992 QCamera2HardwareInterface *hwi = pCam->hwi; 993 CHECK_HWI(hwi); 994 995 if (pCam->mode == CAM_MODE_PRIMARY) { 996 QCamera2HardwareInterface::release_recording_frame(pCam->dev, opaque); 997 break; 998 } 999 } 1000 LOGH("X"); 1001 } 1002 1003 /*=========================================================================== 1004 * FUNCTION : auto_focus 1005 * 1006 * DESCRIPTION: Performs auto focus on camera 1007 * 1008 * PARAMETERS : 1009 * @device : camera hardware device info 1010 * 1011 * RETURN : 1012 * NO_ERROR : success 1013 * other: non-zero failure code 1014 *==========================================================================*/ 1015 int QCameraMuxer::auto_focus(struct camera_device * device) 1016 { 1017 LOGH("E"); 1018 CHECK_MUXER_ERROR(); 1019 int rc = NO_ERROR; 1020 qcamera_physical_descriptor_t *pCam = NULL; 1021 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 1022 CHECK_CAMERA_ERROR(cam); 1023 1024 for (uint32_t i = 0; i < cam->numCameras; i++) { 1025 pCam = gMuxer->getPhysicalCamera(cam, i); 1026 CHECK_CAMERA_ERROR(pCam); 1027 1028 QCamera2HardwareInterface *hwi = pCam->hwi; 1029 CHECK_HWI_ERROR(hwi); 1030 // Call auto focus on main camera 1031 if (pCam->mode == CAM_MODE_PRIMARY) { 1032 rc = QCamera2HardwareInterface::auto_focus(pCam->dev); 1033 if (rc != NO_ERROR) { 1034 LOGE("Error auto focusing !! "); 1035 return rc; 1036 } 1037 break; 1038 } 1039 } 1040 LOGH("X"); 1041 return rc; 1042 } 1043 1044 /*=========================================================================== 1045 * FUNCTION : cancel_auto_focus 1046 * 1047 * DESCRIPTION: Cancels auto focus 1048 * 1049 * PARAMETERS : 1050 * @device : camera hardware device info 1051 * 1052 * RETURN : 1053 * NO_ERROR : success 1054 * other: non-zero failure code 1055 *==========================================================================*/ 1056 int QCameraMuxer::cancel_auto_focus(struct camera_device * device) 1057 { 1058 LOGH("E"); 1059 CHECK_MUXER_ERROR(); 1060 int rc = NO_ERROR; 1061 qcamera_physical_descriptor_t *pCam = NULL; 1062 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 1063 CHECK_CAMERA_ERROR(cam); 1064 1065 for (uint32_t i = 0; i < cam->numCameras; i++) { 1066 pCam = gMuxer->getPhysicalCamera(cam, i); 1067 CHECK_CAMERA_ERROR(pCam); 1068 1069 QCamera2HardwareInterface *hwi = pCam->hwi; 1070 CHECK_HWI_ERROR(hwi); 1071 // Cancel auto focus on primary camera 1072 if (pCam->mode == CAM_MODE_PRIMARY) { 1073 rc = QCamera2HardwareInterface::cancel_auto_focus(pCam->dev); 1074 if (rc != NO_ERROR) { 1075 LOGE("Error cancelling auto focus !! "); 1076 return rc; 1077 } 1078 break; 1079 } 1080 } 1081 LOGH("X"); 1082 return rc; 1083 } 1084 1085 /*=========================================================================== 1086 * FUNCTION : take_picture 1087 * 1088 * DESCRIPTION: Take snapshots on device 1089 * 1090 * PARAMETERS : 1091 * @device : camera hardware device info 1092 * 1093 * RETURN : 1094 * NO_ERROR : success 1095 * other: non-zero failure code 1096 *==========================================================================*/ 1097 int QCameraMuxer::take_picture(struct camera_device * device) 1098 { 1099 LOGH("E"); 1100 CHECK_MUXER_ERROR(); 1101 int rc = NO_ERROR; 1102 bool previewRestartNeeded = false; 1103 qcamera_physical_descriptor_t *pCam = NULL; 1104 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 1105 CHECK_CAMERA_ERROR(cam); 1106 1107 char prop[PROPERTY_VALUE_MAX]; 1108 property_get("persist.camera.dual.camera.mpo", prop, "1"); 1109 gMuxer->m_bMpoEnabled = atoi(prop); 1110 // If only one Physical Camera included in Logical, disable MPO 1111 int numOfAcitvePhyCam = 0; 1112 gMuxer->getActiveNumOfPhyCam(cam, numOfAcitvePhyCam); 1113 if (gMuxer->m_bMpoEnabled && numOfAcitvePhyCam <= 1) { 1114 gMuxer->m_bMpoEnabled = 0; 1115 } 1116 LOGH("dualCamera MPO Enabled:%d ", gMuxer->m_bMpoEnabled); 1117 1118 if (!gMuxer->mJpegClientHandle) { 1119 // set up jpeg handles 1120 pCam = gMuxer->getPhysicalCamera(cam, 0); 1121 CHECK_CAMERA_ERROR(pCam); 1122 1123 QCamera2HardwareInterface *hwi = pCam->hwi; 1124 CHECK_HWI_ERROR(hwi); 1125 1126 rc = hwi->getJpegHandleInfo(&gMuxer->mJpegOps, &gMuxer->mJpegMpoOps, 1127 &gMuxer->mJpegClientHandle); 1128 if (rc != NO_ERROR) { 1129 LOGE("Error retrieving jpeg handle!"); 1130 return rc; 1131 } 1132 1133 for (uint32_t i = 1; i < cam->numCameras; i++) { 1134 pCam = gMuxer->getPhysicalCamera(cam, i); 1135 CHECK_CAMERA_ERROR(pCam); 1136 1137 QCamera2HardwareInterface *hwi = pCam->hwi; 1138 CHECK_HWI_ERROR(hwi); 1139 1140 rc = hwi->setJpegHandleInfo(&gMuxer->mJpegOps, &gMuxer->mJpegMpoOps, 1141 gMuxer->mJpegClientHandle); 1142 if (rc != NO_ERROR) { 1143 LOGE("Error setting jpeg handle %d!", i); 1144 return rc; 1145 } 1146 } 1147 } 1148 1149 // prepare snapshot for main camera 1150 for (uint32_t i = 0; i < cam->numCameras; i++) { 1151 pCam = gMuxer->getPhysicalCamera(cam, i); 1152 CHECK_CAMERA_ERROR(pCam); 1153 1154 QCamera2HardwareInterface *hwi = pCam->hwi; 1155 CHECK_HWI_ERROR(hwi); 1156 1157 if (pCam->mode == CAM_MODE_PRIMARY) { 1158 rc = hwi->prepare_snapshot(pCam->dev); 1159 if (rc != NO_ERROR) { 1160 LOGE("Error preparing for snapshot !! "); 1161 return rc; 1162 } 1163 } 1164 // set Mpo composition for each session 1165 rc = hwi->setMpoComposition(gMuxer->m_bMpoEnabled); 1166 //disable MPO if AOST features are enabled 1167 if (rc != NO_ERROR) { 1168 gMuxer->m_bMpoEnabled = 0; 1169 rc = NO_ERROR; 1170 } 1171 } 1172 1173 // initialize Jpeg Queues 1174 gMuxer->m_MainJpegQ.init(); 1175 gMuxer->m_AuxJpegQ.init(); 1176 gMuxer->m_ComposeMpoTh.sendCmd( 1177 CAMERA_CMD_TYPE_START_DATA_PROC, FALSE, FALSE); 1178 1179 // In cases where recording hint is set, preview is running, 1180 // hwi->take_picture will internally restart the preview. 1181 // To take the preview restart control in muxer, 1182 // 1. call pre_take_picture first 1183 for (uint32_t i = 0; i < cam->numCameras; i++) { 1184 pCam = gMuxer->getPhysicalCamera(cam, i); 1185 CHECK_CAMERA_ERROR(pCam); 1186 1187 QCamera2HardwareInterface *hwi = pCam->hwi; 1188 CHECK_HWI_ERROR(hwi); 1189 1190 // no need to call pre_take_pic on Aux if not MPO (for AOST,liveshot...etc.) 1191 if ( (gMuxer->m_bMpoEnabled == 1) || (pCam->mode == CAM_MODE_PRIMARY) ) { 1192 rc = hwi->pre_take_picture(pCam->dev); 1193 if (rc != NO_ERROR) { 1194 LOGE("Error preparing take_picture!! "); 1195 return rc; 1196 } 1197 } 1198 } 1199 1200 // 2. Check if preview restart is needed. Check all cameras. 1201 for (uint32_t i = 0; i < cam->numCameras; i++) { 1202 pCam = gMuxer->getPhysicalCamera(cam, i); 1203 CHECK_CAMERA_ERROR(pCam); 1204 1205 QCamera2HardwareInterface *hwi = pCam->hwi; 1206 CHECK_HWI_ERROR(hwi); 1207 1208 if (hwi->isPreviewRestartNeeded()) { 1209 previewRestartNeeded = hwi->isPreviewRestartNeeded(); 1210 break; 1211 } 1212 } 1213 1214 if (previewRestartNeeded) { 1215 // 3. if preview restart needed. stop the preview first 1216 for (uint32_t i = 0; i < cam->numCameras; i++) { 1217 pCam = gMuxer->getPhysicalCamera(cam, i); 1218 CHECK_CAMERA_ERROR(pCam); 1219 1220 QCamera2HardwareInterface *hwi = pCam->hwi; 1221 CHECK_HWI_ERROR(hwi); 1222 1223 rc = hwi->restart_stop_preview(pCam->dev); 1224 if (rc != NO_ERROR) { 1225 LOGE("Error in restart stop preview!! "); 1226 return rc; 1227 } 1228 } 1229 1230 //4. Update the recording hint value to FALSE 1231 for (uint32_t i = 0; i < cam->numCameras; i++) { 1232 pCam = gMuxer->getPhysicalCamera(cam, i); 1233 CHECK_CAMERA_ERROR(pCam); 1234 1235 QCamera2HardwareInterface *hwi = pCam->hwi; 1236 CHECK_HWI_ERROR(hwi); 1237 1238 rc = hwi->setRecordingHintValue(FALSE); 1239 if (rc != NO_ERROR) { 1240 LOGE("Error in setting recording hint value!! "); 1241 return rc; 1242 } 1243 } 1244 1245 // 5. start the preview 1246 for (uint32_t i = 0; i < cam->numCameras; i++) { 1247 pCam = gMuxer->getPhysicalCamera(cam, i); 1248 CHECK_CAMERA_ERROR(pCam); 1249 1250 QCamera2HardwareInterface *hwi = pCam->hwi; 1251 CHECK_HWI_ERROR(hwi); 1252 1253 rc = hwi->restart_start_preview(pCam->dev); 1254 if (rc != NO_ERROR) { 1255 LOGE("Error in restart start preview!! "); 1256 return rc; 1257 } 1258 } 1259 } 1260 1261 // As frame sync for dual cameras is enabled, the take picture call 1262 // for secondary camera is handled only till HAL level to init corresponding 1263 // pproc channel and update statemachine. 1264 // This call is forwarded to mm-camera-intf only for primary camera 1265 // Primary camera should receive the take picture call after all secondary 1266 // camera statemachines are updated 1267 for (int32_t i = cam->numCameras-1 ; i >= 0; i--) { 1268 pCam = gMuxer->getPhysicalCamera(cam, i); 1269 CHECK_CAMERA_ERROR(pCam); 1270 1271 QCamera2HardwareInterface *hwi = pCam->hwi; 1272 CHECK_HWI_ERROR(hwi); 1273 1274 // no need to call take_pic on Aux if not MPO (for AOST) 1275 if ( (gMuxer->m_bMpoEnabled == 1) || (pCam->mode == CAM_MODE_PRIMARY) ) { 1276 rc = QCamera2HardwareInterface::take_picture(pCam->dev); 1277 if (rc != NO_ERROR) { 1278 LOGE("Error taking picture !! "); 1279 return rc; 1280 } 1281 } 1282 } 1283 LOGH("X"); 1284 return rc; 1285 } 1286 1287 /*=========================================================================== 1288 * FUNCTION : cancel_picture 1289 * 1290 * DESCRIPTION: Cancel the take picture call 1291 * 1292 * PARAMETERS : 1293 * @device : camera hardware device info 1294 * 1295 * RETURN : 1296 * NO_ERROR : success 1297 * other: non-zero failure code 1298 *==========================================================================*/ 1299 int QCameraMuxer::cancel_picture(struct camera_device * device) 1300 { 1301 LOGH("E"); 1302 CHECK_MUXER_ERROR(); 1303 int rc = NO_ERROR; 1304 qcamera_physical_descriptor_t *pCam = NULL; 1305 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 1306 CHECK_CAMERA_ERROR(cam); 1307 1308 for (uint32_t i = 0; i < cam->numCameras; i++) { 1309 pCam = gMuxer->getPhysicalCamera(cam, i); 1310 CHECK_CAMERA_ERROR(pCam); 1311 1312 QCamera2HardwareInterface *hwi = pCam->hwi; 1313 CHECK_HWI_ERROR(hwi); 1314 1315 rc = QCamera2HardwareInterface::cancel_picture(pCam->dev); 1316 if (rc != NO_ERROR) { 1317 LOGE("Error cancelling picture !! "); 1318 return rc; 1319 } 1320 } 1321 gMuxer->m_ComposeMpoTh.sendCmd(CAMERA_CMD_TYPE_STOP_DATA_PROC, FALSE, FALSE); 1322 // flush Jpeg Queues 1323 gMuxer->m_MainJpegQ.flush(); 1324 gMuxer->m_AuxJpegQ.flush(); 1325 1326 LOGH("X"); 1327 return rc; 1328 } 1329 1330 /*=========================================================================== 1331 * FUNCTION : set_parameters 1332 * 1333 * DESCRIPTION: Sets the parameters on camera 1334 * 1335 * PARAMETERS : 1336 * @device : camera hardware device info 1337 * @parms : Parameters to be set on camera 1338 * 1339 * RETURN : 1340 * NO_ERROR : success 1341 * other: non-zero failure code 1342 *==========================================================================*/ 1343 int QCameraMuxer::set_parameters(struct camera_device * device, 1344 const char *parms) 1345 1346 { 1347 LOGH("E"); 1348 CHECK_MUXER_ERROR(); 1349 int rc = NO_ERROR; 1350 qcamera_physical_descriptor_t *pCam = NULL; 1351 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 1352 bool needRestart = false; 1353 CHECK_CAMERA_ERROR(cam); 1354 1355 for (uint32_t i = 0; i < cam->numCameras; i++) { 1356 pCam = gMuxer->getPhysicalCamera(cam, i); 1357 CHECK_CAMERA_ERROR(pCam); 1358 1359 QCamera2HardwareInterface *hwi = pCam->hwi; 1360 CHECK_HWI_ERROR(hwi); 1361 1362 rc = QCamera2HardwareInterface::set_parameters(pCam->dev, parms); 1363 if (rc != NO_ERROR) { 1364 LOGE("Error setting parameters !! "); 1365 return rc; 1366 } 1367 1368 needRestart |= hwi->getNeedRestart(); 1369 } 1370 1371 if (needRestart) { 1372 for (uint32_t i = 0; i < cam->numCameras; i++) { 1373 pCam = gMuxer->getPhysicalCamera(cam, i); 1374 CHECK_CAMERA_ERROR(pCam); 1375 1376 QCamera2HardwareInterface *hwi = pCam->hwi; 1377 CHECK_HWI_ERROR(hwi); 1378 1379 LOGD("stopping preview for cam %d", i); 1380 rc = QCamera2HardwareInterface::stop_after_set_params(pCam->dev); 1381 if (rc != NO_ERROR) { 1382 LOGE("Error stopping camera rc=%d!! ", rc); 1383 return rc; 1384 } 1385 } 1386 } 1387 1388 for (uint32_t i = 0; i < cam->numCameras; i++) { 1389 pCam = gMuxer->getPhysicalCamera(cam, i); 1390 CHECK_CAMERA_ERROR(pCam); 1391 1392 QCamera2HardwareInterface *hwi = pCam->hwi; 1393 CHECK_HWI_ERROR(hwi); 1394 1395 LOGD("commiting parameters for cam %d", i); 1396 rc = QCamera2HardwareInterface::commit_params(pCam->dev); 1397 if (rc != NO_ERROR) { 1398 LOGE("Error committing parameters rc=%d!! ", rc); 1399 return rc; 1400 } 1401 } 1402 1403 if (needRestart) { 1404 for (uint32_t i = 0; i < cam->numCameras; i++) { 1405 pCam = gMuxer->getPhysicalCamera(cam, i); 1406 CHECK_CAMERA_ERROR(pCam); 1407 1408 QCamera2HardwareInterface *hwi = pCam->hwi; 1409 CHECK_HWI_ERROR(hwi); 1410 1411 LOGD("restarting preview for cam %d", i); 1412 rc = QCamera2HardwareInterface::restart_after_set_params(pCam->dev); 1413 if (rc != NO_ERROR) { 1414 LOGE("Error restarting camera rc=%d!! ", rc); 1415 return rc; 1416 } 1417 } 1418 } 1419 1420 LOGH(" X"); 1421 return rc; 1422 } 1423 1424 /*=========================================================================== 1425 * FUNCTION : get_parameters 1426 * 1427 * DESCRIPTION: Gets the parameters on camera 1428 * 1429 * PARAMETERS : 1430 * @device : camera hardware device info 1431 * 1432 * RETURN : Parameter string or NULL 1433 *==========================================================================*/ 1434 char* QCameraMuxer::get_parameters(struct camera_device * device) 1435 { 1436 LOGH("E"); 1437 1438 if (!gMuxer) 1439 return NULL; 1440 1441 char* ret = NULL; 1442 qcamera_physical_descriptor_t *pCam = NULL; 1443 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 1444 if (!cam) { 1445 LOGE("Error getting logical camera"); 1446 return NULL; 1447 } 1448 1449 for (uint32_t i = 0; i < cam->numCameras; i++) { 1450 pCam = gMuxer->getPhysicalCamera(cam, i); 1451 if (!pCam) { 1452 LOGE("Error getting physical camera"); 1453 return NULL; 1454 } 1455 QCamera2HardwareInterface *hwi = pCam->hwi; 1456 if (!hwi) { 1457 LOGE("Allocation of hardware interface failed"); 1458 return NULL; 1459 } 1460 if (pCam->mode == CAM_MODE_PRIMARY) { 1461 // Get only primary camera parameters 1462 ret = QCamera2HardwareInterface::get_parameters(pCam->dev); 1463 break; 1464 } 1465 } 1466 1467 LOGH("X"); 1468 return ret; 1469 } 1470 1471 /*=========================================================================== 1472 * FUNCTION : put_parameters 1473 * 1474 * DESCRIPTION: Puts parameters on camera 1475 * 1476 * PARAMETERS : 1477 * @device : camera hardware device info 1478 * @parm : parameters 1479 * 1480 * RETURN : None 1481 *==========================================================================*/ 1482 void QCameraMuxer::put_parameters(struct camera_device * device, char *parm) 1483 { 1484 LOGH("E"); 1485 CHECK_MUXER(); 1486 qcamera_physical_descriptor_t *pCam = NULL; 1487 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 1488 CHECK_CAMERA(cam); 1489 1490 for (uint32_t i = 0; i < cam->numCameras; i++) { 1491 pCam = gMuxer->getPhysicalCamera(cam, i); 1492 CHECK_CAMERA(pCam); 1493 1494 QCamera2HardwareInterface *hwi = pCam->hwi; 1495 CHECK_HWI(hwi); 1496 1497 if (pCam->mode == CAM_MODE_PRIMARY) { 1498 // Parameters are not used in HWI and hence freed 1499 QCamera2HardwareInterface::put_parameters(pCam->dev, parm); 1500 break; 1501 } 1502 } 1503 LOGH("X"); 1504 } 1505 1506 /*=========================================================================== 1507 * FUNCTION : send_command 1508 * 1509 * DESCRIPTION: Send command to camera 1510 * 1511 * PARAMETERS : 1512 * @device : camera hardware device info 1513 * @cmd : Command 1514 * @arg1/arg2 : command arguments 1515 * 1516 * RETURN : 1517 * NO_ERROR : success 1518 * other: non-zero failure code 1519 *==========================================================================*/ 1520 int QCameraMuxer::send_command(struct camera_device * device, 1521 int32_t cmd, int32_t arg1, int32_t arg2) 1522 { 1523 LOGH("E"); 1524 CHECK_MUXER_ERROR(); 1525 int rc = NO_ERROR; 1526 qcamera_physical_descriptor_t *pCam = NULL; 1527 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 1528 CHECK_CAMERA_ERROR(cam); 1529 1530 for (uint32_t i = 0; i < cam->numCameras; i++) { 1531 pCam = gMuxer->getPhysicalCamera(cam, i); 1532 CHECK_CAMERA_ERROR(pCam); 1533 1534 QCamera2HardwareInterface *hwi = pCam->hwi; 1535 CHECK_HWI_ERROR(hwi); 1536 1537 rc = QCamera2HardwareInterface::send_command(pCam->dev, cmd, arg1, arg2); 1538 if (rc != NO_ERROR) { 1539 LOGE("Error sending command !! "); 1540 return rc; 1541 } 1542 } 1543 1544 switch (cmd) { 1545 #ifndef VANILLA_HAL 1546 case CAMERA_CMD_LONGSHOT_ON: 1547 for (uint32_t i = 0; i < cam->numCameras; i++) { 1548 pCam = gMuxer->getPhysicalCamera(cam, i); 1549 CHECK_CAMERA_ERROR(pCam); 1550 1551 QCamera2HardwareInterface *hwi = pCam->hwi; 1552 CHECK_HWI_ERROR(hwi); 1553 1554 rc = QCamera2HardwareInterface::send_command_restart(pCam->dev, 1555 cmd, arg1, arg2); 1556 if (rc != NO_ERROR) { 1557 LOGE("Error sending command restart !! "); 1558 return rc; 1559 } 1560 } 1561 break; 1562 case CAMERA_CMD_LONGSHOT_OFF: 1563 gMuxer->m_ComposeMpoTh.sendCmd(CAMERA_CMD_TYPE_STOP_DATA_PROC, 1564 FALSE, FALSE); 1565 // flush Jpeg Queues 1566 gMuxer->m_MainJpegQ.flush(); 1567 gMuxer->m_AuxJpegQ.flush(); 1568 break; 1569 #endif 1570 default: 1571 // do nothing 1572 rc = NO_ERROR; 1573 break; 1574 } 1575 1576 LOGH("X"); 1577 return rc; 1578 } 1579 1580 /*=========================================================================== 1581 * FUNCTION : release 1582 * 1583 * DESCRIPTION: Release the camera 1584 * 1585 * PARAMETERS : 1586 * @device : camera hardware device info 1587 * 1588 * RETURN : None 1589 *==========================================================================*/ 1590 void QCameraMuxer::release(struct camera_device * device) 1591 { 1592 LOGH("E"); 1593 CHECK_MUXER(); 1594 qcamera_physical_descriptor_t *pCam = NULL; 1595 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 1596 CHECK_CAMERA(cam); 1597 1598 for (uint32_t i = 0; i < cam->numCameras; i++) { 1599 pCam = gMuxer->getPhysicalCamera(cam, i); 1600 CHECK_CAMERA(pCam); 1601 1602 QCamera2HardwareInterface *hwi = pCam->hwi; 1603 CHECK_HWI(hwi); 1604 1605 QCamera2HardwareInterface::release(pCam->dev); 1606 } 1607 LOGH("X"); 1608 } 1609 1610 /*=========================================================================== 1611 * FUNCTION : dump 1612 * 1613 * DESCRIPTION: Dump the camera info 1614 * 1615 * PARAMETERS : 1616 * @device : camera hardware device info 1617 * @fd : fd 1618 * 1619 * RETURN : 1620 * NO_ERROR : success 1621 * other: non-zero failure code 1622 *==========================================================================*/ 1623 int QCameraMuxer::dump(struct camera_device * device, int fd) 1624 { 1625 LOGH("E"); 1626 CHECK_MUXER_ERROR(); 1627 int rc = NO_ERROR; 1628 qcamera_physical_descriptor_t *pCam = NULL; 1629 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(device); 1630 CHECK_CAMERA_ERROR(cam); 1631 1632 for (uint32_t i = 0; i < cam->numCameras; i++) { 1633 pCam = gMuxer->getPhysicalCamera(cam, i); 1634 CHECK_CAMERA_ERROR(pCam); 1635 1636 QCamera2HardwareInterface *hwi = pCam->hwi; 1637 CHECK_HWI_ERROR(hwi); 1638 1639 rc = QCamera2HardwareInterface::dump(pCam->dev, fd); 1640 if (rc != NO_ERROR) { 1641 LOGE("Error dumping"); 1642 return rc; 1643 } 1644 } 1645 LOGH("X"); 1646 return rc; 1647 } 1648 1649 /*=========================================================================== 1650 * FUNCTION : close_camera_device 1651 * 1652 * DESCRIPTION: Close the camera 1653 * 1654 * PARAMETERS : 1655 * @hw_dev : camera hardware device info 1656 * 1657 * RETURN : 1658 * NO_ERROR : success 1659 * other: non-zero failure code 1660 *==========================================================================*/ 1661 int QCameraMuxer::close_camera_device(hw_device_t *hw_dev) 1662 { 1663 LOGH("E"); 1664 CHECK_MUXER_ERROR(); 1665 int rc = NO_ERROR; 1666 qcamera_physical_descriptor_t *pCam = NULL; 1667 camera_device_t *cam_dev = (camera_device_t*)hw_dev; 1668 qcamera_logical_descriptor_t *cam = gMuxer->getLogicalCamera(cam_dev); 1669 CHECK_CAMERA_ERROR(cam); 1670 1671 // Unlink camera sessions 1672 if (cam->bSyncOn) { 1673 if (cam->numCameras > 1) { 1674 uint sessionId = 0; 1675 // unbundle primary camera with all aux cameras 1676 for (uint32_t i = 0; i < cam->numCameras; i++) { 1677 pCam = gMuxer->getPhysicalCamera(cam, i); 1678 CHECK_CAMERA_ERROR(pCam); 1679 1680 QCamera2HardwareInterface *hwi = pCam->hwi; 1681 CHECK_HWI_ERROR(hwi); 1682 1683 if(pCam->mode == CAM_MODE_PRIMARY) { 1684 // bundle primary cam with all aux cameras 1685 for (uint32_t j = 0; j < cam->numCameras; j++) { 1686 if (j == cam->nPrimaryPhyCamIndex) { 1687 continue; 1688 } 1689 sessionId = cam->sId[j]; 1690 LOGH("Related cam id: %d, server id: %d sync OFF" 1691 " related session_id %d", 1692 cam->pId[i], cam->sId[i], sessionId); 1693 rc = hwi->bundleRelatedCameras(false, sessionId); 1694 if (rc != NO_ERROR) { 1695 LOGE("Error Bundling physical cameras !! "); 1696 break; 1697 } 1698 } 1699 } 1700 1701 if (pCam->mode == CAM_MODE_SECONDARY) { 1702 // unbundle all aux cam with primary cams 1703 sessionId = cam->sId[cam->nPrimaryPhyCamIndex]; 1704 LOGH("Related cam id: %d, server id: %d sync OFF" 1705 " related session_id %d", 1706 cam->pId[i], cam->sId[i], sessionId); 1707 rc = hwi->bundleRelatedCameras(false, sessionId); 1708 if (rc != NO_ERROR) { 1709 LOGE("Error Bundling physical cameras !! "); 1710 break; 1711 } 1712 } 1713 } 1714 } 1715 cam->bSyncOn = false; 1716 } 1717 1718 // Attempt to close all cameras regardless of unbundle results 1719 for (uint32_t i = 0; i < cam->numCameras; i++) { 1720 pCam = gMuxer->getPhysicalCamera(cam, i); 1721 CHECK_CAMERA_ERROR(pCam); 1722 1723 hw_device_t *dev = (hw_device_t*)(pCam->dev); 1724 LOGH("hw device %x, hw %x", dev, pCam->hwi); 1725 1726 rc = QCamera2HardwareInterface::close_camera_device(dev); 1727 if (rc != NO_ERROR) { 1728 LOGE("Error closing camera"); 1729 } 1730 pCam->hwi = NULL; 1731 pCam->dev = NULL; 1732 } 1733 1734 // Reset JPEG client handle 1735 gMuxer->setJpegHandle(0); 1736 LOGH("X, rc: %d", rc); 1737 return rc; 1738 } 1739 1740 /*=========================================================================== 1741 * FUNCTION : setupLogicalCameras 1742 * 1743 * DESCRIPTION : Creates Camera Muxer if not created 1744 * 1745 * RETURN : 1746 * NO_ERROR : success 1747 * other: non-zero failure code 1748 *==========================================================================*/ 1749 int QCameraMuxer::setupLogicalCameras() 1750 { 1751 int rc = NO_ERROR; 1752 char prop[PROPERTY_VALUE_MAX]; 1753 int i = 0; 1754 int primaryType = CAM_TYPE_MAIN; 1755 1756 LOGH("[%d] E: rc = %d", rc); 1757 // Signifies whether AUX camera has to be exposed as physical camera 1758 property_get("persist.camera.aux.camera", prop, "0"); 1759 m_bAuxCameraExposed = atoi(prop); 1760 1761 // Signifies whether AUX camera needs to be swapped 1762 property_get("persist.camera.auxcamera.swap", prop, "0"); 1763 int swapAux = atoi(prop); 1764 if (swapAux != 0) { 1765 primaryType = CAM_TYPE_AUX; 1766 } 1767 1768 // Check for number of camera present on device 1769 if (!m_nPhyCameras || (m_nPhyCameras > MM_CAMERA_MAX_NUM_SENSORS)) { 1770 LOGE("Error!! Invalid number of cameras: %d", 1771 m_nPhyCameras); 1772 return BAD_VALUE; 1773 } 1774 1775 m_pPhyCamera = new qcamera_physical_descriptor_t[m_nPhyCameras]; 1776 if (!m_pPhyCamera) { 1777 LOGE("Error allocating camera info buffer!!"); 1778 return NO_MEMORY; 1779 } 1780 memset(m_pPhyCamera, 0x00, 1781 (m_nPhyCameras * sizeof(qcamera_physical_descriptor_t))); 1782 uint32_t cameraId = 0; 1783 m_nLogicalCameras = 0; 1784 1785 // Enumerate physical cameras and logical 1786 for (i = 0; i < m_nPhyCameras ; i++, cameraId++) { 1787 camera_info *info = &m_pPhyCamera[i].cam_info; 1788 rc = QCamera2HardwareInterface::getCapabilities(cameraId, 1789 info, &m_pPhyCamera[i].type); 1790 m_pPhyCamera[i].id = cameraId; 1791 m_pPhyCamera[i].device_version = CAMERA_DEVICE_API_VERSION_1_0; 1792 m_pPhyCamera[i].mode = CAM_MODE_PRIMARY; 1793 1794 if (!m_bAuxCameraExposed && (m_pPhyCamera[i].type != primaryType)) { 1795 m_pPhyCamera[i].mode = CAM_MODE_SECONDARY; 1796 LOGH("Camera ID: %d, Aux Camera, type: %d, facing: %d", 1797 cameraId, m_pPhyCamera[i].type, 1798 m_pPhyCamera[i].cam_info.facing); 1799 } 1800 else { 1801 m_nLogicalCameras++; 1802 LOGH("Camera ID: %d, Main Camera, type: %d, facing: %d", 1803 cameraId, m_pPhyCamera[i].type, 1804 m_pPhyCamera[i].cam_info.facing); 1805 } 1806 } 1807 1808 if (!m_nLogicalCameras) { 1809 // No Main camera detected, return from here 1810 LOGE("Error !!!! detecting main camera!!"); 1811 delete [] m_pPhyCamera; 1812 m_pPhyCamera = NULL; 1813 return -ENODEV; 1814 } 1815 // Allocate Logical Camera descriptors 1816 m_pLogicalCamera = new qcamera_logical_descriptor_t[m_nLogicalCameras]; 1817 if (!m_pLogicalCamera) { 1818 LOGE("Error !!!! allocating camera info buffer!!"); 1819 delete [] m_pPhyCamera; 1820 m_pPhyCamera = NULL; 1821 return NO_MEMORY; 1822 } 1823 memset(m_pLogicalCamera, 0x00, 1824 (m_nLogicalCameras * sizeof(qcamera_logical_descriptor_t))); 1825 // Assign MAIN cameras for each logical camera 1826 int index = 0; 1827 for (i = 0; i < m_nPhyCameras ; i++) { 1828 if (m_pPhyCamera[i].mode == CAM_MODE_PRIMARY) { 1829 m_pLogicalCamera[index].nPrimaryPhyCamIndex = 0; 1830 m_pLogicalCamera[index].id = index; 1831 m_pLogicalCamera[index].device_version = CAMERA_DEVICE_API_VERSION_1_0; 1832 m_pLogicalCamera[index].pId[0] = i; 1833 m_pLogicalCamera[index].type[0] = CAM_TYPE_MAIN; 1834 m_pLogicalCamera[index].mode[0] = CAM_MODE_PRIMARY; 1835 m_pLogicalCamera[index].facing = m_pPhyCamera[i].cam_info.facing; 1836 m_pLogicalCamera[index].numCameras++; 1837 LOGH("Logical Main Camera ID: %d, facing: %d," 1838 "Phy Id: %d type: %d mode: %d", 1839 m_pLogicalCamera[index].id, 1840 m_pLogicalCamera[index].facing, 1841 m_pLogicalCamera[index].pId[0], 1842 m_pLogicalCamera[index].type[0], 1843 m_pLogicalCamera[index].mode[0]); 1844 1845 index++; 1846 } 1847 } 1848 //Now assign AUX cameras to logical camera 1849 for (i = 0; i < m_nPhyCameras ; i++) { 1850 if (m_pPhyCamera[i].mode == CAM_MODE_SECONDARY) { 1851 for (int j = 0; j < m_nLogicalCameras; j++) { 1852 int n = m_pLogicalCamera[j].numCameras; 1853 ///@note n can only be 1 at this point 1854 if ((n < MAX_NUM_CAMERA_PER_BUNDLE) && 1855 (m_pLogicalCamera[j].facing == 1856 m_pPhyCamera[i].cam_info.facing)) { 1857 m_pLogicalCamera[j].pId[n] = i; 1858 m_pLogicalCamera[j].type[n] = CAM_TYPE_AUX; 1859 m_pLogicalCamera[j].mode[n] = CAM_MODE_SECONDARY; 1860 m_pLogicalCamera[j].numCameras++; 1861 LOGH("Aux %d for Logical Camera ID: %d," 1862 "aux phy id:%d, type: %d mode: %d", 1863 n, j, m_pLogicalCamera[j].pId[n], 1864 m_pLogicalCamera[j].type[n], m_pLogicalCamera[j].mode[n]); 1865 } 1866 } 1867 } 1868 } 1869 //Print logical and physical camera tables 1870 for (i = 0; i < m_nLogicalCameras ; i++) { 1871 for (uint8_t j = 0; j < m_pLogicalCamera[i].numCameras; j++) { 1872 LOGH("Logical Camera ID: %d, index: %d, " 1873 "facing: %d, Phy Id: %d type: %d mode: %d", 1874 i, j, m_pLogicalCamera[i].facing, 1875 m_pLogicalCamera[i].pId[j], m_pLogicalCamera[i].type[j], 1876 m_pLogicalCamera[i].mode[j]); 1877 } 1878 } 1879 LOGH("[%d] X: rc = %d", rc); 1880 return rc; 1881 } 1882 1883 /*=========================================================================== 1884 * FUNCTION : getNumberOfCameras 1885 * 1886 * DESCRIPTION: query number of logical cameras detected 1887 * 1888 * RETURN : number of cameras detected 1889 *==========================================================================*/ 1890 int QCameraMuxer::getNumberOfCameras() 1891 { 1892 return m_nLogicalCameras; 1893 } 1894 1895 /*=========================================================================== 1896 * FUNCTION : getCameraInfo 1897 * 1898 * DESCRIPTION: query camera information with its ID 1899 * 1900 * PARAMETERS : 1901 * @camera_id : camera ID 1902 * @info : ptr to camera info struct 1903 * 1904 * RETURN : int32_t type of status 1905 * NO_ERROR -- success 1906 * none-zero failure code 1907 *==========================================================================*/ 1908 int QCameraMuxer::getCameraInfo(int camera_id, 1909 struct camera_info *info, __unused cam_sync_type_t *p_cam_type) 1910 { 1911 int rc = NO_ERROR; 1912 LOGH("E, camera_id = %d", camera_id); 1913 1914 if (!m_nLogicalCameras || (camera_id >= m_nLogicalCameras) || 1915 !info || (camera_id < 0)) { 1916 LOGE("m_nLogicalCameras: %d, camera id: %d", 1917 m_nLogicalCameras, camera_id); 1918 return -ENODEV; 1919 } 1920 1921 if (!m_pLogicalCamera || !m_pPhyCamera) { 1922 LOGE("Error! Cameras not initialized!"); 1923 return NO_INIT; 1924 } 1925 uint32_t phy_id = 1926 m_pLogicalCamera[camera_id].pId[ 1927 m_pLogicalCamera[camera_id].nPrimaryPhyCamIndex]; 1928 // Call HAL3 getCamInfo to get the flash light info through static metatdata 1929 // regardless of HAL version 1930 rc = QCamera3HardwareInterface::getCamInfo(phy_id, info); 1931 info->device_version = CAMERA_DEVICE_API_VERSION_1_0; // Hardcode the HAL to HAL1 1932 LOGH("X"); 1933 return rc; 1934 } 1935 1936 /*=========================================================================== 1937 * FUNCTION : setCallbacks 1938 * 1939 * DESCRIPTION: set callback functions to send asynchronous notifications to 1940 * frameworks. 1941 * 1942 * PARAMETERS : 1943 * @callbacks : callback function pointer 1944 * 1945 * RETURN : int32_t type of status 1946 * NO_ERROR -- success 1947 * none-zero failure code 1948 *==========================================================================*/ 1949 int32_t QCameraMuxer::setCallbacks(const camera_module_callbacks_t *callbacks) 1950 { 1951 if(callbacks) { 1952 m_pCallbacks = callbacks; 1953 return NO_ERROR; 1954 } else { 1955 return BAD_TYPE; 1956 } 1957 } 1958 1959 /*=========================================================================== 1960 * FUNCTION : setDataCallback 1961 * 1962 * DESCRIPTION: set data callback function for snapshots 1963 * 1964 * PARAMETERS : 1965 * @data_cb : callback function pointer 1966 * 1967 * RETURN : int32_t type of status 1968 * NO_ERROR -- success 1969 * none-zero failure code 1970 *==========================================================================*/ 1971 int32_t QCameraMuxer::setDataCallback(camera_data_callback data_cb) 1972 { 1973 if(data_cb) { 1974 mDataCb = data_cb; 1975 return NO_ERROR; 1976 } else { 1977 return BAD_TYPE; 1978 } 1979 } 1980 1981 /*=========================================================================== 1982 * FUNCTION : setMemoryCallback 1983 * 1984 * DESCRIPTION: set get memory callback for memory allocations 1985 * 1986 * PARAMETERS : 1987 * @get_memory : callback function pointer 1988 * 1989 * RETURN : int32_t type of status 1990 * NO_ERROR -- success 1991 * none-zero failure code 1992 *==========================================================================*/ 1993 int32_t QCameraMuxer::setMemoryCallback(camera_request_memory get_memory) 1994 { 1995 if(get_memory) { 1996 mGetMemoryCb = get_memory; 1997 return NO_ERROR; 1998 } else { 1999 return BAD_TYPE; 2000 } 2001 } 2002 2003 /*=========================================================================== 2004 * FUNCTION : setMpoCallbackCookie 2005 * 2006 * DESCRIPTION: set mpo callback cookie. will be used for sending final MPO callbacks 2007 * to framework 2008 * 2009 * PARAMETERS : 2010 * @mpoCbCookie : callback function pointer 2011 * 2012 * RETURN : int32_t type of status 2013 * NO_ERROR -- success 2014 * none-zero failure code 2015 *==========================================================================*/ 2016 int32_t QCameraMuxer::setMpoCallbackCookie(void* mpoCbCookie) 2017 { 2018 if(mpoCbCookie) { 2019 m_pMpoCallbackCookie = mpoCbCookie; 2020 return NO_ERROR; 2021 } else { 2022 return BAD_TYPE; 2023 } 2024 } 2025 2026 /*=========================================================================== 2027 * FUNCTION : getMpoCallbackCookie 2028 * 2029 * DESCRIPTION: gets the mpo callback cookie. will be used for sending final MPO callbacks 2030 * to framework 2031 * 2032 * PARAMETERS :none 2033 * 2034 * RETURN :void ptr to the mpo callback cookie 2035 *==========================================================================*/ 2036 void* QCameraMuxer::getMpoCallbackCookie(void) 2037 { 2038 return m_pMpoCallbackCookie; 2039 } 2040 2041 /*=========================================================================== 2042 * FUNCTION : setMainJpegCallbackCookie 2043 * 2044 * DESCRIPTION: set jpeg callback cookie. 2045 * set to phy cam instance of the primary related cam instance 2046 * 2047 * PARAMETERS : 2048 * @jpegCbCookie : ptr to jpeg cookie 2049 * 2050 * RETURN : int32_t type of status 2051 * NO_ERROR -- success 2052 * none-zero failure code 2053 *==========================================================================*/ 2054 int32_t QCameraMuxer::setMainJpegCallbackCookie(void* jpegCbCookie) 2055 { 2056 if(jpegCbCookie) { 2057 m_pJpegCallbackCookie = jpegCbCookie; 2058 return NO_ERROR; 2059 } else { 2060 return BAD_TYPE; 2061 } 2062 } 2063 2064 /*=========================================================================== 2065 * FUNCTION : getMainJpegCallbackCookie 2066 * 2067 * DESCRIPTION: gets the jpeg callback cookie for primary related cam instance 2068 * set to phy cam instance of the primary related cam instance 2069 * 2070 * PARAMETERS :none 2071 * 2072 * RETURN :void ptr to the jpeg callback cookie 2073 *==========================================================================*/ 2074 void* QCameraMuxer::getMainJpegCallbackCookie(void) 2075 { 2076 return m_pJpegCallbackCookie; 2077 } 2078 2079 /*=========================================================================== 2080 * FUNCTION : cameraDeviceOpen 2081 * 2082 * DESCRIPTION: open a camera device with its ID 2083 * 2084 * PARAMETERS : 2085 * @camera_id : camera ID 2086 * @hw_device : ptr to struct storing camera hardware device info 2087 * 2088 * RETURN : int32_t type of status 2089 * NO_ERROR -- success 2090 * none-zero failure code 2091 *==========================================================================*/ 2092 int QCameraMuxer::cameraDeviceOpen(int camera_id, 2093 struct hw_device_t **hw_device) 2094 { 2095 int rc = NO_ERROR; 2096 uint32_t phyId = 0; 2097 qcamera_logical_descriptor_t *cam = NULL; 2098 2099 if (camera_id < 0 || camera_id >= m_nLogicalCameras) { 2100 LOGE("Camera id %d not found!", camera_id); 2101 return -ENODEV; 2102 } 2103 2104 if ( NULL == m_pLogicalCamera) { 2105 LOGE("Hal descriptor table is not initialized!"); 2106 return NO_INIT; 2107 } 2108 2109 char prop[PROPERTY_VALUE_MAX]; 2110 property_get("persist.camera.dc.frame.sync", prop, "1"); 2111 m_bFrameSyncEnabled = atoi(prop); 2112 2113 // Get logical camera 2114 cam = &m_pLogicalCamera[camera_id]; 2115 2116 if (m_pLogicalCamera[camera_id].device_version == 2117 CAMERA_DEVICE_API_VERSION_1_0) { 2118 // HW Dev Holders 2119 hw_device_t *hw_dev[cam->numCameras]; 2120 2121 if (m_pPhyCamera[cam->pId[0]].type != CAM_TYPE_MAIN) { 2122 LOGE("Physical camera at index 0 is not main!"); 2123 return UNKNOWN_ERROR; 2124 } 2125 2126 // Open all physical cameras 2127 for (uint32_t i = 0; i < cam->numCameras; i++) { 2128 phyId = cam->pId[i]; 2129 QCamera2HardwareInterface *hw = 2130 new QCamera2HardwareInterface((uint32_t)phyId); 2131 if (!hw) { 2132 LOGE("Allocation of hardware interface failed"); 2133 return NO_MEMORY; 2134 } 2135 hw_dev[i] = NULL; 2136 2137 // Make Camera HWI aware of its mode 2138 cam_sync_related_sensors_event_info_t info; 2139 info.sync_control = CAM_SYNC_RELATED_SENSORS_ON; 2140 info.mode = m_pPhyCamera[phyId].mode; 2141 info.type = m_pPhyCamera[phyId].type; 2142 rc = hw->setRelatedCamSyncInfo(&info); 2143 hw->setFrameSyncEnabled(m_bFrameSyncEnabled); 2144 if (rc != NO_ERROR) { 2145 LOGE("setRelatedCamSyncInfo failed %d", rc); 2146 delete hw; 2147 return rc; 2148 } 2149 2150 rc = hw->openCamera(&hw_dev[i]); 2151 if (rc != NO_ERROR) { 2152 delete hw; 2153 return rc; 2154 } 2155 hw->getCameraSessionId(&m_pPhyCamera[phyId].camera_server_id); 2156 m_pPhyCamera[phyId].dev = reinterpret_cast<camera_device_t*>(hw_dev[i]); 2157 m_pPhyCamera[phyId].hwi = hw; 2158 cam->sId[i] = m_pPhyCamera[phyId].camera_server_id; 2159 LOGH("camera id %d server id : %d hw device %x, hw %x", 2160 phyId, cam->sId[i], hw_dev[i], hw); 2161 } 2162 } else { 2163 LOGE("Device version for camera id %d invalid %d", 2164 camera_id, m_pLogicalCamera[camera_id].device_version); 2165 return BAD_VALUE; 2166 } 2167 2168 cam->dev.common.tag = HARDWARE_DEVICE_TAG; 2169 cam->dev.common.version = HARDWARE_DEVICE_API_VERSION(1, 0); 2170 cam->dev.common.close = close_camera_device; 2171 cam->dev.ops = &mCameraMuxerOps; 2172 cam->dev.priv = (void*)cam; 2173 *hw_device = &cam->dev.common; 2174 return rc; 2175 } 2176 2177 2178 /*=========================================================================== 2179 * FUNCTION : getLogicalCamera 2180 * 2181 * DESCRIPTION: Get logical camera descriptor 2182 * 2183 * PARAMETERS : 2184 * @device : camera hardware device info 2185 * 2186 * RETURN : logical camera descriptor or NULL 2187 *==========================================================================*/ 2188 qcamera_logical_descriptor_t* QCameraMuxer::getLogicalCamera( 2189 struct camera_device * device) 2190 { 2191 if(device && device->priv){ 2192 return (qcamera_logical_descriptor_t*)(device->priv); 2193 } 2194 return NULL; 2195 } 2196 2197 /*=========================================================================== 2198 * FUNCTION : getPhysicalCamera 2199 * 2200 * DESCRIPTION: Get physical camera descriptor 2201 * 2202 * PARAMETERS : 2203 * @log_cam : Logical camera descriptor 2204 * @index : physical camera index 2205 * 2206 * RETURN : physical camera descriptor or NULL 2207 *==========================================================================*/ 2208 qcamera_physical_descriptor_t* QCameraMuxer::getPhysicalCamera( 2209 qcamera_logical_descriptor_t* log_cam, uint32_t index) 2210 { 2211 if(!log_cam){ 2212 return NULL; 2213 } 2214 return &m_pPhyCamera[log_cam->pId[index]]; 2215 } 2216 2217 /*=========================================================================== 2218 * FUNCTION : getActiveNumOfPhyCam 2219 * 2220 * DESCRIPTION: Get active physical camera number in Logical Camera 2221 * 2222 * PARAMETERS : 2223 * @log_cam : Logical camera descriptor 2224 * @numOfAcitvePhyCam : number of active physical camera in Logical Camera. 2225 * 2226 * RETURN : 2227 * NO_ERROR : success 2228 * ENODEV : Camera not found 2229 * other: non-zero failure code 2230 *==========================================================================*/ 2231 int32_t QCameraMuxer::getActiveNumOfPhyCam( 2232 qcamera_logical_descriptor_t* log_cam, int& numOfAcitvePhyCam) 2233 { 2234 CHECK_CAMERA_ERROR(log_cam); 2235 2236 numOfAcitvePhyCam = log_cam->numCameras; 2237 return NO_ERROR; 2238 } 2239 2240 2241 /*=========================================================================== 2242 * FUNCTION : sendEvtNotify 2243 * 2244 * DESCRIPTION: send event notify to HWI for error callbacks 2245 * 2246 * PARAMETERS : 2247 * @msg_type: msg type to be sent 2248 * @ext1 : optional extension1 2249 * @ext2 : optional extension2 2250 * 2251 * RETURN : int32_t type of status 2252 * NO_ERROR -- success 2253 * none-zero failure code 2254 *==========================================================================*/ 2255 int32_t QCameraMuxer::sendEvtNotify(int32_t msg_type, int32_t ext1, 2256 int32_t ext2) 2257 { 2258 LOGH("E"); 2259 2260 CHECK_MUXER_ERROR(); 2261 2262 qcamera_physical_descriptor_t *pCam = NULL; 2263 pCam = (qcamera_physical_descriptor_t*)(gMuxer->getMainJpegCallbackCookie()); 2264 2265 CHECK_CAMERA_ERROR(pCam); 2266 2267 QCamera2HardwareInterface *hwi = pCam->hwi; 2268 CHECK_HWI_ERROR(hwi); 2269 2270 LOGH("X"); 2271 return pCam->hwi->sendEvtNotify(msg_type, ext1, ext2); 2272 } 2273 2274 /*=========================================================================== 2275 * FUNCTION : composeMpo 2276 * 2277 * DESCRIPTION: Composition of the 2 MPOs 2278 * 2279 * PARAMETERS : none 2280 * @main_Jpeg: pointer to info to Main Jpeg 2281 * @aux_Jpeg : pointer to info to Aux JPEG 2282 * 2283 * RETURN : none 2284 *==========================================================================*/ 2285 void QCameraMuxer::composeMpo(cam_compose_jpeg_info_t* main_Jpeg, 2286 cam_compose_jpeg_info_t* aux_Jpeg) 2287 { 2288 LOGH("E Main Jpeg %p Aux Jpeg %p", main_Jpeg, aux_Jpeg); 2289 2290 CHECK_MUXER(); 2291 if(main_Jpeg == NULL || aux_Jpeg == NULL) { 2292 LOGE("input buffers invalid, ret = NO_MEMORY"); 2293 gMuxer->sendEvtNotify(CAMERA_MSG_ERROR, UNKNOWN_ERROR, 0); 2294 return; 2295 } 2296 2297 pthread_mutex_lock(&m_JpegLock); 2298 2299 m_pRelCamMpoJpeg = mGetMemoryCb(-1, main_Jpeg->buffer->size + 2300 aux_Jpeg->buffer->size, 1, m_pMpoCallbackCookie); 2301 if (NULL == m_pRelCamMpoJpeg) { 2302 LOGE("getMemory for mpo, ret = NO_MEMORY"); 2303 gMuxer->sendEvtNotify(CAMERA_MSG_ERROR, UNKNOWN_ERROR, 0); 2304 pthread_mutex_unlock(&m_JpegLock); 2305 return; 2306 } 2307 2308 // fill all structures to send for composition 2309 mm_jpeg_mpo_info_t mpo_compose_info; 2310 mpo_compose_info.num_of_images = 2; 2311 mpo_compose_info.primary_image.buf_filled_len = main_Jpeg->buffer->size; 2312 mpo_compose_info.primary_image.buf_vaddr = 2313 (uint8_t*)(main_Jpeg->buffer->data); 2314 mpo_compose_info.aux_images[0].buf_filled_len = aux_Jpeg->buffer->size; 2315 mpo_compose_info.aux_images[0].buf_vaddr = 2316 (uint8_t*)(aux_Jpeg->buffer->data); 2317 mpo_compose_info.output_buff.buf_vaddr = 2318 (uint8_t*)m_pRelCamMpoJpeg->data; 2319 mpo_compose_info.output_buff.buf_filled_len = 0; 2320 mpo_compose_info.output_buff_size = main_Jpeg->buffer->size + 2321 aux_Jpeg->buffer->size; 2322 2323 LOGD("MPO buffer size %d\n" 2324 "expected size %d, mpo_compose_info.output_buff_size %d", 2325 m_pRelCamMpoJpeg->size, 2326 main_Jpeg->buffer->size + aux_Jpeg->buffer->size, 2327 mpo_compose_info.output_buff_size); 2328 2329 LOGD("MPO primary buffer filled lengths\n" 2330 "mpo_compose_info.primary_image.buf_filled_len %d\n" 2331 "mpo_compose_info.primary_image.buf_vaddr %p", 2332 mpo_compose_info.primary_image.buf_filled_len, 2333 mpo_compose_info.primary_image.buf_vaddr); 2334 2335 LOGD("MPO aux buffer filled lengths\n" 2336 "mpo_compose_info.aux_images[0].buf_filled_len %d" 2337 "mpo_compose_info.aux_images[0].buf_vaddr %p", 2338 mpo_compose_info.aux_images[0].buf_filled_len, 2339 mpo_compose_info.aux_images[0].buf_vaddr); 2340 2341 if(m_bDumpImages) { 2342 LOGD("Dumping Main Image for MPO"); 2343 char buf_main[QCAMERA_MAX_FILEPATH_LENGTH]; 2344 memset(buf_main, 0, sizeof(buf_main)); 2345 snprintf(buf_main, sizeof(buf_main), 2346 QCAMERA_DUMP_FRM_LOCATION "Main.jpg"); 2347 2348 int file_fd_main = open(buf_main, O_RDWR | O_CREAT, 0777); 2349 if (file_fd_main >= 0) { 2350 ssize_t written_len = write(file_fd_main, 2351 mpo_compose_info.primary_image.buf_vaddr, 2352 mpo_compose_info.primary_image.buf_filled_len); 2353 fchmod(file_fd_main, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH); 2354 LOGD("written number of bytes for main Image %zd\n", 2355 written_len); 2356 close(file_fd_main); 2357 } 2358 2359 LOGD("Dumping Aux Image for MPO"); 2360 char buf_aux[QCAMERA_MAX_FILEPATH_LENGTH]; 2361 memset(buf_aux, 0, sizeof(buf_aux)); 2362 snprintf(buf_aux, sizeof(buf_aux), 2363 QCAMERA_DUMP_FRM_LOCATION "Aux.jpg"); 2364 2365 int file_fd_aux = open(buf_aux, O_RDWR | O_CREAT, 0777); 2366 if (file_fd_aux >= 0) { 2367 ssize_t written_len = write(file_fd_aux, 2368 mpo_compose_info.aux_images[0].buf_vaddr, 2369 mpo_compose_info.aux_images[0].buf_filled_len); 2370 fchmod(file_fd_aux, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH); 2371 LOGD("written number of bytes for Aux Image %zd\n", 2372 written_len); 2373 close(file_fd_aux); 2374 } 2375 } 2376 2377 int32_t rc = mJpegMpoOps.compose_mpo(&mpo_compose_info); 2378 LOGD("Compose mpo returned %d", rc); 2379 2380 if(rc != NO_ERROR) { 2381 LOGE("ComposeMpo failed, ret = %d", rc); 2382 gMuxer->sendEvtNotify(CAMERA_MSG_ERROR, UNKNOWN_ERROR, 0); 2383 pthread_mutex_unlock(&m_JpegLock); 2384 return; 2385 } 2386 2387 if(m_bDumpImages) { 2388 char buf_mpo[QCAMERA_MAX_FILEPATH_LENGTH]; 2389 memset(buf_mpo, 0, sizeof(buf_mpo)); 2390 snprintf(buf_mpo, sizeof(buf_mpo), 2391 QCAMERA_DUMP_FRM_LOCATION "Composed.MPO"); 2392 2393 int file_fd_mpo = open(buf_mpo, O_RDWR | O_CREAT, 0777); 2394 if (file_fd_mpo >= 0) { 2395 ssize_t written_len = write(file_fd_mpo, 2396 m_pRelCamMpoJpeg->data, 2397 m_pRelCamMpoJpeg->size); 2398 fchmod(file_fd_mpo, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH); 2399 LOGD("written number of bytes for MPO Image %zd\n", 2400 written_len); 2401 close(file_fd_mpo); 2402 } 2403 } 2404 2405 mDataCb(main_Jpeg->msg_type, 2406 m_pRelCamMpoJpeg, 2407 main_Jpeg->index, 2408 main_Jpeg->metadata, 2409 m_pMpoCallbackCookie); 2410 2411 if (NULL != m_pRelCamMpoJpeg) { 2412 m_pRelCamMpoJpeg->release(m_pRelCamMpoJpeg); 2413 m_pRelCamMpoJpeg = NULL; 2414 } 2415 2416 pthread_mutex_unlock(&m_JpegLock); 2417 LOGH("X"); 2418 return; 2419 } 2420 2421 /*=========================================================================== 2422 * FUNCTION : matchFrameId 2423 * 2424 * DESCRIPTION: function to match frame ids within queue nodes 2425 * 2426 * PARAMETERS : 2427 * @data: pointer to queue node to be matched for condition 2428 * @user_data: caller can add more info here 2429 * @match_data : value to be matched against 2430 * 2431 * RETURN : true or false based on whether match was successful or not 2432 *==========================================================================*/ 2433 bool QCameraMuxer::matchFrameId(void *data, __unused void *user_data, 2434 void *match_data) 2435 { 2436 LOGH("E"); 2437 2438 if (!data || !match_data) { 2439 return false; 2440 } 2441 2442 cam_compose_jpeg_info_t * node = (cam_compose_jpeg_info_t *) data; 2443 uint32_t frame_idx = *((uint32_t *) match_data); 2444 LOGH("X"); 2445 return node->frame_idx == frame_idx; 2446 } 2447 2448 /*=========================================================================== 2449 * FUNCTION : findPreviousJpegs 2450 * 2451 * DESCRIPTION: Finds Jpegs in the queue with index less than delivered one 2452 * 2453 * PARAMETERS : 2454 * @data: pointer to queue node to be matched for condition 2455 * @user_data: caller can add more info here 2456 * @match_data : value to be matched against 2457 * 2458 * RETURN : true or false based on whether match was successful or not 2459 *==========================================================================*/ 2460 bool QCameraMuxer::findPreviousJpegs(void *data, __unused void *user_data, 2461 void *match_data) 2462 { 2463 LOGH("E"); 2464 2465 if (!data || !match_data) { 2466 return false; 2467 } 2468 cam_compose_jpeg_info_t * node = (cam_compose_jpeg_info_t *) data; 2469 uint32_t frame_idx = *((uint32_t *) match_data); 2470 LOGH("X"); 2471 return node->frame_idx < frame_idx; 2472 } 2473 2474 /*=========================================================================== 2475 * FUNCTION : releaseJpegInfo 2476 * 2477 * DESCRIPTION: callback function for the release of individual nodes 2478 * in the JPEG queues. 2479 * 2480 * PARAMETERS : 2481 * @data : ptr to the data to be released 2482 * @user_data : caller can add more info here 2483 * 2484 * RETURN : None 2485 *==========================================================================*/ 2486 void QCameraMuxer::releaseJpegInfo(void *data, __unused void *user_data) 2487 { 2488 LOGH("E"); 2489 2490 cam_compose_jpeg_info_t *jpegInfo = (cam_compose_jpeg_info_t *)data; 2491 if(jpegInfo && jpegInfo->release_cb) { 2492 if (jpegInfo->release_data != NULL) { 2493 jpegInfo->release_cb(jpegInfo->release_data, 2494 jpegInfo->release_cookie, 2495 NO_ERROR); 2496 } 2497 } 2498 LOGH("X"); 2499 } 2500 2501 /*=========================================================================== 2502 * FUNCTION : composeMpoRoutine 2503 * 2504 * DESCRIPTION: specialized thread for MPO composition 2505 * 2506 * PARAMETERS : 2507 * @data : pointer to the thread owner 2508 * 2509 * RETURN : void* to thread 2510 *==========================================================================*/ 2511 void* QCameraMuxer::composeMpoRoutine(__unused void *data) 2512 { 2513 LOGH("E"); 2514 if (!gMuxer) { 2515 LOGE("Error getting muxer "); 2516 return NULL; 2517 } 2518 2519 int running = 1; 2520 int ret; 2521 uint8_t is_active = FALSE; 2522 QCameraCmdThread *cmdThread = &gMuxer->m_ComposeMpoTh; 2523 cmdThread->setName("CAM_ComposeMpo"); 2524 2525 do { 2526 do { 2527 ret = cam_sem_wait(&cmdThread->cmd_sem); 2528 if (ret != 0 && errno != EINVAL) { 2529 LOGE("cam_sem_wait error (%s)", strerror(errno)); 2530 return NULL; 2531 } 2532 } while (ret != 0); 2533 2534 // we got notified about new cmd avail in cmd queue 2535 camera_cmd_type_t cmd = cmdThread->getCmd(); 2536 switch (cmd) { 2537 case CAMERA_CMD_TYPE_START_DATA_PROC: 2538 { 2539 LOGH("start ComposeMpo processing"); 2540 is_active = TRUE; 2541 2542 // signal cmd is completed 2543 cam_sem_post(&cmdThread->sync_sem); 2544 } 2545 break; 2546 case CAMERA_CMD_TYPE_STOP_DATA_PROC: 2547 { 2548 LOGH("stop ComposeMpo processing"); 2549 is_active = FALSE; 2550 2551 // signal cmd is completed 2552 cam_sem_post(&cmdThread->sync_sem); 2553 } 2554 break; 2555 case CAMERA_CMD_TYPE_DO_NEXT_JOB: 2556 { 2557 if (is_active == TRUE) { 2558 LOGH("Mpo Composition Requested"); 2559 cam_compose_jpeg_info_t *main_jpeg_node = NULL; 2560 cam_compose_jpeg_info_t *aux_jpeg_node = NULL; 2561 bool foundMatch = false; 2562 while (!gMuxer->m_MainJpegQ.isEmpty() && 2563 !gMuxer->m_AuxJpegQ.isEmpty()) { 2564 main_jpeg_node = (cam_compose_jpeg_info_t *) 2565 gMuxer->m_MainJpegQ.dequeue(); 2566 if (main_jpeg_node != NULL) { 2567 LOGD("main_jpeg_node found frame idx %d" 2568 "ptr %p buffer_ptr %p buffer_size %d", 2569 main_jpeg_node->frame_idx, 2570 main_jpeg_node, 2571 main_jpeg_node->buffer->data, 2572 main_jpeg_node->buffer->size); 2573 // find matching aux node in Aux Jpeg Queue 2574 aux_jpeg_node = 2575 (cam_compose_jpeg_info_t *) gMuxer-> 2576 m_AuxJpegQ.dequeue(); 2577 if (aux_jpeg_node != NULL) { 2578 LOGD("aux_jpeg_node found frame idx %d" 2579 "ptr %p buffer_ptr %p buffer_size %d", 2580 aux_jpeg_node->frame_idx, 2581 aux_jpeg_node, 2582 aux_jpeg_node->buffer->data, 2583 aux_jpeg_node->buffer->size); 2584 foundMatch = true; 2585 // start MPO composition 2586 gMuxer->composeMpo(main_jpeg_node, 2587 aux_jpeg_node); 2588 } 2589 } 2590 if (main_jpeg_node != NULL) { 2591 if ( main_jpeg_node->release_cb ) { 2592 main_jpeg_node->release_cb( 2593 main_jpeg_node->release_data, 2594 main_jpeg_node->release_cookie, 2595 NO_ERROR); 2596 } 2597 free(main_jpeg_node); 2598 main_jpeg_node = NULL; 2599 } else { 2600 LOGH("Mpo Match not found"); 2601 } 2602 if (aux_jpeg_node != NULL) { 2603 if (aux_jpeg_node->release_cb) { 2604 aux_jpeg_node->release_cb( 2605 aux_jpeg_node->release_data, 2606 aux_jpeg_node->release_cookie, 2607 NO_ERROR); 2608 } 2609 free(aux_jpeg_node); 2610 aux_jpeg_node = NULL; 2611 } else { 2612 LOGH("Mpo Match not found"); 2613 } 2614 } 2615 } 2616 break; 2617 } 2618 case CAMERA_CMD_TYPE_EXIT: 2619 LOGH("ComposeMpo thread exit"); 2620 running = 0; 2621 break; 2622 default: 2623 break; 2624 } 2625 } while (running); 2626 LOGH("X"); 2627 return NULL; 2628 } 2629 2630 /*=========================================================================== 2631 * FUNCTION : jpeg_data_callback 2632 * 2633 * DESCRIPTION: JPEG data callback for snapshot 2634 * 2635 * PARAMETERS : 2636 * @msg_type : callback msg type 2637 * @data : data ptr of the buffer 2638 * @index : index of the frame 2639 * @metadata : metadata associated with the buffer 2640 * @user : callback cookie returned back to the user 2641 * @frame_idx : frame index for matching frames 2642 * @release_cb : callback function for releasing the data memory 2643 * @release_cookie : cookie for the release callback function 2644 * @release_data :pointer indicating what needs to be released 2645 * 2646 * RETURN : none 2647 *==========================================================================*/ 2648 void QCameraMuxer::jpeg_data_callback(int32_t msg_type, 2649 const camera_memory_t *data, unsigned int index, 2650 camera_frame_metadata_t *metadata, void *user, 2651 uint32_t frame_idx, camera_release_callback release_cb, 2652 void *release_cookie, void *release_data) 2653 { 2654 LOGH("E"); 2655 CHECK_MUXER(); 2656 2657 if(data != NULL) { 2658 LOGH("jpeg received: data %p size %d data ptr %p frameIdx %d", 2659 data, data->size, data->data, frame_idx); 2660 int rc = gMuxer->storeJpeg(((qcamera_physical_descriptor_t*)(user))->type, 2661 msg_type, data, index, metadata, user, frame_idx, release_cb, 2662 release_cookie, release_data); 2663 if(rc != NO_ERROR) { 2664 gMuxer->sendEvtNotify(CAMERA_MSG_ERROR, UNKNOWN_ERROR, 0); 2665 } 2666 } else { 2667 gMuxer->sendEvtNotify(CAMERA_MSG_ERROR, UNKNOWN_ERROR, 0); 2668 } 2669 LOGH("X"); 2670 return; 2671 } 2672 2673 /*=========================================================================== 2674 * FUNCTION : storeJpeg 2675 * 2676 * DESCRIPTION: Stores jpegs from multiple related cam instances into a common Queue 2677 * 2678 * PARAMETERS : 2679 * @cam_type : indicates whether main or aux camera sent the Jpeg callback 2680 * @msg_type : callback msg type 2681 * @data : data ptr of the buffer 2682 * @index : index of the frame 2683 * @metadata : metadata associated with the buffer 2684 * @user : callback cookie returned back to the user 2685 * @frame_idx : frame index for matching frames 2686 * @release_cb : callback function for releasing the data memory 2687 * @release_cookie : cookie for the release callback function 2688 * @release_data :pointer indicating what needs to be released 2689 * 2690 * RETURN : int32_t type of status 2691 * NO_ERROR -- success 2692 * none-zero failure code 2693 *==========================================================================*/ 2694 int32_t QCameraMuxer::storeJpeg(cam_sync_type_t cam_type, 2695 int32_t msg_type, const camera_memory_t *data, unsigned int index, 2696 camera_frame_metadata_t *metadata, void *user,uint32_t frame_idx, 2697 camera_release_callback release_cb, void *release_cookie, 2698 void *release_data) 2699 { 2700 LOGH("E jpeg received: data %p size %d data ptr %p frameIdx %d", 2701 data, data->size, data->data, frame_idx); 2702 2703 CHECK_MUXER_ERROR(); 2704 2705 if (!m_bMpoEnabled) { 2706 if (cam_type == CAM_TYPE_MAIN) { 2707 // send data callback only incase of main camera 2708 // aux image is ignored and released back 2709 mDataCb(msg_type, 2710 data, 2711 index, 2712 metadata, 2713 m_pMpoCallbackCookie); 2714 } 2715 if (release_cb) { 2716 release_cb(release_data, release_cookie, NO_ERROR); 2717 } 2718 LOGH("X"); 2719 return NO_ERROR; 2720 } 2721 2722 cam_compose_jpeg_info_t* pJpegFrame = 2723 (cam_compose_jpeg_info_t*)malloc(sizeof(cam_compose_jpeg_info_t)); 2724 if (!pJpegFrame) { 2725 LOGE("Allocation failed for MPO nodes"); 2726 return NO_MEMORY; 2727 } 2728 memset(pJpegFrame, 0, sizeof(*pJpegFrame)); 2729 2730 pJpegFrame->msg_type = msg_type; 2731 pJpegFrame->buffer = const_cast<camera_memory_t*>(data); 2732 pJpegFrame->index = index; 2733 pJpegFrame->metadata = metadata; 2734 pJpegFrame->user = user; 2735 pJpegFrame->valid = true; 2736 pJpegFrame->frame_idx = frame_idx; 2737 pJpegFrame->release_cb = release_cb; 2738 pJpegFrame->release_cookie = release_cookie; 2739 pJpegFrame->release_data = release_data; 2740 if(cam_type == CAM_TYPE_MAIN) { 2741 if (m_MainJpegQ.enqueue((void *)pJpegFrame)) { 2742 LOGD("Main FrameIdx %d", pJpegFrame->frame_idx); 2743 if (m_MainJpegQ.getCurrentSize() > 0) { 2744 LOGD("Trigger Compose"); 2745 m_ComposeMpoTh.sendCmd(CAMERA_CMD_TYPE_DO_NEXT_JOB, FALSE, FALSE); 2746 } 2747 } else { 2748 LOGE("Enqueue Failed for Main Jpeg Q"); 2749 if ( pJpegFrame->release_cb ) { 2750 // release other buffer also here 2751 pJpegFrame->release_cb( 2752 pJpegFrame->release_data, 2753 pJpegFrame->release_cookie, 2754 NO_ERROR); 2755 } 2756 free(pJpegFrame); 2757 pJpegFrame = NULL; 2758 return NO_MEMORY; 2759 } 2760 2761 } else { 2762 if (m_AuxJpegQ.enqueue((void *)pJpegFrame)) { 2763 LOGD("Aux FrameIdx %d", pJpegFrame->frame_idx); 2764 if (m_AuxJpegQ.getCurrentSize() > 0) { 2765 LOGD("Trigger Compose"); 2766 m_ComposeMpoTh.sendCmd(CAMERA_CMD_TYPE_DO_NEXT_JOB, FALSE, FALSE); 2767 } 2768 } else { 2769 LOGE("Enqueue Failed for Aux Jpeg Q"); 2770 if ( pJpegFrame->release_cb ) { 2771 // release other buffer also here 2772 pJpegFrame->release_cb( 2773 pJpegFrame->release_data, 2774 pJpegFrame->release_cookie, 2775 NO_ERROR); 2776 } 2777 free(pJpegFrame); 2778 pJpegFrame = NULL; 2779 return NO_MEMORY; 2780 } 2781 } 2782 LOGH("X"); 2783 2784 return NO_ERROR; 2785 } 2786 2787 2788 // Muxer Ops 2789 camera_device_ops_t QCameraMuxer::mCameraMuxerOps = { 2790 .set_preview_window = QCameraMuxer::set_preview_window, 2791 .set_callbacks = QCameraMuxer::set_callBacks, 2792 .enable_msg_type = QCameraMuxer::enable_msg_type, 2793 .disable_msg_type = QCameraMuxer::disable_msg_type, 2794 .msg_type_enabled = QCameraMuxer::msg_type_enabled, 2795 2796 .start_preview = QCameraMuxer::start_preview, 2797 .stop_preview = QCameraMuxer::stop_preview, 2798 .preview_enabled = QCameraMuxer::preview_enabled, 2799 .store_meta_data_in_buffers= QCameraMuxer::store_meta_data_in_buffers, 2800 2801 .start_recording = QCameraMuxer::start_recording, 2802 .stop_recording = QCameraMuxer::stop_recording, 2803 .recording_enabled = QCameraMuxer::recording_enabled, 2804 .release_recording_frame = QCameraMuxer::release_recording_frame, 2805 2806 .auto_focus = QCameraMuxer::auto_focus, 2807 .cancel_auto_focus = QCameraMuxer::cancel_auto_focus, 2808 2809 .take_picture = QCameraMuxer::take_picture, 2810 .cancel_picture = QCameraMuxer::cancel_picture, 2811 2812 .set_parameters = QCameraMuxer::set_parameters, 2813 .get_parameters = QCameraMuxer::get_parameters, 2814 .put_parameters = QCameraMuxer::put_parameters, 2815 .send_command = QCameraMuxer::send_command, 2816 2817 .release = QCameraMuxer::release, 2818 .dump = QCameraMuxer::dump, 2819 }; 2820 2821 2822 }; // namespace android 2823