StreamingProcessor.cpp revision 8cca0750a84c2d97224c0cfef7cf255308ee80b3
1/* 2 * Copyright (C) 2012 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 "Camera2-StreamingProcessor" 18#define ATRACE_TAG ATRACE_TAG_CAMERA 19//#define LOG_NDEBUG 0 20//#define LOG_NNDEBUG 0 // Per-frame verbose logging 21 22#ifdef LOG_NNDEBUG 23#define ALOGVV(...) ALOGV(__VA_ARGS__) 24#else 25#define ALOGVV(...) ((void)0) 26#endif 27 28#include <cutils/properties.h> 29#include <utils/Log.h> 30#include <utils/Trace.h> 31#include <gui/BufferItem.h> 32#include <gui/Surface.h> 33#include <media/hardware/HardwareAPI.h> 34 35#include "common/CameraDeviceBase.h" 36#include "api1/Camera2Client.h" 37#include "api1/client2/StreamingProcessor.h" 38#include "api1/client2/Camera2Heap.h" 39 40namespace android { 41namespace camera2 { 42 43StreamingProcessor::StreamingProcessor(sp<Camera2Client> client): 44 mClient(client), 45 mDevice(client->getCameraDevice()), 46 mId(client->getCameraId()), 47 mActiveRequest(NONE), 48 mPaused(false), 49 mPreviewRequestId(Camera2Client::kPreviewRequestIdStart), 50 mPreviewStreamId(NO_STREAM), 51 mRecordingRequestId(Camera2Client::kRecordingRequestIdStart), 52 mRecordingStreamId(NO_STREAM) 53{ 54} 55 56StreamingProcessor::~StreamingProcessor() { 57 deletePreviewStream(); 58 deleteRecordingStream(); 59} 60 61status_t StreamingProcessor::setPreviewWindow(sp<Surface> window) { 62 ATRACE_CALL(); 63 status_t res; 64 65 res = deletePreviewStream(); 66 if (res != OK) return res; 67 68 Mutex::Autolock m(mMutex); 69 70 mPreviewWindow = window; 71 72 return OK; 73} 74 75status_t StreamingProcessor::setRecordingWindow(sp<Surface> window) { 76 ATRACE_CALL(); 77 status_t res; 78 79 res = deleteRecordingStream(); 80 if (res != OK) return res; 81 82 Mutex::Autolock m(mMutex); 83 84 mRecordingWindow = window; 85 86 return OK; 87} 88 89bool StreamingProcessor::haveValidPreviewWindow() const { 90 Mutex::Autolock m(mMutex); 91 return mPreviewWindow != 0; 92} 93 94bool StreamingProcessor::haveValidRecordingWindow() const { 95 Mutex::Autolock m(mMutex); 96 return mRecordingWindow != nullptr; 97} 98 99status_t StreamingProcessor::updatePreviewRequest(const Parameters ¶ms) { 100 ATRACE_CALL(); 101 status_t res; 102 sp<CameraDeviceBase> device = mDevice.promote(); 103 if (device == 0) { 104 ALOGE("%s: Camera %d: Device does not exist", __FUNCTION__, mId); 105 return INVALID_OPERATION; 106 } 107 108 Mutex::Autolock m(mMutex); 109 if (mPreviewRequest.entryCount() == 0) { 110 sp<Camera2Client> client = mClient.promote(); 111 if (client == 0) { 112 ALOGE("%s: Camera %d: Client does not exist", __FUNCTION__, mId); 113 return INVALID_OPERATION; 114 } 115 116 // Use CAMERA3_TEMPLATE_ZERO_SHUTTER_LAG for ZSL streaming case. 117 if (client->getCameraDeviceVersion() >= CAMERA_DEVICE_API_VERSION_3_0) { 118 if (params.zslMode && !params.recordingHint) { 119 res = device->createDefaultRequest(CAMERA3_TEMPLATE_ZERO_SHUTTER_LAG, 120 &mPreviewRequest); 121 } else { 122 res = device->createDefaultRequest(CAMERA3_TEMPLATE_PREVIEW, 123 &mPreviewRequest); 124 } 125 } else { 126 res = device->createDefaultRequest(CAMERA2_TEMPLATE_PREVIEW, 127 &mPreviewRequest); 128 } 129 130 if (res != OK) { 131 ALOGE("%s: Camera %d: Unable to create default preview request: " 132 "%s (%d)", __FUNCTION__, mId, strerror(-res), res); 133 return res; 134 } 135 } 136 137 res = params.updateRequest(&mPreviewRequest); 138 if (res != OK) { 139 ALOGE("%s: Camera %d: Unable to update common entries of preview " 140 "request: %s (%d)", __FUNCTION__, mId, 141 strerror(-res), res); 142 return res; 143 } 144 145 res = mPreviewRequest.update(ANDROID_REQUEST_ID, 146 &mPreviewRequestId, 1); 147 if (res != OK) { 148 ALOGE("%s: Camera %d: Unable to update request id for preview: %s (%d)", 149 __FUNCTION__, mId, strerror(-res), res); 150 return res; 151 } 152 153 return OK; 154} 155 156status_t StreamingProcessor::updatePreviewStream(const Parameters ¶ms) { 157 ATRACE_CALL(); 158 Mutex::Autolock m(mMutex); 159 160 status_t res; 161 sp<CameraDeviceBase> device = mDevice.promote(); 162 if (device == 0) { 163 ALOGE("%s: Camera %d: Device does not exist", __FUNCTION__, mId); 164 return INVALID_OPERATION; 165 } 166 167 if (mPreviewStreamId != NO_STREAM) { 168 // Check if stream parameters have to change 169 uint32_t currentWidth, currentHeight; 170 res = device->getStreamInfo(mPreviewStreamId, 171 ¤tWidth, ¤tHeight, 0, 0); 172 if (res != OK) { 173 ALOGE("%s: Camera %d: Error querying preview stream info: " 174 "%s (%d)", __FUNCTION__, mId, strerror(-res), res); 175 return res; 176 } 177 if (currentWidth != (uint32_t)params.previewWidth || 178 currentHeight != (uint32_t)params.previewHeight) { 179 ALOGV("%s: Camera %d: Preview size switch: %d x %d -> %d x %d", 180 __FUNCTION__, mId, currentWidth, currentHeight, 181 params.previewWidth, params.previewHeight); 182 res = device->waitUntilDrained(); 183 if (res != OK) { 184 ALOGE("%s: Camera %d: Error waiting for preview to drain: " 185 "%s (%d)", __FUNCTION__, mId, strerror(-res), res); 186 return res; 187 } 188 res = device->deleteStream(mPreviewStreamId); 189 if (res != OK) { 190 ALOGE("%s: Camera %d: Unable to delete old output stream " 191 "for preview: %s (%d)", __FUNCTION__, mId, 192 strerror(-res), res); 193 return res; 194 } 195 mPreviewStreamId = NO_STREAM; 196 } 197 } 198 199 if (mPreviewStreamId == NO_STREAM) { 200 res = device->createStream(mPreviewWindow, 201 params.previewWidth, params.previewHeight, 202 CAMERA2_HAL_PIXEL_FORMAT_OPAQUE, HAL_DATASPACE_UNKNOWN, 203 CAMERA3_STREAM_ROTATION_0, &mPreviewStreamId); 204 if (res != OK) { 205 ALOGE("%s: Camera %d: Unable to create preview stream: %s (%d)", 206 __FUNCTION__, mId, strerror(-res), res); 207 return res; 208 } 209 } 210 211 res = device->setStreamTransform(mPreviewStreamId, 212 params.previewTransform); 213 if (res != OK) { 214 ALOGE("%s: Camera %d: Unable to set preview stream transform: " 215 "%s (%d)", __FUNCTION__, mId, strerror(-res), res); 216 return res; 217 } 218 219 return OK; 220} 221 222status_t StreamingProcessor::deletePreviewStream() { 223 ATRACE_CALL(); 224 status_t res; 225 226 Mutex::Autolock m(mMutex); 227 228 if (mPreviewStreamId != NO_STREAM) { 229 sp<CameraDeviceBase> device = mDevice.promote(); 230 if (device == 0) { 231 ALOGE("%s: Camera %d: Device does not exist", __FUNCTION__, mId); 232 return INVALID_OPERATION; 233 } 234 235 ALOGV("%s: for cameraId %d on streamId %d", 236 __FUNCTION__, mId, mPreviewStreamId); 237 238 res = device->waitUntilDrained(); 239 if (res != OK) { 240 ALOGE("%s: Error waiting for preview to drain: %s (%d)", 241 __FUNCTION__, strerror(-res), res); 242 return res; 243 } 244 res = device->deleteStream(mPreviewStreamId); 245 if (res != OK) { 246 ALOGE("%s: Unable to delete old preview stream: %s (%d)", 247 __FUNCTION__, strerror(-res), res); 248 return res; 249 } 250 mPreviewStreamId = NO_STREAM; 251 } 252 return OK; 253} 254 255int StreamingProcessor::getPreviewStreamId() const { 256 Mutex::Autolock m(mMutex); 257 return mPreviewStreamId; 258} 259 260status_t StreamingProcessor::updateRecordingRequest(const Parameters ¶ms) { 261 ATRACE_CALL(); 262 status_t res; 263 Mutex::Autolock m(mMutex); 264 265 sp<CameraDeviceBase> device = mDevice.promote(); 266 if (device == 0) { 267 ALOGE("%s: Camera %d: Device does not exist", __FUNCTION__, mId); 268 return INVALID_OPERATION; 269 } 270 271 if (mRecordingRequest.entryCount() == 0) { 272 res = device->createDefaultRequest(CAMERA2_TEMPLATE_VIDEO_RECORD, 273 &mRecordingRequest); 274 if (res != OK) { 275 ALOGE("%s: Camera %d: Unable to create default recording request:" 276 " %s (%d)", __FUNCTION__, mId, strerror(-res), res); 277 return res; 278 } 279 } 280 281 res = params.updateRequest(&mRecordingRequest); 282 if (res != OK) { 283 ALOGE("%s: Camera %d: Unable to update common entries of recording " 284 "request: %s (%d)", __FUNCTION__, mId, 285 strerror(-res), res); 286 return res; 287 } 288 289 res = mRecordingRequest.update(ANDROID_REQUEST_ID, 290 &mRecordingRequestId, 1); 291 if (res != OK) { 292 ALOGE("%s: Camera %d: Unable to update request id for request: %s (%d)", 293 __FUNCTION__, mId, strerror(-res), res); 294 return res; 295 } 296 297 return OK; 298} 299 300status_t StreamingProcessor::recordingStreamNeedsUpdate( 301 const Parameters ¶ms, bool *needsUpdate) { 302 status_t res; 303 304 if (needsUpdate == 0) { 305 ALOGE("%s: Camera %d: invalid argument", __FUNCTION__, mId); 306 return INVALID_OPERATION; 307 } 308 309 if (mRecordingStreamId == NO_STREAM) { 310 *needsUpdate = true; 311 return OK; 312 } 313 314 sp<CameraDeviceBase> device = mDevice.promote(); 315 if (device == 0) { 316 ALOGE("%s: Camera %d: Device does not exist", __FUNCTION__, mId); 317 return INVALID_OPERATION; 318 } 319 320 uint32_t currentWidth, currentHeight, currentFormat; 321 android_dataspace currentDataSpace; 322 res = device->getStreamInfo(mRecordingStreamId, 323 ¤tWidth, ¤tHeight, ¤tFormat, ¤tDataSpace); 324 if (res != OK) { 325 ALOGE("%s: Camera %d: Error querying recording output stream info: " 326 "%s (%d)", __FUNCTION__, mId, 327 strerror(-res), res); 328 return res; 329 } 330 331 if (mRecordingWindow == nullptr || 332 currentWidth != (uint32_t)params.videoWidth || 333 currentHeight != (uint32_t)params.videoHeight || 334 currentFormat != (uint32_t)params.videoFormat || 335 currentDataSpace != params.videoDataSpace) { 336 *needsUpdate = true; 337 } 338 *needsUpdate = false; 339 return res; 340} 341 342status_t StreamingProcessor::updateRecordingStream(const Parameters ¶ms) { 343 ATRACE_CALL(); 344 status_t res; 345 Mutex::Autolock m(mMutex); 346 347 sp<CameraDeviceBase> device = mDevice.promote(); 348 if (device == 0) { 349 ALOGE("%s: Camera %d: Device does not exist", __FUNCTION__, mId); 350 return INVALID_OPERATION; 351 } 352 353 if (mRecordingStreamId != NO_STREAM) { 354 // Check if stream parameters have to change 355 uint32_t currentWidth, currentHeight; 356 uint32_t currentFormat; 357 android_dataspace currentDataSpace; 358 res = device->getStreamInfo(mRecordingStreamId, 359 ¤tWidth, ¤tHeight, 360 ¤tFormat, ¤tDataSpace); 361 if (res != OK) { 362 ALOGE("%s: Camera %d: Error querying recording output stream info: " 363 "%s (%d)", __FUNCTION__, mId, 364 strerror(-res), res); 365 return res; 366 } 367 if (currentWidth != (uint32_t)params.videoWidth || 368 currentHeight != (uint32_t)params.videoHeight || 369 currentFormat != (uint32_t)params.videoFormat || 370 currentDataSpace != params.videoDataSpace) { 371 // TODO: Should wait to be sure previous recording has finished 372 res = device->deleteStream(mRecordingStreamId); 373 374 if (res == -EBUSY) { 375 ALOGV("%s: Camera %d: Device is busy, call " 376 "updateRecordingStream after it becomes idle", 377 __FUNCTION__, mId); 378 return res; 379 } else if (res != OK) { 380 ALOGE("%s: Camera %d: Unable to delete old output stream " 381 "for recording: %s (%d)", __FUNCTION__, 382 mId, strerror(-res), res); 383 return res; 384 } 385 mRecordingStreamId = NO_STREAM; 386 } 387 } 388 389 if (mRecordingStreamId == NO_STREAM) { 390 res = device->createStream(mRecordingWindow, 391 params.videoWidth, params.videoHeight, 392 params.videoFormat, params.videoDataSpace, 393 CAMERA3_STREAM_ROTATION_0, &mRecordingStreamId); 394 if (res != OK) { 395 ALOGE("%s: Camera %d: Can't create output stream for recording: " 396 "%s (%d)", __FUNCTION__, mId, 397 strerror(-res), res); 398 return res; 399 } 400 } 401 402 return OK; 403} 404 405status_t StreamingProcessor::deleteRecordingStream() { 406 ATRACE_CALL(); 407 status_t res; 408 409 Mutex::Autolock m(mMutex); 410 411 if (mRecordingStreamId != NO_STREAM) { 412 sp<CameraDeviceBase> device = mDevice.promote(); 413 if (device == 0) { 414 ALOGE("%s: Camera %d: Device does not exist", __FUNCTION__, mId); 415 return INVALID_OPERATION; 416 } 417 418 res = device->waitUntilDrained(); 419 if (res != OK) { 420 ALOGE("%s: Error waiting for HAL to drain: %s (%d)", 421 __FUNCTION__, strerror(-res), res); 422 return res; 423 } 424 res = device->deleteStream(mRecordingStreamId); 425 if (res != OK) { 426 ALOGE("%s: Unable to delete recording stream: %s (%d)", 427 __FUNCTION__, strerror(-res), res); 428 return res; 429 } 430 mRecordingStreamId = NO_STREAM; 431 } 432 return OK; 433} 434 435int StreamingProcessor::getRecordingStreamId() const { 436 return mRecordingStreamId; 437} 438 439status_t StreamingProcessor::startStream(StreamType type, 440 const Vector<int32_t> &outputStreams) { 441 ATRACE_CALL(); 442 status_t res; 443 444 if (type == NONE) return INVALID_OPERATION; 445 446 sp<CameraDeviceBase> device = mDevice.promote(); 447 if (device == 0) { 448 ALOGE("%s: Camera %d: Device does not exist", __FUNCTION__, mId); 449 return INVALID_OPERATION; 450 } 451 452 ALOGV("%s: Camera %d: type = %d", __FUNCTION__, mId, type); 453 454 Mutex::Autolock m(mMutex); 455 456 CameraMetadata &request = (type == PREVIEW) ? 457 mPreviewRequest : mRecordingRequest; 458 459 res = request.update( 460 ANDROID_REQUEST_OUTPUT_STREAMS, 461 outputStreams); 462 if (res != OK) { 463 ALOGE("%s: Camera %d: Unable to set up preview request: %s (%d)", 464 __FUNCTION__, mId, strerror(-res), res); 465 return res; 466 } 467 468 res = request.sort(); 469 if (res != OK) { 470 ALOGE("%s: Camera %d: Error sorting preview request: %s (%d)", 471 __FUNCTION__, mId, strerror(-res), res); 472 return res; 473 } 474 475 res = device->setStreamingRequest(request); 476 if (res != OK) { 477 ALOGE("%s: Camera %d: Unable to set preview request to start preview: " 478 "%s (%d)", 479 __FUNCTION__, mId, strerror(-res), res); 480 return res; 481 } 482 mActiveRequest = type; 483 mPaused = false; 484 mActiveStreamIds = outputStreams; 485 return OK; 486} 487 488status_t StreamingProcessor::togglePauseStream(bool pause) { 489 ATRACE_CALL(); 490 status_t res; 491 492 sp<CameraDeviceBase> device = mDevice.promote(); 493 if (device == 0) { 494 ALOGE("%s: Camera %d: Device does not exist", __FUNCTION__, mId); 495 return INVALID_OPERATION; 496 } 497 498 ALOGV("%s: Camera %d: toggling pause to %d", __FUNCTION__, mId, pause); 499 500 Mutex::Autolock m(mMutex); 501 502 if (mActiveRequest == NONE) { 503 ALOGE("%s: Camera %d: Can't toggle pause, streaming was not started", 504 __FUNCTION__, mId); 505 return INVALID_OPERATION; 506 } 507 508 if (mPaused == pause) { 509 return OK; 510 } 511 512 if (pause) { 513 res = device->clearStreamingRequest(); 514 if (res != OK) { 515 ALOGE("%s: Camera %d: Can't clear stream request: %s (%d)", 516 __FUNCTION__, mId, strerror(-res), res); 517 return res; 518 } 519 } else { 520 CameraMetadata &request = 521 (mActiveRequest == PREVIEW) ? mPreviewRequest 522 : mRecordingRequest; 523 res = device->setStreamingRequest(request); 524 if (res != OK) { 525 ALOGE("%s: Camera %d: Unable to set preview request to resume: " 526 "%s (%d)", 527 __FUNCTION__, mId, strerror(-res), res); 528 return res; 529 } 530 } 531 532 mPaused = pause; 533 return OK; 534} 535 536status_t StreamingProcessor::stopStream() { 537 ATRACE_CALL(); 538 status_t res; 539 540 Mutex::Autolock m(mMutex); 541 542 sp<CameraDeviceBase> device = mDevice.promote(); 543 if (device == 0) { 544 ALOGE("%s: Camera %d: Device does not exist", __FUNCTION__, mId); 545 return INVALID_OPERATION; 546 } 547 548 res = device->clearStreamingRequest(); 549 if (res != OK) { 550 ALOGE("%s: Camera %d: Can't clear stream request: %s (%d)", 551 __FUNCTION__, mId, strerror(-res), res); 552 return res; 553 } 554 555 mActiveRequest = NONE; 556 mActiveStreamIds.clear(); 557 mPaused = false; 558 559 return OK; 560} 561 562int32_t StreamingProcessor::getActiveRequestId() const { 563 Mutex::Autolock m(mMutex); 564 switch (mActiveRequest) { 565 case NONE: 566 return 0; 567 case PREVIEW: 568 return mPreviewRequestId; 569 case RECORD: 570 return mRecordingRequestId; 571 default: 572 ALOGE("%s: Unexpected mode %d", __FUNCTION__, mActiveRequest); 573 return 0; 574 } 575} 576 577status_t StreamingProcessor::incrementStreamingIds() { 578 ATRACE_CALL(); 579 Mutex::Autolock m(mMutex); 580 581 mPreviewRequestId++; 582 if (mPreviewRequestId >= Camera2Client::kPreviewRequestIdEnd) { 583 mPreviewRequestId = Camera2Client::kPreviewRequestIdStart; 584 } 585 mRecordingRequestId++; 586 if (mRecordingRequestId >= Camera2Client::kRecordingRequestIdEnd) { 587 mRecordingRequestId = Camera2Client::kRecordingRequestIdStart; 588 } 589 return OK; 590} 591 592status_t StreamingProcessor::dump(int fd, const Vector<String16>& /*args*/) { 593 String8 result; 594 595 result.append(" Current requests:\n"); 596 if (mPreviewRequest.entryCount() != 0) { 597 result.append(" Preview request:\n"); 598 write(fd, result.string(), result.size()); 599 mPreviewRequest.dump(fd, 2, 6); 600 result.clear(); 601 } else { 602 result.append(" Preview request: undefined\n"); 603 } 604 605 if (mRecordingRequest.entryCount() != 0) { 606 result = " Recording request:\n"; 607 write(fd, result.string(), result.size()); 608 mRecordingRequest.dump(fd, 2, 6); 609 result.clear(); 610 } else { 611 result = " Recording request: undefined\n"; 612 } 613 614 const char* streamTypeString[] = { 615 "none", "preview", "record" 616 }; 617 result.append(String8::format(" Active request: %s (paused: %s)\n", 618 streamTypeString[mActiveRequest], 619 mPaused ? "yes" : "no")); 620 621 write(fd, result.string(), result.size()); 622 623 return OK; 624} 625 626}; // namespace camera2 627}; // namespace android 628