1/* Copyright (c) 2012-2014, The Linux Foundataion. 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 "QCamera3Stream" 31//#define LOG_NDEBUG 0 32 33#include <utils/Log.h> 34#include <utils/Errors.h> 35#include "QCamera3HWI.h" 36#include "QCamera3Stream.h" 37#include "QCamera3Channel.h" 38 39using namespace android; 40 41namespace qcamera { 42 43/*=========================================================================== 44 * FUNCTION : get_bufs 45 * 46 * DESCRIPTION: static function entry to allocate stream buffers 47 * 48 * PARAMETERS : 49 * @offset : offset info of stream buffers 50 * @num_bufs : number of buffers allocated 51 * @initial_reg_flag: flag to indicate if buffer needs to be registered 52 * at kernel initially 53 * @bufs : output of allocated buffers 54 * @ops_tbl : ptr to buf mapping/unmapping ops 55 * @user_data : user data ptr of ops_tbl 56 * 57 * RETURN : int32_t type of status 58 * NO_ERROR -- success 59 * none-zero failure code 60 *==========================================================================*/ 61int32_t QCamera3Stream::get_bufs( 62 cam_frame_len_offset_t *offset, 63 uint8_t *num_bufs, 64 uint8_t **initial_reg_flag, 65 mm_camera_buf_def_t **bufs, 66 mm_camera_map_unmap_ops_tbl_t *ops_tbl, 67 void *user_data) 68{ 69 QCamera3Stream *stream = reinterpret_cast<QCamera3Stream *>(user_data); 70 if (!stream) { 71 ALOGE("getBufs invalid stream pointer"); 72 return NO_MEMORY; 73 } 74 return stream->getBufs(offset, num_bufs, initial_reg_flag, bufs, ops_tbl); 75} 76 77/*=========================================================================== 78 * FUNCTION : put_bufs 79 * 80 * DESCRIPTION: static function entry to deallocate stream buffers 81 * 82 * PARAMETERS : 83 * @ops_tbl : ptr to buf mapping/unmapping ops 84 * @user_data : user data ptr of ops_tbl 85 * 86 * RETURN : int32_t type of status 87 * NO_ERROR -- success 88 * none-zero failure code 89 *==========================================================================*/ 90int32_t QCamera3Stream::put_bufs( 91 mm_camera_map_unmap_ops_tbl_t *ops_tbl, 92 void *user_data) 93{ 94 QCamera3Stream *stream = reinterpret_cast<QCamera3Stream *>(user_data); 95 if (!stream) { 96 ALOGE("putBufs invalid stream pointer"); 97 return NO_MEMORY; 98 } 99 return stream->putBufs(ops_tbl); 100} 101 102/*=========================================================================== 103 * FUNCTION : invalidate_buf 104 * 105 * DESCRIPTION: static function entry to invalidate a specific stream buffer 106 * 107 * PARAMETERS : 108 * @index : index of the stream buffer to invalidate 109 * @user_data : user data ptr of ops_tbl 110 * 111 * RETURN : int32_t type of status 112 * NO_ERROR -- success 113 * none-zero failure code 114 *==========================================================================*/ 115int32_t QCamera3Stream::invalidate_buf(int index, void *user_data) 116{ 117 QCamera3Stream *stream = reinterpret_cast<QCamera3Stream *>(user_data); 118 if (!stream) { 119 ALOGE("invalid stream pointer"); 120 return NO_MEMORY; 121 } 122 return stream->invalidateBuf(index); 123} 124 125/*=========================================================================== 126 * FUNCTION : clean_invalidate_buf 127 * 128 * DESCRIPTION: static function entry to clean and invalidate a specific stream buffer 129 * 130 * PARAMETERS : 131 * @index : index of the stream buffer to invalidate 132 * @user_data : user data ptr of ops_tbl 133 * 134 * RETURN : int32_t type of status 135 * NO_ERROR -- success 136 * none-zero failure code 137 *==========================================================================*/ 138int32_t QCamera3Stream::clean_invalidate_buf(int index, void *user_data) 139{ 140 QCamera3Stream *stream = reinterpret_cast<QCamera3Stream *>(user_data); 141 if (!stream) { 142 ALOGE("invalid stream pointer"); 143 return NO_MEMORY; 144 } 145 return stream->cleanInvalidateBuf(index); 146} 147 148/*=========================================================================== 149 * FUNCTION : QCamera3Stream 150 * 151 * DESCRIPTION: constructor of QCamera3Stream 152 * 153 * PARAMETERS : 154 * @allocator : memory allocator obj 155 * @camHandle : camera handle 156 * @chId : channel handle 157 * @camOps : ptr to camera ops table 158 * @paddingInfo: ptr to padding info 159 * 160 * RETURN : None 161 *==========================================================================*/ 162QCamera3Stream::QCamera3Stream(uint32_t camHandle, 163 uint32_t chId, 164 mm_camera_ops_t *camOps, 165 cam_padding_info_t *paddingInfo, 166 QCamera3Channel *channel) : 167 mCamHandle(camHandle), 168 mChannelHandle(chId), 169 mHandle(0), 170 mCamOps(camOps), 171 mStreamInfo(NULL), 172 mMemOps(NULL), 173 mNumBufs(0), 174 mDataCB(NULL), 175 mUserData(NULL), 176 mDataQ(releaseFrameData, this), 177 mStreamInfoBuf(NULL), 178 mStreamBufs(NULL), 179 mBufDefs(NULL), 180 mChannel(channel) 181{ 182 mMemVtbl.user_data = this; 183 mMemVtbl.get_bufs = get_bufs; 184 mMemVtbl.put_bufs = put_bufs; 185 mMemVtbl.invalidate_buf = invalidate_buf; 186 mMemVtbl.clean_invalidate_buf = clean_invalidate_buf; 187 memset(&mFrameLenOffset, 0, sizeof(mFrameLenOffset)); 188 memcpy(&mPaddingInfo, paddingInfo, sizeof(cam_padding_info_t)); 189} 190 191/*=========================================================================== 192 * FUNCTION : ~QCamera3Stream 193 * 194 * DESCRIPTION: deconstructor of QCamera3Stream 195 * 196 * PARAMETERS : None 197 * 198 * RETURN : None 199 *==========================================================================*/ 200QCamera3Stream::~QCamera3Stream() 201{ 202 if (mStreamInfoBuf != NULL) { 203 int rc = mCamOps->unmap_stream_buf(mCamHandle, 204 mChannelHandle, mHandle, CAM_MAPPING_BUF_TYPE_STREAM_INFO, 0, -1); 205 if (rc < 0) { 206 ALOGE("Failed to map stream info buffer"); 207 } 208 mStreamInfoBuf->deallocate(); 209 delete mStreamInfoBuf; 210 mStreamInfoBuf = NULL; 211 } 212 213 // delete stream 214 if (mHandle > 0) { 215 mCamOps->delete_stream(mCamHandle, mChannelHandle, mHandle); 216 mHandle = 0; 217 } 218} 219 220/*=========================================================================== 221 * FUNCTION : init 222 * 223 * DESCRIPTION: initialize stream obj 224 * 225 * PARAMETERS : 226 * @streamInfoBuf: ptr to buf that contains stream info 227 * @stream_cb : stream data notify callback. Can be NULL if not needed 228 * @userdata : user data ptr 229 * 230 * RETURN : int32_t type of status 231 * NO_ERROR -- success 232 * none-zero failure code 233 *==========================================================================*/ 234int32_t QCamera3Stream::init(cam_stream_type_t streamType, 235 cam_format_t streamFormat, 236 cam_dimension_t streamDim, 237 cam_stream_reproc_config_t* reprocess_config, 238 uint8_t minNumBuffers, 239 uint32_t postprocess_mask, 240 cam_is_type_t is_type, 241 hal3_stream_cb_routine stream_cb, 242 void *userdata) 243{ 244 int32_t rc = OK; 245 mm_camera_stream_config_t stream_config; 246 247 mHandle = mCamOps->add_stream(mCamHandle, mChannelHandle); 248 if (!mHandle) { 249 ALOGE("add_stream failed"); 250 rc = UNKNOWN_ERROR; 251 goto done; 252 } 253 254 // allocate and map stream info memory 255 mStreamInfoBuf = new QCamera3HeapMemory(); 256 if (mStreamInfoBuf == NULL) { 257 ALOGE("%s: no memory for stream info buf obj", __func__); 258 rc = -ENOMEM; 259 goto err1; 260 } 261 rc = mStreamInfoBuf->allocate(1, sizeof(cam_stream_info_t), false); 262 if (rc < 0) { 263 ALOGE("%s: no memory for stream info", __func__); 264 rc = -ENOMEM; 265 goto err2; 266 } 267 268 mStreamInfo = 269 reinterpret_cast<cam_stream_info_t *>(mStreamInfoBuf->getPtr(0)); 270 memset(mStreamInfo, 0, sizeof(cam_stream_info_t)); 271 mStreamInfo->stream_type = streamType; 272 mStreamInfo->fmt = streamFormat; 273 mStreamInfo->dim = streamDim; 274 mStreamInfo->num_bufs = minNumBuffers; 275 mStreamInfo->pp_config.feature_mask = postprocess_mask; 276 ALOGV("%s: stream_type is %d, feature_mask is %d", 277 __func__, mStreamInfo->stream_type, mStreamInfo->pp_config.feature_mask); 278 mStreamInfo->is_type = is_type; 279 rc = mCamOps->map_stream_buf(mCamHandle, 280 mChannelHandle, mHandle, CAM_MAPPING_BUF_TYPE_STREAM_INFO, 281 0, -1, mStreamInfoBuf->getFd(0), mStreamInfoBuf->getSize(0)); 282 if (rc < 0) { 283 ALOGE("Failed to map stream info buffer"); 284 goto err3; 285 } 286 287 mNumBufs = minNumBuffers; 288 if (reprocess_config != NULL) { 289 mStreamInfo->reprocess_config = *reprocess_config; 290 mStreamInfo->streaming_mode = CAM_STREAMING_MODE_BURST; 291 //mStreamInfo->num_of_burst = reprocess_config->offline.num_of_bufs; 292 mStreamInfo->num_of_burst = 1; 293 ALOGI("%s: num_of_burst is %d", __func__, mStreamInfo->num_of_burst); 294 } else { 295 mStreamInfo->streaming_mode = CAM_STREAMING_MODE_CONTINUOUS; 296 } 297 298 // Configure the stream 299 stream_config.stream_info = mStreamInfo; 300 stream_config.mem_vtbl = mMemVtbl; 301 stream_config.padding_info = mPaddingInfo; 302 stream_config.userdata = this; 303 stream_config.stream_cb = dataNotifyCB; 304 305 rc = mCamOps->config_stream(mCamHandle, 306 mChannelHandle, mHandle, &stream_config); 307 if (rc < 0) { 308 ALOGE("Failed to config stream, rc = %d", rc); 309 goto err4; 310 } 311 312 mDataCB = stream_cb; 313 mUserData = userdata; 314 return 0; 315 316err4: 317 mCamOps->unmap_stream_buf(mCamHandle, 318 mChannelHandle, mHandle, CAM_MAPPING_BUF_TYPE_STREAM_INFO, 0, -1); 319err3: 320 mStreamInfoBuf->deallocate(); 321err2: 322 delete mStreamInfoBuf; 323 mStreamInfoBuf = NULL; 324 mStreamInfo = NULL; 325err1: 326 mCamOps->delete_stream(mCamHandle, mChannelHandle, mHandle); 327 mHandle = 0; 328 mNumBufs = 0; 329done: 330 return rc; 331} 332 333/*=========================================================================== 334 * FUNCTION : start 335 * 336 * DESCRIPTION: start stream. Will start main stream thread to handle stream 337 * related ops. 338 * 339 * PARAMETERS : none 340 * 341 * RETURN : int32_t type of status 342 * NO_ERROR -- success 343 * none-zero failure code 344 *==========================================================================*/ 345int32_t QCamera3Stream::start() 346{ 347 int32_t rc = 0; 348 349 mDataQ.init(); 350 rc = mProcTh.launch(dataProcRoutine, this); 351 return rc; 352} 353 354/*=========================================================================== 355 * FUNCTION : stop 356 * 357 * DESCRIPTION: stop stream. Will stop main stream thread 358 * 359 * PARAMETERS : none 360 * 361 * RETURN : int32_t type of status 362 * NO_ERROR -- success 363 * none-zero failure code 364 *==========================================================================*/ 365int32_t QCamera3Stream::stop() 366{ 367 int32_t rc = 0; 368 rc = mProcTh.exit(); 369 return rc; 370} 371 372/*=========================================================================== 373 * FUNCTION : processDataNotify 374 * 375 * DESCRIPTION: process stream data notify 376 * 377 * PARAMETERS : 378 * @frame : stream frame received 379 * 380 * RETURN : int32_t type of status 381 * NO_ERROR -- success 382 * none-zero failure code 383 *==========================================================================*/ 384int32_t QCamera3Stream::processDataNotify(mm_camera_super_buf_t *frame) 385{ 386 CDBG("%s: E\n", __func__); 387 int32_t rc; 388 if (mDataQ.enqueue((void *)frame)) { 389 rc = mProcTh.sendCmd(CAMERA_CMD_TYPE_DO_NEXT_JOB, FALSE, FALSE); 390 } else { 391 ALOGD("%s: Stream thread is not active, no ops here", __func__); 392 bufDone(frame->bufs[0]->buf_idx); 393 free(frame); 394 rc = NO_ERROR; 395 } 396 CDBG("%s: X\n", __func__); 397 return rc; 398} 399 400/*=========================================================================== 401 * FUNCTION : dataNotifyCB 402 * 403 * DESCRIPTION: callback for data notify. This function is registered with 404 * mm-camera-interface to handle data notify 405 * 406 * PARAMETERS : 407 * @recvd_frame : stream frame received 408 * userdata : user data ptr 409 * 410 * RETURN : none 411 *==========================================================================*/ 412void QCamera3Stream::dataNotifyCB(mm_camera_super_buf_t *recvd_frame, 413 void *userdata) 414{ 415 CDBG("%s: E\n", __func__); 416 QCamera3Stream* stream = (QCamera3Stream *)userdata; 417 if (stream == NULL || 418 recvd_frame == NULL || 419 recvd_frame->bufs[0] == NULL || 420 recvd_frame->bufs[0]->stream_id != stream->getMyHandle()) { 421 ALOGE("%s: Not a valid stream to handle buf", __func__); 422 return; 423 } 424 425 mm_camera_super_buf_t *frame = 426 (mm_camera_super_buf_t *)malloc(sizeof(mm_camera_super_buf_t)); 427 if (frame == NULL) { 428 ALOGE("%s: No mem for mm_camera_buf_def_t", __func__); 429 stream->bufDone(recvd_frame->bufs[0]->buf_idx); 430 return; 431 } 432 *frame = *recvd_frame; 433 stream->processDataNotify(frame); 434 return; 435} 436 437/*=========================================================================== 438 * FUNCTION : dataProcRoutine 439 * 440 * DESCRIPTION: function to process data in the main stream thread 441 * 442 * PARAMETERS : 443 * @data : user data ptr 444 * 445 * RETURN : none 446 *==========================================================================*/ 447void *QCamera3Stream::dataProcRoutine(void *data) 448{ 449 int running = 1; 450 int ret; 451 QCamera3Stream *pme = (QCamera3Stream *)data; 452 QCameraCmdThread *cmdThread = &pme->mProcTh; 453 cmdThread->setName("cam_stream_proc"); 454 455 CDBG("%s: E", __func__); 456 do { 457 do { 458 ret = cam_sem_wait(&cmdThread->cmd_sem); 459 if (ret != 0 && errno != EINVAL) { 460 ALOGE("%s: cam_sem_wait error (%s)", 461 __func__, strerror(errno)); 462 return NULL; 463 } 464 } while (ret != 0); 465 466 // we got notified about new cmd avail in cmd queue 467 camera_cmd_type_t cmd = cmdThread->getCmd(); 468 switch (cmd) { 469 case CAMERA_CMD_TYPE_DO_NEXT_JOB: 470 { 471 CDBG("%s: Do next job", __func__); 472 mm_camera_super_buf_t *frame = 473 (mm_camera_super_buf_t *)pme->mDataQ.dequeue(); 474 if (NULL != frame) { 475 if (pme->mDataCB != NULL) { 476 pme->mDataCB(frame, pme, pme->mUserData); 477 } else { 478 // no data cb routine, return buf here 479 pme->bufDone(frame->bufs[0]->buf_idx); 480 } 481 } 482 } 483 break; 484 case CAMERA_CMD_TYPE_EXIT: 485 CDBG_HIGH("%s: Exit", __func__); 486 /* flush data buf queue */ 487 pme->mDataQ.flush(); 488 running = 0; 489 break; 490 default: 491 break; 492 } 493 } while (running); 494 CDBG("%s: X", __func__); 495 return NULL; 496} 497 498/*=========================================================================== 499 * FUNCTION : getInternalFormatBuffer 500 * 501 * DESCRIPTION: return buffer in the internal format structure 502 * 503 * PARAMETERS : 504 * @index : index of buffer to be returned 505 * 506 * RETURN : int32_t type of status 507 * NO_ERROR -- success 508 * none-zero failure code 509 *==========================================================================*/ 510mm_camera_buf_def_t* QCamera3Stream::getInternalFormatBuffer(int index) 511{ 512 mm_camera_buf_def_t *rc = NULL; 513 if ((index >= mNumBufs) || (mBufDefs == NULL) || 514 (NULL == mBufDefs[index].mem_info)) { 515 ALOGE("%s:Index out of range/no internal buffers yet", __func__); 516 return NULL; 517 } 518 519 rc = (mm_camera_buf_def_t*)malloc(sizeof(mm_camera_buf_def_t)); 520 if(rc) { 521 memcpy(rc, &mBufDefs[index], sizeof(mm_camera_buf_def_t)); 522 } else { 523 ALOGE("%s: Failed to allocate memory",__func__); 524 } 525 return rc; 526} 527 528/*=========================================================================== 529 * FUNCTION : bufDone 530 * 531 * DESCRIPTION: return stream buffer to kernel 532 * 533 * PARAMETERS : 534 * @index : index of buffer to be returned 535 * 536 * RETURN : int32_t type of status 537 * NO_ERROR -- success 538 * none-zero failure code 539 *==========================================================================*/ 540int32_t QCamera3Stream::bufDone(int index) 541{ 542 int32_t rc = NO_ERROR; 543 544 if (index >= mNumBufs || mBufDefs == NULL) 545 return BAD_INDEX; 546 547 if( NULL == mBufDefs[index].mem_info) { 548 if (NULL == mMemOps) { 549 ALOGE("%s: Camera operations not initialized", __func__); 550 return NO_INIT; 551 } 552 553 rc = mMemOps->map_ops(index, -1, mStreamBufs->getFd(index), 554 mStreamBufs->getSize(index), mMemOps->userdata); 555 if (rc < 0) { 556 ALOGE("%s: Failed to map camera buffer %d", __func__, index); 557 return rc; 558 } 559 560 rc = mStreamBufs->getBufDef(mFrameLenOffset, mBufDefs[index], index); 561 if (NO_ERROR != rc) { 562 ALOGE("%s: Couldn't find camera buffer definition", __func__); 563 mMemOps->unmap_ops(index, -1, mMemOps->userdata); 564 return rc; 565 } 566 } 567 568 rc = mCamOps->qbuf(mCamHandle, mChannelHandle, &mBufDefs[index]); 569 if (rc < 0) 570 return FAILED_TRANSACTION; 571 572 return rc; 573} 574 575/*=========================================================================== 576 * FUNCTION : getBufs 577 * 578 * DESCRIPTION: allocate stream buffers 579 * 580 * PARAMETERS : 581 * @offset : offset info of stream buffers 582 * @num_bufs : number of buffers allocated 583 * @initial_reg_flag: flag to indicate if buffer needs to be registered 584 * at kernel initially 585 * @bufs : output of allocated buffers 586 * @ops_tbl : ptr to buf mapping/unmapping ops 587 * 588 * RETURN : int32_t type of status 589 * NO_ERROR -- success 590 * none-zero failure code 591 *==========================================================================*/ 592int32_t QCamera3Stream::getBufs(cam_frame_len_offset_t *offset, 593 uint8_t *num_bufs, 594 uint8_t **initial_reg_flag, 595 mm_camera_buf_def_t **bufs, 596 mm_camera_map_unmap_ops_tbl_t *ops_tbl) 597{ 598 int rc = NO_ERROR; 599 uint8_t *regFlags; 600 601 if (!ops_tbl) { 602 ALOGE("%s: ops_tbl is NULL", __func__); 603 return INVALID_OPERATION; 604 } 605 606 mFrameLenOffset = *offset; 607 mMemOps = ops_tbl; 608 609 mStreamBufs = mChannel->getStreamBufs(mFrameLenOffset.frame_len); 610 if (!mStreamBufs) { 611 ALOGE("%s: Failed to allocate stream buffers", __func__); 612 return NO_MEMORY; 613 } 614 615 int registeredBuffers = mStreamBufs->getCnt(); 616 for (int i = 0; i < registeredBuffers; i++) { 617 rc = ops_tbl->map_ops(i, -1, mStreamBufs->getFd(i), 618 mStreamBufs->getSize(i), ops_tbl->userdata); 619 if (rc < 0) { 620 ALOGE("%s: map_stream_buf failed: %d", __func__, rc); 621 for (int j = 0; j < i; j++) { 622 ops_tbl->unmap_ops(j, -1, ops_tbl->userdata); 623 } 624 return INVALID_OPERATION; 625 } 626 } 627 628 //regFlags array is allocated by us, but consumed and freed by mm-camera-interface 629 regFlags = (uint8_t *)malloc(sizeof(uint8_t) * mNumBufs); 630 if (!regFlags) { 631 ALOGE("%s: Out of memory", __func__); 632 for (int i = 0; i < registeredBuffers; i++) { 633 ops_tbl->unmap_ops(i, -1, ops_tbl->userdata); 634 } 635 return NO_MEMORY; 636 } 637 memset(regFlags, 0, sizeof(uint8_t) * mNumBufs); 638 639 mBufDefs = (mm_camera_buf_def_t *)malloc(mNumBufs * sizeof(mm_camera_buf_def_t)); 640 if (mBufDefs == NULL) { 641 ALOGE("%s: Failed to allocate mm_camera_buf_def_t %d", __func__, rc); 642 for (int i = 0; i < registeredBuffers; i++) { 643 ops_tbl->unmap_ops(i, -1, ops_tbl->userdata); 644 } 645 free(regFlags); 646 regFlags = NULL; 647 return INVALID_OPERATION; 648 } 649 memset(mBufDefs, 0, mNumBufs * sizeof(mm_camera_buf_def_t)); 650 for (int i = 0; i < registeredBuffers; i++) { 651 mStreamBufs->getBufDef(mFrameLenOffset, mBufDefs[i], i); 652 } 653 654 rc = mStreamBufs->getRegFlags(regFlags); 655 if (rc < 0) { 656 ALOGE("%s: getRegFlags failed %d", __func__, rc); 657 for (int i = 0; i < registeredBuffers; i++) { 658 ops_tbl->unmap_ops(i, -1, ops_tbl->userdata); 659 } 660 free(mBufDefs); 661 mBufDefs = NULL; 662 free(regFlags); 663 regFlags = NULL; 664 return INVALID_OPERATION; 665 } 666 667 *num_bufs = mNumBufs; 668 *initial_reg_flag = regFlags; 669 *bufs = mBufDefs; 670 return NO_ERROR; 671} 672 673/*=========================================================================== 674 * FUNCTION : putBufs 675 * 676 * DESCRIPTION: deallocate stream buffers 677 * 678 * PARAMETERS : 679 * @ops_tbl : ptr to buf mapping/unmapping ops 680 * 681 * RETURN : int32_t type of status 682 * NO_ERROR -- success 683 * none-zero failure code 684 *==========================================================================*/ 685int32_t QCamera3Stream::putBufs(mm_camera_map_unmap_ops_tbl_t *ops_tbl) 686{ 687 int rc = NO_ERROR; 688 for (int i = 0; i < mNumBufs; i++) { 689 if (NULL != mBufDefs[i].mem_info) { 690 rc = ops_tbl->unmap_ops(i, -1, ops_tbl->userdata); 691 if (rc < 0) { 692 ALOGE("%s: map_stream_buf failed: %d", __func__, rc); 693 } 694 } 695 } 696 mBufDefs = NULL; // mBufDefs just keep a ptr to the buffer 697 // mm-camera-interface own the buffer, so no need to free 698 memset(&mFrameLenOffset, 0, sizeof(mFrameLenOffset)); 699 mChannel->putStreamBufs(); 700 701 return rc; 702} 703 704/*=========================================================================== 705 * FUNCTION : invalidateBuf 706 * 707 * DESCRIPTION: invalidate a specific stream buffer 708 * 709 * PARAMETERS : 710 * @index : index of the buffer to invalidate 711 * 712 * RETURN : int32_t type of status 713 * NO_ERROR -- success 714 * none-zero failure code 715 *==========================================================================*/ 716int32_t QCamera3Stream::invalidateBuf(int index) 717{ 718 return mStreamBufs->invalidateCache(index); 719} 720 721/*=========================================================================== 722 * FUNCTION : cleanInvalidateBuf 723 * 724 * DESCRIPTION: clean and invalidate a specific stream buffer 725 * 726 * PARAMETERS : 727 * @index : index of the buffer to invalidate 728 * 729 * RETURN : int32_t type of status 730 * NO_ERROR -- success 731 * none-zero failure code 732 *==========================================================================*/ 733int32_t QCamera3Stream::cleanInvalidateBuf(int index) 734{ 735 return mStreamBufs->cleanInvalidateCache(index); 736} 737 738/*=========================================================================== 739 * FUNCTION : getFrameOffset 740 * 741 * DESCRIPTION: query stream buffer frame offset info 742 * 743 * PARAMETERS : 744 * @offset : reference to struct to store the queried frame offset info 745 * 746 * RETURN : int32_t type of status 747 * NO_ERROR -- success 748 * none-zero failure code 749 *==========================================================================*/ 750int32_t QCamera3Stream::getFrameOffset(cam_frame_len_offset_t &offset) 751{ 752 offset = mFrameLenOffset; 753 return 0; 754} 755 756/*=========================================================================== 757 * FUNCTION : getFrameDimension 758 * 759 * DESCRIPTION: query stream frame dimension info 760 * 761 * PARAMETERS : 762 * @dim : reference to struct to store the queried frame dimension 763 * 764 * RETURN : int32_t type of status 765 * NO_ERROR -- success 766 * none-zero failure code 767 *==========================================================================*/ 768int32_t QCamera3Stream::getFrameDimension(cam_dimension_t &dim) 769{ 770 if (mStreamInfo != NULL) { 771 dim = mStreamInfo->dim; 772 return 0; 773 } 774 return -1; 775} 776 777/*=========================================================================== 778 * FUNCTION : getFormat 779 * 780 * DESCRIPTION: query stream format 781 * 782 * PARAMETERS : 783 * @fmt : reference to stream format 784 * 785 * RETURN : int32_t type of status 786 * NO_ERROR -- success 787 * none-zero failure code 788 *==========================================================================*/ 789int32_t QCamera3Stream::getFormat(cam_format_t &fmt) 790{ 791 if (mStreamInfo != NULL) { 792 fmt = mStreamInfo->fmt; 793 return 0; 794 } 795 return -1; 796} 797 798/*=========================================================================== 799 * FUNCTION : getMyServerID 800 * 801 * DESCRIPTION: query server stream ID 802 * 803 * PARAMETERS : None 804 * 805 * RETURN : stream ID from server 806 *==========================================================================*/ 807uint32_t QCamera3Stream::getMyServerID() { 808 if (mStreamInfo != NULL) { 809 return mStreamInfo->stream_svr_id; 810 } else { 811 return 0; 812 } 813} 814 815/*=========================================================================== 816 * FUNCTION : getMyType 817 * 818 * DESCRIPTION: query stream type 819 * 820 * PARAMETERS : None 821 * 822 * RETURN : type of stream 823 *==========================================================================*/ 824cam_stream_type_t QCamera3Stream::getMyType() const 825{ 826 if (mStreamInfo != NULL) { 827 return mStreamInfo->stream_type; 828 } else { 829 return CAM_STREAM_TYPE_MAX; 830 } 831} 832 833/*=========================================================================== 834 * FUNCTION : mapBuf 835 * 836 * DESCRIPTION: map stream related buffer to backend server 837 * 838 * PARAMETERS : 839 * @buf_type : mapping type of buffer 840 * @buf_idx : index of buffer 841 * @plane_idx: plane index 842 * @fd : fd of the buffer 843 * @size : lenght of the buffer 844 * 845 * RETURN : int32_t type of status 846 * NO_ERROR -- success 847 * none-zero failure code 848 *==========================================================================*/ 849int32_t QCamera3Stream::mapBuf(uint8_t buf_type, 850 uint32_t buf_idx, 851 int32_t plane_idx, 852 int fd, 853 uint32_t size) 854{ 855 return mCamOps->map_stream_buf(mCamHandle, mChannelHandle, 856 mHandle, buf_type, 857 buf_idx, plane_idx, 858 fd, size); 859 860} 861 862/*=========================================================================== 863 * FUNCTION : unmapBuf 864 * 865 * DESCRIPTION: unmap stream related buffer to backend server 866 * 867 * PARAMETERS : 868 * @buf_type : mapping type of buffer 869 * @buf_idx : index of buffer 870 * @plane_idx: plane index 871 * 872 * RETURN : int32_t type of status 873 * NO_ERROR -- success 874 * none-zero failure code 875 *==========================================================================*/ 876int32_t QCamera3Stream::unmapBuf(uint8_t buf_type, uint32_t buf_idx, int32_t plane_idx) 877{ 878 return mCamOps->unmap_stream_buf(mCamHandle, mChannelHandle, 879 mHandle, buf_type, 880 buf_idx, plane_idx); 881} 882 883/*=========================================================================== 884 * FUNCTION : setParameter 885 * 886 * DESCRIPTION: set stream based parameters 887 * 888 * PARAMETERS : 889 * @param : ptr to parameters to be set 890 * 891 * RETURN : int32_t type of status 892 * NO_ERROR -- success 893 * none-zero failure code 894 *==========================================================================*/ 895int32_t QCamera3Stream::setParameter(cam_stream_parm_buffer_t ¶m) 896{ 897 int32_t rc = NO_ERROR; 898 mStreamInfo->parm_buf = param; 899 rc = mCamOps->set_stream_parms(mCamHandle, 900 mChannelHandle, 901 mHandle, 902 &mStreamInfo->parm_buf); 903 if (rc == NO_ERROR) { 904 param = mStreamInfo->parm_buf; 905 } 906 return rc; 907} 908 909/*=========================================================================== 910 * FUNCTION : releaseFrameData 911 * 912 * DESCRIPTION: callback function to release frame data node 913 * 914 * PARAMETERS : 915 * @data : ptr to post process input data 916 * @user_data : user data ptr (QCameraReprocessor) 917 * 918 * RETURN : None 919 *==========================================================================*/ 920void QCamera3Stream::releaseFrameData(void *data, void *user_data) 921{ 922 QCamera3Stream *pme = (QCamera3Stream *)user_data; 923 mm_camera_super_buf_t *frame = (mm_camera_super_buf_t *)data; 924 if (NULL != pme) { 925 pme->bufDone(frame->bufs[0]->buf_idx); 926 } 927} 928 929}; // namespace qcamera 930