Camera3OutputStream.cpp revision e8c535e833ed135895e99ca81aa3b85d80d7cf3c
1/* 2 * Copyright (C) 2013 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17#define LOG_TAG "Camera3-OutputStream" 18#define ATRACE_TAG ATRACE_TAG_CAMERA 19//#define LOG_NDEBUG 0 20 21#include <utils/Log.h> 22#include <utils/Trace.h> 23#include "Camera3OutputStream.h" 24 25#ifndef container_of 26#define container_of(ptr, type, member) \ 27 (type *)((char*)(ptr) - offsetof(type, member)) 28#endif 29 30namespace android { 31 32namespace camera3 { 33 34Camera3OutputStream::Camera3OutputStream(int id, 35 sp<Surface> consumer, 36 uint32_t width, uint32_t height, int format, 37 android_dataspace dataSpace, camera3_stream_rotation_t rotation, 38 nsecs_t timestampOffset, int setId) : 39 Camera3IOStreamBase(id, CAMERA3_STREAM_OUTPUT, width, height, 40 /*maxSize*/0, format, dataSpace, rotation, setId), 41 mConsumer(consumer), 42 mTransform(0), 43 mTraceFirstBuffer(true), 44 mUseBufferManager(false), 45 mTimestampOffset(timestampOffset) { 46 47 if (mConsumer == NULL) { 48 ALOGE("%s: Consumer is NULL!", __FUNCTION__); 49 mState = STATE_ERROR; 50 } 51 52 if (setId > CAMERA3_STREAM_SET_ID_INVALID) { 53 mBufferReleasedListener = new BufferReleasedListener(this); 54 } 55} 56 57Camera3OutputStream::Camera3OutputStream(int id, 58 sp<Surface> consumer, 59 uint32_t width, uint32_t height, size_t maxSize, int format, 60 android_dataspace dataSpace, camera3_stream_rotation_t rotation, 61 nsecs_t timestampOffset, int setId) : 62 Camera3IOStreamBase(id, CAMERA3_STREAM_OUTPUT, width, height, maxSize, 63 format, dataSpace, rotation, setId), 64 mConsumer(consumer), 65 mTransform(0), 66 mTraceFirstBuffer(true), 67 mUseMonoTimestamp(false), 68 mUseBufferManager(false), 69 mTimestampOffset(timestampOffset) { 70 71 if (format != HAL_PIXEL_FORMAT_BLOB && format != HAL_PIXEL_FORMAT_RAW_OPAQUE) { 72 ALOGE("%s: Bad format for size-only stream: %d", __FUNCTION__, 73 format); 74 mState = STATE_ERROR; 75 } 76 77 if (mConsumer == NULL) { 78 ALOGE("%s: Consumer is NULL!", __FUNCTION__); 79 mState = STATE_ERROR; 80 } 81 82 if (setId > CAMERA3_STREAM_SET_ID_INVALID) { 83 mBufferReleasedListener = new BufferReleasedListener(this); 84 } 85} 86 87Camera3OutputStream::Camera3OutputStream(int id, camera3_stream_type_t type, 88 uint32_t width, uint32_t height, 89 int format, 90 android_dataspace dataSpace, 91 camera3_stream_rotation_t rotation, 92 int setId) : 93 Camera3IOStreamBase(id, type, width, height, 94 /*maxSize*/0, 95 format, dataSpace, rotation, setId), 96 mTransform(0), 97 mTraceFirstBuffer(true), 98 mUseMonoTimestamp(false), 99 mUseBufferManager(false) { 100 101 if (setId > CAMERA3_STREAM_SET_ID_INVALID) { 102 mBufferReleasedListener = new BufferReleasedListener(this); 103 } 104 105 // Subclasses expected to initialize mConsumer themselves 106} 107 108 109Camera3OutputStream::~Camera3OutputStream() { 110 disconnectLocked(); 111} 112 113status_t Camera3OutputStream::getBufferLocked(camera3_stream_buffer *buffer) { 114 ATRACE_CALL(); 115 status_t res; 116 117 if ((res = getBufferPreconditionCheckLocked()) != OK) { 118 return res; 119 } 120 121 ANativeWindowBuffer* anb; 122 int fenceFd = -1; 123 if (mUseBufferManager) { 124 sp<GraphicBuffer> gb; 125 res = mBufferManager->getBufferForStream(getId(), getStreamSetId(), &gb, &fenceFd); 126 if (res != OK) { 127 ALOGE("%s: Stream %d: Can't get next output buffer from buffer manager: %s (%d)", 128 __FUNCTION__, mId, strerror(-res), res); 129 return res; 130 } 131 // Attach this buffer to the bufferQueue: the buffer will be in dequeue state after a 132 // successful return. 133 anb = gb.get(); 134 res = mConsumer->attachBuffer(anb); 135 if (res != OK) { 136 ALOGE("%s: Stream %d: Can't attach the output buffer to this surface: %s (%d)", 137 __FUNCTION__, mId, strerror(-res), res); 138 return res; 139 } 140 } else { 141 /** 142 * Release the lock briefly to avoid deadlock for below scenario: 143 * Thread 1: StreamingProcessor::startStream -> Camera3Stream::isConfiguring(). 144 * This thread acquired StreamingProcessor lock and try to lock Camera3Stream lock. 145 * Thread 2: Camera3Stream::returnBuffer->StreamingProcessor::onFrameAvailable(). 146 * This thread acquired Camera3Stream lock and bufferQueue lock, and try to lock 147 * StreamingProcessor lock. 148 * Thread 3: Camera3Stream::getBuffer(). This thread acquired Camera3Stream lock 149 * and try to lock bufferQueue lock. 150 * Then there is circular locking dependency. 151 */ 152 sp<ANativeWindow> currentConsumer = mConsumer; 153 mLock.unlock(); 154 155 res = currentConsumer->dequeueBuffer(currentConsumer.get(), &anb, &fenceFd); 156 mLock.lock(); 157 if (res != OK) { 158 ALOGE("%s: Stream %d: Can't dequeue next output buffer: %s (%d)", 159 __FUNCTION__, mId, strerror(-res), res); 160 161 // Only transition to STATE_ABANDONED from STATE_CONFIGURED. (If it is STATE_PREPARING, 162 // let prepareNextBuffer handle the error.) 163 if (res == NO_INIT && mState == STATE_CONFIGURED) { 164 mState = STATE_ABANDONED; 165 } 166 167 return res; 168 } 169 } 170 171 /** 172 * FenceFD now owned by HAL except in case of error, 173 * in which case we reassign it to acquire_fence 174 */ 175 handoutBufferLocked(*buffer, &(anb->handle), /*acquireFence*/fenceFd, 176 /*releaseFence*/-1, CAMERA3_BUFFER_STATUS_OK, /*output*/true); 177 178 return OK; 179} 180 181status_t Camera3OutputStream::returnBufferLocked( 182 const camera3_stream_buffer &buffer, 183 nsecs_t timestamp) { 184 ATRACE_CALL(); 185 186 status_t res = returnAnyBufferLocked(buffer, timestamp, /*output*/true); 187 188 if (res != OK) { 189 return res; 190 } 191 192 mLastTimestamp = timestamp; 193 194 return OK; 195} 196 197status_t Camera3OutputStream::returnBufferCheckedLocked( 198 const camera3_stream_buffer &buffer, 199 nsecs_t timestamp, 200 bool output, 201 /*out*/ 202 sp<Fence> *releaseFenceOut) { 203 204 (void)output; 205 ALOG_ASSERT(output, "Expected output to be true"); 206 207 status_t res; 208 209 // Fence management - always honor release fence from HAL 210 sp<Fence> releaseFence = new Fence(buffer.release_fence); 211 int anwReleaseFence = releaseFence->dup(); 212 213 /** 214 * Release the lock briefly to avoid deadlock with 215 * StreamingProcessor::startStream -> Camera3Stream::isConfiguring (this 216 * thread will go into StreamingProcessor::onFrameAvailable) during 217 * queueBuffer 218 */ 219 sp<ANativeWindow> currentConsumer = mConsumer; 220 mLock.unlock(); 221 222 /** 223 * Return buffer back to ANativeWindow 224 */ 225 if (buffer.status == CAMERA3_BUFFER_STATUS_ERROR) { 226 // Cancel buffer 227 res = currentConsumer->cancelBuffer(currentConsumer.get(), 228 container_of(buffer.buffer, ANativeWindowBuffer, handle), 229 anwReleaseFence); 230 if (res != OK) { 231 ALOGE("%s: Stream %d: Error cancelling buffer to native window:" 232 " %s (%d)", __FUNCTION__, mId, strerror(-res), res); 233 } 234 235 if (mUseBufferManager) { 236 // Return this buffer back to buffer manager. 237 mBufferReleasedListener->onBufferReleased(); 238 } 239 } else { 240 if (mTraceFirstBuffer && (stream_type == CAMERA3_STREAM_OUTPUT)) { 241 { 242 char traceLog[48]; 243 snprintf(traceLog, sizeof(traceLog), "Stream %d: first full buffer\n", mId); 244 ATRACE_NAME(traceLog); 245 } 246 mTraceFirstBuffer = false; 247 } 248 249 /* Certain consumers (such as AudioSource or HardwareComposer) use 250 * MONOTONIC time, causing time misalignment if camera timestamp is 251 * in BOOTTIME. Do the conversion if necessary. */ 252 res = native_window_set_buffers_timestamp(mConsumer.get(), 253 mUseMonoTimestamp ? timestamp - mTimestampOffset : timestamp); 254 if (res != OK) { 255 ALOGE("%s: Stream %d: Error setting timestamp: %s (%d)", 256 __FUNCTION__, mId, strerror(-res), res); 257 return res; 258 } 259 260 res = currentConsumer->queueBuffer(currentConsumer.get(), 261 container_of(buffer.buffer, ANativeWindowBuffer, handle), 262 anwReleaseFence); 263 if (res != OK) { 264 ALOGE("%s: Stream %d: Error queueing buffer to native window: " 265 "%s (%d)", __FUNCTION__, mId, strerror(-res), res); 266 } 267 } 268 mLock.lock(); 269 270 // Once a valid buffer has been returned to the queue, can no longer 271 // dequeue all buffers for preallocation. 272 if (buffer.status != CAMERA3_BUFFER_STATUS_ERROR) { 273 mStreamUnpreparable = true; 274 } 275 276 if (res != OK) { 277 close(anwReleaseFence); 278 } 279 280 *releaseFenceOut = releaseFence; 281 282 return res; 283} 284 285void Camera3OutputStream::dump(int fd, const Vector<String16> &args) const { 286 (void) args; 287 String8 lines; 288 lines.appendFormat(" Stream[%d]: Output\n", mId); 289 lines.appendFormat(" Consumer name: %s\n", mConsumerName.string()); 290 write(fd, lines.string(), lines.size()); 291 292 Camera3IOStreamBase::dump(fd, args); 293} 294 295status_t Camera3OutputStream::setTransform(int transform) { 296 ATRACE_CALL(); 297 Mutex::Autolock l(mLock); 298 return setTransformLocked(transform); 299} 300 301status_t Camera3OutputStream::setTransformLocked(int transform) { 302 status_t res = OK; 303 if (mState == STATE_ERROR) { 304 ALOGE("%s: Stream in error state", __FUNCTION__); 305 return INVALID_OPERATION; 306 } 307 308 mTransform = transform; 309 if (mState == STATE_CONFIGURED) { 310 res = native_window_set_buffers_transform(mConsumer.get(), 311 transform); 312 if (res != OK) { 313 ALOGE("%s: Unable to configure stream transform to %x: %s (%d)", 314 __FUNCTION__, transform, strerror(-res), res); 315 } 316 } 317 return res; 318} 319 320status_t Camera3OutputStream::configureQueueLocked() { 321 status_t res; 322 323 mTraceFirstBuffer = true; 324 if ((res = Camera3IOStreamBase::configureQueueLocked()) != OK) { 325 return res; 326 } 327 328 ALOG_ASSERT(mConsumer != 0, "mConsumer should never be NULL"); 329 330 // Configure consumer-side ANativeWindow interface. The listener may be used 331 // to notify buffer manager (if it is used) of the returned buffers. 332 res = mConsumer->connect(NATIVE_WINDOW_API_CAMERA, /*listener*/mBufferReleasedListener); 333 if (res != OK) { 334 ALOGE("%s: Unable to connect to native window for stream %d", 335 __FUNCTION__, mId); 336 return res; 337 } 338 339 mConsumerName = mConsumer->getConsumerName(); 340 341 res = native_window_set_usage(mConsumer.get(), camera3_stream::usage); 342 if (res != OK) { 343 ALOGE("%s: Unable to configure usage %08x for stream %d", 344 __FUNCTION__, camera3_stream::usage, mId); 345 return res; 346 } 347 348 res = native_window_set_scaling_mode(mConsumer.get(), 349 NATIVE_WINDOW_SCALING_MODE_SCALE_TO_WINDOW); 350 if (res != OK) { 351 ALOGE("%s: Unable to configure stream scaling: %s (%d)", 352 __FUNCTION__, strerror(-res), res); 353 return res; 354 } 355 356 if (mMaxSize == 0) { 357 // For buffers of known size 358 res = native_window_set_buffers_dimensions(mConsumer.get(), 359 camera3_stream::width, camera3_stream::height); 360 } else { 361 // For buffers with bounded size 362 res = native_window_set_buffers_dimensions(mConsumer.get(), 363 mMaxSize, 1); 364 } 365 if (res != OK) { 366 ALOGE("%s: Unable to configure stream buffer dimensions" 367 " %d x %d (maxSize %zu) for stream %d", 368 __FUNCTION__, camera3_stream::width, camera3_stream::height, 369 mMaxSize, mId); 370 return res; 371 } 372 res = native_window_set_buffers_format(mConsumer.get(), 373 camera3_stream::format); 374 if (res != OK) { 375 ALOGE("%s: Unable to configure stream buffer format %#x for stream %d", 376 __FUNCTION__, camera3_stream::format, mId); 377 return res; 378 } 379 380 res = native_window_set_buffers_data_space(mConsumer.get(), 381 camera3_stream::data_space); 382 if (res != OK) { 383 ALOGE("%s: Unable to configure stream dataspace %#x for stream %d", 384 __FUNCTION__, camera3_stream::data_space, mId); 385 return res; 386 } 387 388 int maxConsumerBuffers; 389 res = static_cast<ANativeWindow*>(mConsumer.get())->query( 390 mConsumer.get(), 391 NATIVE_WINDOW_MIN_UNDEQUEUED_BUFFERS, &maxConsumerBuffers); 392 if (res != OK) { 393 ALOGE("%s: Unable to query consumer undequeued" 394 " buffer count for stream %d", __FUNCTION__, mId); 395 return res; 396 } 397 398 ALOGV("%s: Consumer wants %d buffers, HAL wants %d", __FUNCTION__, 399 maxConsumerBuffers, camera3_stream::max_buffers); 400 if (camera3_stream::max_buffers == 0) { 401 ALOGE("%s: Camera HAL requested max_buffer count: %d, requires at least 1", 402 __FUNCTION__, camera3_stream::max_buffers); 403 return INVALID_OPERATION; 404 } 405 406 mTotalBufferCount = maxConsumerBuffers + camera3_stream::max_buffers; 407 mHandoutTotalBufferCount = 0; 408 mFrameCount = 0; 409 mLastTimestamp = 0; 410 mUseMonoTimestamp = (isConsumedByHWComposer() | isVideoStream()); 411 412 res = native_window_set_buffer_count(mConsumer.get(), 413 mTotalBufferCount); 414 if (res != OK) { 415 ALOGE("%s: Unable to set buffer count for stream %d", 416 __FUNCTION__, mId); 417 return res; 418 } 419 420 res = native_window_set_buffers_transform(mConsumer.get(), 421 mTransform); 422 if (res != OK) { 423 ALOGE("%s: Unable to configure stream transform to %x: %s (%d)", 424 __FUNCTION__, mTransform, strerror(-res), res); 425 } 426 427 /** 428 * Camera3 Buffer manager is only supported by HAL3.3 onwards, as the older HALs requires 429 * buffers to be statically allocated for internal static buffer registration, while the 430 * buffers provided by buffer manager are really dynamically allocated. Camera3Device only 431 * sets the mBufferManager if device version is > HAL3.2, which guarantees that the buffer 432 * manager setup is skipped in below code. Note that HAL3.2 is also excluded here, as some 433 * HAL3.2 devices may not support the dynamic buffer registeration. 434 */ 435 if (mBufferManager != 0 && mSetId > CAMERA3_STREAM_SET_ID_INVALID) { 436 StreamInfo streamInfo( 437 getId(), getStreamSetId(), getWidth(), getHeight(), getFormat(), getDataSpace(), 438 camera3_stream::usage, mTotalBufferCount, /*isConfigured*/true); 439 res = mBufferManager->registerStream(streamInfo); 440 if (res == OK) { 441 // Disable buffer allocation for this BufferQueue, buffer manager will take over 442 // the buffer allocation responsibility. 443 mConsumer->getIGraphicBufferProducer()->allowAllocation(false); 444 mUseBufferManager = true; 445 } else { 446 ALOGE("%s: Unable to register stream %d to camera3 buffer manager, " 447 "(error %d %s), fall back to BufferQueue for buffer management!", 448 __FUNCTION__, mId, res, strerror(-res)); 449 } 450 } 451 452 return OK; 453} 454 455status_t Camera3OutputStream::disconnectLocked() { 456 status_t res; 457 458 if ((res = Camera3IOStreamBase::disconnectLocked()) != OK) { 459 return res; 460 } 461 462 ALOGV("%s: disconnecting stream %d from native window", __FUNCTION__, getId()); 463 464 res = native_window_api_disconnect(mConsumer.get(), 465 NATIVE_WINDOW_API_CAMERA); 466 467 /** 468 * This is not an error. if client calling process dies, the window will 469 * also die and all calls to it will return DEAD_OBJECT, thus it's already 470 * "disconnected" 471 */ 472 if (res == DEAD_OBJECT) { 473 ALOGW("%s: While disconnecting stream %d from native window, the" 474 " native window died from under us", __FUNCTION__, mId); 475 } 476 else if (res != OK) { 477 ALOGE("%s: Unable to disconnect stream %d from native window " 478 "(error %d %s)", 479 __FUNCTION__, mId, res, strerror(-res)); 480 mState = STATE_ERROR; 481 return res; 482 } 483 484 // Since device is already idle, there is no getBuffer call to buffer manager, unregister the 485 // stream at this point should be safe. 486 if (mUseBufferManager) { 487 res = mBufferManager->unregisterStream(getId(), getStreamSetId()); 488 if (res != OK) { 489 ALOGE("%s: Unable to unregister stream %d from buffer manager " 490 "(error %d %s)", __FUNCTION__, mId, res, strerror(-res)); 491 mState = STATE_ERROR; 492 return res; 493 } 494 // Note that, to make prepare/teardown case work, we must not mBufferManager.clear(), as 495 // the stream is still in usable state after this call. 496 mUseBufferManager = false; 497 } 498 499 mState = (mState == STATE_IN_RECONFIG) ? STATE_IN_CONFIG 500 : STATE_CONSTRUCTED; 501 return OK; 502} 503 504status_t Camera3OutputStream::getEndpointUsage(uint32_t *usage) const { 505 506 status_t res; 507 int32_t u = 0; 508 res = static_cast<ANativeWindow*>(mConsumer.get())->query(mConsumer.get(), 509 NATIVE_WINDOW_CONSUMER_USAGE_BITS, &u); 510 511 // If an opaque output stream's endpoint is ImageReader, add 512 // GRALLOC_USAGE_HW_CAMERA_ZSL to the usage so HAL knows it will be used 513 // for the ZSL use case. 514 // Assume it's for ImageReader if the consumer usage doesn't have any of these bits set: 515 // 1. GRALLOC_USAGE_HW_TEXTURE 516 // 2. GRALLOC_USAGE_HW_RENDER 517 // 3. GRALLOC_USAGE_HW_COMPOSER 518 // 4. GRALLOC_USAGE_HW_VIDEO_ENCODER 519 if (camera3_stream::format == HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED && 520 (u & (GRALLOC_USAGE_HW_TEXTURE | GRALLOC_USAGE_HW_RENDER | GRALLOC_USAGE_HW_COMPOSER | 521 GRALLOC_USAGE_HW_VIDEO_ENCODER)) == 0) { 522 u |= GRALLOC_USAGE_HW_CAMERA_ZSL; 523 } 524 525 *usage = u; 526 return res; 527} 528 529bool Camera3OutputStream::isVideoStream() const { 530 uint32_t usage = 0; 531 status_t res = getEndpointUsage(&usage); 532 if (res != OK) { 533 ALOGE("%s: getting end point usage failed: %s (%d).", __FUNCTION__, strerror(-res), res); 534 return false; 535 } 536 537 return (usage & GRALLOC_USAGE_HW_VIDEO_ENCODER) != 0; 538} 539 540status_t Camera3OutputStream::setBufferManager(sp<Camera3BufferManager> bufferManager) { 541 Mutex::Autolock l(mLock); 542 if (mState != STATE_CONSTRUCTED) { 543 ALOGE("%s: this method can only be called when stream in in CONSTRUCTED state.", 544 __FUNCTION__); 545 return INVALID_OPERATION; 546 } 547 mBufferManager = bufferManager; 548 549 return OK; 550} 551 552void Camera3OutputStream::BufferReleasedListener::onBufferReleased() { 553 sp<Camera3OutputStream> stream = mParent.promote(); 554 if (stream == nullptr) { 555 ALOGV("%s: Parent camera3 output stream was destroyed", __FUNCTION__); 556 return; 557 } 558 559 Mutex::Autolock l(stream->mLock); 560 if (!(stream->mUseBufferManager)) { 561 return; 562 } 563 564 sp<Fence> fence; 565 sp<GraphicBuffer> buffer; 566 int fenceFd = -1; 567 status_t res = stream->mConsumer->detachNextBuffer(&buffer, &fence); 568 if (res == NO_MEMORY) { 569 // This may rarely happen, which indicates that the released buffer was freed by other 570 // call (e.g., attachBuffer, dequeueBuffer etc.) before reaching here. We should notify the 571 // buffer manager that this buffer has been freed. It's not fatal, but should be avoided, 572 // therefore log a warning. 573 buffer = 0; 574 ALOGW("%s: the released buffer has already been freed by the buffer queue!", __FUNCTION__); 575 } else if (res != OK) { 576 // Other errors are fatal. 577 ALOGE("%s: detach next buffer failed: %s (%d).", __FUNCTION__, strerror(-res), res); 578 stream->mState = STATE_ERROR; 579 return; 580 } 581 582 if (fence!= 0 && fence->isValid()) { 583 fenceFd = fence->dup(); 584 } 585 res = stream->mBufferManager->returnBufferForStream(stream->getId(), stream->getStreamSetId(), 586 buffer, fenceFd); 587 if (res != OK) { 588 ALOGE("%s: return buffer to buffer manager failed: %s (%d).", __FUNCTION__, 589 strerror(-res), res); 590 stream->mState = STATE_ERROR; 591 } 592} 593 594bool Camera3OutputStream::isConsumedByHWComposer() const { 595 uint32_t usage = 0; 596 status_t res = getEndpointUsage(&usage); 597 if (res != OK) { 598 ALOGE("%s: getting end point usage failed: %s (%d).", __FUNCTION__, strerror(-res), res); 599 return false; 600 } 601 602 return (usage & GRALLOC_USAGE_HW_COMPOSER) != 0; 603} 604 605}; // namespace camera3 606 607}; // namespace android 608