diff options
author | Android Build Coastguard Worker <android-build-coastguard-worker@google.com> | 2023-04-04 22:29:13 +0000 |
---|---|---|
committer | Android Build Coastguard Worker <android-build-coastguard-worker@google.com> | 2023-04-04 22:29:13 +0000 |
commit | d780c42029ccae205389f68907b272861f88f801 (patch) | |
tree | 04352a5adf8cb6753af3d99d4c80c214a3213860 | |
parent | 307d3c13187bafb71b0b565a2d30f10749bb0c1b (diff) | |
parent | e9117c7122741bc6d4422545c42584a321649c1a (diff) | |
download | av-d780c42029ccae205389f68907b272861f88f801.tar.gz |
Snap for 9883729 from e9117c7122741bc6d4422545c42584a321649c1a to mainline-sdkext-releaseaml_sdk_331812000aml_sdk_331811000android13-mainline-sdkext-release
Change-Id: I0a14f857668c0eedc20839457e8f66a6f7357139
-rw-r--r-- | media/codec2/components/vpx/C2SoftVpxEnc.cpp | 91 | ||||
-rw-r--r-- | media/codec2/components/vpx/C2SoftVpxEnc.h | 7 | ||||
-rw-r--r-- | media/libmedia/tests/codeclist/Android.bp | 2 | ||||
-rw-r--r-- | media/libstagefright/MediaCodec.cpp | 3 | ||||
-rw-r--r-- | media/libstagefright/NuMediaExtractor.cpp | 14 |
5 files changed, 100 insertions, 17 deletions
diff --git a/media/codec2/components/vpx/C2SoftVpxEnc.cpp b/media/codec2/components/vpx/C2SoftVpxEnc.cpp index f99ee248df..daf7a61bac 100644 --- a/media/codec2/components/vpx/C2SoftVpxEnc.cpp +++ b/media/codec2/components/vpx/C2SoftVpxEnc.cpp @@ -59,7 +59,7 @@ C2SoftVpxEnc::IntfImpl::IntfImpl(const std::shared_ptr<C2ReflectorHelper> &helpe addParameter( DefineParam(mSize, C2_PARAMKEY_PICTURE_SIZE) - .withDefault(new C2StreamPictureSizeInfo::input(0u, 320, 240)) + .withDefault(new C2StreamPictureSizeInfo::input(0u, 64, 64)) .withFields({ C2F(mSize, width).inRange(2, 2048, 2), C2F(mSize, height).inRange(2, 2048, 2), @@ -81,7 +81,7 @@ C2SoftVpxEnc::IntfImpl::IntfImpl(const std::shared_ptr<C2ReflectorHelper> &helpe addParameter( DefineParam(mFrameRate, C2_PARAMKEY_FRAME_RATE) - .withDefault(new C2StreamFrameRateInfo::output(0u, 30.)) + .withDefault(new C2StreamFrameRateInfo::output(0u, 1.)) // TODO: More restriction? .withFields({C2F(mFrameRate, value).greaterThan(0.)}) .withSetter( @@ -127,10 +127,18 @@ C2SoftVpxEnc::IntfImpl::IntfImpl(const std::shared_ptr<C2ReflectorHelper> &helpe C2F(mProfileLevel, profile).equalTo( PROFILE_VP9_0 ), - C2F(mProfileLevel, level).equalTo( - LEVEL_VP9_4_1), + C2F(mProfileLevel, level).oneOf({ + C2Config::LEVEL_VP9_1, + C2Config::LEVEL_VP9_1_1, + C2Config::LEVEL_VP9_2, + C2Config::LEVEL_VP9_2_1, + C2Config::LEVEL_VP9_3, + C2Config::LEVEL_VP9_3_1, + C2Config::LEVEL_VP9_4, + C2Config::LEVEL_VP9_4_1, + }), }) - .withSetter(ProfileLevelSetter) + .withSetter(ProfileLevelSetter, mSize, mFrameRate, mBitrate) .build()); #else addParameter( @@ -144,7 +152,7 @@ C2SoftVpxEnc::IntfImpl::IntfImpl(const std::shared_ptr<C2ReflectorHelper> &helpe C2F(mProfileLevel, level).equalTo( LEVEL_UNUSED), }) - .withSetter(ProfileLevelSetter) + .withSetter(ProfileLevelSetter, mSize, mFrameRate, mBitrate) .build()); #endif addParameter( @@ -217,14 +225,81 @@ C2R C2SoftVpxEnc::IntfImpl::SizeSetter(bool mayBlock, } C2R C2SoftVpxEnc::IntfImpl::ProfileLevelSetter(bool mayBlock, - C2P<C2StreamProfileLevelInfo::output>& me) { + C2P<C2StreamProfileLevelInfo::output>& me, + const C2P<C2StreamPictureSizeInfo::input>& size, + const C2P<C2StreamFrameRateInfo::output>& frameRate, + const C2P<C2StreamBitrateInfo::output>& bitrate) { (void)mayBlock; +#ifdef VP9 if (!me.F(me.v.profile).supportsAtAll(me.v.profile)) { me.set().profile = PROFILE_VP9_0; } - if (!me.F(me.v.level).supportsAtAll(me.v.level)) { + struct LevelLimits { + C2Config::level_t level; + float samplesPerSec; + uint64_t samples; + uint32_t bitrate; + size_t dimension; + }; + constexpr LevelLimits kLimits[] = { + {LEVEL_VP9_1, 829440, 36864, 200000, 512}, + {LEVEL_VP9_1_1, 2764800, 73728, 800000, 768}, + {LEVEL_VP9_2, 4608000, 122880, 1800000, 960}, + {LEVEL_VP9_2_1, 9216000, 245760, 3600000, 1344}, + {LEVEL_VP9_3, 20736000, 552960, 7200000, 2048}, + {LEVEL_VP9_3_1, 36864000, 983040, 12000000, 2752}, + {LEVEL_VP9_4, 83558400, 2228224, 18000000, 4160}, + {LEVEL_VP9_4_1, 160432128, 2228224, 30000000, 4160}, + }; + + uint64_t samples = size.v.width * size.v.height; + float samplesPerSec = float(samples) * frameRate.v.value; + size_t dimension = std::max(size.v.width, size.v.height); + + // Check if the supplied level meets the samples / bitrate requirements. + // If not, update the level with the lowest level meeting the requirements. + bool found = false; + + // By default needsUpdate = false in case the supplied level does meet + // the requirements. + bool needsUpdate = false; + for (const LevelLimits& limit : kLimits) { + if (samples <= limit.samples && samplesPerSec <= limit.samplesPerSec && + bitrate.v.value <= limit.bitrate && dimension <= limit.dimension) { + // This is the lowest level that meets the requirements, and if + // we haven't seen the supplied level yet, that means we don't + // need the update. + if (needsUpdate) { + ALOGD("Given level %x does not cover current configuration: " + "adjusting to %x", + me.v.level, limit.level); + me.set().level = limit.level; + } + found = true; + break; + } + if (me.v.level == limit.level) { + // We break out of the loop when the lowest feasible level is + // found. The fact that we're here means that our level doesn't + // meet the requirement and needs to be updated. + needsUpdate = true; + } + } + if (!found) { + // We set to the highest supported level. me.set().level = LEVEL_VP9_4_1; } +#else + (void)size; + (void)frameRate; + (void)bitrate; + if (!me.F(me.v.profile).supportsAtAll(me.v.profile)) { + me.set().profile = PROFILE_VP8_0; + } + if (!me.F(me.v.level).supportsAtAll(me.v.level)) { + me.set().level = LEVEL_UNUSED; + } +#endif return C2R::Ok(); } diff --git a/media/codec2/components/vpx/C2SoftVpxEnc.h b/media/codec2/components/vpx/C2SoftVpxEnc.h index 714fadb504..bfb4444e2a 100644 --- a/media/codec2/components/vpx/C2SoftVpxEnc.h +++ b/media/codec2/components/vpx/C2SoftVpxEnc.h @@ -243,9 +243,10 @@ class C2SoftVpxEnc::IntfImpl : public SimpleInterface<void>::BaseParams { static C2R SizeSetter(bool mayBlock, const C2P<C2StreamPictureSizeInfo::input> &oldMe, C2P<C2StreamPictureSizeInfo::input> &me); - static C2R ProfileLevelSetter( - bool mayBlock, - C2P<C2StreamProfileLevelInfo::output> &me); + static C2R ProfileLevelSetter(bool mayBlock, C2P<C2StreamProfileLevelInfo::output>& me, + const C2P<C2StreamPictureSizeInfo::input>& size, + const C2P<C2StreamFrameRateInfo::output>& frameRate, + const C2P<C2StreamBitrateInfo::output>& bitrate); static C2R LayeringSetter(bool mayBlock, C2P<C2StreamTemporalLayeringTuning::output>& me); diff --git a/media/libmedia/tests/codeclist/Android.bp b/media/libmedia/tests/codeclist/Android.bp index 2ed3126ca7..6f3010c0e6 100644 --- a/media/libmedia/tests/codeclist/Android.bp +++ b/media/libmedia/tests/codeclist/Android.bp @@ -25,7 +25,7 @@ package { cc_test { name: "CodecListTest", - test_suites: ["device-tests", "mts"], + test_suites: ["device-tests"], gtest: true, // Support multilib variants (using different suffix per sub-architecture), which is needed on diff --git a/media/libstagefright/MediaCodec.cpp b/media/libstagefright/MediaCodec.cpp index d71faa799f..e63e574c5b 100644 --- a/media/libstagefright/MediaCodec.cpp +++ b/media/libstagefright/MediaCodec.cpp @@ -5584,6 +5584,9 @@ status_t MediaCodec::setParameters(const sp<AMessage> ¶ms) { } status_t MediaCodec::onSetParameters(const sp<AMessage> ¶ms) { + if (mState == UNINITIALIZED || mState == INITIALIZING) { + return NO_INIT; + } updateLowLatency(params); mapFormat(mComponentName, params, nullptr, false); updateTunnelPeek(params); diff --git a/media/libstagefright/NuMediaExtractor.cpp b/media/libstagefright/NuMediaExtractor.cpp index 2b45f2d16d..5b39618ad7 100644 --- a/media/libstagefright/NuMediaExtractor.cpp +++ b/media/libstagefright/NuMediaExtractor.cpp @@ -639,9 +639,11 @@ status_t NuMediaExtractor::appendVorbisNumPageSamples( numPageSamples = -1; } + // insert, including accounting for the space used. memcpy((uint8_t *)buffer->data() + mbuf->range_length(), &numPageSamples, sizeof(numPageSamples)); + buffer->setRange(buffer->offset(), buffer->size() + sizeof(numPageSamples)); uint32_t type; const void *data; @@ -690,6 +692,8 @@ status_t NuMediaExtractor::readSampleData(const sp<ABuffer> &buffer) { ssize_t minIndex = fetchAllTrackSamples(); + buffer->setRange(0, 0); // start with an empty buffer + if (minIndex < 0) { return ERROR_END_OF_STREAM; } @@ -705,25 +709,25 @@ status_t NuMediaExtractor::readSampleData(const sp<ABuffer> &buffer) { sampleSize += sizeof(int32_t); } + // capacity() is ok since we cleared out the buffer if (buffer->capacity() < sampleSize) { return -ENOMEM; } + const size_t srclen = it->mBuffer->range_length(); const uint8_t *src = (const uint8_t *)it->mBuffer->data() + it->mBuffer->range_offset(); - memcpy((uint8_t *)buffer->data(), src, it->mBuffer->range_length()); + memcpy((uint8_t *)buffer->data(), src, srclen); + buffer->setRange(0, srclen); status_t err = OK; if (info->mTrackFlags & kIsVorbis) { + // adjusts range when it inserts the extra bits err = appendVorbisNumPageSamples(it->mBuffer, buffer); } - if (err == OK) { - buffer->setRange(0, sampleSize); - } - return err; } |