1 /* 2 * Copyright (C) 2009 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_NDEBUG 0 18 #define LOG_TAG "OMXCodec" 19 #include <utils/Log.h> 20 21 #include "include/AACEncoder.h" 22 23 #include "include/ESDS.h" 24 25 #include <binder/IServiceManager.h> 26 #include <binder/MemoryDealer.h> 27 #include <binder/ProcessState.h> 28 #include <HardwareAPI.h> 29 #include <media/stagefright/foundation/ADebug.h> 30 #include <media/IMediaPlayerService.h> 31 #include <media/stagefright/MediaBuffer.h> 32 #include <media/stagefright/MediaBufferGroup.h> 33 #include <media/stagefright/MediaDefs.h> 34 #include <media/stagefright/MediaCodecList.h> 35 #include <media/stagefright/MediaExtractor.h> 36 #include <media/stagefright/MetaData.h> 37 #include <media/stagefright/OMXCodec.h> 38 #include <media/stagefright/Utils.h> 39 #include <media/stagefright/SkipCutBuffer.h> 40 #include <utils/Vector.h> 41 42 #include <OMX_Audio.h> 43 #include <OMX_Component.h> 44 45 #include "include/avc_utils.h" 46 47 namespace android { 48 49 // Treat time out as an error if we have not received any output 50 // buffers after 3 seconds. 51 const static int64_t kBufferFilledEventTimeOutNs = 3000000000LL; 52 53 // OMX Spec defines less than 50 color formats. If the query for 54 // color format is executed for more than kMaxColorFormatSupported, 55 // the query will fail to avoid looping forever. 56 // 1000 is more than enough for us to tell whether the omx 57 // component in question is buggy or not. 58 const static uint32_t kMaxColorFormatSupported = 1000; 59 60 #define FACTORY_CREATE_ENCODER(name) \ 61 static sp<MediaSource> Make##name(const sp<MediaSource> &source, const sp<MetaData> &meta) { \ 62 return new name(source, meta); \ 63 } 64 65 #define FACTORY_REF(name) { #name, Make##name }, 66 67 FACTORY_CREATE_ENCODER(AACEncoder) 68 69 static sp<MediaSource> InstantiateSoftwareEncoder( 70 const char *name, const sp<MediaSource> &source, 71 const sp<MetaData> &meta) { 72 struct FactoryInfo { 73 const char *name; 74 sp<MediaSource> (*CreateFunc)(const sp<MediaSource> &, const sp<MetaData> &); 75 }; 76 77 static const FactoryInfo kFactoryInfo[] = { 78 FACTORY_REF(AACEncoder) 79 }; 80 for (size_t i = 0; 81 i < sizeof(kFactoryInfo) / sizeof(kFactoryInfo[0]); ++i) { 82 if (!strcmp(name, kFactoryInfo[i].name)) { 83 return (*kFactoryInfo[i].CreateFunc)(source, meta); 84 } 85 } 86 87 return NULL; 88 } 89 90 #undef FACTORY_CREATE_ENCODER 91 #undef FACTORY_REF 92 93 #define CODEC_LOGI(x, ...) ALOGI("[%s] "x, mComponentName, ##__VA_ARGS__) 94 #define CODEC_LOGV(x, ...) ALOGV("[%s] "x, mComponentName, ##__VA_ARGS__) 95 #define CODEC_LOGE(x, ...) ALOGE("[%s] "x, mComponentName, ##__VA_ARGS__) 96 97 struct OMXCodecObserver : public BnOMXObserver { 98 OMXCodecObserver() { 99 } 100 101 void setCodec(const sp<OMXCodec> &target) { 102 mTarget = target; 103 } 104 105 // from IOMXObserver 106 virtual void onMessage(const omx_message &msg) { 107 sp<OMXCodec> codec = mTarget.promote(); 108 109 if (codec.get() != NULL) { 110 Mutex::Autolock autoLock(codec->mLock); 111 codec->on_message(msg); 112 codec.clear(); 113 } 114 } 115 116 protected: 117 virtual ~OMXCodecObserver() {} 118 119 private: 120 wp<OMXCodec> mTarget; 121 122 OMXCodecObserver(const OMXCodecObserver &); 123 OMXCodecObserver &operator=(const OMXCodecObserver &); 124 }; 125 126 template<class T> 127 static void InitOMXParams(T *params) { 128 params->nSize = sizeof(T); 129 params->nVersion.s.nVersionMajor = 1; 130 params->nVersion.s.nVersionMinor = 0; 131 params->nVersion.s.nRevision = 0; 132 params->nVersion.s.nStep = 0; 133 } 134 135 static bool IsSoftwareCodec(const char *componentName) { 136 if (!strncmp("OMX.google.", componentName, 11)) { 137 return true; 138 } 139 140 if (!strncmp("OMX.", componentName, 4)) { 141 return false; 142 } 143 144 return true; 145 } 146 147 // A sort order in which OMX software codecs are first, followed 148 // by other (non-OMX) software codecs, followed by everything else. 149 static int CompareSoftwareCodecsFirst( 150 const OMXCodec::CodecNameAndQuirks *elem1, 151 const OMXCodec::CodecNameAndQuirks *elem2) { 152 bool isOMX1 = !strncmp(elem1->mName.string(), "OMX.", 4); 153 bool isOMX2 = !strncmp(elem2->mName.string(), "OMX.", 4); 154 155 bool isSoftwareCodec1 = IsSoftwareCodec(elem1->mName.string()); 156 bool isSoftwareCodec2 = IsSoftwareCodec(elem2->mName.string()); 157 158 if (isSoftwareCodec1) { 159 if (!isSoftwareCodec2) { return -1; } 160 161 if (isOMX1) { 162 if (isOMX2) { return 0; } 163 164 return -1; 165 } else { 166 if (isOMX2) { return 0; } 167 168 return 1; 169 } 170 171 return -1; 172 } 173 174 if (isSoftwareCodec2) { 175 return 1; 176 } 177 178 return 0; 179 } 180 181 // static 182 void OMXCodec::findMatchingCodecs( 183 const char *mime, 184 bool createEncoder, const char *matchComponentName, 185 uint32_t flags, 186 Vector<CodecNameAndQuirks> *matchingCodecs) { 187 matchingCodecs->clear(); 188 189 const MediaCodecList *list = MediaCodecList::getInstance(); 190 if (list == NULL) { 191 return; 192 } 193 194 size_t index = 0; 195 for (;;) { 196 ssize_t matchIndex = 197 list->findCodecByType(mime, createEncoder, index); 198 199 if (matchIndex < 0) { 200 break; 201 } 202 203 index = matchIndex + 1; 204 205 const char *componentName = list->getCodecName(matchIndex); 206 207 // If a specific codec is requested, skip the non-matching ones. 208 if (matchComponentName && strcmp(componentName, matchComponentName)) { 209 continue; 210 } 211 212 // When requesting software-only codecs, only push software codecs 213 // When requesting hardware-only codecs, only push hardware codecs 214 // When there is request neither for software-only nor for 215 // hardware-only codecs, push all codecs 216 if (((flags & kSoftwareCodecsOnly) && IsSoftwareCodec(componentName)) || 217 ((flags & kHardwareCodecsOnly) && !IsSoftwareCodec(componentName)) || 218 (!(flags & (kSoftwareCodecsOnly | kHardwareCodecsOnly)))) { 219 220 ssize_t index = matchingCodecs->add(); 221 CodecNameAndQuirks *entry = &matchingCodecs->editItemAt(index); 222 entry->mName = String8(componentName); 223 entry->mQuirks = getComponentQuirks(list, matchIndex); 224 225 ALOGV("matching '%s' quirks 0x%08x", 226 entry->mName.string(), entry->mQuirks); 227 } 228 } 229 230 if (flags & kPreferSoftwareCodecs) { 231 matchingCodecs->sort(CompareSoftwareCodecsFirst); 232 } 233 } 234 235 // static 236 uint32_t OMXCodec::getComponentQuirks( 237 const MediaCodecList *list, size_t index) { 238 uint32_t quirks = 0; 239 if (list->codecHasQuirk( 240 index, "requires-allocate-on-input-ports")) { 241 quirks |= kRequiresAllocateBufferOnInputPorts; 242 } 243 if (list->codecHasQuirk( 244 index, "requires-allocate-on-output-ports")) { 245 quirks |= kRequiresAllocateBufferOnOutputPorts; 246 } 247 if (list->codecHasQuirk( 248 index, "output-buffers-are-unreadable")) { 249 quirks |= kOutputBuffersAreUnreadable; 250 } 251 252 return quirks; 253 } 254 255 // static 256 bool OMXCodec::findCodecQuirks(const char *componentName, uint32_t *quirks) { 257 const MediaCodecList *list = MediaCodecList::getInstance(); 258 259 if (list == NULL) { 260 return false; 261 } 262 263 ssize_t index = list->findCodecByName(componentName); 264 265 if (index < 0) { 266 return false; 267 } 268 269 *quirks = getComponentQuirks(list, index); 270 271 return true; 272 } 273 274 // static 275 sp<MediaSource> OMXCodec::Create( 276 const sp<IOMX> &omx, 277 const sp<MetaData> &meta, bool createEncoder, 278 const sp<MediaSource> &source, 279 const char *matchComponentName, 280 uint32_t flags, 281 const sp<ANativeWindow> &nativeWindow) { 282 int32_t requiresSecureBuffers; 283 if (source->getFormat()->findInt32( 284 kKeyRequiresSecureBuffers, 285 &requiresSecureBuffers) 286 && requiresSecureBuffers) { 287 flags |= kIgnoreCodecSpecificData; 288 flags |= kUseSecureInputBuffers; 289 } 290 291 const char *mime; 292 bool success = meta->findCString(kKeyMIMEType, &mime); 293 CHECK(success); 294 295 Vector<CodecNameAndQuirks> matchingCodecs; 296 findMatchingCodecs( 297 mime, createEncoder, matchComponentName, flags, &matchingCodecs); 298 299 if (matchingCodecs.isEmpty()) { 300 ALOGV("No matching codecs! (mime: %s, createEncoder: %s, " 301 "matchComponentName: %s, flags: 0x%x)", 302 mime, createEncoder ? "true" : "false", matchComponentName, flags); 303 return NULL; 304 } 305 306 sp<OMXCodecObserver> observer = new OMXCodecObserver; 307 IOMX::node_id node = 0; 308 309 for (size_t i = 0; i < matchingCodecs.size(); ++i) { 310 const char *componentNameBase = matchingCodecs[i].mName.string(); 311 uint32_t quirks = matchingCodecs[i].mQuirks; 312 const char *componentName = componentNameBase; 313 314 AString tmp; 315 if (flags & kUseSecureInputBuffers) { 316 tmp = componentNameBase; 317 tmp.append(".secure"); 318 319 componentName = tmp.c_str(); 320 } 321 322 if (createEncoder) { 323 sp<MediaSource> softwareCodec = 324 InstantiateSoftwareEncoder(componentName, source, meta); 325 326 if (softwareCodec != NULL) { 327 ALOGV("Successfully allocated software codec '%s'", componentName); 328 329 return softwareCodec; 330 } 331 } 332 333 ALOGV("Attempting to allocate OMX node '%s'", componentName); 334 335 if (!createEncoder 336 && (quirks & kOutputBuffersAreUnreadable) 337 && (flags & kClientNeedsFramebuffer)) { 338 if (strncmp(componentName, "OMX.SEC.", 8)) { 339 // For OMX.SEC.* decoders we can enable a special mode that 340 // gives the client access to the framebuffer contents. 341 342 ALOGW("Component '%s' does not give the client access to " 343 "the framebuffer contents. Skipping.", 344 componentName); 345 346 continue; 347 } 348 } 349 350 status_t err = omx->allocateNode(componentName, observer, &node); 351 if (err == OK) { 352 ALOGV("Successfully allocated OMX node '%s'", componentName); 353 354 sp<OMXCodec> codec = new OMXCodec( 355 omx, node, quirks, flags, 356 createEncoder, mime, componentName, 357 source, nativeWindow); 358 359 observer->setCodec(codec); 360 361 err = codec->configureCodec(meta); 362 363 if (err == OK) { 364 if (!strcmp("OMX.Nvidia.mpeg2v.decode", componentName)) { 365 codec->mFlags |= kOnlySubmitOneInputBufferAtOneTime; 366 } 367 368 return codec; 369 } 370 371 ALOGV("Failed to configure codec '%s'", componentName); 372 } 373 } 374 375 return NULL; 376 } 377 378 status_t OMXCodec::parseAVCCodecSpecificData( 379 const void *data, size_t size, 380 unsigned *profile, unsigned *level) { 381 const uint8_t *ptr = (const uint8_t *)data; 382 383 // verify minimum size and configurationVersion == 1. 384 if (size < 7 || ptr[0] != 1) { 385 return ERROR_MALFORMED; 386 } 387 388 *profile = ptr[1]; 389 *level = ptr[3]; 390 391 // There is decodable content out there that fails the following 392 // assertion, let's be lenient for now... 393 // CHECK((ptr[4] >> 2) == 0x3f); // reserved 394 395 size_t lengthSize = 1 + (ptr[4] & 3); 396 397 // commented out check below as H264_QVGA_500_NO_AUDIO.3gp 398 // violates it... 399 // CHECK((ptr[5] >> 5) == 7); // reserved 400 401 size_t numSeqParameterSets = ptr[5] & 31; 402 403 ptr += 6; 404 size -= 6; 405 406 for (size_t i = 0; i < numSeqParameterSets; ++i) { 407 if (size < 2) { 408 return ERROR_MALFORMED; 409 } 410 411 size_t length = U16_AT(ptr); 412 413 ptr += 2; 414 size -= 2; 415 416 if (size < length) { 417 return ERROR_MALFORMED; 418 } 419 420 addCodecSpecificData(ptr, length); 421 422 ptr += length; 423 size -= length; 424 } 425 426 if (size < 1) { 427 return ERROR_MALFORMED; 428 } 429 430 size_t numPictureParameterSets = *ptr; 431 ++ptr; 432 --size; 433 434 for (size_t i = 0; i < numPictureParameterSets; ++i) { 435 if (size < 2) { 436 return ERROR_MALFORMED; 437 } 438 439 size_t length = U16_AT(ptr); 440 441 ptr += 2; 442 size -= 2; 443 444 if (size < length) { 445 return ERROR_MALFORMED; 446 } 447 448 addCodecSpecificData(ptr, length); 449 450 ptr += length; 451 size -= length; 452 } 453 454 return OK; 455 } 456 457 status_t OMXCodec::configureCodec(const sp<MetaData> &meta) { 458 ALOGV("configureCodec protected=%d", 459 (mFlags & kEnableGrallocUsageProtected) ? 1 : 0); 460 461 if (!(mFlags & kIgnoreCodecSpecificData)) { 462 uint32_t type; 463 const void *data; 464 size_t size; 465 if (meta->findData(kKeyESDS, &type, &data, &size)) { 466 ESDS esds((const char *)data, size); 467 CHECK_EQ(esds.InitCheck(), (status_t)OK); 468 469 const void *codec_specific_data; 470 size_t codec_specific_data_size; 471 esds.getCodecSpecificInfo( 472 &codec_specific_data, &codec_specific_data_size); 473 474 addCodecSpecificData( 475 codec_specific_data, codec_specific_data_size); 476 } else if (meta->findData(kKeyAVCC, &type, &data, &size)) { 477 // Parse the AVCDecoderConfigurationRecord 478 479 unsigned profile, level; 480 status_t err; 481 if ((err = parseAVCCodecSpecificData( 482 data, size, &profile, &level)) != OK) { 483 ALOGE("Malformed AVC codec specific data."); 484 return err; 485 } 486 487 CODEC_LOGI( 488 "AVC profile = %u (%s), level = %u", 489 profile, AVCProfileToString(profile), level); 490 } else if (meta->findData(kKeyVorbisInfo, &type, &data, &size)) { 491 addCodecSpecificData(data, size); 492 493 CHECK(meta->findData(kKeyVorbisBooks, &type, &data, &size)); 494 addCodecSpecificData(data, size); 495 } 496 } 497 498 int32_t bitRate = 0; 499 if (mIsEncoder) { 500 CHECK(meta->findInt32(kKeyBitRate, &bitRate)); 501 } 502 if (!strcasecmp(MEDIA_MIMETYPE_AUDIO_AMR_NB, mMIME)) { 503 setAMRFormat(false /* isWAMR */, bitRate); 504 } else if (!strcasecmp(MEDIA_MIMETYPE_AUDIO_AMR_WB, mMIME)) { 505 setAMRFormat(true /* isWAMR */, bitRate); 506 } else if (!strcasecmp(MEDIA_MIMETYPE_AUDIO_AAC, mMIME)) { 507 int32_t numChannels, sampleRate, aacProfile; 508 CHECK(meta->findInt32(kKeyChannelCount, &numChannels)); 509 CHECK(meta->findInt32(kKeySampleRate, &sampleRate)); 510 511 if (!meta->findInt32(kKeyAACProfile, &aacProfile)) { 512 aacProfile = OMX_AUDIO_AACObjectNull; 513 } 514 515 int32_t isADTS; 516 if (!meta->findInt32(kKeyIsADTS, &isADTS)) { 517 isADTS = false; 518 } 519 520 status_t err = setAACFormat(numChannels, sampleRate, bitRate, aacProfile, isADTS); 521 if (err != OK) { 522 CODEC_LOGE("setAACFormat() failed (err = %d)", err); 523 return err; 524 } 525 } else if (!strcasecmp(MEDIA_MIMETYPE_AUDIO_MPEG, mMIME)) { 526 int32_t numChannels, sampleRate; 527 if (meta->findInt32(kKeyChannelCount, &numChannels) 528 && meta->findInt32(kKeySampleRate, &sampleRate)) { 529 // Since we did not always check for these, leave them optional 530 // and have the decoder figure it all out. 531 setRawAudioFormat( 532 mIsEncoder ? kPortIndexInput : kPortIndexOutput, 533 sampleRate, 534 numChannels); 535 } 536 } else if (!strcasecmp(MEDIA_MIMETYPE_AUDIO_G711_ALAW, mMIME) 537 || !strcasecmp(MEDIA_MIMETYPE_AUDIO_G711_MLAW, mMIME)) { 538 // These are PCM-like formats with a fixed sample rate but 539 // a variable number of channels. 540 541 int32_t numChannels; 542 CHECK(meta->findInt32(kKeyChannelCount, &numChannels)); 543 544 setG711Format(numChannels); 545 } else if (!strcasecmp(MEDIA_MIMETYPE_AUDIO_RAW, mMIME)) { 546 CHECK(!mIsEncoder); 547 548 int32_t numChannels, sampleRate; 549 CHECK(meta->findInt32(kKeyChannelCount, &numChannels)); 550 CHECK(meta->findInt32(kKeySampleRate, &sampleRate)); 551 552 setRawAudioFormat(kPortIndexInput, sampleRate, numChannels); 553 } 554 555 if (!strncasecmp(mMIME, "video/", 6)) { 556 557 if (mIsEncoder) { 558 setVideoInputFormat(mMIME, meta); 559 } else { 560 status_t err = setVideoOutputFormat( 561 mMIME, meta); 562 563 if (err != OK) { 564 return err; 565 } 566 } 567 } 568 569 int32_t maxInputSize; 570 if (meta->findInt32(kKeyMaxInputSize, &maxInputSize)) { 571 setMinBufferSize(kPortIndexInput, (OMX_U32)maxInputSize); 572 } 573 574 initOutputFormat(meta); 575 576 if ((mFlags & kClientNeedsFramebuffer) 577 && !strncmp(mComponentName, "OMX.SEC.", 8)) { 578 // This appears to no longer be needed??? 579 580 OMX_INDEXTYPE index; 581 582 status_t err = 583 mOMX->getExtensionIndex( 584 mNode, 585 "OMX.SEC.index.ThumbnailMode", 586 &index); 587 588 if (err != OK) { 589 return err; 590 } 591 592 OMX_BOOL enable = OMX_TRUE; 593 err = mOMX->setConfig(mNode, index, &enable, sizeof(enable)); 594 595 if (err != OK) { 596 CODEC_LOGE("setConfig('OMX.SEC.index.ThumbnailMode') " 597 "returned error 0x%08x", err); 598 599 return err; 600 } 601 602 mQuirks &= ~kOutputBuffersAreUnreadable; 603 } 604 605 if (mNativeWindow != NULL 606 && !mIsEncoder 607 && !strncasecmp(mMIME, "video/", 6) 608 && !strncmp(mComponentName, "OMX.", 4)) { 609 status_t err = initNativeWindow(); 610 if (err != OK) { 611 return err; 612 } 613 } 614 615 return OK; 616 } 617 618 void OMXCodec::setMinBufferSize(OMX_U32 portIndex, OMX_U32 size) { 619 OMX_PARAM_PORTDEFINITIONTYPE def; 620 InitOMXParams(&def); 621 def.nPortIndex = portIndex; 622 623 status_t err = mOMX->getParameter( 624 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 625 CHECK_EQ(err, (status_t)OK); 626 627 if ((portIndex == kPortIndexInput && (mQuirks & kInputBufferSizesAreBogus)) 628 || (def.nBufferSize < size)) { 629 def.nBufferSize = size; 630 } 631 632 err = mOMX->setParameter( 633 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 634 CHECK_EQ(err, (status_t)OK); 635 636 err = mOMX->getParameter( 637 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 638 CHECK_EQ(err, (status_t)OK); 639 640 // Make sure the setting actually stuck. 641 if (portIndex == kPortIndexInput 642 && (mQuirks & kInputBufferSizesAreBogus)) { 643 CHECK_EQ(def.nBufferSize, size); 644 } else { 645 CHECK(def.nBufferSize >= size); 646 } 647 } 648 649 status_t OMXCodec::setVideoPortFormatType( 650 OMX_U32 portIndex, 651 OMX_VIDEO_CODINGTYPE compressionFormat, 652 OMX_COLOR_FORMATTYPE colorFormat) { 653 OMX_VIDEO_PARAM_PORTFORMATTYPE format; 654 InitOMXParams(&format); 655 format.nPortIndex = portIndex; 656 format.nIndex = 0; 657 bool found = false; 658 659 OMX_U32 index = 0; 660 for (;;) { 661 format.nIndex = index; 662 status_t err = mOMX->getParameter( 663 mNode, OMX_IndexParamVideoPortFormat, 664 &format, sizeof(format)); 665 666 if (err != OK) { 667 return err; 668 } 669 670 // The following assertion is violated by TI's video decoder. 671 // CHECK_EQ(format.nIndex, index); 672 673 #if 1 674 CODEC_LOGV("portIndex: %ld, index: %ld, eCompressionFormat=%d eColorFormat=%d", 675 portIndex, 676 index, format.eCompressionFormat, format.eColorFormat); 677 #endif 678 679 if (format.eCompressionFormat == compressionFormat 680 && format.eColorFormat == colorFormat) { 681 found = true; 682 break; 683 } 684 685 ++index; 686 if (index >= kMaxColorFormatSupported) { 687 CODEC_LOGE("color format %d or compression format %d is not supported", 688 colorFormat, compressionFormat); 689 return UNKNOWN_ERROR; 690 } 691 } 692 693 if (!found) { 694 return UNKNOWN_ERROR; 695 } 696 697 CODEC_LOGV("found a match."); 698 status_t err = mOMX->setParameter( 699 mNode, OMX_IndexParamVideoPortFormat, 700 &format, sizeof(format)); 701 702 return err; 703 } 704 705 static size_t getFrameSize( 706 OMX_COLOR_FORMATTYPE colorFormat, int32_t width, int32_t height) { 707 switch (colorFormat) { 708 case OMX_COLOR_FormatYCbYCr: 709 case OMX_COLOR_FormatCbYCrY: 710 return width * height * 2; 711 712 case OMX_COLOR_FormatYUV420Planar: 713 case OMX_COLOR_FormatYUV420SemiPlanar: 714 case OMX_TI_COLOR_FormatYUV420PackedSemiPlanar: 715 /* 716 * FIXME: For the Opaque color format, the frame size does not 717 * need to be (w*h*3)/2. It just needs to 718 * be larger than certain minimum buffer size. However, 719 * currently, this opaque foramt has been tested only on 720 * YUV420 formats. If that is changed, then we need to revisit 721 * this part in the future 722 */ 723 case OMX_COLOR_FormatAndroidOpaque: 724 return (width * height * 3) / 2; 725 726 default: 727 CHECK(!"Should not be here. Unsupported color format."); 728 break; 729 } 730 } 731 732 status_t OMXCodec::findTargetColorFormat( 733 const sp<MetaData>& meta, OMX_COLOR_FORMATTYPE *colorFormat) { 734 ALOGV("findTargetColorFormat"); 735 CHECK(mIsEncoder); 736 737 *colorFormat = OMX_COLOR_FormatYUV420SemiPlanar; 738 int32_t targetColorFormat; 739 if (meta->findInt32(kKeyColorFormat, &targetColorFormat)) { 740 *colorFormat = (OMX_COLOR_FORMATTYPE) targetColorFormat; 741 } 742 743 // Check whether the target color format is supported. 744 return isColorFormatSupported(*colorFormat, kPortIndexInput); 745 } 746 747 status_t OMXCodec::isColorFormatSupported( 748 OMX_COLOR_FORMATTYPE colorFormat, int portIndex) { 749 ALOGV("isColorFormatSupported: %d", static_cast<int>(colorFormat)); 750 751 // Enumerate all the color formats supported by 752 // the omx component to see whether the given 753 // color format is supported. 754 OMX_VIDEO_PARAM_PORTFORMATTYPE portFormat; 755 InitOMXParams(&portFormat); 756 portFormat.nPortIndex = portIndex; 757 OMX_U32 index = 0; 758 portFormat.nIndex = index; 759 while (true) { 760 if (OMX_ErrorNone != mOMX->getParameter( 761 mNode, OMX_IndexParamVideoPortFormat, 762 &portFormat, sizeof(portFormat))) { 763 break; 764 } 765 // Make sure that omx component does not overwrite 766 // the incremented index (bug 2897413). 767 CHECK_EQ(index, portFormat.nIndex); 768 if (portFormat.eColorFormat == colorFormat) { 769 CODEC_LOGV("Found supported color format: %d", portFormat.eColorFormat); 770 return OK; // colorFormat is supported! 771 } 772 ++index; 773 portFormat.nIndex = index; 774 775 if (index >= kMaxColorFormatSupported) { 776 CODEC_LOGE("More than %ld color formats are supported???", index); 777 break; 778 } 779 } 780 781 CODEC_LOGE("color format %d is not supported", colorFormat); 782 return UNKNOWN_ERROR; 783 } 784 785 void OMXCodec::setVideoInputFormat( 786 const char *mime, const sp<MetaData>& meta) { 787 788 int32_t width, height, frameRate, bitRate, stride, sliceHeight; 789 bool success = meta->findInt32(kKeyWidth, &width); 790 success = success && meta->findInt32(kKeyHeight, &height); 791 success = success && meta->findInt32(kKeyFrameRate, &frameRate); 792 success = success && meta->findInt32(kKeyBitRate, &bitRate); 793 success = success && meta->findInt32(kKeyStride, &stride); 794 success = success && meta->findInt32(kKeySliceHeight, &sliceHeight); 795 CHECK(success); 796 CHECK(stride != 0); 797 798 OMX_VIDEO_CODINGTYPE compressionFormat = OMX_VIDEO_CodingUnused; 799 if (!strcasecmp(MEDIA_MIMETYPE_VIDEO_AVC, mime)) { 800 compressionFormat = OMX_VIDEO_CodingAVC; 801 } else if (!strcasecmp(MEDIA_MIMETYPE_VIDEO_MPEG4, mime)) { 802 compressionFormat = OMX_VIDEO_CodingMPEG4; 803 } else if (!strcasecmp(MEDIA_MIMETYPE_VIDEO_H263, mime)) { 804 compressionFormat = OMX_VIDEO_CodingH263; 805 } else { 806 ALOGE("Not a supported video mime type: %s", mime); 807 CHECK(!"Should not be here. Not a supported video mime type."); 808 } 809 810 OMX_COLOR_FORMATTYPE colorFormat; 811 CHECK_EQ((status_t)OK, findTargetColorFormat(meta, &colorFormat)); 812 813 status_t err; 814 OMX_PARAM_PORTDEFINITIONTYPE def; 815 OMX_VIDEO_PORTDEFINITIONTYPE *video_def = &def.format.video; 816 817 //////////////////////// Input port ///////////////////////// 818 CHECK_EQ(setVideoPortFormatType( 819 kPortIndexInput, OMX_VIDEO_CodingUnused, 820 colorFormat), (status_t)OK); 821 822 InitOMXParams(&def); 823 def.nPortIndex = kPortIndexInput; 824 825 err = mOMX->getParameter( 826 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 827 CHECK_EQ(err, (status_t)OK); 828 829 def.nBufferSize = getFrameSize(colorFormat, 830 stride > 0? stride: -stride, sliceHeight); 831 832 CHECK_EQ((int)def.eDomain, (int)OMX_PortDomainVideo); 833 834 video_def->nFrameWidth = width; 835 video_def->nFrameHeight = height; 836 video_def->nStride = stride; 837 video_def->nSliceHeight = sliceHeight; 838 video_def->xFramerate = (frameRate << 16); // Q16 format 839 video_def->eCompressionFormat = OMX_VIDEO_CodingUnused; 840 video_def->eColorFormat = colorFormat; 841 842 err = mOMX->setParameter( 843 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 844 CHECK_EQ(err, (status_t)OK); 845 846 //////////////////////// Output port ///////////////////////// 847 CHECK_EQ(setVideoPortFormatType( 848 kPortIndexOutput, compressionFormat, OMX_COLOR_FormatUnused), 849 (status_t)OK); 850 InitOMXParams(&def); 851 def.nPortIndex = kPortIndexOutput; 852 853 err = mOMX->getParameter( 854 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 855 856 CHECK_EQ(err, (status_t)OK); 857 CHECK_EQ((int)def.eDomain, (int)OMX_PortDomainVideo); 858 859 video_def->nFrameWidth = width; 860 video_def->nFrameHeight = height; 861 video_def->xFramerate = 0; // No need for output port 862 video_def->nBitrate = bitRate; // Q16 format 863 video_def->eCompressionFormat = compressionFormat; 864 video_def->eColorFormat = OMX_COLOR_FormatUnused; 865 if (mQuirks & kRequiresLargerEncoderOutputBuffer) { 866 // Increases the output buffer size 867 def.nBufferSize = ((def.nBufferSize * 3) >> 1); 868 } 869 870 err = mOMX->setParameter( 871 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 872 CHECK_EQ(err, (status_t)OK); 873 874 /////////////////// Codec-specific //////////////////////// 875 switch (compressionFormat) { 876 case OMX_VIDEO_CodingMPEG4: 877 { 878 CHECK_EQ(setupMPEG4EncoderParameters(meta), (status_t)OK); 879 break; 880 } 881 882 case OMX_VIDEO_CodingH263: 883 CHECK_EQ(setupH263EncoderParameters(meta), (status_t)OK); 884 break; 885 886 case OMX_VIDEO_CodingAVC: 887 { 888 CHECK_EQ(setupAVCEncoderParameters(meta), (status_t)OK); 889 break; 890 } 891 892 default: 893 CHECK(!"Support for this compressionFormat to be implemented."); 894 break; 895 } 896 } 897 898 static OMX_U32 setPFramesSpacing(int32_t iFramesInterval, int32_t frameRate) { 899 if (iFramesInterval < 0) { 900 return 0xFFFFFFFF; 901 } else if (iFramesInterval == 0) { 902 return 0; 903 } 904 OMX_U32 ret = frameRate * iFramesInterval - 1; 905 CHECK(ret > 1); 906 return ret; 907 } 908 909 status_t OMXCodec::setupErrorCorrectionParameters() { 910 OMX_VIDEO_PARAM_ERRORCORRECTIONTYPE errorCorrectionType; 911 InitOMXParams(&errorCorrectionType); 912 errorCorrectionType.nPortIndex = kPortIndexOutput; 913 914 status_t err = mOMX->getParameter( 915 mNode, OMX_IndexParamVideoErrorCorrection, 916 &errorCorrectionType, sizeof(errorCorrectionType)); 917 if (err != OK) { 918 ALOGW("Error correction param query is not supported"); 919 return OK; // Optional feature. Ignore this failure 920 } 921 922 errorCorrectionType.bEnableHEC = OMX_FALSE; 923 errorCorrectionType.bEnableResync = OMX_TRUE; 924 errorCorrectionType.nResynchMarkerSpacing = 256; 925 errorCorrectionType.bEnableDataPartitioning = OMX_FALSE; 926 errorCorrectionType.bEnableRVLC = OMX_FALSE; 927 928 err = mOMX->setParameter( 929 mNode, OMX_IndexParamVideoErrorCorrection, 930 &errorCorrectionType, sizeof(errorCorrectionType)); 931 if (err != OK) { 932 ALOGW("Error correction param configuration is not supported"); 933 } 934 935 // Optional feature. Ignore the failure. 936 return OK; 937 } 938 939 status_t OMXCodec::setupBitRate(int32_t bitRate) { 940 OMX_VIDEO_PARAM_BITRATETYPE bitrateType; 941 InitOMXParams(&bitrateType); 942 bitrateType.nPortIndex = kPortIndexOutput; 943 944 status_t err = mOMX->getParameter( 945 mNode, OMX_IndexParamVideoBitrate, 946 &bitrateType, sizeof(bitrateType)); 947 CHECK_EQ(err, (status_t)OK); 948 949 bitrateType.eControlRate = OMX_Video_ControlRateVariable; 950 bitrateType.nTargetBitrate = bitRate; 951 952 err = mOMX->setParameter( 953 mNode, OMX_IndexParamVideoBitrate, 954 &bitrateType, sizeof(bitrateType)); 955 CHECK_EQ(err, (status_t)OK); 956 return OK; 957 } 958 959 status_t OMXCodec::getVideoProfileLevel( 960 const sp<MetaData>& meta, 961 const CodecProfileLevel& defaultProfileLevel, 962 CodecProfileLevel &profileLevel) { 963 CODEC_LOGV("Default profile: %ld, level %ld", 964 defaultProfileLevel.mProfile, defaultProfileLevel.mLevel); 965 966 // Are the default profile and level overwriten? 967 int32_t profile, level; 968 if (!meta->findInt32(kKeyVideoProfile, &profile)) { 969 profile = defaultProfileLevel.mProfile; 970 } 971 if (!meta->findInt32(kKeyVideoLevel, &level)) { 972 level = defaultProfileLevel.mLevel; 973 } 974 CODEC_LOGV("Target profile: %d, level: %d", profile, level); 975 976 // Are the target profile and level supported by the encoder? 977 OMX_VIDEO_PARAM_PROFILELEVELTYPE param; 978 InitOMXParams(¶m); 979 param.nPortIndex = kPortIndexOutput; 980 for (param.nProfileIndex = 0;; ++param.nProfileIndex) { 981 status_t err = mOMX->getParameter( 982 mNode, OMX_IndexParamVideoProfileLevelQuerySupported, 983 ¶m, sizeof(param)); 984 985 if (err != OK) break; 986 987 int32_t supportedProfile = static_cast<int32_t>(param.eProfile); 988 int32_t supportedLevel = static_cast<int32_t>(param.eLevel); 989 CODEC_LOGV("Supported profile: %d, level %d", 990 supportedProfile, supportedLevel); 991 992 if (profile == supportedProfile && 993 level <= supportedLevel) { 994 // We can further check whether the level is a valid 995 // value; but we will leave that to the omx encoder component 996 // via OMX_SetParameter call. 997 profileLevel.mProfile = profile; 998 profileLevel.mLevel = level; 999 return OK; 1000 } 1001 } 1002 1003 CODEC_LOGE("Target profile (%d) and level (%d) is not supported", 1004 profile, level); 1005 return BAD_VALUE; 1006 } 1007 1008 status_t OMXCodec::setupH263EncoderParameters(const sp<MetaData>& meta) { 1009 int32_t iFramesInterval, frameRate, bitRate; 1010 bool success = meta->findInt32(kKeyBitRate, &bitRate); 1011 success = success && meta->findInt32(kKeyFrameRate, &frameRate); 1012 success = success && meta->findInt32(kKeyIFramesInterval, &iFramesInterval); 1013 CHECK(success); 1014 OMX_VIDEO_PARAM_H263TYPE h263type; 1015 InitOMXParams(&h263type); 1016 h263type.nPortIndex = kPortIndexOutput; 1017 1018 status_t err = mOMX->getParameter( 1019 mNode, OMX_IndexParamVideoH263, &h263type, sizeof(h263type)); 1020 CHECK_EQ(err, (status_t)OK); 1021 1022 h263type.nAllowedPictureTypes = 1023 OMX_VIDEO_PictureTypeI | OMX_VIDEO_PictureTypeP; 1024 1025 h263type.nPFrames = setPFramesSpacing(iFramesInterval, frameRate); 1026 if (h263type.nPFrames == 0) { 1027 h263type.nAllowedPictureTypes = OMX_VIDEO_PictureTypeI; 1028 } 1029 h263type.nBFrames = 0; 1030 1031 // Check profile and level parameters 1032 CodecProfileLevel defaultProfileLevel, profileLevel; 1033 defaultProfileLevel.mProfile = h263type.eProfile; 1034 defaultProfileLevel.mLevel = h263type.eLevel; 1035 err = getVideoProfileLevel(meta, defaultProfileLevel, profileLevel); 1036 if (err != OK) return err; 1037 h263type.eProfile = static_cast<OMX_VIDEO_H263PROFILETYPE>(profileLevel.mProfile); 1038 h263type.eLevel = static_cast<OMX_VIDEO_H263LEVELTYPE>(profileLevel.mLevel); 1039 1040 h263type.bPLUSPTYPEAllowed = OMX_FALSE; 1041 h263type.bForceRoundingTypeToZero = OMX_FALSE; 1042 h263type.nPictureHeaderRepetition = 0; 1043 h263type.nGOBHeaderInterval = 0; 1044 1045 err = mOMX->setParameter( 1046 mNode, OMX_IndexParamVideoH263, &h263type, sizeof(h263type)); 1047 CHECK_EQ(err, (status_t)OK); 1048 1049 CHECK_EQ(setupBitRate(bitRate), (status_t)OK); 1050 CHECK_EQ(setupErrorCorrectionParameters(), (status_t)OK); 1051 1052 return OK; 1053 } 1054 1055 status_t OMXCodec::setupMPEG4EncoderParameters(const sp<MetaData>& meta) { 1056 int32_t iFramesInterval, frameRate, bitRate; 1057 bool success = meta->findInt32(kKeyBitRate, &bitRate); 1058 success = success && meta->findInt32(kKeyFrameRate, &frameRate); 1059 success = success && meta->findInt32(kKeyIFramesInterval, &iFramesInterval); 1060 CHECK(success); 1061 OMX_VIDEO_PARAM_MPEG4TYPE mpeg4type; 1062 InitOMXParams(&mpeg4type); 1063 mpeg4type.nPortIndex = kPortIndexOutput; 1064 1065 status_t err = mOMX->getParameter( 1066 mNode, OMX_IndexParamVideoMpeg4, &mpeg4type, sizeof(mpeg4type)); 1067 CHECK_EQ(err, (status_t)OK); 1068 1069 mpeg4type.nSliceHeaderSpacing = 0; 1070 mpeg4type.bSVH = OMX_FALSE; 1071 mpeg4type.bGov = OMX_FALSE; 1072 1073 mpeg4type.nAllowedPictureTypes = 1074 OMX_VIDEO_PictureTypeI | OMX_VIDEO_PictureTypeP; 1075 1076 mpeg4type.nPFrames = setPFramesSpacing(iFramesInterval, frameRate); 1077 if (mpeg4type.nPFrames == 0) { 1078 mpeg4type.nAllowedPictureTypes = OMX_VIDEO_PictureTypeI; 1079 } 1080 mpeg4type.nBFrames = 0; 1081 mpeg4type.nIDCVLCThreshold = 0; 1082 mpeg4type.bACPred = OMX_TRUE; 1083 mpeg4type.nMaxPacketSize = 256; 1084 mpeg4type.nTimeIncRes = 1000; 1085 mpeg4type.nHeaderExtension = 0; 1086 mpeg4type.bReversibleVLC = OMX_FALSE; 1087 1088 // Check profile and level parameters 1089 CodecProfileLevel defaultProfileLevel, profileLevel; 1090 defaultProfileLevel.mProfile = mpeg4type.eProfile; 1091 defaultProfileLevel.mLevel = mpeg4type.eLevel; 1092 err = getVideoProfileLevel(meta, defaultProfileLevel, profileLevel); 1093 if (err != OK) return err; 1094 mpeg4type.eProfile = static_cast<OMX_VIDEO_MPEG4PROFILETYPE>(profileLevel.mProfile); 1095 mpeg4type.eLevel = static_cast<OMX_VIDEO_MPEG4LEVELTYPE>(profileLevel.mLevel); 1096 1097 err = mOMX->setParameter( 1098 mNode, OMX_IndexParamVideoMpeg4, &mpeg4type, sizeof(mpeg4type)); 1099 CHECK_EQ(err, (status_t)OK); 1100 1101 CHECK_EQ(setupBitRate(bitRate), (status_t)OK); 1102 CHECK_EQ(setupErrorCorrectionParameters(), (status_t)OK); 1103 1104 return OK; 1105 } 1106 1107 status_t OMXCodec::setupAVCEncoderParameters(const sp<MetaData>& meta) { 1108 int32_t iFramesInterval, frameRate, bitRate; 1109 bool success = meta->findInt32(kKeyBitRate, &bitRate); 1110 success = success && meta->findInt32(kKeyFrameRate, &frameRate); 1111 success = success && meta->findInt32(kKeyIFramesInterval, &iFramesInterval); 1112 CHECK(success); 1113 1114 OMX_VIDEO_PARAM_AVCTYPE h264type; 1115 InitOMXParams(&h264type); 1116 h264type.nPortIndex = kPortIndexOutput; 1117 1118 status_t err = mOMX->getParameter( 1119 mNode, OMX_IndexParamVideoAvc, &h264type, sizeof(h264type)); 1120 CHECK_EQ(err, (status_t)OK); 1121 1122 h264type.nAllowedPictureTypes = 1123 OMX_VIDEO_PictureTypeI | OMX_VIDEO_PictureTypeP; 1124 1125 // Check profile and level parameters 1126 CodecProfileLevel defaultProfileLevel, profileLevel; 1127 defaultProfileLevel.mProfile = h264type.eProfile; 1128 defaultProfileLevel.mLevel = h264type.eLevel; 1129 err = getVideoProfileLevel(meta, defaultProfileLevel, profileLevel); 1130 if (err != OK) return err; 1131 h264type.eProfile = static_cast<OMX_VIDEO_AVCPROFILETYPE>(profileLevel.mProfile); 1132 h264type.eLevel = static_cast<OMX_VIDEO_AVCLEVELTYPE>(profileLevel.mLevel); 1133 1134 // XXX 1135 if (h264type.eProfile != OMX_VIDEO_AVCProfileBaseline) { 1136 ALOGW("Use baseline profile instead of %d for AVC recording", 1137 h264type.eProfile); 1138 h264type.eProfile = OMX_VIDEO_AVCProfileBaseline; 1139 } 1140 1141 if (h264type.eProfile == OMX_VIDEO_AVCProfileBaseline) { 1142 h264type.nSliceHeaderSpacing = 0; 1143 h264type.bUseHadamard = OMX_TRUE; 1144 h264type.nRefFrames = 1; 1145 h264type.nBFrames = 0; 1146 h264type.nPFrames = setPFramesSpacing(iFramesInterval, frameRate); 1147 if (h264type.nPFrames == 0) { 1148 h264type.nAllowedPictureTypes = OMX_VIDEO_PictureTypeI; 1149 } 1150 h264type.nRefIdx10ActiveMinus1 = 0; 1151 h264type.nRefIdx11ActiveMinus1 = 0; 1152 h264type.bEntropyCodingCABAC = OMX_FALSE; 1153 h264type.bWeightedPPrediction = OMX_FALSE; 1154 h264type.bconstIpred = OMX_FALSE; 1155 h264type.bDirect8x8Inference = OMX_FALSE; 1156 h264type.bDirectSpatialTemporal = OMX_FALSE; 1157 h264type.nCabacInitIdc = 0; 1158 } 1159 1160 if (h264type.nBFrames != 0) { 1161 h264type.nAllowedPictureTypes |= OMX_VIDEO_PictureTypeB; 1162 } 1163 1164 h264type.bEnableUEP = OMX_FALSE; 1165 h264type.bEnableFMO = OMX_FALSE; 1166 h264type.bEnableASO = OMX_FALSE; 1167 h264type.bEnableRS = OMX_FALSE; 1168 h264type.bFrameMBsOnly = OMX_TRUE; 1169 h264type.bMBAFF = OMX_FALSE; 1170 h264type.eLoopFilterMode = OMX_VIDEO_AVCLoopFilterEnable; 1171 1172 err = mOMX->setParameter( 1173 mNode, OMX_IndexParamVideoAvc, &h264type, sizeof(h264type)); 1174 CHECK_EQ(err, (status_t)OK); 1175 1176 CHECK_EQ(setupBitRate(bitRate), (status_t)OK); 1177 1178 return OK; 1179 } 1180 1181 status_t OMXCodec::setVideoOutputFormat( 1182 const char *mime, const sp<MetaData>& meta) { 1183 1184 int32_t width, height; 1185 bool success = meta->findInt32(kKeyWidth, &width); 1186 success = success && meta->findInt32(kKeyHeight, &height); 1187 CHECK(success); 1188 1189 CODEC_LOGV("setVideoOutputFormat width=%ld, height=%ld", width, height); 1190 1191 OMX_VIDEO_CODINGTYPE compressionFormat = OMX_VIDEO_CodingUnused; 1192 if (!strcasecmp(MEDIA_MIMETYPE_VIDEO_AVC, mime)) { 1193 compressionFormat = OMX_VIDEO_CodingAVC; 1194 } else if (!strcasecmp(MEDIA_MIMETYPE_VIDEO_MPEG4, mime)) { 1195 compressionFormat = OMX_VIDEO_CodingMPEG4; 1196 } else if (!strcasecmp(MEDIA_MIMETYPE_VIDEO_H263, mime)) { 1197 compressionFormat = OMX_VIDEO_CodingH263; 1198 } else if (!strcasecmp(MEDIA_MIMETYPE_VIDEO_VP8, mime)) { 1199 compressionFormat = OMX_VIDEO_CodingVP8; 1200 } else if (!strcasecmp(MEDIA_MIMETYPE_VIDEO_VP9, mime)) { 1201 compressionFormat = OMX_VIDEO_CodingVP9; 1202 } else if (!strcasecmp(MEDIA_MIMETYPE_VIDEO_MPEG2, mime)) { 1203 compressionFormat = OMX_VIDEO_CodingMPEG2; 1204 } else { 1205 ALOGE("Not a supported video mime type: %s", mime); 1206 CHECK(!"Should not be here. Not a supported video mime type."); 1207 } 1208 1209 status_t err = setVideoPortFormatType( 1210 kPortIndexInput, compressionFormat, OMX_COLOR_FormatUnused); 1211 1212 if (err != OK) { 1213 return err; 1214 } 1215 1216 #if 1 1217 { 1218 OMX_VIDEO_PARAM_PORTFORMATTYPE format; 1219 InitOMXParams(&format); 1220 format.nPortIndex = kPortIndexOutput; 1221 format.nIndex = 0; 1222 1223 status_t err = mOMX->getParameter( 1224 mNode, OMX_IndexParamVideoPortFormat, 1225 &format, sizeof(format)); 1226 CHECK_EQ(err, (status_t)OK); 1227 CHECK_EQ((int)format.eCompressionFormat, (int)OMX_VIDEO_CodingUnused); 1228 1229 int32_t colorFormat; 1230 if (meta->findInt32(kKeyColorFormat, &colorFormat) 1231 && colorFormat != OMX_COLOR_FormatUnused 1232 && colorFormat != format.eColorFormat) { 1233 1234 while (OMX_ErrorNoMore != err) { 1235 format.nIndex++; 1236 err = mOMX->getParameter( 1237 mNode, OMX_IndexParamVideoPortFormat, 1238 &format, sizeof(format)); 1239 if (format.eColorFormat == colorFormat) { 1240 break; 1241 } 1242 } 1243 if (format.eColorFormat != colorFormat) { 1244 CODEC_LOGE("Color format %d is not supported", colorFormat); 1245 return ERROR_UNSUPPORTED; 1246 } 1247 } 1248 1249 err = mOMX->setParameter( 1250 mNode, OMX_IndexParamVideoPortFormat, 1251 &format, sizeof(format)); 1252 1253 if (err != OK) { 1254 return err; 1255 } 1256 } 1257 #endif 1258 1259 OMX_PARAM_PORTDEFINITIONTYPE def; 1260 InitOMXParams(&def); 1261 def.nPortIndex = kPortIndexInput; 1262 1263 OMX_VIDEO_PORTDEFINITIONTYPE *video_def = &def.format.video; 1264 1265 err = mOMX->getParameter( 1266 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 1267 1268 CHECK_EQ(err, (status_t)OK); 1269 1270 #if 1 1271 // XXX Need a (much) better heuristic to compute input buffer sizes. 1272 const size_t X = 64 * 1024; 1273 if (def.nBufferSize < X) { 1274 def.nBufferSize = X; 1275 } 1276 #endif 1277 1278 CHECK_EQ((int)def.eDomain, (int)OMX_PortDomainVideo); 1279 1280 video_def->nFrameWidth = width; 1281 video_def->nFrameHeight = height; 1282 1283 video_def->eCompressionFormat = compressionFormat; 1284 video_def->eColorFormat = OMX_COLOR_FormatUnused; 1285 1286 err = mOMX->setParameter( 1287 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 1288 1289 if (err != OK) { 1290 return err; 1291 } 1292 1293 //////////////////////////////////////////////////////////////////////////// 1294 1295 InitOMXParams(&def); 1296 def.nPortIndex = kPortIndexOutput; 1297 1298 err = mOMX->getParameter( 1299 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 1300 CHECK_EQ(err, (status_t)OK); 1301 CHECK_EQ((int)def.eDomain, (int)OMX_PortDomainVideo); 1302 1303 #if 0 1304 def.nBufferSize = 1305 (((width + 15) & -16) * ((height + 15) & -16) * 3) / 2; // YUV420 1306 #endif 1307 1308 video_def->nFrameWidth = width; 1309 video_def->nFrameHeight = height; 1310 1311 err = mOMX->setParameter( 1312 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 1313 1314 return err; 1315 } 1316 1317 OMXCodec::OMXCodec( 1318 const sp<IOMX> &omx, IOMX::node_id node, 1319 uint32_t quirks, uint32_t flags, 1320 bool isEncoder, 1321 const char *mime, 1322 const char *componentName, 1323 const sp<MediaSource> &source, 1324 const sp<ANativeWindow> &nativeWindow) 1325 : mOMX(omx), 1326 mOMXLivesLocally(omx->livesLocally(node, getpid())), 1327 mNode(node), 1328 mQuirks(quirks), 1329 mFlags(flags), 1330 mIsEncoder(isEncoder), 1331 mIsVideo(!strncasecmp("video/", mime, 6)), 1332 mMIME(strdup(mime)), 1333 mComponentName(strdup(componentName)), 1334 mSource(source), 1335 mCodecSpecificDataIndex(0), 1336 mState(LOADED), 1337 mInitialBufferSubmit(true), 1338 mSignalledEOS(false), 1339 mNoMoreOutputData(false), 1340 mOutputPortSettingsHaveChanged(false), 1341 mSeekTimeUs(-1), 1342 mSeekMode(ReadOptions::SEEK_CLOSEST_SYNC), 1343 mTargetTimeUs(-1), 1344 mOutputPortSettingsChangedPending(false), 1345 mSkipCutBuffer(NULL), 1346 mLeftOverBuffer(NULL), 1347 mPaused(false), 1348 mNativeWindow( 1349 (!strncmp(componentName, "OMX.google.", 11) 1350 || !strcmp(componentName, "OMX.Nvidia.mpeg2v.decode")) 1351 ? NULL : nativeWindow) { 1352 mPortStatus[kPortIndexInput] = ENABLED; 1353 mPortStatus[kPortIndexOutput] = ENABLED; 1354 1355 setComponentRole(); 1356 } 1357 1358 // static 1359 void OMXCodec::setComponentRole( 1360 const sp<IOMX> &omx, IOMX::node_id node, bool isEncoder, 1361 const char *mime) { 1362 struct MimeToRole { 1363 const char *mime; 1364 const char *decoderRole; 1365 const char *encoderRole; 1366 }; 1367 1368 static const MimeToRole kMimeToRole[] = { 1369 { MEDIA_MIMETYPE_AUDIO_MPEG, 1370 "audio_decoder.mp3", "audio_encoder.mp3" }, 1371 { MEDIA_MIMETYPE_AUDIO_MPEG_LAYER_I, 1372 "audio_decoder.mp1", "audio_encoder.mp1" }, 1373 { MEDIA_MIMETYPE_AUDIO_MPEG_LAYER_II, 1374 "audio_decoder.mp2", "audio_encoder.mp2" }, 1375 { MEDIA_MIMETYPE_AUDIO_AMR_NB, 1376 "audio_decoder.amrnb", "audio_encoder.amrnb" }, 1377 { MEDIA_MIMETYPE_AUDIO_AMR_WB, 1378 "audio_decoder.amrwb", "audio_encoder.amrwb" }, 1379 { MEDIA_MIMETYPE_AUDIO_AAC, 1380 "audio_decoder.aac", "audio_encoder.aac" }, 1381 { MEDIA_MIMETYPE_AUDIO_VORBIS, 1382 "audio_decoder.vorbis", "audio_encoder.vorbis" }, 1383 { MEDIA_MIMETYPE_AUDIO_G711_MLAW, 1384 "audio_decoder.g711mlaw", "audio_encoder.g711mlaw" }, 1385 { MEDIA_MIMETYPE_AUDIO_G711_ALAW, 1386 "audio_decoder.g711alaw", "audio_encoder.g711alaw" }, 1387 { MEDIA_MIMETYPE_VIDEO_AVC, 1388 "video_decoder.avc", "video_encoder.avc" }, 1389 { MEDIA_MIMETYPE_VIDEO_MPEG4, 1390 "video_decoder.mpeg4", "video_encoder.mpeg4" }, 1391 { MEDIA_MIMETYPE_VIDEO_H263, 1392 "video_decoder.h263", "video_encoder.h263" }, 1393 { MEDIA_MIMETYPE_VIDEO_VP8, 1394 "video_decoder.vp8", "video_encoder.vp8" }, 1395 { MEDIA_MIMETYPE_VIDEO_VP9, 1396 "video_decoder.vp9", "video_encoder.vp9" }, 1397 { MEDIA_MIMETYPE_AUDIO_RAW, 1398 "audio_decoder.raw", "audio_encoder.raw" }, 1399 { MEDIA_MIMETYPE_AUDIO_FLAC, 1400 "audio_decoder.flac", "audio_encoder.flac" }, 1401 { MEDIA_MIMETYPE_AUDIO_MSGSM, 1402 "audio_decoder.gsm", "audio_encoder.gsm" }, 1403 }; 1404 1405 static const size_t kNumMimeToRole = 1406 sizeof(kMimeToRole) / sizeof(kMimeToRole[0]); 1407 1408 size_t i; 1409 for (i = 0; i < kNumMimeToRole; ++i) { 1410 if (!strcasecmp(mime, kMimeToRole[i].mime)) { 1411 break; 1412 } 1413 } 1414 1415 if (i == kNumMimeToRole) { 1416 return; 1417 } 1418 1419 const char *role = 1420 isEncoder ? kMimeToRole[i].encoderRole 1421 : kMimeToRole[i].decoderRole; 1422 1423 if (role != NULL) { 1424 OMX_PARAM_COMPONENTROLETYPE roleParams; 1425 InitOMXParams(&roleParams); 1426 1427 strncpy((char *)roleParams.cRole, 1428 role, OMX_MAX_STRINGNAME_SIZE - 1); 1429 1430 roleParams.cRole[OMX_MAX_STRINGNAME_SIZE - 1] = '\0'; 1431 1432 status_t err = omx->setParameter( 1433 node, OMX_IndexParamStandardComponentRole, 1434 &roleParams, sizeof(roleParams)); 1435 1436 if (err != OK) { 1437 ALOGW("Failed to set standard component role '%s'.", role); 1438 } 1439 } 1440 } 1441 1442 void OMXCodec::setComponentRole() { 1443 setComponentRole(mOMX, mNode, mIsEncoder, mMIME); 1444 } 1445 1446 OMXCodec::~OMXCodec() { 1447 mSource.clear(); 1448 1449 CHECK(mState == LOADED || mState == ERROR || mState == LOADED_TO_IDLE); 1450 1451 status_t err = mOMX->freeNode(mNode); 1452 CHECK_EQ(err, (status_t)OK); 1453 1454 mNode = NULL; 1455 setState(DEAD); 1456 1457 clearCodecSpecificData(); 1458 1459 free(mComponentName); 1460 mComponentName = NULL; 1461 1462 free(mMIME); 1463 mMIME = NULL; 1464 } 1465 1466 status_t OMXCodec::init() { 1467 // mLock is held. 1468 1469 CHECK_EQ((int)mState, (int)LOADED); 1470 1471 status_t err; 1472 if (!(mQuirks & kRequiresLoadedToIdleAfterAllocation)) { 1473 err = mOMX->sendCommand(mNode, OMX_CommandStateSet, OMX_StateIdle); 1474 CHECK_EQ(err, (status_t)OK); 1475 setState(LOADED_TO_IDLE); 1476 } 1477 1478 err = allocateBuffers(); 1479 if (err != (status_t)OK) { 1480 return err; 1481 } 1482 1483 if (mQuirks & kRequiresLoadedToIdleAfterAllocation) { 1484 err = mOMX->sendCommand(mNode, OMX_CommandStateSet, OMX_StateIdle); 1485 CHECK_EQ(err, (status_t)OK); 1486 1487 setState(LOADED_TO_IDLE); 1488 } 1489 1490 while (mState != EXECUTING && mState != ERROR) { 1491 mAsyncCompletion.wait(mLock); 1492 } 1493 1494 return mState == ERROR ? UNKNOWN_ERROR : OK; 1495 } 1496 1497 // static 1498 bool OMXCodec::isIntermediateState(State state) { 1499 return state == LOADED_TO_IDLE 1500 || state == IDLE_TO_EXECUTING 1501 || state == EXECUTING_TO_IDLE 1502 || state == IDLE_TO_LOADED 1503 || state == RECONFIGURING; 1504 } 1505 1506 status_t OMXCodec::allocateBuffers() { 1507 status_t err = allocateBuffersOnPort(kPortIndexInput); 1508 1509 if (err != OK) { 1510 return err; 1511 } 1512 1513 return allocateBuffersOnPort(kPortIndexOutput); 1514 } 1515 1516 status_t OMXCodec::allocateBuffersOnPort(OMX_U32 portIndex) { 1517 if (mNativeWindow != NULL && portIndex == kPortIndexOutput) { 1518 return allocateOutputBuffersFromNativeWindow(); 1519 } 1520 1521 if ((mFlags & kEnableGrallocUsageProtected) && portIndex == kPortIndexOutput) { 1522 ALOGE("protected output buffers must be stent to an ANativeWindow"); 1523 return PERMISSION_DENIED; 1524 } 1525 1526 status_t err = OK; 1527 if ((mFlags & kStoreMetaDataInVideoBuffers) 1528 && portIndex == kPortIndexInput) { 1529 err = mOMX->storeMetaDataInBuffers(mNode, kPortIndexInput, OMX_TRUE); 1530 if (err != OK) { 1531 ALOGE("Storing meta data in video buffers is not supported"); 1532 return err; 1533 } 1534 } 1535 1536 OMX_PARAM_PORTDEFINITIONTYPE def; 1537 InitOMXParams(&def); 1538 def.nPortIndex = portIndex; 1539 1540 err = mOMX->getParameter( 1541 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 1542 1543 if (err != OK) { 1544 return err; 1545 } 1546 1547 CODEC_LOGV("allocating %lu buffers of size %lu on %s port", 1548 def.nBufferCountActual, def.nBufferSize, 1549 portIndex == kPortIndexInput ? "input" : "output"); 1550 1551 size_t totalSize = def.nBufferCountActual * def.nBufferSize; 1552 mDealer[portIndex] = new MemoryDealer(totalSize, "OMXCodec"); 1553 1554 for (OMX_U32 i = 0; i < def.nBufferCountActual; ++i) { 1555 sp<IMemory> mem = mDealer[portIndex]->allocate(def.nBufferSize); 1556 CHECK(mem.get() != NULL); 1557 1558 BufferInfo info; 1559 info.mData = NULL; 1560 info.mSize = def.nBufferSize; 1561 1562 IOMX::buffer_id buffer; 1563 if (portIndex == kPortIndexInput 1564 && ((mQuirks & kRequiresAllocateBufferOnInputPorts) 1565 || (mFlags & kUseSecureInputBuffers))) { 1566 if (mOMXLivesLocally) { 1567 mem.clear(); 1568 1569 err = mOMX->allocateBuffer( 1570 mNode, portIndex, def.nBufferSize, &buffer, 1571 &info.mData); 1572 } else { 1573 err = mOMX->allocateBufferWithBackup( 1574 mNode, portIndex, mem, &buffer); 1575 } 1576 } else if (portIndex == kPortIndexOutput 1577 && (mQuirks & kRequiresAllocateBufferOnOutputPorts)) { 1578 if (mOMXLivesLocally) { 1579 mem.clear(); 1580 1581 err = mOMX->allocateBuffer( 1582 mNode, portIndex, def.nBufferSize, &buffer, 1583 &info.mData); 1584 } else { 1585 err = mOMX->allocateBufferWithBackup( 1586 mNode, portIndex, mem, &buffer); 1587 } 1588 } else { 1589 err = mOMX->useBuffer(mNode, portIndex, mem, &buffer); 1590 } 1591 1592 if (err != OK) { 1593 ALOGE("allocate_buffer_with_backup failed"); 1594 return err; 1595 } 1596 1597 if (mem != NULL) { 1598 info.mData = mem->pointer(); 1599 } 1600 1601 info.mBuffer = buffer; 1602 info.mStatus = OWNED_BY_US; 1603 info.mMem = mem; 1604 info.mMediaBuffer = NULL; 1605 1606 if (portIndex == kPortIndexOutput) { 1607 if (!(mOMXLivesLocally 1608 && (mQuirks & kRequiresAllocateBufferOnOutputPorts) 1609 && (mQuirks & kDefersOutputBufferAllocation))) { 1610 // If the node does not fill in the buffer ptr at this time, 1611 // we will defer creating the MediaBuffer until receiving 1612 // the first FILL_BUFFER_DONE notification instead. 1613 info.mMediaBuffer = new MediaBuffer(info.mData, info.mSize); 1614 info.mMediaBuffer->setObserver(this); 1615 } 1616 } 1617 1618 mPortBuffers[portIndex].push(info); 1619 1620 CODEC_LOGV("allocated buffer %p on %s port", buffer, 1621 portIndex == kPortIndexInput ? "input" : "output"); 1622 } 1623 1624 if (portIndex == kPortIndexOutput) { 1625 1626 sp<MetaData> meta = mSource->getFormat(); 1627 int32_t delay = 0; 1628 if (!meta->findInt32(kKeyEncoderDelay, &delay)) { 1629 delay = 0; 1630 } 1631 int32_t padding = 0; 1632 if (!meta->findInt32(kKeyEncoderPadding, &padding)) { 1633 padding = 0; 1634 } 1635 int32_t numchannels = 0; 1636 if (delay + padding) { 1637 if (mOutputFormat->findInt32(kKeyChannelCount, &numchannels)) { 1638 size_t frameSize = numchannels * sizeof(int16_t); 1639 if (mSkipCutBuffer != NULL) { 1640 size_t prevbuffersize = mSkipCutBuffer->size(); 1641 if (prevbuffersize != 0) { 1642 ALOGW("Replacing SkipCutBuffer holding %d bytes", prevbuffersize); 1643 } 1644 } 1645 mSkipCutBuffer = new SkipCutBuffer(delay * frameSize, padding * frameSize); 1646 } 1647 } 1648 } 1649 1650 // dumpPortStatus(portIndex); 1651 1652 if (portIndex == kPortIndexInput && (mFlags & kUseSecureInputBuffers)) { 1653 Vector<MediaBuffer *> buffers; 1654 for (size_t i = 0; i < def.nBufferCountActual; ++i) { 1655 const BufferInfo &info = mPortBuffers[kPortIndexInput].itemAt(i); 1656 1657 MediaBuffer *mbuf = new MediaBuffer(info.mData, info.mSize); 1658 buffers.push(mbuf); 1659 } 1660 1661 status_t err = mSource->setBuffers(buffers); 1662 1663 if (err != OK) { 1664 for (size_t i = 0; i < def.nBufferCountActual; ++i) { 1665 buffers.editItemAt(i)->release(); 1666 } 1667 buffers.clear(); 1668 1669 CODEC_LOGE( 1670 "Codec requested to use secure input buffers but " 1671 "upstream source didn't support that."); 1672 1673 return err; 1674 } 1675 } 1676 1677 return OK; 1678 } 1679 1680 status_t OMXCodec::applyRotation() { 1681 sp<MetaData> meta = mSource->getFormat(); 1682 1683 int32_t rotationDegrees; 1684 if (!meta->findInt32(kKeyRotation, &rotationDegrees)) { 1685 rotationDegrees = 0; 1686 } 1687 1688 uint32_t transform; 1689 switch (rotationDegrees) { 1690 case 0: transform = 0; break; 1691 case 90: transform = HAL_TRANSFORM_ROT_90; break; 1692 case 180: transform = HAL_TRANSFORM_ROT_180; break; 1693 case 270: transform = HAL_TRANSFORM_ROT_270; break; 1694 default: transform = 0; break; 1695 } 1696 1697 status_t err = OK; 1698 1699 if (transform) { 1700 err = native_window_set_buffers_transform( 1701 mNativeWindow.get(), transform); 1702 ALOGE("native_window_set_buffers_transform failed: %s (%d)", 1703 strerror(-err), -err); 1704 } 1705 1706 return err; 1707 } 1708 1709 status_t OMXCodec::allocateOutputBuffersFromNativeWindow() { 1710 // Get the number of buffers needed. 1711 OMX_PARAM_PORTDEFINITIONTYPE def; 1712 InitOMXParams(&def); 1713 def.nPortIndex = kPortIndexOutput; 1714 1715 status_t err = mOMX->getParameter( 1716 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 1717 if (err != OK) { 1718 CODEC_LOGE("getParameter failed: %d", err); 1719 return err; 1720 } 1721 1722 err = native_window_set_buffers_geometry( 1723 mNativeWindow.get(), 1724 def.format.video.nFrameWidth, 1725 def.format.video.nFrameHeight, 1726 def.format.video.eColorFormat); 1727 1728 if (err != 0) { 1729 ALOGE("native_window_set_buffers_geometry failed: %s (%d)", 1730 strerror(-err), -err); 1731 return err; 1732 } 1733 1734 err = applyRotation(); 1735 if (err != OK) { 1736 return err; 1737 } 1738 1739 // Set up the native window. 1740 OMX_U32 usage = 0; 1741 err = mOMX->getGraphicBufferUsage(mNode, kPortIndexOutput, &usage); 1742 if (err != 0) { 1743 ALOGW("querying usage flags from OMX IL component failed: %d", err); 1744 // XXX: Currently this error is logged, but not fatal. 1745 usage = 0; 1746 } 1747 if (mFlags & kEnableGrallocUsageProtected) { 1748 usage |= GRALLOC_USAGE_PROTECTED; 1749 } 1750 1751 // Make sure to check whether either Stagefright or the video decoder 1752 // requested protected buffers. 1753 if (usage & GRALLOC_USAGE_PROTECTED) { 1754 // Verify that the ANativeWindow sends images directly to 1755 // SurfaceFlinger. 1756 int queuesToNativeWindow = 0; 1757 err = mNativeWindow->query( 1758 mNativeWindow.get(), NATIVE_WINDOW_QUEUES_TO_WINDOW_COMPOSER, 1759 &queuesToNativeWindow); 1760 if (err != 0) { 1761 ALOGE("error authenticating native window: %d", err); 1762 return err; 1763 } 1764 if (queuesToNativeWindow != 1) { 1765 ALOGE("native window could not be authenticated"); 1766 return PERMISSION_DENIED; 1767 } 1768 } 1769 1770 ALOGV("native_window_set_usage usage=0x%lx", usage); 1771 err = native_window_set_usage( 1772 mNativeWindow.get(), usage | GRALLOC_USAGE_HW_TEXTURE | GRALLOC_USAGE_EXTERNAL_DISP); 1773 if (err != 0) { 1774 ALOGE("native_window_set_usage failed: %s (%d)", strerror(-err), -err); 1775 return err; 1776 } 1777 1778 int minUndequeuedBufs = 0; 1779 err = mNativeWindow->query(mNativeWindow.get(), 1780 NATIVE_WINDOW_MIN_UNDEQUEUED_BUFFERS, &minUndequeuedBufs); 1781 if (err != 0) { 1782 ALOGE("NATIVE_WINDOW_MIN_UNDEQUEUED_BUFFERS query failed: %s (%d)", 1783 strerror(-err), -err); 1784 return err; 1785 } 1786 1787 // XXX: Is this the right logic to use? It's not clear to me what the OMX 1788 // buffer counts refer to - how do they account for the renderer holding on 1789 // to buffers? 1790 if (def.nBufferCountActual < def.nBufferCountMin + minUndequeuedBufs) { 1791 OMX_U32 newBufferCount = def.nBufferCountMin + minUndequeuedBufs; 1792 def.nBufferCountActual = newBufferCount; 1793 err = mOMX->setParameter( 1794 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 1795 if (err != OK) { 1796 CODEC_LOGE("setting nBufferCountActual to %lu failed: %d", 1797 newBufferCount, err); 1798 return err; 1799 } 1800 } 1801 1802 err = native_window_set_buffer_count( 1803 mNativeWindow.get(), def.nBufferCountActual); 1804 if (err != 0) { 1805 ALOGE("native_window_set_buffer_count failed: %s (%d)", strerror(-err), 1806 -err); 1807 return err; 1808 } 1809 1810 CODEC_LOGV("allocating %lu buffers from a native window of size %lu on " 1811 "output port", def.nBufferCountActual, def.nBufferSize); 1812 1813 // Dequeue buffers and send them to OMX 1814 for (OMX_U32 i = 0; i < def.nBufferCountActual; i++) { 1815 ANativeWindowBuffer* buf; 1816 err = native_window_dequeue_buffer_and_wait(mNativeWindow.get(), &buf); 1817 if (err != 0) { 1818 ALOGE("dequeueBuffer failed: %s (%d)", strerror(-err), -err); 1819 break; 1820 } 1821 1822 sp<GraphicBuffer> graphicBuffer(new GraphicBuffer(buf, false)); 1823 BufferInfo info; 1824 info.mData = NULL; 1825 info.mSize = def.nBufferSize; 1826 info.mStatus = OWNED_BY_US; 1827 info.mMem = NULL; 1828 info.mMediaBuffer = new MediaBuffer(graphicBuffer); 1829 info.mMediaBuffer->setObserver(this); 1830 mPortBuffers[kPortIndexOutput].push(info); 1831 1832 IOMX::buffer_id bufferId; 1833 err = mOMX->useGraphicBuffer(mNode, kPortIndexOutput, graphicBuffer, 1834 &bufferId); 1835 if (err != 0) { 1836 CODEC_LOGE("registering GraphicBuffer with OMX IL component " 1837 "failed: %d", err); 1838 break; 1839 } 1840 1841 mPortBuffers[kPortIndexOutput].editItemAt(i).mBuffer = bufferId; 1842 1843 CODEC_LOGV("registered graphic buffer with ID %p (pointer = %p)", 1844 bufferId, graphicBuffer.get()); 1845 } 1846 1847 OMX_U32 cancelStart; 1848 OMX_U32 cancelEnd; 1849 if (err != 0) { 1850 // If an error occurred while dequeuing we need to cancel any buffers 1851 // that were dequeued. 1852 cancelStart = 0; 1853 cancelEnd = mPortBuffers[kPortIndexOutput].size(); 1854 } else { 1855 // Return the last two buffers to the native window. 1856 cancelStart = def.nBufferCountActual - minUndequeuedBufs; 1857 cancelEnd = def.nBufferCountActual; 1858 } 1859 1860 for (OMX_U32 i = cancelStart; i < cancelEnd; i++) { 1861 BufferInfo *info = &mPortBuffers[kPortIndexOutput].editItemAt(i); 1862 cancelBufferToNativeWindow(info); 1863 } 1864 1865 return err; 1866 } 1867 1868 status_t OMXCodec::cancelBufferToNativeWindow(BufferInfo *info) { 1869 CHECK_EQ((int)info->mStatus, (int)OWNED_BY_US); 1870 CODEC_LOGV("Calling cancelBuffer on buffer %p", info->mBuffer); 1871 int err = mNativeWindow->cancelBuffer( 1872 mNativeWindow.get(), info->mMediaBuffer->graphicBuffer().get(), -1); 1873 if (err != 0) { 1874 CODEC_LOGE("cancelBuffer failed w/ error 0x%08x", err); 1875 1876 setState(ERROR); 1877 return err; 1878 } 1879 info->mStatus = OWNED_BY_NATIVE_WINDOW; 1880 return OK; 1881 } 1882 1883 OMXCodec::BufferInfo* OMXCodec::dequeueBufferFromNativeWindow() { 1884 // Dequeue the next buffer from the native window. 1885 ANativeWindowBuffer* buf; 1886 int fenceFd = -1; 1887 int err = native_window_dequeue_buffer_and_wait(mNativeWindow.get(), &buf); 1888 if (err != 0) { 1889 CODEC_LOGE("dequeueBuffer failed w/ error 0x%08x", err); 1890 1891 setState(ERROR); 1892 return 0; 1893 } 1894 1895 // Determine which buffer we just dequeued. 1896 Vector<BufferInfo> *buffers = &mPortBuffers[kPortIndexOutput]; 1897 BufferInfo *bufInfo = 0; 1898 for (size_t i = 0; i < buffers->size(); i++) { 1899 sp<GraphicBuffer> graphicBuffer = buffers->itemAt(i). 1900 mMediaBuffer->graphicBuffer(); 1901 if (graphicBuffer->handle == buf->handle) { 1902 bufInfo = &buffers->editItemAt(i); 1903 break; 1904 } 1905 } 1906 1907 if (bufInfo == 0) { 1908 CODEC_LOGE("dequeued unrecognized buffer: %p", buf); 1909 1910 setState(ERROR); 1911 return 0; 1912 } 1913 1914 // The native window no longer owns the buffer. 1915 CHECK_EQ((int)bufInfo->mStatus, (int)OWNED_BY_NATIVE_WINDOW); 1916 bufInfo->mStatus = OWNED_BY_US; 1917 1918 return bufInfo; 1919 } 1920 1921 status_t OMXCodec::pushBlankBuffersToNativeWindow() { 1922 status_t err = NO_ERROR; 1923 ANativeWindowBuffer* anb = NULL; 1924 int numBufs = 0; 1925 int minUndequeuedBufs = 0; 1926 1927 // We need to reconnect to the ANativeWindow as a CPU client to ensure that 1928 // no frames get dropped by SurfaceFlinger assuming that these are video 1929 // frames. 1930 err = native_window_api_disconnect(mNativeWindow.get(), 1931 NATIVE_WINDOW_API_MEDIA); 1932 if (err != NO_ERROR) { 1933 ALOGE("error pushing blank frames: api_disconnect failed: %s (%d)", 1934 strerror(-err), -err); 1935 return err; 1936 } 1937 1938 err = native_window_api_connect(mNativeWindow.get(), 1939 NATIVE_WINDOW_API_CPU); 1940 if (err != NO_ERROR) { 1941 ALOGE("error pushing blank frames: api_connect failed: %s (%d)", 1942 strerror(-err), -err); 1943 return err; 1944 } 1945 1946 err = native_window_set_buffers_geometry(mNativeWindow.get(), 1, 1, 1947 HAL_PIXEL_FORMAT_RGBX_8888); 1948 if (err != NO_ERROR) { 1949 ALOGE("error pushing blank frames: set_buffers_geometry failed: %s (%d)", 1950 strerror(-err), -err); 1951 goto error; 1952 } 1953 1954 err = native_window_set_usage(mNativeWindow.get(), 1955 GRALLOC_USAGE_SW_WRITE_OFTEN); 1956 if (err != NO_ERROR) { 1957 ALOGE("error pushing blank frames: set_usage failed: %s (%d)", 1958 strerror(-err), -err); 1959 goto error; 1960 } 1961 1962 err = native_window_set_scaling_mode(mNativeWindow.get(), 1963 NATIVE_WINDOW_SCALING_MODE_SCALE_TO_WINDOW); 1964 if (err != OK) { 1965 ALOGE("error pushing blank frames: set_scaling_mode failed: %s (%d)", 1966 strerror(-err), -err); 1967 goto error; 1968 } 1969 1970 err = mNativeWindow->query(mNativeWindow.get(), 1971 NATIVE_WINDOW_MIN_UNDEQUEUED_BUFFERS, &minUndequeuedBufs); 1972 if (err != NO_ERROR) { 1973 ALOGE("error pushing blank frames: MIN_UNDEQUEUED_BUFFERS query " 1974 "failed: %s (%d)", strerror(-err), -err); 1975 goto error; 1976 } 1977 1978 numBufs = minUndequeuedBufs + 1; 1979 err = native_window_set_buffer_count(mNativeWindow.get(), numBufs); 1980 if (err != NO_ERROR) { 1981 ALOGE("error pushing blank frames: set_buffer_count failed: %s (%d)", 1982 strerror(-err), -err); 1983 goto error; 1984 } 1985 1986 // We push numBufs + 1 buffers to ensure that we've drawn into the same 1987 // buffer twice. This should guarantee that the buffer has been displayed 1988 // on the screen and then been replaced, so an previous video frames are 1989 // guaranteed NOT to be currently displayed. 1990 for (int i = 0; i < numBufs + 1; i++) { 1991 int fenceFd = -1; 1992 err = native_window_dequeue_buffer_and_wait(mNativeWindow.get(), &anb); 1993 if (err != NO_ERROR) { 1994 ALOGE("error pushing blank frames: dequeueBuffer failed: %s (%d)", 1995 strerror(-err), -err); 1996 goto error; 1997 } 1998 1999 sp<GraphicBuffer> buf(new GraphicBuffer(anb, false)); 2000 2001 // Fill the buffer with the a 1x1 checkerboard pattern ;) 2002 uint32_t* img = NULL; 2003 err = buf->lock(GRALLOC_USAGE_SW_WRITE_OFTEN, (void**)(&img)); 2004 if (err != NO_ERROR) { 2005 ALOGE("error pushing blank frames: lock failed: %s (%d)", 2006 strerror(-err), -err); 2007 goto error; 2008 } 2009 2010 *img = 0; 2011 2012 err = buf->unlock(); 2013 if (err != NO_ERROR) { 2014 ALOGE("error pushing blank frames: unlock failed: %s (%d)", 2015 strerror(-err), -err); 2016 goto error; 2017 } 2018 2019 err = mNativeWindow->queueBuffer(mNativeWindow.get(), 2020 buf->getNativeBuffer(), -1); 2021 if (err != NO_ERROR) { 2022 ALOGE("error pushing blank frames: queueBuffer failed: %s (%d)", 2023 strerror(-err), -err); 2024 goto error; 2025 } 2026 2027 anb = NULL; 2028 } 2029 2030 error: 2031 2032 if (err != NO_ERROR) { 2033 // Clean up after an error. 2034 if (anb != NULL) { 2035 mNativeWindow->cancelBuffer(mNativeWindow.get(), anb, -1); 2036 } 2037 2038 native_window_api_disconnect(mNativeWindow.get(), 2039 NATIVE_WINDOW_API_CPU); 2040 native_window_api_connect(mNativeWindow.get(), 2041 NATIVE_WINDOW_API_MEDIA); 2042 2043 return err; 2044 } else { 2045 // Clean up after success. 2046 err = native_window_api_disconnect(mNativeWindow.get(), 2047 NATIVE_WINDOW_API_CPU); 2048 if (err != NO_ERROR) { 2049 ALOGE("error pushing blank frames: api_disconnect failed: %s (%d)", 2050 strerror(-err), -err); 2051 return err; 2052 } 2053 2054 err = native_window_api_connect(mNativeWindow.get(), 2055 NATIVE_WINDOW_API_MEDIA); 2056 if (err != NO_ERROR) { 2057 ALOGE("error pushing blank frames: api_connect failed: %s (%d)", 2058 strerror(-err), -err); 2059 return err; 2060 } 2061 2062 return NO_ERROR; 2063 } 2064 } 2065 2066 int64_t OMXCodec::getDecodingTimeUs() { 2067 CHECK(mIsEncoder && mIsVideo); 2068 2069 if (mDecodingTimeList.empty()) { 2070 CHECK(mSignalledEOS || mNoMoreOutputData); 2071 // No corresponding input frame available. 2072 // This could happen when EOS is reached. 2073 return 0; 2074 } 2075 2076 List<int64_t>::iterator it = mDecodingTimeList.begin(); 2077 int64_t timeUs = *it; 2078 mDecodingTimeList.erase(it); 2079 return timeUs; 2080 } 2081 2082 void OMXCodec::on_message(const omx_message &msg) { 2083 if (mState == ERROR) { 2084 /* 2085 * only drop EVENT messages, EBD and FBD are still 2086 * processed for bookkeeping purposes 2087 */ 2088 if (msg.type == omx_message::EVENT) { 2089 ALOGW("Dropping OMX EVENT message - we're in ERROR state."); 2090 return; 2091 } 2092 } 2093 2094 switch (msg.type) { 2095 case omx_message::EVENT: 2096 { 2097 onEvent( 2098 msg.u.event_data.event, msg.u.event_data.data1, 2099 msg.u.event_data.data2); 2100 2101 break; 2102 } 2103 2104 case omx_message::EMPTY_BUFFER_DONE: 2105 { 2106 IOMX::buffer_id buffer = msg.u.extended_buffer_data.buffer; 2107 2108 CODEC_LOGV("EMPTY_BUFFER_DONE(buffer: %p)", buffer); 2109 2110 Vector<BufferInfo> *buffers = &mPortBuffers[kPortIndexInput]; 2111 size_t i = 0; 2112 while (i < buffers->size() && (*buffers)[i].mBuffer != buffer) { 2113 ++i; 2114 } 2115 2116 CHECK(i < buffers->size()); 2117 if ((*buffers)[i].mStatus != OWNED_BY_COMPONENT) { 2118 ALOGW("We already own input buffer %p, yet received " 2119 "an EMPTY_BUFFER_DONE.", buffer); 2120 } 2121 2122 BufferInfo* info = &buffers->editItemAt(i); 2123 info->mStatus = OWNED_BY_US; 2124 2125 // Buffer could not be released until empty buffer done is called. 2126 if (info->mMediaBuffer != NULL) { 2127 info->mMediaBuffer->release(); 2128 info->mMediaBuffer = NULL; 2129 } 2130 2131 if (mPortStatus[kPortIndexInput] == DISABLING) { 2132 CODEC_LOGV("Port is disabled, freeing buffer %p", buffer); 2133 2134 status_t err = freeBuffer(kPortIndexInput, i); 2135 CHECK_EQ(err, (status_t)OK); 2136 } else if (mState != ERROR 2137 && mPortStatus[kPortIndexInput] != SHUTTING_DOWN) { 2138 CHECK_EQ((int)mPortStatus[kPortIndexInput], (int)ENABLED); 2139 2140 if (mFlags & kUseSecureInputBuffers) { 2141 drainAnyInputBuffer(); 2142 } else { 2143 drainInputBuffer(&buffers->editItemAt(i)); 2144 } 2145 } 2146 break; 2147 } 2148 2149 case omx_message::FILL_BUFFER_DONE: 2150 { 2151 IOMX::buffer_id buffer = msg.u.extended_buffer_data.buffer; 2152 OMX_U32 flags = msg.u.extended_buffer_data.flags; 2153 2154 CODEC_LOGV("FILL_BUFFER_DONE(buffer: %p, size: %ld, flags: 0x%08lx, timestamp: %lld us (%.2f secs))", 2155 buffer, 2156 msg.u.extended_buffer_data.range_length, 2157 flags, 2158 msg.u.extended_buffer_data.timestamp, 2159 msg.u.extended_buffer_data.timestamp / 1E6); 2160 2161 Vector<BufferInfo> *buffers = &mPortBuffers[kPortIndexOutput]; 2162 size_t i = 0; 2163 while (i < buffers->size() && (*buffers)[i].mBuffer != buffer) { 2164 ++i; 2165 } 2166 2167 CHECK(i < buffers->size()); 2168 BufferInfo *info = &buffers->editItemAt(i); 2169 2170 if (info->mStatus != OWNED_BY_COMPONENT) { 2171 ALOGW("We already own output buffer %p, yet received " 2172 "a FILL_BUFFER_DONE.", buffer); 2173 } 2174 2175 info->mStatus = OWNED_BY_US; 2176 2177 if (mPortStatus[kPortIndexOutput] == DISABLING) { 2178 CODEC_LOGV("Port is disabled, freeing buffer %p", buffer); 2179 2180 status_t err = freeBuffer(kPortIndexOutput, i); 2181 CHECK_EQ(err, (status_t)OK); 2182 2183 #if 0 2184 } else if (mPortStatus[kPortIndexOutput] == ENABLED 2185 && (flags & OMX_BUFFERFLAG_EOS)) { 2186 CODEC_LOGV("No more output data."); 2187 mNoMoreOutputData = true; 2188 mBufferFilled.signal(); 2189 #endif 2190 } else if (mPortStatus[kPortIndexOutput] != SHUTTING_DOWN) { 2191 CHECK_EQ((int)mPortStatus[kPortIndexOutput], (int)ENABLED); 2192 2193 if (info->mMediaBuffer == NULL) { 2194 CHECK(mOMXLivesLocally); 2195 CHECK(mQuirks & kRequiresAllocateBufferOnOutputPorts); 2196 CHECK(mQuirks & kDefersOutputBufferAllocation); 2197 2198 // The qcom video decoders on Nexus don't actually allocate 2199 // output buffer memory on a call to OMX_AllocateBuffer 2200 // the "pBuffer" member of the OMX_BUFFERHEADERTYPE 2201 // structure is only filled in later. 2202 2203 info->mMediaBuffer = new MediaBuffer( 2204 msg.u.extended_buffer_data.data_ptr, 2205 info->mSize); 2206 info->mMediaBuffer->setObserver(this); 2207 } 2208 2209 MediaBuffer *buffer = info->mMediaBuffer; 2210 bool isGraphicBuffer = buffer->graphicBuffer() != NULL; 2211 2212 if (!isGraphicBuffer 2213 && msg.u.extended_buffer_data.range_offset 2214 + msg.u.extended_buffer_data.range_length 2215 > buffer->size()) { 2216 CODEC_LOGE( 2217 "Codec lied about its buffer size requirements, " 2218 "sending a buffer larger than the originally " 2219 "advertised size in FILL_BUFFER_DONE!"); 2220 } 2221 buffer->set_range( 2222 msg.u.extended_buffer_data.range_offset, 2223 msg.u.extended_buffer_data.range_length); 2224 2225 buffer->meta_data()->clear(); 2226 2227 buffer->meta_data()->setInt64( 2228 kKeyTime, msg.u.extended_buffer_data.timestamp); 2229 2230 if (msg.u.extended_buffer_data.flags & OMX_BUFFERFLAG_SYNCFRAME) { 2231 buffer->meta_data()->setInt32(kKeyIsSyncFrame, true); 2232 } 2233 bool isCodecSpecific = false; 2234 if (msg.u.extended_buffer_data.flags & OMX_BUFFERFLAG_CODECCONFIG) { 2235 buffer->meta_data()->setInt32(kKeyIsCodecConfig, true); 2236 isCodecSpecific = true; 2237 } 2238 2239 if (isGraphicBuffer || mQuirks & kOutputBuffersAreUnreadable) { 2240 buffer->meta_data()->setInt32(kKeyIsUnreadable, true); 2241 } 2242 2243 buffer->meta_data()->setPointer( 2244 kKeyPlatformPrivate, 2245 msg.u.extended_buffer_data.platform_private); 2246 2247 buffer->meta_data()->setPointer( 2248 kKeyBufferID, 2249 msg.u.extended_buffer_data.buffer); 2250 2251 if (msg.u.extended_buffer_data.flags & OMX_BUFFERFLAG_EOS) { 2252 CODEC_LOGV("No more output data."); 2253 mNoMoreOutputData = true; 2254 } 2255 2256 if (mIsEncoder && mIsVideo) { 2257 int64_t decodingTimeUs = isCodecSpecific? 0: getDecodingTimeUs(); 2258 buffer->meta_data()->setInt64(kKeyDecodingTime, decodingTimeUs); 2259 } 2260 2261 if (mTargetTimeUs >= 0) { 2262 CHECK(msg.u.extended_buffer_data.timestamp <= mTargetTimeUs); 2263 2264 if (msg.u.extended_buffer_data.timestamp < mTargetTimeUs) { 2265 CODEC_LOGV( 2266 "skipping output buffer at timestamp %lld us", 2267 msg.u.extended_buffer_data.timestamp); 2268 2269 fillOutputBuffer(info); 2270 break; 2271 } 2272 2273 CODEC_LOGV( 2274 "returning output buffer at target timestamp " 2275 "%lld us", 2276 msg.u.extended_buffer_data.timestamp); 2277 2278 mTargetTimeUs = -1; 2279 } 2280 2281 mFilledBuffers.push_back(i); 2282 mBufferFilled.signal(); 2283 if (mIsEncoder) { 2284 sched_yield(); 2285 } 2286 } 2287 2288 break; 2289 } 2290 2291 default: 2292 { 2293 CHECK(!"should not be here."); 2294 break; 2295 } 2296 } 2297 } 2298 2299 // Has the format changed in any way that the client would have to be aware of? 2300 static bool formatHasNotablyChanged( 2301 const sp<MetaData> &from, const sp<MetaData> &to) { 2302 if (from.get() == NULL && to.get() == NULL) { 2303 return false; 2304 } 2305 2306 if ((from.get() == NULL && to.get() != NULL) 2307 || (from.get() != NULL && to.get() == NULL)) { 2308 return true; 2309 } 2310 2311 const char *mime_from, *mime_to; 2312 CHECK(from->findCString(kKeyMIMEType, &mime_from)); 2313 CHECK(to->findCString(kKeyMIMEType, &mime_to)); 2314 2315 if (strcasecmp(mime_from, mime_to)) { 2316 return true; 2317 } 2318 2319 if (!strcasecmp(mime_from, MEDIA_MIMETYPE_VIDEO_RAW)) { 2320 int32_t colorFormat_from, colorFormat_to; 2321 CHECK(from->findInt32(kKeyColorFormat, &colorFormat_from)); 2322 CHECK(to->findInt32(kKeyColorFormat, &colorFormat_to)); 2323 2324 if (colorFormat_from != colorFormat_to) { 2325 return true; 2326 } 2327 2328 int32_t width_from, width_to; 2329 CHECK(from->findInt32(kKeyWidth, &width_from)); 2330 CHECK(to->findInt32(kKeyWidth, &width_to)); 2331 2332 if (width_from != width_to) { 2333 return true; 2334 } 2335 2336 int32_t height_from, height_to; 2337 CHECK(from->findInt32(kKeyHeight, &height_from)); 2338 CHECK(to->findInt32(kKeyHeight, &height_to)); 2339 2340 if (height_from != height_to) { 2341 return true; 2342 } 2343 2344 int32_t left_from, top_from, right_from, bottom_from; 2345 CHECK(from->findRect( 2346 kKeyCropRect, 2347 &left_from, &top_from, &right_from, &bottom_from)); 2348 2349 int32_t left_to, top_to, right_to, bottom_to; 2350 CHECK(to->findRect( 2351 kKeyCropRect, 2352 &left_to, &top_to, &right_to, &bottom_to)); 2353 2354 if (left_to != left_from || top_to != top_from 2355 || right_to != right_from || bottom_to != bottom_from) { 2356 return true; 2357 } 2358 } else if (!strcasecmp(mime_from, MEDIA_MIMETYPE_AUDIO_RAW)) { 2359 int32_t numChannels_from, numChannels_to; 2360 CHECK(from->findInt32(kKeyChannelCount, &numChannels_from)); 2361 CHECK(to->findInt32(kKeyChannelCount, &numChannels_to)); 2362 2363 if (numChannels_from != numChannels_to) { 2364 return true; 2365 } 2366 2367 int32_t sampleRate_from, sampleRate_to; 2368 CHECK(from->findInt32(kKeySampleRate, &sampleRate_from)); 2369 CHECK(to->findInt32(kKeySampleRate, &sampleRate_to)); 2370 2371 if (sampleRate_from != sampleRate_to) { 2372 return true; 2373 } 2374 } 2375 2376 return false; 2377 } 2378 2379 void OMXCodec::onEvent(OMX_EVENTTYPE event, OMX_U32 data1, OMX_U32 data2) { 2380 switch (event) { 2381 case OMX_EventCmdComplete: 2382 { 2383 onCmdComplete((OMX_COMMANDTYPE)data1, data2); 2384 break; 2385 } 2386 2387 case OMX_EventError: 2388 { 2389 CODEC_LOGE("ERROR(0x%08lx, %ld)", data1, data2); 2390 2391 setState(ERROR); 2392 break; 2393 } 2394 2395 case OMX_EventPortSettingsChanged: 2396 { 2397 CODEC_LOGV("OMX_EventPortSettingsChanged(port=%ld, data2=0x%08lx)", 2398 data1, data2); 2399 2400 if (data2 == 0 || data2 == OMX_IndexParamPortDefinition) { 2401 // There is no need to check whether mFilledBuffers is empty or not 2402 // when the OMX_EventPortSettingsChanged is not meant for reallocating 2403 // the output buffers. 2404 if (data1 == kPortIndexOutput) { 2405 CHECK(mFilledBuffers.empty()); 2406 } 2407 onPortSettingsChanged(data1); 2408 } else if (data1 == kPortIndexOutput && 2409 (data2 == OMX_IndexConfigCommonOutputCrop || 2410 data2 == OMX_IndexConfigCommonScale)) { 2411 2412 sp<MetaData> oldOutputFormat = mOutputFormat; 2413 initOutputFormat(mSource->getFormat()); 2414 2415 if (data2 == OMX_IndexConfigCommonOutputCrop && 2416 formatHasNotablyChanged(oldOutputFormat, mOutputFormat)) { 2417 mOutputPortSettingsHaveChanged = true; 2418 2419 } else if (data2 == OMX_IndexConfigCommonScale) { 2420 OMX_CONFIG_SCALEFACTORTYPE scale; 2421 InitOMXParams(&scale); 2422 scale.nPortIndex = kPortIndexOutput; 2423 2424 // Change display dimension only when necessary. 2425 if (OK == mOMX->getConfig( 2426 mNode, 2427 OMX_IndexConfigCommonScale, 2428 &scale, sizeof(scale))) { 2429 int32_t left, top, right, bottom; 2430 CHECK(mOutputFormat->findRect(kKeyCropRect, 2431 &left, &top, 2432 &right, &bottom)); 2433 2434 // The scale is in 16.16 format. 2435 // scale 1.0 = 0x010000. When there is no 2436 // need to change the display, skip it. 2437 ALOGV("Get OMX_IndexConfigScale: 0x%lx/0x%lx", 2438 scale.xWidth, scale.xHeight); 2439 2440 if (scale.xWidth != 0x010000) { 2441 mOutputFormat->setInt32(kKeyDisplayWidth, 2442 ((right - left + 1) * scale.xWidth) >> 16); 2443 mOutputPortSettingsHaveChanged = true; 2444 } 2445 2446 if (scale.xHeight != 0x010000) { 2447 mOutputFormat->setInt32(kKeyDisplayHeight, 2448 ((bottom - top + 1) * scale.xHeight) >> 16); 2449 mOutputPortSettingsHaveChanged = true; 2450 } 2451 } 2452 } 2453 } 2454 break; 2455 } 2456 2457 #if 0 2458 case OMX_EventBufferFlag: 2459 { 2460 CODEC_LOGV("EVENT_BUFFER_FLAG(%ld)", data1); 2461 2462 if (data1 == kPortIndexOutput) { 2463 mNoMoreOutputData = true; 2464 } 2465 break; 2466 } 2467 #endif 2468 2469 default: 2470 { 2471 CODEC_LOGV("EVENT(%d, %ld, %ld)", event, data1, data2); 2472 break; 2473 } 2474 } 2475 } 2476 2477 void OMXCodec::onCmdComplete(OMX_COMMANDTYPE cmd, OMX_U32 data) { 2478 switch (cmd) { 2479 case OMX_CommandStateSet: 2480 { 2481 onStateChange((OMX_STATETYPE)data); 2482 break; 2483 } 2484 2485 case OMX_CommandPortDisable: 2486 { 2487 OMX_U32 portIndex = data; 2488 CODEC_LOGV("PORT_DISABLED(%ld)", portIndex); 2489 2490 CHECK(mState == EXECUTING || mState == RECONFIGURING); 2491 CHECK_EQ((int)mPortStatus[portIndex], (int)DISABLING); 2492 CHECK_EQ(mPortBuffers[portIndex].size(), 0u); 2493 2494 mPortStatus[portIndex] = DISABLED; 2495 2496 if (mState == RECONFIGURING) { 2497 CHECK_EQ(portIndex, (OMX_U32)kPortIndexOutput); 2498 2499 sp<MetaData> oldOutputFormat = mOutputFormat; 2500 initOutputFormat(mSource->getFormat()); 2501 2502 // Don't notify clients if the output port settings change 2503 // wasn't of importance to them, i.e. it may be that just the 2504 // number of buffers has changed and nothing else. 2505 bool formatChanged = formatHasNotablyChanged(oldOutputFormat, mOutputFormat); 2506 if (!mOutputPortSettingsHaveChanged) { 2507 mOutputPortSettingsHaveChanged = formatChanged; 2508 } 2509 2510 status_t err = enablePortAsync(portIndex); 2511 if (err != OK) { 2512 CODEC_LOGE("enablePortAsync(%ld) failed (err = %d)", portIndex, err); 2513 setState(ERROR); 2514 } else { 2515 err = allocateBuffersOnPort(portIndex); 2516 if (err != OK) { 2517 CODEC_LOGE("allocateBuffersOnPort (%s) failed " 2518 "(err = %d)", 2519 portIndex == kPortIndexInput 2520 ? "input" : "output", 2521 err); 2522 2523 setState(ERROR); 2524 } 2525 } 2526 } 2527 break; 2528 } 2529 2530 case OMX_CommandPortEnable: 2531 { 2532 OMX_U32 portIndex = data; 2533 CODEC_LOGV("PORT_ENABLED(%ld)", portIndex); 2534 2535 CHECK(mState == EXECUTING || mState == RECONFIGURING); 2536 CHECK_EQ((int)mPortStatus[portIndex], (int)ENABLING); 2537 2538 mPortStatus[portIndex] = ENABLED; 2539 2540 if (mState == RECONFIGURING) { 2541 CHECK_EQ(portIndex, (OMX_U32)kPortIndexOutput); 2542 2543 setState(EXECUTING); 2544 2545 fillOutputBuffers(); 2546 } 2547 break; 2548 } 2549 2550 case OMX_CommandFlush: 2551 { 2552 OMX_U32 portIndex = data; 2553 2554 CODEC_LOGV("FLUSH_DONE(%ld)", portIndex); 2555 2556 CHECK_EQ((int)mPortStatus[portIndex], (int)SHUTTING_DOWN); 2557 mPortStatus[portIndex] = ENABLED; 2558 2559 CHECK_EQ(countBuffersWeOwn(mPortBuffers[portIndex]), 2560 mPortBuffers[portIndex].size()); 2561 2562 if (mSkipCutBuffer != NULL && mPortStatus[kPortIndexOutput] == ENABLED) { 2563 mSkipCutBuffer->clear(); 2564 } 2565 2566 if (mState == RECONFIGURING) { 2567 CHECK_EQ(portIndex, (OMX_U32)kPortIndexOutput); 2568 2569 disablePortAsync(portIndex); 2570 } else if (mState == EXECUTING_TO_IDLE) { 2571 if (mPortStatus[kPortIndexInput] == ENABLED 2572 && mPortStatus[kPortIndexOutput] == ENABLED) { 2573 CODEC_LOGV("Finished flushing both ports, now completing " 2574 "transition from EXECUTING to IDLE."); 2575 2576 mPortStatus[kPortIndexInput] = SHUTTING_DOWN; 2577 mPortStatus[kPortIndexOutput] = SHUTTING_DOWN; 2578 2579 status_t err = 2580 mOMX->sendCommand(mNode, OMX_CommandStateSet, OMX_StateIdle); 2581 CHECK_EQ(err, (status_t)OK); 2582 } 2583 } else { 2584 // We're flushing both ports in preparation for seeking. 2585 2586 if (mPortStatus[kPortIndexInput] == ENABLED 2587 && mPortStatus[kPortIndexOutput] == ENABLED) { 2588 CODEC_LOGV("Finished flushing both ports, now continuing from" 2589 " seek-time."); 2590 2591 // We implicitly resume pulling on our upstream source. 2592 mPaused = false; 2593 2594 drainInputBuffers(); 2595 fillOutputBuffers(); 2596 } 2597 2598 if (mOutputPortSettingsChangedPending) { 2599 CODEC_LOGV( 2600 "Honoring deferred output port settings change."); 2601 2602 mOutputPortSettingsChangedPending = false; 2603 onPortSettingsChanged(kPortIndexOutput); 2604 } 2605 } 2606 2607 break; 2608 } 2609 2610 default: 2611 { 2612 CODEC_LOGV("CMD_COMPLETE(%d, %ld)", cmd, data); 2613 break; 2614 } 2615 } 2616 } 2617 2618 void OMXCodec::onStateChange(OMX_STATETYPE newState) { 2619 CODEC_LOGV("onStateChange %d", newState); 2620 2621 switch (newState) { 2622 case OMX_StateIdle: 2623 { 2624 CODEC_LOGV("Now Idle."); 2625 if (mState == LOADED_TO_IDLE) { 2626 status_t err = mOMX->sendCommand( 2627 mNode, OMX_CommandStateSet, OMX_StateExecuting); 2628 2629 CHECK_EQ(err, (status_t)OK); 2630 2631 setState(IDLE_TO_EXECUTING); 2632 } else { 2633 CHECK_EQ((int)mState, (int)EXECUTING_TO_IDLE); 2634 2635 if (countBuffersWeOwn(mPortBuffers[kPortIndexInput]) != 2636 mPortBuffers[kPortIndexInput].size()) { 2637 ALOGE("Codec did not return all input buffers " 2638 "(received %d / %d)", 2639 countBuffersWeOwn(mPortBuffers[kPortIndexInput]), 2640 mPortBuffers[kPortIndexInput].size()); 2641 TRESPASS(); 2642 } 2643 2644 if (countBuffersWeOwn(mPortBuffers[kPortIndexOutput]) != 2645 mPortBuffers[kPortIndexOutput].size()) { 2646 ALOGE("Codec did not return all output buffers " 2647 "(received %d / %d)", 2648 countBuffersWeOwn(mPortBuffers[kPortIndexOutput]), 2649 mPortBuffers[kPortIndexOutput].size()); 2650 TRESPASS(); 2651 } 2652 2653 status_t err = mOMX->sendCommand( 2654 mNode, OMX_CommandStateSet, OMX_StateLoaded); 2655 2656 CHECK_EQ(err, (status_t)OK); 2657 2658 err = freeBuffersOnPort(kPortIndexInput); 2659 CHECK_EQ(err, (status_t)OK); 2660 2661 err = freeBuffersOnPort(kPortIndexOutput); 2662 CHECK_EQ(err, (status_t)OK); 2663 2664 mPortStatus[kPortIndexInput] = ENABLED; 2665 mPortStatus[kPortIndexOutput] = ENABLED; 2666 2667 if ((mFlags & kEnableGrallocUsageProtected) && 2668 mNativeWindow != NULL) { 2669 // We push enough 1x1 blank buffers to ensure that one of 2670 // them has made it to the display. This allows the OMX 2671 // component teardown to zero out any protected buffers 2672 // without the risk of scanning out one of those buffers. 2673 pushBlankBuffersToNativeWindow(); 2674 } 2675 2676 setState(IDLE_TO_LOADED); 2677 } 2678 break; 2679 } 2680 2681 case OMX_StateExecuting: 2682 { 2683 CHECK_EQ((int)mState, (int)IDLE_TO_EXECUTING); 2684 2685 CODEC_LOGV("Now Executing."); 2686 2687 mOutputPortSettingsChangedPending = false; 2688 2689 setState(EXECUTING); 2690 2691 // Buffers will be submitted to the component in the first 2692 // call to OMXCodec::read as mInitialBufferSubmit is true at 2693 // this point. This ensures that this on_message call returns, 2694 // releases the lock and ::init can notice the state change and 2695 // itself return. 2696 break; 2697 } 2698 2699 case OMX_StateLoaded: 2700 { 2701 CHECK_EQ((int)mState, (int)IDLE_TO_LOADED); 2702 2703 CODEC_LOGV("Now Loaded."); 2704 2705 setState(LOADED); 2706 break; 2707 } 2708 2709 case OMX_StateInvalid: 2710 { 2711 setState(ERROR); 2712 break; 2713 } 2714 2715 default: 2716 { 2717 CHECK(!"should not be here."); 2718 break; 2719 } 2720 } 2721 } 2722 2723 // static 2724 size_t OMXCodec::countBuffersWeOwn(const Vector<BufferInfo> &buffers) { 2725 size_t n = 0; 2726 for (size_t i = 0; i < buffers.size(); ++i) { 2727 if (buffers[i].mStatus != OWNED_BY_COMPONENT) { 2728 ++n; 2729 } 2730 } 2731 2732 return n; 2733 } 2734 2735 status_t OMXCodec::freeBuffersOnPort( 2736 OMX_U32 portIndex, bool onlyThoseWeOwn) { 2737 Vector<BufferInfo> *buffers = &mPortBuffers[portIndex]; 2738 2739 status_t stickyErr = OK; 2740 2741 for (size_t i = buffers->size(); i-- > 0;) { 2742 BufferInfo *info = &buffers->editItemAt(i); 2743 2744 if (onlyThoseWeOwn && info->mStatus == OWNED_BY_COMPONENT) { 2745 continue; 2746 } 2747 2748 CHECK(info->mStatus == OWNED_BY_US 2749 || info->mStatus == OWNED_BY_NATIVE_WINDOW); 2750 2751 CODEC_LOGV("freeing buffer %p on port %ld", info->mBuffer, portIndex); 2752 2753 status_t err = freeBuffer(portIndex, i); 2754 2755 if (err != OK) { 2756 stickyErr = err; 2757 } 2758 2759 } 2760 2761 CHECK(onlyThoseWeOwn || buffers->isEmpty()); 2762 2763 return stickyErr; 2764 } 2765 2766 status_t OMXCodec::freeBuffer(OMX_U32 portIndex, size_t bufIndex) { 2767 Vector<BufferInfo> *buffers = &mPortBuffers[portIndex]; 2768 2769 BufferInfo *info = &buffers->editItemAt(bufIndex); 2770 2771 status_t err = mOMX->freeBuffer(mNode, portIndex, info->mBuffer); 2772 2773 if (err == OK && info->mMediaBuffer != NULL) { 2774 CHECK_EQ(portIndex, (OMX_U32)kPortIndexOutput); 2775 info->mMediaBuffer->setObserver(NULL); 2776 2777 // Make sure nobody but us owns this buffer at this point. 2778 CHECK_EQ(info->mMediaBuffer->refcount(), 0); 2779 2780 // Cancel the buffer if it belongs to an ANativeWindow. 2781 sp<GraphicBuffer> graphicBuffer = info->mMediaBuffer->graphicBuffer(); 2782 if (info->mStatus == OWNED_BY_US && graphicBuffer != 0) { 2783 err = cancelBufferToNativeWindow(info); 2784 } 2785 2786 info->mMediaBuffer->release(); 2787 info->mMediaBuffer = NULL; 2788 } 2789 2790 if (err == OK) { 2791 buffers->removeAt(bufIndex); 2792 } 2793 2794 return err; 2795 } 2796 2797 void OMXCodec::onPortSettingsChanged(OMX_U32 portIndex) { 2798 CODEC_LOGV("PORT_SETTINGS_CHANGED(%ld)", portIndex); 2799 2800 CHECK_EQ((int)mState, (int)EXECUTING); 2801 CHECK_EQ(portIndex, (OMX_U32)kPortIndexOutput); 2802 CHECK(!mOutputPortSettingsChangedPending); 2803 2804 if (mPortStatus[kPortIndexOutput] != ENABLED) { 2805 CODEC_LOGV("Deferring output port settings change."); 2806 mOutputPortSettingsChangedPending = true; 2807 return; 2808 } 2809 2810 setState(RECONFIGURING); 2811 2812 if (mQuirks & kNeedsFlushBeforeDisable) { 2813 if (!flushPortAsync(portIndex)) { 2814 onCmdComplete(OMX_CommandFlush, portIndex); 2815 } 2816 } else { 2817 disablePortAsync(portIndex); 2818 } 2819 } 2820 2821 bool OMXCodec::flushPortAsync(OMX_U32 portIndex) { 2822 CHECK(mState == EXECUTING || mState == RECONFIGURING 2823 || mState == EXECUTING_TO_IDLE); 2824 2825 CODEC_LOGV("flushPortAsync(%ld): we own %d out of %d buffers already.", 2826 portIndex, countBuffersWeOwn(mPortBuffers[portIndex]), 2827 mPortBuffers[portIndex].size()); 2828 2829 CHECK_EQ((int)mPortStatus[portIndex], (int)ENABLED); 2830 mPortStatus[portIndex] = SHUTTING_DOWN; 2831 2832 if ((mQuirks & kRequiresFlushCompleteEmulation) 2833 && countBuffersWeOwn(mPortBuffers[portIndex]) 2834 == mPortBuffers[portIndex].size()) { 2835 // No flush is necessary and this component fails to send a 2836 // flush-complete event in this case. 2837 2838 return false; 2839 } 2840 2841 status_t err = 2842 mOMX->sendCommand(mNode, OMX_CommandFlush, portIndex); 2843 CHECK_EQ(err, (status_t)OK); 2844 2845 return true; 2846 } 2847 2848 void OMXCodec::disablePortAsync(OMX_U32 portIndex) { 2849 CHECK(mState == EXECUTING || mState == RECONFIGURING); 2850 2851 CHECK_EQ((int)mPortStatus[portIndex], (int)ENABLED); 2852 mPortStatus[portIndex] = DISABLING; 2853 2854 CODEC_LOGV("sending OMX_CommandPortDisable(%ld)", portIndex); 2855 status_t err = 2856 mOMX->sendCommand(mNode, OMX_CommandPortDisable, portIndex); 2857 CHECK_EQ(err, (status_t)OK); 2858 2859 freeBuffersOnPort(portIndex, true); 2860 } 2861 2862 status_t OMXCodec::enablePortAsync(OMX_U32 portIndex) { 2863 CHECK(mState == EXECUTING || mState == RECONFIGURING); 2864 2865 CHECK_EQ((int)mPortStatus[portIndex], (int)DISABLED); 2866 mPortStatus[portIndex] = ENABLING; 2867 2868 CODEC_LOGV("sending OMX_CommandPortEnable(%ld)", portIndex); 2869 return mOMX->sendCommand(mNode, OMX_CommandPortEnable, portIndex); 2870 } 2871 2872 void OMXCodec::fillOutputBuffers() { 2873 CHECK_EQ((int)mState, (int)EXECUTING); 2874 2875 // This is a workaround for some decoders not properly reporting 2876 // end-of-output-stream. If we own all input buffers and also own 2877 // all output buffers and we already signalled end-of-input-stream, 2878 // the end-of-output-stream is implied. 2879 if (mSignalledEOS 2880 && countBuffersWeOwn(mPortBuffers[kPortIndexInput]) 2881 == mPortBuffers[kPortIndexInput].size() 2882 && countBuffersWeOwn(mPortBuffers[kPortIndexOutput]) 2883 == mPortBuffers[kPortIndexOutput].size()) { 2884 mNoMoreOutputData = true; 2885 mBufferFilled.signal(); 2886 2887 return; 2888 } 2889 2890 Vector<BufferInfo> *buffers = &mPortBuffers[kPortIndexOutput]; 2891 for (size_t i = 0; i < buffers->size(); ++i) { 2892 BufferInfo *info = &buffers->editItemAt(i); 2893 if (info->mStatus == OWNED_BY_US) { 2894 fillOutputBuffer(&buffers->editItemAt(i)); 2895 } 2896 } 2897 } 2898 2899 void OMXCodec::drainInputBuffers() { 2900 CHECK(mState == EXECUTING || mState == RECONFIGURING); 2901 2902 if (mFlags & kUseSecureInputBuffers) { 2903 Vector<BufferInfo> *buffers = &mPortBuffers[kPortIndexInput]; 2904 for (size_t i = 0; i < buffers->size(); ++i) { 2905 if (!drainAnyInputBuffer() 2906 || (mFlags & kOnlySubmitOneInputBufferAtOneTime)) { 2907 break; 2908 } 2909 } 2910 } else { 2911 Vector<BufferInfo> *buffers = &mPortBuffers[kPortIndexInput]; 2912 for (size_t i = 0; i < buffers->size(); ++i) { 2913 BufferInfo *info = &buffers->editItemAt(i); 2914 2915 if (info->mStatus != OWNED_BY_US) { 2916 continue; 2917 } 2918 2919 if (!drainInputBuffer(info)) { 2920 break; 2921 } 2922 2923 if (mFlags & kOnlySubmitOneInputBufferAtOneTime) { 2924 break; 2925 } 2926 } 2927 } 2928 } 2929 2930 bool OMXCodec::drainAnyInputBuffer() { 2931 return drainInputBuffer((BufferInfo *)NULL); 2932 } 2933 2934 OMXCodec::BufferInfo *OMXCodec::findInputBufferByDataPointer(void *ptr) { 2935 Vector<BufferInfo> *infos = &mPortBuffers[kPortIndexInput]; 2936 for (size_t i = 0; i < infos->size(); ++i) { 2937 BufferInfo *info = &infos->editItemAt(i); 2938 2939 if (info->mData == ptr) { 2940 CODEC_LOGV( 2941 "input buffer data ptr = %p, buffer_id = %p", 2942 ptr, 2943 info->mBuffer); 2944 2945 return info; 2946 } 2947 } 2948 2949 TRESPASS(); 2950 } 2951 2952 OMXCodec::BufferInfo *OMXCodec::findEmptyInputBuffer() { 2953 Vector<BufferInfo> *infos = &mPortBuffers[kPortIndexInput]; 2954 for (size_t i = 0; i < infos->size(); ++i) { 2955 BufferInfo *info = &infos->editItemAt(i); 2956 2957 if (info->mStatus == OWNED_BY_US) { 2958 return info; 2959 } 2960 } 2961 2962 TRESPASS(); 2963 } 2964 2965 bool OMXCodec::drainInputBuffer(BufferInfo *info) { 2966 if (info != NULL) { 2967 CHECK_EQ((int)info->mStatus, (int)OWNED_BY_US); 2968 } 2969 2970 if (mSignalledEOS) { 2971 return false; 2972 } 2973 2974 if (mCodecSpecificDataIndex < mCodecSpecificData.size()) { 2975 CHECK(!(mFlags & kUseSecureInputBuffers)); 2976 2977 const CodecSpecificData *specific = 2978 mCodecSpecificData[mCodecSpecificDataIndex]; 2979 2980 size_t size = specific->mSize; 2981 2982 if (!strcasecmp(MEDIA_MIMETYPE_VIDEO_AVC, mMIME) 2983 && !(mQuirks & kWantsNALFragments)) { 2984 static const uint8_t kNALStartCode[4] = 2985 { 0x00, 0x00, 0x00, 0x01 }; 2986 2987 CHECK(info->mSize >= specific->mSize + 4); 2988 2989 size += 4; 2990 2991 memcpy(info->mData, kNALStartCode, 4); 2992 memcpy((uint8_t *)info->mData + 4, 2993 specific->mData, specific->mSize); 2994 } else { 2995 CHECK(info->mSize >= specific->mSize); 2996 memcpy(info->mData, specific->mData, specific->mSize); 2997 } 2998 2999 mNoMoreOutputData = false; 3000 3001 CODEC_LOGV("calling emptyBuffer with codec specific data"); 3002 3003 status_t err = mOMX->emptyBuffer( 3004 mNode, info->mBuffer, 0, size, 3005 OMX_BUFFERFLAG_ENDOFFRAME | OMX_BUFFERFLAG_CODECCONFIG, 3006 0); 3007 CHECK_EQ(err, (status_t)OK); 3008 3009 info->mStatus = OWNED_BY_COMPONENT; 3010 3011 ++mCodecSpecificDataIndex; 3012 return true; 3013 } 3014 3015 if (mPaused) { 3016 return false; 3017 } 3018 3019 status_t err; 3020 3021 bool signalEOS = false; 3022 int64_t timestampUs = 0; 3023 3024 size_t offset = 0; 3025 int32_t n = 0; 3026 3027 3028 for (;;) { 3029 MediaBuffer *srcBuffer; 3030 if (mSeekTimeUs >= 0) { 3031 if (mLeftOverBuffer) { 3032 mLeftOverBuffer->release(); 3033 mLeftOverBuffer = NULL; 3034 } 3035 3036 MediaSource::ReadOptions options; 3037 options.setSeekTo(mSeekTimeUs, mSeekMode); 3038 3039 mSeekTimeUs = -1; 3040 mSeekMode = ReadOptions::SEEK_CLOSEST_SYNC; 3041 mBufferFilled.signal(); 3042 3043 err = mSource->read(&srcBuffer, &options); 3044 3045 if (err == OK) { 3046 int64_t targetTimeUs; 3047 if (srcBuffer->meta_data()->findInt64( 3048 kKeyTargetTime, &targetTimeUs) 3049 && targetTimeUs >= 0) { 3050 CODEC_LOGV("targetTimeUs = %lld us", targetTimeUs); 3051 mTargetTimeUs = targetTimeUs; 3052 } else { 3053 mTargetTimeUs = -1; 3054 } 3055 } 3056 } else if (mLeftOverBuffer) { 3057 srcBuffer = mLeftOverBuffer; 3058 mLeftOverBuffer = NULL; 3059 3060 err = OK; 3061 } else { 3062 err = mSource->read(&srcBuffer); 3063 } 3064 3065 if (err != OK) { 3066 signalEOS = true; 3067 mFinalStatus = err; 3068 mSignalledEOS = true; 3069 mBufferFilled.signal(); 3070 break; 3071 } 3072 3073 if (mFlags & kUseSecureInputBuffers) { 3074 info = findInputBufferByDataPointer(srcBuffer->data()); 3075 CHECK(info != NULL); 3076 } 3077 3078 size_t remainingBytes = info->mSize - offset; 3079 3080 if (srcBuffer->range_length() > remainingBytes) { 3081 if (offset == 0) { 3082 CODEC_LOGE( 3083 "Codec's input buffers are too small to accomodate " 3084 "buffer read from source (info->mSize = %d, srcLength = %d)", 3085 info->mSize, srcBuffer->range_length()); 3086 3087 srcBuffer->release(); 3088 srcBuffer = NULL; 3089 3090 setState(ERROR); 3091 return false; 3092 } 3093 3094 mLeftOverBuffer = srcBuffer; 3095 break; 3096 } 3097 3098 bool releaseBuffer = true; 3099 if (mFlags & kStoreMetaDataInVideoBuffers) { 3100 releaseBuffer = false; 3101 info->mMediaBuffer = srcBuffer; 3102 } 3103 3104 if (mFlags & kUseSecureInputBuffers) { 3105 // Data in "info" is already provided at this time. 3106 3107 releaseBuffer = false; 3108 3109 CHECK(info->mMediaBuffer == NULL); 3110 info->mMediaBuffer = srcBuffer; 3111 } else { 3112 CHECK(srcBuffer->data() != NULL) ; 3113 memcpy((uint8_t *)info->mData + offset, 3114 (const uint8_t *)srcBuffer->data() 3115 + srcBuffer->range_offset(), 3116 srcBuffer->range_length()); 3117 } 3118 3119 int64_t lastBufferTimeUs; 3120 CHECK(srcBuffer->meta_data()->findInt64(kKeyTime, &lastBufferTimeUs)); 3121 CHECK(lastBufferTimeUs >= 0); 3122 if (mIsEncoder && mIsVideo) { 3123 mDecodingTimeList.push_back(lastBufferTimeUs); 3124 } 3125 3126 if (offset == 0) { 3127 timestampUs = lastBufferTimeUs; 3128 } 3129 3130 offset += srcBuffer->range_length(); 3131 3132 if (!strcasecmp(MEDIA_MIMETYPE_AUDIO_VORBIS, mMIME)) { 3133 CHECK(!(mQuirks & kSupportsMultipleFramesPerInputBuffer)); 3134 CHECK_GE(info->mSize, offset + sizeof(int32_t)); 3135 3136 int32_t numPageSamples; 3137 if (!srcBuffer->meta_data()->findInt32( 3138 kKeyValidSamples, &numPageSamples)) { 3139 numPageSamples = -1; 3140 } 3141 3142 memcpy((uint8_t *)info->mData + offset, 3143 &numPageSamples, 3144 sizeof(numPageSamples)); 3145 3146 offset += sizeof(numPageSamples); 3147 } 3148 3149 if (releaseBuffer) { 3150 srcBuffer->release(); 3151 srcBuffer = NULL; 3152 } 3153 3154 ++n; 3155 3156 if (!(mQuirks & kSupportsMultipleFramesPerInputBuffer)) { 3157 break; 3158 } 3159 3160 int64_t coalescedDurationUs = lastBufferTimeUs - timestampUs; 3161 3162 if (coalescedDurationUs > 250000ll) { 3163 // Don't coalesce more than 250ms worth of encoded data at once. 3164 break; 3165 } 3166 } 3167 3168 if (n > 1) { 3169 ALOGV("coalesced %d frames into one input buffer", n); 3170 } 3171 3172 OMX_U32 flags = OMX_BUFFERFLAG_ENDOFFRAME; 3173 3174 if (signalEOS) { 3175 flags |= OMX_BUFFERFLAG_EOS; 3176 } else { 3177 mNoMoreOutputData = false; 3178 } 3179 3180 if (info == NULL) { 3181 CHECK(mFlags & kUseSecureInputBuffers); 3182 CHECK(signalEOS); 3183 3184 // This is fishy, there's still a MediaBuffer corresponding to this 3185 // info available to the source at this point even though we're going 3186 // to use it to signal EOS to the codec. 3187 info = findEmptyInputBuffer(); 3188 } 3189 3190 CODEC_LOGV("Calling emptyBuffer on buffer %p (length %d), " 3191 "timestamp %lld us (%.2f secs)", 3192 info->mBuffer, offset, 3193 timestampUs, timestampUs / 1E6); 3194 3195 err = mOMX->emptyBuffer( 3196 mNode, info->mBuffer, 0, offset, 3197 flags, timestampUs); 3198 3199 if (err != OK) { 3200 setState(ERROR); 3201 return false; 3202 } 3203 3204 info->mStatus = OWNED_BY_COMPONENT; 3205 3206 return true; 3207 } 3208 3209 void OMXCodec::fillOutputBuffer(BufferInfo *info) { 3210 CHECK_EQ((int)info->mStatus, (int)OWNED_BY_US); 3211 3212 if (mNoMoreOutputData) { 3213 CODEC_LOGV("There is no more output data available, not " 3214 "calling fillOutputBuffer"); 3215 return; 3216 } 3217 3218 CODEC_LOGV("Calling fillBuffer on buffer %p", info->mBuffer); 3219 status_t err = mOMX->fillBuffer(mNode, info->mBuffer); 3220 3221 if (err != OK) { 3222 CODEC_LOGE("fillBuffer failed w/ error 0x%08x", err); 3223 3224 setState(ERROR); 3225 return; 3226 } 3227 3228 info->mStatus = OWNED_BY_COMPONENT; 3229 } 3230 3231 bool OMXCodec::drainInputBuffer(IOMX::buffer_id buffer) { 3232 Vector<BufferInfo> *buffers = &mPortBuffers[kPortIndexInput]; 3233 for (size_t i = 0; i < buffers->size(); ++i) { 3234 if ((*buffers)[i].mBuffer == buffer) { 3235 return drainInputBuffer(&buffers->editItemAt(i)); 3236 } 3237 } 3238 3239 CHECK(!"should not be here."); 3240 3241 return false; 3242 } 3243 3244 void OMXCodec::fillOutputBuffer(IOMX::buffer_id buffer) { 3245 Vector<BufferInfo> *buffers = &mPortBuffers[kPortIndexOutput]; 3246 for (size_t i = 0; i < buffers->size(); ++i) { 3247 if ((*buffers)[i].mBuffer == buffer) { 3248 fillOutputBuffer(&buffers->editItemAt(i)); 3249 return; 3250 } 3251 } 3252 3253 CHECK(!"should not be here."); 3254 } 3255 3256 void OMXCodec::setState(State newState) { 3257 mState = newState; 3258 mAsyncCompletion.signal(); 3259 3260 // This may cause some spurious wakeups but is necessary to 3261 // unblock the reader if we enter ERROR state. 3262 mBufferFilled.signal(); 3263 } 3264 3265 status_t OMXCodec::waitForBufferFilled_l() { 3266 3267 if (mIsEncoder) { 3268 // For timelapse video recording, the timelapse video recording may 3269 // not send an input frame for a _long_ time. Do not use timeout 3270 // for video encoding. 3271 return mBufferFilled.wait(mLock); 3272 } 3273 status_t err = mBufferFilled.waitRelative(mLock, kBufferFilledEventTimeOutNs); 3274 if (err != OK) { 3275 CODEC_LOGE("Timed out waiting for output buffers: %d/%d", 3276 countBuffersWeOwn(mPortBuffers[kPortIndexInput]), 3277 countBuffersWeOwn(mPortBuffers[kPortIndexOutput])); 3278 } 3279 return err; 3280 } 3281 3282 void OMXCodec::setRawAudioFormat( 3283 OMX_U32 portIndex, int32_t sampleRate, int32_t numChannels) { 3284 3285 // port definition 3286 OMX_PARAM_PORTDEFINITIONTYPE def; 3287 InitOMXParams(&def); 3288 def.nPortIndex = portIndex; 3289 status_t err = mOMX->getParameter( 3290 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 3291 CHECK_EQ(err, (status_t)OK); 3292 def.format.audio.eEncoding = OMX_AUDIO_CodingPCM; 3293 CHECK_EQ(mOMX->setParameter(mNode, OMX_IndexParamPortDefinition, 3294 &def, sizeof(def)), (status_t)OK); 3295 3296 // pcm param 3297 OMX_AUDIO_PARAM_PCMMODETYPE pcmParams; 3298 InitOMXParams(&pcmParams); 3299 pcmParams.nPortIndex = portIndex; 3300 3301 err = mOMX->getParameter( 3302 mNode, OMX_IndexParamAudioPcm, &pcmParams, sizeof(pcmParams)); 3303 3304 CHECK_EQ(err, (status_t)OK); 3305 3306 pcmParams.nChannels = numChannels; 3307 pcmParams.eNumData = OMX_NumericalDataSigned; 3308 pcmParams.bInterleaved = OMX_TRUE; 3309 pcmParams.nBitPerSample = 16; 3310 pcmParams.nSamplingRate = sampleRate; 3311 pcmParams.ePCMMode = OMX_AUDIO_PCMModeLinear; 3312 3313 CHECK_EQ(getOMXChannelMapping( 3314 numChannels, pcmParams.eChannelMapping), (status_t)OK); 3315 3316 err = mOMX->setParameter( 3317 mNode, OMX_IndexParamAudioPcm, &pcmParams, sizeof(pcmParams)); 3318 3319 CHECK_EQ(err, (status_t)OK); 3320 } 3321 3322 static OMX_AUDIO_AMRBANDMODETYPE pickModeFromBitRate(bool isAMRWB, int32_t bps) { 3323 if (isAMRWB) { 3324 if (bps <= 6600) { 3325 return OMX_AUDIO_AMRBandModeWB0; 3326 } else if (bps <= 8850) { 3327 return OMX_AUDIO_AMRBandModeWB1; 3328 } else if (bps <= 12650) { 3329 return OMX_AUDIO_AMRBandModeWB2; 3330 } else if (bps <= 14250) { 3331 return OMX_AUDIO_AMRBandModeWB3; 3332 } else if (bps <= 15850) { 3333 return OMX_AUDIO_AMRBandModeWB4; 3334 } else if (bps <= 18250) { 3335 return OMX_AUDIO_AMRBandModeWB5; 3336 } else if (bps <= 19850) { 3337 return OMX_AUDIO_AMRBandModeWB6; 3338 } else if (bps <= 23050) { 3339 return OMX_AUDIO_AMRBandModeWB7; 3340 } 3341 3342 // 23850 bps 3343 return OMX_AUDIO_AMRBandModeWB8; 3344 } else { // AMRNB 3345 if (bps <= 4750) { 3346 return OMX_AUDIO_AMRBandModeNB0; 3347 } else if (bps <= 5150) { 3348 return OMX_AUDIO_AMRBandModeNB1; 3349 } else if (bps <= 5900) { 3350 return OMX_AUDIO_AMRBandModeNB2; 3351 } else if (bps <= 6700) { 3352 return OMX_AUDIO_AMRBandModeNB3; 3353 } else if (bps <= 7400) { 3354 return OMX_AUDIO_AMRBandModeNB4; 3355 } else if (bps <= 7950) { 3356 return OMX_AUDIO_AMRBandModeNB5; 3357 } else if (bps <= 10200) { 3358 return OMX_AUDIO_AMRBandModeNB6; 3359 } 3360 3361 // 12200 bps 3362 return OMX_AUDIO_AMRBandModeNB7; 3363 } 3364 } 3365 3366 void OMXCodec::setAMRFormat(bool isWAMR, int32_t bitRate) { 3367 OMX_U32 portIndex = mIsEncoder ? kPortIndexOutput : kPortIndexInput; 3368 3369 OMX_AUDIO_PARAM_AMRTYPE def; 3370 InitOMXParams(&def); 3371 def.nPortIndex = portIndex; 3372 3373 status_t err = 3374 mOMX->getParameter(mNode, OMX_IndexParamAudioAmr, &def, sizeof(def)); 3375 3376 CHECK_EQ(err, (status_t)OK); 3377 3378 def.eAMRFrameFormat = OMX_AUDIO_AMRFrameFormatFSF; 3379 3380 def.eAMRBandMode = pickModeFromBitRate(isWAMR, bitRate); 3381 err = mOMX->setParameter(mNode, OMX_IndexParamAudioAmr, &def, sizeof(def)); 3382 CHECK_EQ(err, (status_t)OK); 3383 3384 //////////////////////// 3385 3386 if (mIsEncoder) { 3387 sp<MetaData> format = mSource->getFormat(); 3388 int32_t sampleRate; 3389 int32_t numChannels; 3390 CHECK(format->findInt32(kKeySampleRate, &sampleRate)); 3391 CHECK(format->findInt32(kKeyChannelCount, &numChannels)); 3392 3393 setRawAudioFormat(kPortIndexInput, sampleRate, numChannels); 3394 } 3395 } 3396 3397 status_t OMXCodec::setAACFormat( 3398 int32_t numChannels, int32_t sampleRate, int32_t bitRate, int32_t aacProfile, bool isADTS) { 3399 if (numChannels > 2) { 3400 ALOGW("Number of channels: (%d) \n", numChannels); 3401 } 3402 3403 if (mIsEncoder) { 3404 if (isADTS) { 3405 return -EINVAL; 3406 } 3407 3408 //////////////// input port //////////////////// 3409 setRawAudioFormat(kPortIndexInput, sampleRate, numChannels); 3410 3411 //////////////// output port //////////////////// 3412 // format 3413 OMX_AUDIO_PARAM_PORTFORMATTYPE format; 3414 InitOMXParams(&format); 3415 format.nPortIndex = kPortIndexOutput; 3416 format.nIndex = 0; 3417 status_t err = OMX_ErrorNone; 3418 while (OMX_ErrorNone == err) { 3419 CHECK_EQ(mOMX->getParameter(mNode, OMX_IndexParamAudioPortFormat, 3420 &format, sizeof(format)), (status_t)OK); 3421 if (format.eEncoding == OMX_AUDIO_CodingAAC) { 3422 break; 3423 } 3424 format.nIndex++; 3425 } 3426 CHECK_EQ((status_t)OK, err); 3427 CHECK_EQ(mOMX->setParameter(mNode, OMX_IndexParamAudioPortFormat, 3428 &format, sizeof(format)), (status_t)OK); 3429 3430 // port definition 3431 OMX_PARAM_PORTDEFINITIONTYPE def; 3432 InitOMXParams(&def); 3433 def.nPortIndex = kPortIndexOutput; 3434 CHECK_EQ(mOMX->getParameter(mNode, OMX_IndexParamPortDefinition, 3435 &def, sizeof(def)), (status_t)OK); 3436 def.format.audio.bFlagErrorConcealment = OMX_TRUE; 3437 def.format.audio.eEncoding = OMX_AUDIO_CodingAAC; 3438 CHECK_EQ(mOMX->setParameter(mNode, OMX_IndexParamPortDefinition, 3439 &def, sizeof(def)), (status_t)OK); 3440 3441 // profile 3442 OMX_AUDIO_PARAM_AACPROFILETYPE profile; 3443 InitOMXParams(&profile); 3444 profile.nPortIndex = kPortIndexOutput; 3445 CHECK_EQ(mOMX->getParameter(mNode, OMX_IndexParamAudioAac, 3446 &profile, sizeof(profile)), (status_t)OK); 3447 profile.nChannels = numChannels; 3448 profile.eChannelMode = (numChannels == 1? 3449 OMX_AUDIO_ChannelModeMono: OMX_AUDIO_ChannelModeStereo); 3450 profile.nSampleRate = sampleRate; 3451 profile.nBitRate = bitRate; 3452 profile.nAudioBandWidth = 0; 3453 profile.nFrameLength = 0; 3454 profile.nAACtools = OMX_AUDIO_AACToolAll; 3455 profile.nAACERtools = OMX_AUDIO_AACERNone; 3456 profile.eAACProfile = (OMX_AUDIO_AACPROFILETYPE) aacProfile; 3457 profile.eAACStreamFormat = OMX_AUDIO_AACStreamFormatMP4FF; 3458 err = mOMX->setParameter(mNode, OMX_IndexParamAudioAac, 3459 &profile, sizeof(profile)); 3460 3461 if (err != OK) { 3462 CODEC_LOGE("setParameter('OMX_IndexParamAudioAac') failed " 3463 "(err = %d)", 3464 err); 3465 return err; 3466 } 3467 } else { 3468 OMX_AUDIO_PARAM_AACPROFILETYPE profile; 3469 InitOMXParams(&profile); 3470 profile.nPortIndex = kPortIndexInput; 3471 3472 status_t err = mOMX->getParameter( 3473 mNode, OMX_IndexParamAudioAac, &profile, sizeof(profile)); 3474 CHECK_EQ(err, (status_t)OK); 3475 3476 profile.nChannels = numChannels; 3477 profile.nSampleRate = sampleRate; 3478 3479 profile.eAACStreamFormat = 3480 isADTS 3481 ? OMX_AUDIO_AACStreamFormatMP4ADTS 3482 : OMX_AUDIO_AACStreamFormatMP4FF; 3483 3484 err = mOMX->setParameter( 3485 mNode, OMX_IndexParamAudioAac, &profile, sizeof(profile)); 3486 3487 if (err != OK) { 3488 CODEC_LOGE("setParameter('OMX_IndexParamAudioAac') failed " 3489 "(err = %d)", 3490 err); 3491 return err; 3492 } 3493 } 3494 3495 return OK; 3496 } 3497 3498 void OMXCodec::setG711Format(int32_t numChannels) { 3499 CHECK(!mIsEncoder); 3500 setRawAudioFormat(kPortIndexInput, 8000, numChannels); 3501 } 3502 3503 void OMXCodec::setImageOutputFormat( 3504 OMX_COLOR_FORMATTYPE format, OMX_U32 width, OMX_U32 height) { 3505 CODEC_LOGV("setImageOutputFormat(%ld, %ld)", width, height); 3506 3507 #if 0 3508 OMX_INDEXTYPE index; 3509 status_t err = mOMX->get_extension_index( 3510 mNode, "OMX.TI.JPEG.decode.Config.OutputColorFormat", &index); 3511 CHECK_EQ(err, (status_t)OK); 3512 3513 err = mOMX->set_config(mNode, index, &format, sizeof(format)); 3514 CHECK_EQ(err, (status_t)OK); 3515 #endif 3516 3517 OMX_PARAM_PORTDEFINITIONTYPE def; 3518 InitOMXParams(&def); 3519 def.nPortIndex = kPortIndexOutput; 3520 3521 status_t err = mOMX->getParameter( 3522 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 3523 CHECK_EQ(err, (status_t)OK); 3524 3525 CHECK_EQ((int)def.eDomain, (int)OMX_PortDomainImage); 3526 3527 OMX_IMAGE_PORTDEFINITIONTYPE *imageDef = &def.format.image; 3528 3529 CHECK_EQ((int)imageDef->eCompressionFormat, (int)OMX_IMAGE_CodingUnused); 3530 imageDef->eColorFormat = format; 3531 imageDef->nFrameWidth = width; 3532 imageDef->nFrameHeight = height; 3533 3534 switch (format) { 3535 case OMX_COLOR_FormatYUV420PackedPlanar: 3536 case OMX_COLOR_FormatYUV411Planar: 3537 { 3538 def.nBufferSize = (width * height * 3) / 2; 3539 break; 3540 } 3541 3542 case OMX_COLOR_FormatCbYCrY: 3543 { 3544 def.nBufferSize = width * height * 2; 3545 break; 3546 } 3547 3548 case OMX_COLOR_Format32bitARGB8888: 3549 { 3550 def.nBufferSize = width * height * 4; 3551 break; 3552 } 3553 3554 case OMX_COLOR_Format16bitARGB4444: 3555 case OMX_COLOR_Format16bitARGB1555: 3556 case OMX_COLOR_Format16bitRGB565: 3557 case OMX_COLOR_Format16bitBGR565: 3558 { 3559 def.nBufferSize = width * height * 2; 3560 break; 3561 } 3562 3563 default: 3564 CHECK(!"Should not be here. Unknown color format."); 3565 break; 3566 } 3567 3568 def.nBufferCountActual = def.nBufferCountMin; 3569 3570 err = mOMX->setParameter( 3571 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 3572 CHECK_EQ(err, (status_t)OK); 3573 } 3574 3575 void OMXCodec::setJPEGInputFormat( 3576 OMX_U32 width, OMX_U32 height, OMX_U32 compressedSize) { 3577 OMX_PARAM_PORTDEFINITIONTYPE def; 3578 InitOMXParams(&def); 3579 def.nPortIndex = kPortIndexInput; 3580 3581 status_t err = mOMX->getParameter( 3582 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 3583 CHECK_EQ(err, (status_t)OK); 3584 3585 CHECK_EQ((int)def.eDomain, (int)OMX_PortDomainImage); 3586 OMX_IMAGE_PORTDEFINITIONTYPE *imageDef = &def.format.image; 3587 3588 CHECK_EQ((int)imageDef->eCompressionFormat, (int)OMX_IMAGE_CodingJPEG); 3589 imageDef->nFrameWidth = width; 3590 imageDef->nFrameHeight = height; 3591 3592 def.nBufferSize = compressedSize; 3593 def.nBufferCountActual = def.nBufferCountMin; 3594 3595 err = mOMX->setParameter( 3596 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 3597 CHECK_EQ(err, (status_t)OK); 3598 } 3599 3600 void OMXCodec::addCodecSpecificData(const void *data, size_t size) { 3601 CodecSpecificData *specific = 3602 (CodecSpecificData *)malloc(sizeof(CodecSpecificData) + size - 1); 3603 3604 specific->mSize = size; 3605 memcpy(specific->mData, data, size); 3606 3607 mCodecSpecificData.push(specific); 3608 } 3609 3610 void OMXCodec::clearCodecSpecificData() { 3611 for (size_t i = 0; i < mCodecSpecificData.size(); ++i) { 3612 free(mCodecSpecificData.editItemAt(i)); 3613 } 3614 mCodecSpecificData.clear(); 3615 mCodecSpecificDataIndex = 0; 3616 } 3617 3618 status_t OMXCodec::start(MetaData *meta) { 3619 Mutex::Autolock autoLock(mLock); 3620 3621 if (mState != LOADED) { 3622 CODEC_LOGE("called start in the unexpected state: %d", mState); 3623 return UNKNOWN_ERROR; 3624 } 3625 3626 sp<MetaData> params = new MetaData; 3627 if (mQuirks & kWantsNALFragments) { 3628 params->setInt32(kKeyWantsNALFragments, true); 3629 } 3630 if (meta) { 3631 int64_t startTimeUs = 0; 3632 int64_t timeUs; 3633 if (meta->findInt64(kKeyTime, &timeUs)) { 3634 startTimeUs = timeUs; 3635 } 3636 params->setInt64(kKeyTime, startTimeUs); 3637 } 3638 3639 mCodecSpecificDataIndex = 0; 3640 mInitialBufferSubmit = true; 3641 mSignalledEOS = false; 3642 mNoMoreOutputData = false; 3643 mOutputPortSettingsHaveChanged = false; 3644 mSeekTimeUs = -1; 3645 mSeekMode = ReadOptions::SEEK_CLOSEST_SYNC; 3646 mTargetTimeUs = -1; 3647 mFilledBuffers.clear(); 3648 mPaused = false; 3649 3650 status_t err; 3651 if (mIsEncoder) { 3652 // Calling init() before starting its source so that we can configure, 3653 // if supported, the source to use exactly the same number of input 3654 // buffers as requested by the encoder. 3655 if ((err = init()) != OK) { 3656 CODEC_LOGE("init failed: %d", err); 3657 return err; 3658 } 3659 3660 params->setInt32(kKeyNumBuffers, mPortBuffers[kPortIndexInput].size()); 3661 err = mSource->start(params.get()); 3662 if (err != OK) { 3663 CODEC_LOGE("source failed to start: %d", err); 3664 stopOmxComponent_l(); 3665 } 3666 return err; 3667 } 3668 3669 // Decoder case 3670 if ((err = mSource->start(params.get())) != OK) { 3671 CODEC_LOGE("source failed to start: %d", err); 3672 return err; 3673 } 3674 return init(); 3675 } 3676 3677 status_t OMXCodec::stop() { 3678 CODEC_LOGV("stop mState=%d", mState); 3679 Mutex::Autolock autoLock(mLock); 3680 status_t err = stopOmxComponent_l(); 3681 mSource->stop(); 3682 3683 CODEC_LOGV("stopped in state %d", mState); 3684 return err; 3685 } 3686 3687 status_t OMXCodec::stopOmxComponent_l() { 3688 CODEC_LOGV("stopOmxComponent_l mState=%d", mState); 3689 3690 while (isIntermediateState(mState)) { 3691 mAsyncCompletion.wait(mLock); 3692 } 3693 3694 bool isError = false; 3695 switch (mState) { 3696 case LOADED: 3697 break; 3698 3699 case ERROR: 3700 { 3701 if (mPortStatus[kPortIndexOutput] == ENABLING) { 3702 // Codec is in a wedged state (technical term) 3703 // We've seen an output port settings change from the codec, 3704 // We've disabled the output port, then freed the output 3705 // buffers, initiated re-enabling the output port but 3706 // failed to reallocate the output buffers. 3707 // There doesn't seem to be a way to orderly transition 3708 // from executing->idle and idle->loaded now that the 3709 // output port hasn't been reenabled yet... 3710 // Simply free as many resources as we can and pretend 3711 // that we're in LOADED state so that the destructor 3712 // will free the component instance without asserting. 3713 freeBuffersOnPort(kPortIndexInput, true /* onlyThoseWeOwn */); 3714 freeBuffersOnPort(kPortIndexOutput, true /* onlyThoseWeOwn */); 3715 setState(LOADED); 3716 break; 3717 } else { 3718 OMX_STATETYPE state = OMX_StateInvalid; 3719 status_t err = mOMX->getState(mNode, &state); 3720 CHECK_EQ(err, (status_t)OK); 3721 3722 if (state != OMX_StateExecuting) { 3723 break; 3724 } 3725 // else fall through to the idling code 3726 } 3727 3728 isError = true; 3729 } 3730 3731 case EXECUTING: 3732 { 3733 setState(EXECUTING_TO_IDLE); 3734 3735 if (mQuirks & kRequiresFlushBeforeShutdown) { 3736 CODEC_LOGV("This component requires a flush before transitioning " 3737 "from EXECUTING to IDLE..."); 3738 3739 bool emulateInputFlushCompletion = 3740 !flushPortAsync(kPortIndexInput); 3741 3742 bool emulateOutputFlushCompletion = 3743 !flushPortAsync(kPortIndexOutput); 3744 3745 if (emulateInputFlushCompletion) { 3746 onCmdComplete(OMX_CommandFlush, kPortIndexInput); 3747 } 3748 3749 if (emulateOutputFlushCompletion) { 3750 onCmdComplete(OMX_CommandFlush, kPortIndexOutput); 3751 } 3752 } else { 3753 mPortStatus[kPortIndexInput] = SHUTTING_DOWN; 3754 mPortStatus[kPortIndexOutput] = SHUTTING_DOWN; 3755 3756 status_t err = 3757 mOMX->sendCommand(mNode, OMX_CommandStateSet, OMX_StateIdle); 3758 CHECK_EQ(err, (status_t)OK); 3759 } 3760 3761 while (mState != LOADED && mState != ERROR) { 3762 mAsyncCompletion.wait(mLock); 3763 } 3764 3765 if (isError) { 3766 // We were in the ERROR state coming in, so restore that now 3767 // that we've idled the OMX component. 3768 setState(ERROR); 3769 } 3770 3771 break; 3772 } 3773 3774 default: 3775 { 3776 CHECK(!"should not be here."); 3777 break; 3778 } 3779 } 3780 3781 if (mLeftOverBuffer) { 3782 mLeftOverBuffer->release(); 3783 mLeftOverBuffer = NULL; 3784 } 3785 3786 return OK; 3787 } 3788 3789 sp<MetaData> OMXCodec::getFormat() { 3790 Mutex::Autolock autoLock(mLock); 3791 3792 return mOutputFormat; 3793 } 3794 3795 status_t OMXCodec::read( 3796 MediaBuffer **buffer, const ReadOptions *options) { 3797 status_t err = OK; 3798 *buffer = NULL; 3799 3800 Mutex::Autolock autoLock(mLock); 3801 3802 if (mState != EXECUTING && mState != RECONFIGURING) { 3803 return UNKNOWN_ERROR; 3804 } 3805 3806 bool seeking = false; 3807 int64_t seekTimeUs; 3808 ReadOptions::SeekMode seekMode; 3809 if (options && options->getSeekTo(&seekTimeUs, &seekMode)) { 3810 seeking = true; 3811 } 3812 3813 if (mInitialBufferSubmit) { 3814 mInitialBufferSubmit = false; 3815 3816 if (seeking) { 3817 CHECK(seekTimeUs >= 0); 3818 mSeekTimeUs = seekTimeUs; 3819 mSeekMode = seekMode; 3820 3821 // There's no reason to trigger the code below, there's 3822 // nothing to flush yet. 3823 seeking = false; 3824 mPaused = false; 3825 } 3826 3827 drainInputBuffers(); 3828 3829 if (mState == EXECUTING) { 3830 // Otherwise mState == RECONFIGURING and this code will trigger 3831 // after the output port is reenabled. 3832 fillOutputBuffers(); 3833 } 3834 } 3835 3836 if (seeking) { 3837 while (mState == RECONFIGURING) { 3838 if ((err = waitForBufferFilled_l()) != OK) { 3839 return err; 3840 } 3841 } 3842 3843 if (mState != EXECUTING) { 3844 return UNKNOWN_ERROR; 3845 } 3846 3847 CODEC_LOGV("seeking to %lld us (%.2f secs)", seekTimeUs, seekTimeUs / 1E6); 3848 3849 mSignalledEOS = false; 3850 3851 CHECK(seekTimeUs >= 0); 3852 mSeekTimeUs = seekTimeUs; 3853 mSeekMode = seekMode; 3854 3855 mFilledBuffers.clear(); 3856 3857 CHECK_EQ((int)mState, (int)EXECUTING); 3858 3859 bool emulateInputFlushCompletion = !flushPortAsync(kPortIndexInput); 3860 bool emulateOutputFlushCompletion = !flushPortAsync(kPortIndexOutput); 3861 3862 if (emulateInputFlushCompletion) { 3863 onCmdComplete(OMX_CommandFlush, kPortIndexInput); 3864 } 3865 3866 if (emulateOutputFlushCompletion) { 3867 onCmdComplete(OMX_CommandFlush, kPortIndexOutput); 3868 } 3869 3870 while (mSeekTimeUs >= 0) { 3871 if ((err = waitForBufferFilled_l()) != OK) { 3872 return err; 3873 } 3874 } 3875 } 3876 3877 while (mState != ERROR && !mNoMoreOutputData && mFilledBuffers.empty()) { 3878 if ((err = waitForBufferFilled_l()) != OK) { 3879 return err; 3880 } 3881 } 3882 3883 if (mState == ERROR) { 3884 return UNKNOWN_ERROR; 3885 } 3886 3887 if (mFilledBuffers.empty()) { 3888 return mSignalledEOS ? mFinalStatus : ERROR_END_OF_STREAM; 3889 } 3890 3891 if (mOutputPortSettingsHaveChanged) { 3892 mOutputPortSettingsHaveChanged = false; 3893 3894 return INFO_FORMAT_CHANGED; 3895 } 3896 3897 size_t index = *mFilledBuffers.begin(); 3898 mFilledBuffers.erase(mFilledBuffers.begin()); 3899 3900 BufferInfo *info = &mPortBuffers[kPortIndexOutput].editItemAt(index); 3901 CHECK_EQ((int)info->mStatus, (int)OWNED_BY_US); 3902 info->mStatus = OWNED_BY_CLIENT; 3903 3904 info->mMediaBuffer->add_ref(); 3905 if (mSkipCutBuffer != NULL) { 3906 mSkipCutBuffer->submit(info->mMediaBuffer); 3907 } 3908 *buffer = info->mMediaBuffer; 3909 3910 return OK; 3911 } 3912 3913 void OMXCodec::signalBufferReturned(MediaBuffer *buffer) { 3914 Mutex::Autolock autoLock(mLock); 3915 3916 Vector<BufferInfo> *buffers = &mPortBuffers[kPortIndexOutput]; 3917 for (size_t i = 0; i < buffers->size(); ++i) { 3918 BufferInfo *info = &buffers->editItemAt(i); 3919 3920 if (info->mMediaBuffer == buffer) { 3921 CHECK_EQ((int)mPortStatus[kPortIndexOutput], (int)ENABLED); 3922 CHECK_EQ((int)info->mStatus, (int)OWNED_BY_CLIENT); 3923 3924 info->mStatus = OWNED_BY_US; 3925 3926 if (buffer->graphicBuffer() == 0) { 3927 fillOutputBuffer(info); 3928 } else { 3929 sp<MetaData> metaData = info->mMediaBuffer->meta_data(); 3930 int32_t rendered = 0; 3931 if (!metaData->findInt32(kKeyRendered, &rendered)) { 3932 rendered = 0; 3933 } 3934 if (!rendered) { 3935 status_t err = cancelBufferToNativeWindow(info); 3936 if (err < 0) { 3937 return; 3938 } 3939 } 3940 3941 info->mStatus = OWNED_BY_NATIVE_WINDOW; 3942 3943 // Dequeue the next buffer from the native window. 3944 BufferInfo *nextBufInfo = dequeueBufferFromNativeWindow(); 3945 if (nextBufInfo == 0) { 3946 return; 3947 } 3948 3949 // Give the buffer to the OMX node to fill. 3950 fillOutputBuffer(nextBufInfo); 3951 } 3952 return; 3953 } 3954 } 3955 3956 CHECK(!"should not be here."); 3957 } 3958 3959 static const char *imageCompressionFormatString(OMX_IMAGE_CODINGTYPE type) { 3960 static const char *kNames[] = { 3961 "OMX_IMAGE_CodingUnused", 3962 "OMX_IMAGE_CodingAutoDetect", 3963 "OMX_IMAGE_CodingJPEG", 3964 "OMX_IMAGE_CodingJPEG2K", 3965 "OMX_IMAGE_CodingEXIF", 3966 "OMX_IMAGE_CodingTIFF", 3967 "OMX_IMAGE_CodingGIF", 3968 "OMX_IMAGE_CodingPNG", 3969 "OMX_IMAGE_CodingLZW", 3970 "OMX_IMAGE_CodingBMP", 3971 }; 3972 3973 size_t numNames = sizeof(kNames) / sizeof(kNames[0]); 3974 3975 if (type < 0 || (size_t)type >= numNames) { 3976 return "UNKNOWN"; 3977 } else { 3978 return kNames[type]; 3979 } 3980 } 3981 3982 static const char *colorFormatString(OMX_COLOR_FORMATTYPE type) { 3983 static const char *kNames[] = { 3984 "OMX_COLOR_FormatUnused", 3985 "OMX_COLOR_FormatMonochrome", 3986 "OMX_COLOR_Format8bitRGB332", 3987 "OMX_COLOR_Format12bitRGB444", 3988 "OMX_COLOR_Format16bitARGB4444", 3989 "OMX_COLOR_Format16bitARGB1555", 3990 "OMX_COLOR_Format16bitRGB565", 3991 "OMX_COLOR_Format16bitBGR565", 3992 "OMX_COLOR_Format18bitRGB666", 3993 "OMX_COLOR_Format18bitARGB1665", 3994 "OMX_COLOR_Format19bitARGB1666", 3995 "OMX_COLOR_Format24bitRGB888", 3996 "OMX_COLOR_Format24bitBGR888", 3997 "OMX_COLOR_Format24bitARGB1887", 3998 "OMX_COLOR_Format25bitARGB1888", 3999 "OMX_COLOR_Format32bitBGRA8888", 4000 "OMX_COLOR_Format32bitARGB8888", 4001 "OMX_COLOR_FormatYUV411Planar", 4002 "OMX_COLOR_FormatYUV411PackedPlanar", 4003 "OMX_COLOR_FormatYUV420Planar", 4004 "OMX_COLOR_FormatYUV420PackedPlanar", 4005 "OMX_COLOR_FormatYUV420SemiPlanar", 4006 "OMX_COLOR_FormatYUV422Planar", 4007 "OMX_COLOR_FormatYUV422PackedPlanar", 4008 "OMX_COLOR_FormatYUV422SemiPlanar", 4009 "OMX_COLOR_FormatYCbYCr", 4010 "OMX_COLOR_FormatYCrYCb", 4011 "OMX_COLOR_FormatCbYCrY", 4012 "OMX_COLOR_FormatCrYCbY", 4013 "OMX_COLOR_FormatYUV444Interleaved", 4014 "OMX_COLOR_FormatRawBayer8bit", 4015 "OMX_COLOR_FormatRawBayer10bit", 4016 "OMX_COLOR_FormatRawBayer8bitcompressed", 4017 "OMX_COLOR_FormatL2", 4018 "OMX_COLOR_FormatL4", 4019 "OMX_COLOR_FormatL8", 4020 "OMX_COLOR_FormatL16", 4021 "OMX_COLOR_FormatL24", 4022 "OMX_COLOR_FormatL32", 4023 "OMX_COLOR_FormatYUV420PackedSemiPlanar", 4024 "OMX_COLOR_FormatYUV422PackedSemiPlanar", 4025 "OMX_COLOR_Format18BitBGR666", 4026 "OMX_COLOR_Format24BitARGB6666", 4027 "OMX_COLOR_Format24BitABGR6666", 4028 }; 4029 4030 size_t numNames = sizeof(kNames) / sizeof(kNames[0]); 4031 4032 if (type == OMX_TI_COLOR_FormatYUV420PackedSemiPlanar) { 4033 return "OMX_TI_COLOR_FormatYUV420PackedSemiPlanar"; 4034 } else if (type == OMX_QCOM_COLOR_FormatYVU420SemiPlanar) { 4035 return "OMX_QCOM_COLOR_FormatYVU420SemiPlanar"; 4036 } else if (type < 0 || (size_t)type >= numNames) { 4037 return "UNKNOWN"; 4038 } else { 4039 return kNames[type]; 4040 } 4041 } 4042 4043 static const char *videoCompressionFormatString(OMX_VIDEO_CODINGTYPE type) { 4044 static const char *kNames[] = { 4045 "OMX_VIDEO_CodingUnused", 4046 "OMX_VIDEO_CodingAutoDetect", 4047 "OMX_VIDEO_CodingMPEG2", 4048 "OMX_VIDEO_CodingH263", 4049 "OMX_VIDEO_CodingMPEG4", 4050 "OMX_VIDEO_CodingWMV", 4051 "OMX_VIDEO_CodingRV", 4052 "OMX_VIDEO_CodingAVC", 4053 "OMX_VIDEO_CodingMJPEG", 4054 }; 4055 4056 size_t numNames = sizeof(kNames) / sizeof(kNames[0]); 4057 4058 if (type < 0 || (size_t)type >= numNames) { 4059 return "UNKNOWN"; 4060 } else { 4061 return kNames[type]; 4062 } 4063 } 4064 4065 static const char *audioCodingTypeString(OMX_AUDIO_CODINGTYPE type) { 4066 static const char *kNames[] = { 4067 "OMX_AUDIO_CodingUnused", 4068 "OMX_AUDIO_CodingAutoDetect", 4069 "OMX_AUDIO_CodingPCM", 4070 "OMX_AUDIO_CodingADPCM", 4071 "OMX_AUDIO_CodingAMR", 4072 "OMX_AUDIO_CodingGSMFR", 4073 "OMX_AUDIO_CodingGSMEFR", 4074 "OMX_AUDIO_CodingGSMHR", 4075 "OMX_AUDIO_CodingPDCFR", 4076 "OMX_AUDIO_CodingPDCEFR", 4077 "OMX_AUDIO_CodingPDCHR", 4078 "OMX_AUDIO_CodingTDMAFR", 4079 "OMX_AUDIO_CodingTDMAEFR", 4080 "OMX_AUDIO_CodingQCELP8", 4081 "OMX_AUDIO_CodingQCELP13", 4082 "OMX_AUDIO_CodingEVRC", 4083 "OMX_AUDIO_CodingSMV", 4084 "OMX_AUDIO_CodingG711", 4085 "OMX_AUDIO_CodingG723", 4086 "OMX_AUDIO_CodingG726", 4087 "OMX_AUDIO_CodingG729", 4088 "OMX_AUDIO_CodingAAC", 4089 "OMX_AUDIO_CodingMP3", 4090 "OMX_AUDIO_CodingSBC", 4091 "OMX_AUDIO_CodingVORBIS", 4092 "OMX_AUDIO_CodingWMA", 4093 "OMX_AUDIO_CodingRA", 4094 "OMX_AUDIO_CodingMIDI", 4095 }; 4096 4097 size_t numNames = sizeof(kNames) / sizeof(kNames[0]); 4098 4099 if (type < 0 || (size_t)type >= numNames) { 4100 return "UNKNOWN"; 4101 } else { 4102 return kNames[type]; 4103 } 4104 } 4105 4106 static const char *audioPCMModeString(OMX_AUDIO_PCMMODETYPE type) { 4107 static const char *kNames[] = { 4108 "OMX_AUDIO_PCMModeLinear", 4109 "OMX_AUDIO_PCMModeALaw", 4110 "OMX_AUDIO_PCMModeMULaw", 4111 }; 4112 4113 size_t numNames = sizeof(kNames) / sizeof(kNames[0]); 4114 4115 if (type < 0 || (size_t)type >= numNames) { 4116 return "UNKNOWN"; 4117 } else { 4118 return kNames[type]; 4119 } 4120 } 4121 4122 static const char *amrBandModeString(OMX_AUDIO_AMRBANDMODETYPE type) { 4123 static const char *kNames[] = { 4124 "OMX_AUDIO_AMRBandModeUnused", 4125 "OMX_AUDIO_AMRBandModeNB0", 4126 "OMX_AUDIO_AMRBandModeNB1", 4127 "OMX_AUDIO_AMRBandModeNB2", 4128 "OMX_AUDIO_AMRBandModeNB3", 4129 "OMX_AUDIO_AMRBandModeNB4", 4130 "OMX_AUDIO_AMRBandModeNB5", 4131 "OMX_AUDIO_AMRBandModeNB6", 4132 "OMX_AUDIO_AMRBandModeNB7", 4133 "OMX_AUDIO_AMRBandModeWB0", 4134 "OMX_AUDIO_AMRBandModeWB1", 4135 "OMX_AUDIO_AMRBandModeWB2", 4136 "OMX_AUDIO_AMRBandModeWB3", 4137 "OMX_AUDIO_AMRBandModeWB4", 4138 "OMX_AUDIO_AMRBandModeWB5", 4139 "OMX_AUDIO_AMRBandModeWB6", 4140 "OMX_AUDIO_AMRBandModeWB7", 4141 "OMX_AUDIO_AMRBandModeWB8", 4142 }; 4143 4144 size_t numNames = sizeof(kNames) / sizeof(kNames[0]); 4145 4146 if (type < 0 || (size_t)type >= numNames) { 4147 return "UNKNOWN"; 4148 } else { 4149 return kNames[type]; 4150 } 4151 } 4152 4153 static const char *amrFrameFormatString(OMX_AUDIO_AMRFRAMEFORMATTYPE type) { 4154 static const char *kNames[] = { 4155 "OMX_AUDIO_AMRFrameFormatConformance", 4156 "OMX_AUDIO_AMRFrameFormatIF1", 4157 "OMX_AUDIO_AMRFrameFormatIF2", 4158 "OMX_AUDIO_AMRFrameFormatFSF", 4159 "OMX_AUDIO_AMRFrameFormatRTPPayload", 4160 "OMX_AUDIO_AMRFrameFormatITU", 4161 }; 4162 4163 size_t numNames = sizeof(kNames) / sizeof(kNames[0]); 4164 4165 if (type < 0 || (size_t)type >= numNames) { 4166 return "UNKNOWN"; 4167 } else { 4168 return kNames[type]; 4169 } 4170 } 4171 4172 void OMXCodec::dumpPortStatus(OMX_U32 portIndex) { 4173 OMX_PARAM_PORTDEFINITIONTYPE def; 4174 InitOMXParams(&def); 4175 def.nPortIndex = portIndex; 4176 4177 status_t err = mOMX->getParameter( 4178 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 4179 CHECK_EQ(err, (status_t)OK); 4180 4181 printf("%s Port = {\n", portIndex == kPortIndexInput ? "Input" : "Output"); 4182 4183 CHECK((portIndex == kPortIndexInput && def.eDir == OMX_DirInput) 4184 || (portIndex == kPortIndexOutput && def.eDir == OMX_DirOutput)); 4185 4186 printf(" nBufferCountActual = %ld\n", def.nBufferCountActual); 4187 printf(" nBufferCountMin = %ld\n", def.nBufferCountMin); 4188 printf(" nBufferSize = %ld\n", def.nBufferSize); 4189 4190 switch (def.eDomain) { 4191 case OMX_PortDomainImage: 4192 { 4193 const OMX_IMAGE_PORTDEFINITIONTYPE *imageDef = &def.format.image; 4194 4195 printf("\n"); 4196 printf(" // Image\n"); 4197 printf(" nFrameWidth = %ld\n", imageDef->nFrameWidth); 4198 printf(" nFrameHeight = %ld\n", imageDef->nFrameHeight); 4199 printf(" nStride = %ld\n", imageDef->nStride); 4200 4201 printf(" eCompressionFormat = %s\n", 4202 imageCompressionFormatString(imageDef->eCompressionFormat)); 4203 4204 printf(" eColorFormat = %s\n", 4205 colorFormatString(imageDef->eColorFormat)); 4206 4207 break; 4208 } 4209 4210 case OMX_PortDomainVideo: 4211 { 4212 OMX_VIDEO_PORTDEFINITIONTYPE *videoDef = &def.format.video; 4213 4214 printf("\n"); 4215 printf(" // Video\n"); 4216 printf(" nFrameWidth = %ld\n", videoDef->nFrameWidth); 4217 printf(" nFrameHeight = %ld\n", videoDef->nFrameHeight); 4218 printf(" nStride = %ld\n", videoDef->nStride); 4219 4220 printf(" eCompressionFormat = %s\n", 4221 videoCompressionFormatString(videoDef->eCompressionFormat)); 4222 4223 printf(" eColorFormat = %s\n", 4224 colorFormatString(videoDef->eColorFormat)); 4225 4226 break; 4227 } 4228 4229 case OMX_PortDomainAudio: 4230 { 4231 OMX_AUDIO_PORTDEFINITIONTYPE *audioDef = &def.format.audio; 4232 4233 printf("\n"); 4234 printf(" // Audio\n"); 4235 printf(" eEncoding = %s\n", 4236 audioCodingTypeString(audioDef->eEncoding)); 4237 4238 if (audioDef->eEncoding == OMX_AUDIO_CodingPCM) { 4239 OMX_AUDIO_PARAM_PCMMODETYPE params; 4240 InitOMXParams(¶ms); 4241 params.nPortIndex = portIndex; 4242 4243 err = mOMX->getParameter( 4244 mNode, OMX_IndexParamAudioPcm, ¶ms, sizeof(params)); 4245 CHECK_EQ(err, (status_t)OK); 4246 4247 printf(" nSamplingRate = %ld\n", params.nSamplingRate); 4248 printf(" nChannels = %ld\n", params.nChannels); 4249 printf(" bInterleaved = %d\n", params.bInterleaved); 4250 printf(" nBitPerSample = %ld\n", params.nBitPerSample); 4251 4252 printf(" eNumData = %s\n", 4253 params.eNumData == OMX_NumericalDataSigned 4254 ? "signed" : "unsigned"); 4255 4256 printf(" ePCMMode = %s\n", audioPCMModeString(params.ePCMMode)); 4257 } else if (audioDef->eEncoding == OMX_AUDIO_CodingAMR) { 4258 OMX_AUDIO_PARAM_AMRTYPE amr; 4259 InitOMXParams(&amr); 4260 amr.nPortIndex = portIndex; 4261 4262 err = mOMX->getParameter( 4263 mNode, OMX_IndexParamAudioAmr, &amr, sizeof(amr)); 4264 CHECK_EQ(err, (status_t)OK); 4265 4266 printf(" nChannels = %ld\n", amr.nChannels); 4267 printf(" eAMRBandMode = %s\n", 4268 amrBandModeString(amr.eAMRBandMode)); 4269 printf(" eAMRFrameFormat = %s\n", 4270 amrFrameFormatString(amr.eAMRFrameFormat)); 4271 } 4272 4273 break; 4274 } 4275 4276 default: 4277 { 4278 printf(" // Unknown\n"); 4279 break; 4280 } 4281 } 4282 4283 printf("}\n"); 4284 } 4285 4286 status_t OMXCodec::initNativeWindow() { 4287 // Enable use of a GraphicBuffer as the output for this node. This must 4288 // happen before getting the IndexParamPortDefinition parameter because it 4289 // will affect the pixel format that the node reports. 4290 status_t err = mOMX->enableGraphicBuffers(mNode, kPortIndexOutput, OMX_TRUE); 4291 if (err != 0) { 4292 return err; 4293 } 4294 4295 return OK; 4296 } 4297 4298 void OMXCodec::initNativeWindowCrop() { 4299 int32_t left, top, right, bottom; 4300 4301 CHECK(mOutputFormat->findRect( 4302 kKeyCropRect, 4303 &left, &top, &right, &bottom)); 4304 4305 android_native_rect_t crop; 4306 crop.left = left; 4307 crop.top = top; 4308 crop.right = right + 1; 4309 crop.bottom = bottom + 1; 4310 4311 // We'll ignore any errors here, if the surface is 4312 // already invalid, we'll know soon enough. 4313 native_window_set_crop(mNativeWindow.get(), &crop); 4314 } 4315 4316 void OMXCodec::initOutputFormat(const sp<MetaData> &inputFormat) { 4317 mOutputFormat = new MetaData; 4318 mOutputFormat->setCString(kKeyDecoderComponent, mComponentName); 4319 if (mIsEncoder) { 4320 int32_t timeScale; 4321 if (inputFormat->findInt32(kKeyTimeScale, &timeScale)) { 4322 mOutputFormat->setInt32(kKeyTimeScale, timeScale); 4323 } 4324 } 4325 4326 OMX_PARAM_PORTDEFINITIONTYPE def; 4327 InitOMXParams(&def); 4328 def.nPortIndex = kPortIndexOutput; 4329 4330 status_t err = mOMX->getParameter( 4331 mNode, OMX_IndexParamPortDefinition, &def, sizeof(def)); 4332 CHECK_EQ(err, (status_t)OK); 4333 4334 switch (def.eDomain) { 4335 case OMX_PortDomainImage: 4336 { 4337 OMX_IMAGE_PORTDEFINITIONTYPE *imageDef = &def.format.image; 4338 CHECK_EQ((int)imageDef->eCompressionFormat, 4339 (int)OMX_IMAGE_CodingUnused); 4340 4341 mOutputFormat->setCString(kKeyMIMEType, MEDIA_MIMETYPE_VIDEO_RAW); 4342 mOutputFormat->setInt32(kKeyColorFormat, imageDef->eColorFormat); 4343 mOutputFormat->setInt32(kKeyWidth, imageDef->nFrameWidth); 4344 mOutputFormat->setInt32(kKeyHeight, imageDef->nFrameHeight); 4345 break; 4346 } 4347 4348 case OMX_PortDomainAudio: 4349 { 4350 OMX_AUDIO_PORTDEFINITIONTYPE *audio_def = &def.format.audio; 4351 4352 if (audio_def->eEncoding == OMX_AUDIO_CodingPCM) { 4353 OMX_AUDIO_PARAM_PCMMODETYPE params; 4354 InitOMXParams(¶ms); 4355 params.nPortIndex = kPortIndexOutput; 4356 4357 err = mOMX->getParameter( 4358 mNode, OMX_IndexParamAudioPcm, ¶ms, sizeof(params)); 4359 CHECK_EQ(err, (status_t)OK); 4360 4361 CHECK_EQ((int)params.eNumData, (int)OMX_NumericalDataSigned); 4362 CHECK_EQ(params.nBitPerSample, 16u); 4363 CHECK_EQ((int)params.ePCMMode, (int)OMX_AUDIO_PCMModeLinear); 4364 4365 int32_t numChannels, sampleRate; 4366 inputFormat->findInt32(kKeyChannelCount, &numChannels); 4367 inputFormat->findInt32(kKeySampleRate, &sampleRate); 4368 4369 if ((OMX_U32)numChannels != params.nChannels) { 4370 ALOGV("Codec outputs a different number of channels than " 4371 "the input stream contains (contains %d channels, " 4372 "codec outputs %ld channels).", 4373 numChannels, params.nChannels); 4374 } 4375 4376 if (sampleRate != (int32_t)params.nSamplingRate) { 4377 ALOGV("Codec outputs at different sampling rate than " 4378 "what the input stream contains (contains data at " 4379 "%d Hz, codec outputs %lu Hz)", 4380 sampleRate, params.nSamplingRate); 4381 } 4382 4383 mOutputFormat->setCString( 4384 kKeyMIMEType, MEDIA_MIMETYPE_AUDIO_RAW); 4385 4386 // Use the codec-advertised number of channels, as some 4387 // codecs appear to output stereo even if the input data is 4388 // mono. If we know the codec lies about this information, 4389 // use the actual number of channels instead. 4390 mOutputFormat->setInt32( 4391 kKeyChannelCount, 4392 (mQuirks & kDecoderLiesAboutNumberOfChannels) 4393 ? numChannels : params.nChannels); 4394 4395 mOutputFormat->setInt32(kKeySampleRate, params.nSamplingRate); 4396 } else if (audio_def->eEncoding == OMX_AUDIO_CodingAMR) { 4397 OMX_AUDIO_PARAM_AMRTYPE amr; 4398 InitOMXParams(&amr); 4399 amr.nPortIndex = kPortIndexOutput; 4400 4401 err = mOMX->getParameter( 4402 mNode, OMX_IndexParamAudioAmr, &amr, sizeof(amr)); 4403 CHECK_EQ(err, (status_t)OK); 4404 4405 CHECK_EQ(amr.nChannels, 1u); 4406 mOutputFormat->setInt32(kKeyChannelCount, 1); 4407 4408 if (amr.eAMRBandMode >= OMX_AUDIO_AMRBandModeNB0 4409 && amr.eAMRBandMode <= OMX_AUDIO_AMRBandModeNB7) { 4410 mOutputFormat->setCString( 4411 kKeyMIMEType, MEDIA_MIMETYPE_AUDIO_AMR_NB); 4412 mOutputFormat->setInt32(kKeySampleRate, 8000); 4413 } else if (amr.eAMRBandMode >= OMX_AUDIO_AMRBandModeWB0 4414 && amr.eAMRBandMode <= OMX_AUDIO_AMRBandModeWB8) { 4415 mOutputFormat->setCString( 4416 kKeyMIMEType, MEDIA_MIMETYPE_AUDIO_AMR_WB); 4417 mOutputFormat->setInt32(kKeySampleRate, 16000); 4418 } else { 4419 CHECK(!"Unknown AMR band mode."); 4420 } 4421 } else if (audio_def->eEncoding == OMX_AUDIO_CodingAAC) { 4422 mOutputFormat->setCString( 4423 kKeyMIMEType, MEDIA_MIMETYPE_AUDIO_AAC); 4424 int32_t numChannels, sampleRate, bitRate; 4425 inputFormat->findInt32(kKeyChannelCount, &numChannels); 4426 inputFormat->findInt32(kKeySampleRate, &sampleRate); 4427 inputFormat->findInt32(kKeyBitRate, &bitRate); 4428 mOutputFormat->setInt32(kKeyChannelCount, numChannels); 4429 mOutputFormat->setInt32(kKeySampleRate, sampleRate); 4430 mOutputFormat->setInt32(kKeyBitRate, bitRate); 4431 } else { 4432 CHECK(!"Should not be here. Unknown audio encoding."); 4433 } 4434 break; 4435 } 4436 4437 case OMX_PortDomainVideo: 4438 { 4439 OMX_VIDEO_PORTDEFINITIONTYPE *video_def = &def.format.video; 4440 4441 if (video_def->eCompressionFormat == OMX_VIDEO_CodingUnused) { 4442 mOutputFormat->setCString( 4443 kKeyMIMEType, MEDIA_MIMETYPE_VIDEO_RAW); 4444 } else if (video_def->eCompressionFormat == OMX_VIDEO_CodingMPEG4) { 4445 mOutputFormat->setCString( 4446 kKeyMIMEType, MEDIA_MIMETYPE_VIDEO_MPEG4); 4447 } else if (video_def->eCompressionFormat == OMX_VIDEO_CodingH263) { 4448 mOutputFormat->setCString( 4449 kKeyMIMEType, MEDIA_MIMETYPE_VIDEO_H263); 4450 } else if (video_def->eCompressionFormat == OMX_VIDEO_CodingAVC) { 4451 mOutputFormat->setCString( 4452 kKeyMIMEType, MEDIA_MIMETYPE_VIDEO_AVC); 4453 } else { 4454 CHECK(!"Unknown compression format."); 4455 } 4456 4457 mOutputFormat->setInt32(kKeyWidth, video_def->nFrameWidth); 4458 mOutputFormat->setInt32(kKeyHeight, video_def->nFrameHeight); 4459 mOutputFormat->setInt32(kKeyColorFormat, video_def->eColorFormat); 4460 4461 if (!mIsEncoder) { 4462 OMX_CONFIG_RECTTYPE rect; 4463 InitOMXParams(&rect); 4464 rect.nPortIndex = kPortIndexOutput; 4465 status_t err = 4466 mOMX->getConfig( 4467 mNode, OMX_IndexConfigCommonOutputCrop, 4468 &rect, sizeof(rect)); 4469 4470 CODEC_LOGI( 4471 "video dimensions are %ld x %ld", 4472 video_def->nFrameWidth, video_def->nFrameHeight); 4473 4474 if (err == OK) { 4475 CHECK_GE(rect.nLeft, 0); 4476 CHECK_GE(rect.nTop, 0); 4477 CHECK_GE(rect.nWidth, 0u); 4478 CHECK_GE(rect.nHeight, 0u); 4479 CHECK_LE(rect.nLeft + rect.nWidth - 1, video_def->nFrameWidth); 4480 CHECK_LE(rect.nTop + rect.nHeight - 1, video_def->nFrameHeight); 4481 4482 mOutputFormat->setRect( 4483 kKeyCropRect, 4484 rect.nLeft, 4485 rect.nTop, 4486 rect.nLeft + rect.nWidth - 1, 4487 rect.nTop + rect.nHeight - 1); 4488 4489 CODEC_LOGI( 4490 "Crop rect is %ld x %ld @ (%ld, %ld)", 4491 rect.nWidth, rect.nHeight, rect.nLeft, rect.nTop); 4492 } else { 4493 mOutputFormat->setRect( 4494 kKeyCropRect, 4495 0, 0, 4496 video_def->nFrameWidth - 1, 4497 video_def->nFrameHeight - 1); 4498 } 4499 4500 if (mNativeWindow != NULL) { 4501 initNativeWindowCrop(); 4502 } 4503 } 4504 break; 4505 } 4506 4507 default: 4508 { 4509 CHECK(!"should not be here, neither audio nor video."); 4510 break; 4511 } 4512 } 4513 4514 // If the input format contains rotation information, flag the output 4515 // format accordingly. 4516 4517 int32_t rotationDegrees; 4518 if (mSource->getFormat()->findInt32(kKeyRotation, &rotationDegrees)) { 4519 mOutputFormat->setInt32(kKeyRotation, rotationDegrees); 4520 } 4521 } 4522 4523 status_t OMXCodec::pause() { 4524 Mutex::Autolock autoLock(mLock); 4525 4526 mPaused = true; 4527 4528 return OK; 4529 } 4530 4531 //////////////////////////////////////////////////////////////////////////////// 4532 4533 status_t QueryCodecs( 4534 const sp<IOMX> &omx, 4535 const char *mime, bool queryDecoders, bool hwCodecOnly, 4536 Vector<CodecCapabilities> *results) { 4537 Vector<OMXCodec::CodecNameAndQuirks> matchingCodecs; 4538 results->clear(); 4539 4540 OMXCodec::findMatchingCodecs(mime, 4541 !queryDecoders /*createEncoder*/, 4542 NULL /*matchComponentName*/, 4543 hwCodecOnly ? OMXCodec::kHardwareCodecsOnly : 0 /*flags*/, 4544 &matchingCodecs); 4545 4546 for (size_t c = 0; c < matchingCodecs.size(); c++) { 4547 const char *componentName = matchingCodecs.itemAt(c).mName.string(); 4548 4549 results->push(); 4550 CodecCapabilities *caps = &results->editItemAt(results->size() - 1); 4551 4552 status_t err = 4553 QueryCodec(omx, componentName, mime, !queryDecoders, caps); 4554 4555 if (err != OK) { 4556 results->removeAt(results->size() - 1); 4557 } 4558 } 4559 4560 return OK; 4561 } 4562 4563 status_t QueryCodec( 4564 const sp<IOMX> &omx, 4565 const char *componentName, const char *mime, 4566 bool isEncoder, 4567 CodecCapabilities *caps) { 4568 if (strncmp(componentName, "OMX.", 4)) { 4569 // Not an OpenMax component but a software codec. 4570 caps->mFlags = 0; 4571 caps->mComponentName = componentName; 4572 return OK; 4573 } 4574 4575 sp<OMXCodecObserver> observer = new OMXCodecObserver; 4576 IOMX::node_id node; 4577 status_t err = omx->allocateNode(componentName, observer, &node); 4578 4579 if (err != OK) { 4580 return err; 4581 } 4582 4583 OMXCodec::setComponentRole(omx, node, isEncoder, mime); 4584 4585 caps->mFlags = 0; 4586 caps->mComponentName = componentName; 4587 4588 OMX_VIDEO_PARAM_PROFILELEVELTYPE param; 4589 InitOMXParams(¶m); 4590 4591 param.nPortIndex = !isEncoder ? 0 : 1; 4592 4593 for (param.nProfileIndex = 0;; ++param.nProfileIndex) { 4594 err = omx->getParameter( 4595 node, OMX_IndexParamVideoProfileLevelQuerySupported, 4596 ¶m, sizeof(param)); 4597 4598 if (err != OK) { 4599 break; 4600 } 4601 4602 CodecProfileLevel profileLevel; 4603 profileLevel.mProfile = param.eProfile; 4604 profileLevel.mLevel = param.eLevel; 4605 4606 caps->mProfileLevels.push(profileLevel); 4607 } 4608 4609 // Color format query 4610 OMX_VIDEO_PARAM_PORTFORMATTYPE portFormat; 4611 InitOMXParams(&portFormat); 4612 portFormat.nPortIndex = !isEncoder ? 1 : 0; 4613 for (portFormat.nIndex = 0;; ++portFormat.nIndex) { 4614 err = omx->getParameter( 4615 node, OMX_IndexParamVideoPortFormat, 4616 &portFormat, sizeof(portFormat)); 4617 if (err != OK) { 4618 break; 4619 } 4620 caps->mColorFormats.push(portFormat.eColorFormat); 4621 } 4622 4623 if (!isEncoder && !strncmp(mime, "video/", 6)) { 4624 if (omx->storeMetaDataInBuffers( 4625 node, 1 /* port index */, OMX_TRUE) == OK || 4626 omx->prepareForAdaptivePlayback( 4627 node, 1 /* port index */, OMX_TRUE, 4628 1280 /* width */, 720 /* height */) == OK) { 4629 caps->mFlags |= CodecCapabilities::kFlagSupportsAdaptivePlayback; 4630 } 4631 } 4632 4633 CHECK_EQ(omx->freeNode(node), (status_t)OK); 4634 4635 return OK; 4636 } 4637 4638 status_t QueryCodecs( 4639 const sp<IOMX> &omx, 4640 const char *mimeType, bool queryDecoders, 4641 Vector<CodecCapabilities> *results) { 4642 return QueryCodecs(omx, mimeType, queryDecoders, false /*hwCodecOnly*/, results); 4643 } 4644 4645 // These are supposed be equivalent to the logic in 4646 // "audio_channel_out_mask_from_count". 4647 status_t getOMXChannelMapping(size_t numChannels, OMX_AUDIO_CHANNELTYPE map[]) { 4648 switch (numChannels) { 4649 case 1: 4650 map[0] = OMX_AUDIO_ChannelCF; 4651 break; 4652 case 2: 4653 map[0] = OMX_AUDIO_ChannelLF; 4654 map[1] = OMX_AUDIO_ChannelRF; 4655 break; 4656 case 3: 4657 map[0] = OMX_AUDIO_ChannelLF; 4658 map[1] = OMX_AUDIO_ChannelRF; 4659 map[2] = OMX_AUDIO_ChannelCF; 4660 break; 4661 case 4: 4662 map[0] = OMX_AUDIO_ChannelLF; 4663 map[1] = OMX_AUDIO_ChannelRF; 4664 map[2] = OMX_AUDIO_ChannelLR; 4665 map[3] = OMX_AUDIO_ChannelRR; 4666 break; 4667 case 5: 4668 map[0] = OMX_AUDIO_ChannelLF; 4669 map[1] = OMX_AUDIO_ChannelRF; 4670 map[2] = OMX_AUDIO_ChannelCF; 4671 map[3] = OMX_AUDIO_ChannelLR; 4672 map[4] = OMX_AUDIO_ChannelRR; 4673 break; 4674 case 6: 4675 map[0] = OMX_AUDIO_ChannelLF; 4676 map[1] = OMX_AUDIO_ChannelRF; 4677 map[2] = OMX_AUDIO_ChannelCF; 4678 map[3] = OMX_AUDIO_ChannelLFE; 4679 map[4] = OMX_AUDIO_ChannelLR; 4680 map[5] = OMX_AUDIO_ChannelRR; 4681 break; 4682 case 7: 4683 map[0] = OMX_AUDIO_ChannelLF; 4684 map[1] = OMX_AUDIO_ChannelRF; 4685 map[2] = OMX_AUDIO_ChannelCF; 4686 map[3] = OMX_AUDIO_ChannelLFE; 4687 map[4] = OMX_AUDIO_ChannelLR; 4688 map[5] = OMX_AUDIO_ChannelRR; 4689 map[6] = OMX_AUDIO_ChannelCS; 4690 break; 4691 case 8: 4692 map[0] = OMX_AUDIO_ChannelLF; 4693 map[1] = OMX_AUDIO_ChannelRF; 4694 map[2] = OMX_AUDIO_ChannelCF; 4695 map[3] = OMX_AUDIO_ChannelLFE; 4696 map[4] = OMX_AUDIO_ChannelLR; 4697 map[5] = OMX_AUDIO_ChannelRR; 4698 map[6] = OMX_AUDIO_ChannelLS; 4699 map[7] = OMX_AUDIO_ChannelRS; 4700 break; 4701 default: 4702 return -EINVAL; 4703 } 4704 4705 return OK; 4706 } 4707 4708 } // namespace android 4709