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