Loading media/java/android/media/MediaCodec.java +20 −2 Original line number Diff line number Diff line Loading @@ -1602,7 +1602,9 @@ final public class MediaCodec { private EventHandler mCallbackHandler; private Callback mCallback; private OnFrameRenderedListener mOnFrameRenderedListener; private Object mListenerLock = new Object(); private final Object mListenerLock = new Object(); private MediaCodecInfo mCodecInfo; private final Object mCodecInfoLock = new Object(); private static final int EVENT_CALLBACK = 1; private static final int EVENT_SET_CALLBACK = 2; Loading Loading @@ -3469,8 +3471,24 @@ final public class MediaCodec { */ @NonNull public MediaCodecInfo getCodecInfo() { return MediaCodecList.getInfoFor(getName()); // Get the codec name first. If the codec is already released, // IllegalStateException will be thrown here. String name = getName(); synchronized (mCodecInfoLock) { if (mCodecInfo == null) { // Get the codec info for this codec itself first. Only initialize // the full codec list if this somehow fails because it can be slow. mCodecInfo = getOwnCodecInfo(); if (mCodecInfo == null) { mCodecInfo = MediaCodecList.getInfoFor(name); } } return mCodecInfo; } } @NonNull private native final MediaCodecInfo getOwnCodecInfo(); @NonNull private native final ByteBuffer[] getBuffers(boolean input); Loading media/java/android/media/MediaCodecInfo.java +25 −18 Original line number Diff line number Diff line Loading @@ -829,14 +829,24 @@ public final class MediaCodecInfo { /** @hide */ public CodecCapabilities dup() { return new CodecCapabilities( // clone writable arrays Arrays.copyOf(profileLevels, profileLevels.length), Arrays.copyOf(colorFormats, colorFormats.length), isEncoder(), mFlagsVerified, mDefaultFormat, mCapabilitiesInfo); CodecCapabilities caps = new CodecCapabilities(); // profileLevels and colorFormats may be modified by client. caps.profileLevels = Arrays.copyOf(profileLevels, profileLevels.length); caps.colorFormats = Arrays.copyOf(colorFormats, colorFormats.length); caps.mMime = mMime; caps.mMaxSupportedInstances = mMaxSupportedInstances; caps.mFlagsRequired = mFlagsRequired; caps.mFlagsSupported = mFlagsSupported; caps.mFlagsVerified = mFlagsVerified; caps.mAudioCaps = mAudioCaps; caps.mVideoCaps = mVideoCaps; caps.mEncoderCaps = mEncoderCaps; caps.mDefaultFormat = mDefaultFormat; caps.mCapabilitiesInfo = mCapabilitiesInfo; return caps; } /** Loading Loading @@ -898,13 +908,13 @@ public final class MediaCodecInfo { if (mMime.toLowerCase().startsWith("audio/")) { mAudioCaps = AudioCapabilities.create(info, this); mAudioCaps.setDefaultFormat(mDefaultFormat); mAudioCaps.getDefaultFormat(mDefaultFormat); } else if (mMime.toLowerCase().startsWith("video/")) { mVideoCaps = VideoCapabilities.create(info, this); } if (encoder) { mEncoderCaps = EncoderCapabilities.create(info, this); mEncoderCaps.setDefaultFormat(mDefaultFormat); mEncoderCaps.getDefaultFormat(mDefaultFormat); } final Map<String, Object> global = MediaCodecList.getGlobalSettings(); Loading Loading @@ -990,8 +1000,7 @@ public final class MediaCodecInfo { return caps; } /** @hide */ public void init(MediaFormat info, CodecCapabilities parent) { private void init(MediaFormat info, CodecCapabilities parent) { mParent = parent; initWithPlatformLimits(); applyLevelLimits(); Loading Loading @@ -1171,7 +1180,7 @@ public final class MediaCodecInfo { } /** @hide */ public void setDefaultFormat(MediaFormat format) { public void getDefaultFormat(MediaFormat format) { // report settings that have only a single choice if (mBitrateRange.getLower().equals(mBitrateRange.getUpper())) { format.setInteger(MediaFormat.KEY_BIT_RATE, mBitrateRange.getLower()); Loading Loading @@ -1585,8 +1594,7 @@ public final class MediaCodecInfo { return caps; } /** @hide */ public void init(MediaFormat info, CodecCapabilities parent) { private void init(MediaFormat info, CodecCapabilities parent) { mParent = parent; initWithPlatformLimits(); applyLevelLimits(); Loading Loading @@ -2707,8 +2715,7 @@ public final class MediaCodecInfo { return caps; } /** @hide */ public void init(MediaFormat info, CodecCapabilities parent) { private void init(MediaFormat info, CodecCapabilities parent) { // no support for complexity or quality yet mParent = parent; mComplexityRange = Range.create(0, 0); Loading Loading @@ -2789,7 +2796,7 @@ public final class MediaCodecInfo { } /** @hide */ public void setDefaultFormat(MediaFormat format) { public void getDefaultFormat(MediaFormat format) { // don't list trivial quality/complexity as default for now if (!mQualityRange.getUpper().equals(mQualityRange.getLower()) && mDefaultQuality != null) { Loading media/jni/android_media_MediaCodec.cpp +153 −0 Original line number Diff line number Diff line Loading @@ -29,6 +29,7 @@ #include "android_util_Binder.h" #include "jni.h" #include <nativehelper/JNIHelp.h> #include <nativehelper/ScopedLocalRef.h> #include <android/hardware/cas/native/1.0/IDescrambler.h> Loading Loading @@ -98,6 +99,13 @@ static struct { jint AesCbc; } gCryptoModes; static struct { jclass capsClazz; jmethodID capsCtorId; jclass profileLevelClazz; jfieldID profileField; jfieldID levelField; } gCodecInfo; struct fields_t { jfieldID context; Loading Loading @@ -625,6 +633,103 @@ status_t JMediaCodec::getName(JNIEnv *env, jstring *nameStr) const { return OK; } static jobject getCodecCapabilitiesObject( JNIEnv *env, const char *mime, bool isEncoder, const sp<MediaCodecInfo::Capabilities> &capabilities) { Vector<MediaCodecInfo::ProfileLevel> profileLevels; Vector<uint32_t> colorFormats; sp<AMessage> defaultFormat = new AMessage(); defaultFormat->setString("mime", mime); capabilities->getSupportedColorFormats(&colorFormats); capabilities->getSupportedProfileLevels(&profileLevels); uint32_t flags = capabilities->getFlags(); sp<AMessage> details = capabilities->getDetails(); jobject defaultFormatObj = NULL; if (ConvertMessageToMap(env, defaultFormat, &defaultFormatObj)) { return NULL; } ScopedLocalRef<jobject> defaultFormatRef(env, defaultFormatObj); jobject detailsObj = NULL; if (ConvertMessageToMap(env, details, &detailsObj)) { return NULL; } ScopedLocalRef<jobject> detailsRef(env, detailsObj); ScopedLocalRef<jobjectArray> profileLevelArray(env, env->NewObjectArray( profileLevels.size(), gCodecInfo.profileLevelClazz, NULL)); for (size_t i = 0; i < profileLevels.size(); ++i) { const MediaCodecInfo::ProfileLevel &src = profileLevels.itemAt(i); ScopedLocalRef<jobject> srcRef(env, env->AllocObject( gCodecInfo.profileLevelClazz)); env->SetIntField(srcRef.get(), gCodecInfo.profileField, src.mProfile); env->SetIntField(srcRef.get(), gCodecInfo.levelField, src.mLevel); env->SetObjectArrayElement(profileLevelArray.get(), i, srcRef.get()); } ScopedLocalRef<jintArray> colorFormatsArray( env, env->NewIntArray(colorFormats.size())); for (size_t i = 0; i < colorFormats.size(); ++i) { jint val = colorFormats.itemAt(i); env->SetIntArrayRegion(colorFormatsArray.get(), i, 1, &val); } return env->NewObject( gCodecInfo.capsClazz, gCodecInfo.capsCtorId, profileLevelArray.get(), colorFormatsArray.get(), isEncoder, flags, defaultFormatRef.get(), detailsRef.get()); } status_t JMediaCodec::getCodecInfo(JNIEnv *env, jobject *codecInfoObject) const { sp<MediaCodecInfo> codecInfo; status_t err = mCodec->getCodecInfo(&codecInfo); if (err != OK) { return err; } ScopedLocalRef<jstring> nameObject(env, env->NewStringUTF(codecInfo->getCodecName())); bool isEncoder = codecInfo->isEncoder(); Vector<AString> mimes; codecInfo->getSupportedMimes(&mimes); ScopedLocalRef<jobjectArray> capsArrayObj(env, env->NewObjectArray(mimes.size(), gCodecInfo.capsClazz, NULL)); for (size_t i = 0; i < mimes.size(); i++) { const sp<MediaCodecInfo::Capabilities> caps = codecInfo->getCapabilitiesFor(mimes[i].c_str()); ScopedLocalRef<jobject> capsObj(env, getCodecCapabilitiesObject( env, mimes[i].c_str(), isEncoder, caps)); env->SetObjectArrayElement(capsArrayObj.get(), i, capsObj.get()); } ScopedLocalRef<jclass> codecInfoClazz(env, env->FindClass("android/media/MediaCodecInfo")); CHECK(codecInfoClazz.get() != NULL); jmethodID codecInfoCtorID = env->GetMethodID(codecInfoClazz.get(), "<init>", "(Ljava/lang/String;Z[Landroid/media/MediaCodecInfo$CodecCapabilities;)V"); *codecInfoObject = env->NewObject(codecInfoClazz.get(), codecInfoCtorID, nameObject.get(), isEncoder, capsArrayObj.get()); return OK; } status_t JMediaCodec::getMetrics(JNIEnv *, MediaAnalyticsItem * &reply) const { status_t status = mCodec->getMetrics(reply); Loading Loading @@ -1665,6 +1770,29 @@ static jobject android_media_MediaCodec_getName( return NULL; } static jobject android_media_MediaCodec_getOwnCodecInfo( JNIEnv *env, jobject thiz) { ALOGV("android_media_MediaCodec_getOwnCodecInfo"); sp<JMediaCodec> codec = getMediaCodec(env, thiz); if (codec == NULL) { throwExceptionAsNecessary(env, INVALID_OPERATION); return NULL; } jobject codecInfoObj; status_t err = codec->getCodecInfo(env, &codecInfoObj); if (err == OK) { return codecInfoObj; } throwExceptionAsNecessary(env, err); return NULL; } static jobject android_media_MediaCodec_native_getMetrics(JNIEnv *env, jobject thiz) { Loading Loading @@ -1877,6 +2005,28 @@ static void android_media_MediaCodec_native_init(JNIEnv *env) { field = env->GetFieldID(clazz.get(), "mPersistentObject", "J"); CHECK(field != NULL); gPersistentSurfaceClassInfo.mPersistentObject = field; clazz.reset(env->FindClass("android/media/MediaCodecInfo$CodecCapabilities")); CHECK(clazz.get() != NULL); gCodecInfo.capsClazz = (jclass)env->NewGlobalRef(clazz.get()); method = env->GetMethodID(clazz.get(), "<init>", "([Landroid/media/MediaCodecInfo$CodecProfileLevel;[IZI" "Ljava/util/Map;Ljava/util/Map;)V"); CHECK(method != NULL); gCodecInfo.capsCtorId = method; clazz.reset(env->FindClass("android/media/MediaCodecInfo$CodecProfileLevel")); CHECK(clazz.get() != NULL); gCodecInfo.profileLevelClazz = (jclass)env->NewGlobalRef(clazz.get()); field = env->GetFieldID(clazz.get(), "profile", "I"); CHECK(field != NULL); gCodecInfo.profileField = field; field = env->GetFieldID(clazz.get(), "level", "I"); CHECK(field != NULL); gCodecInfo.levelField = field; } static void android_media_MediaCodec_native_setup( Loading Loading @@ -2002,6 +2152,9 @@ static const JNINativeMethod gMethods[] = { { "getName", "()Ljava/lang/String;", (void *)android_media_MediaCodec_getName }, { "getOwnCodecInfo", "()Landroid/media/MediaCodecInfo;", (void *)android_media_MediaCodec_getOwnCodecInfo }, { "native_getMetrics", "()Landroid/os/PersistableBundle;", (void *)android_media_MediaCodec_native_getMetrics}, Loading media/jni/android_media_MediaCodec.h +2 −0 Original line number Diff line number Diff line Loading @@ -120,6 +120,8 @@ struct JMediaCodec : public AHandler { status_t getName(JNIEnv *env, jstring *name) const; status_t getCodecInfo(JNIEnv *env, jobject *codecInfo) const; status_t getMetrics(JNIEnv *env, MediaAnalyticsItem * &reply) const; status_t setParameters(const sp<AMessage> ¶ms); Loading Loading
media/java/android/media/MediaCodec.java +20 −2 Original line number Diff line number Diff line Loading @@ -1602,7 +1602,9 @@ final public class MediaCodec { private EventHandler mCallbackHandler; private Callback mCallback; private OnFrameRenderedListener mOnFrameRenderedListener; private Object mListenerLock = new Object(); private final Object mListenerLock = new Object(); private MediaCodecInfo mCodecInfo; private final Object mCodecInfoLock = new Object(); private static final int EVENT_CALLBACK = 1; private static final int EVENT_SET_CALLBACK = 2; Loading Loading @@ -3469,8 +3471,24 @@ final public class MediaCodec { */ @NonNull public MediaCodecInfo getCodecInfo() { return MediaCodecList.getInfoFor(getName()); // Get the codec name first. If the codec is already released, // IllegalStateException will be thrown here. String name = getName(); synchronized (mCodecInfoLock) { if (mCodecInfo == null) { // Get the codec info for this codec itself first. Only initialize // the full codec list if this somehow fails because it can be slow. mCodecInfo = getOwnCodecInfo(); if (mCodecInfo == null) { mCodecInfo = MediaCodecList.getInfoFor(name); } } return mCodecInfo; } } @NonNull private native final MediaCodecInfo getOwnCodecInfo(); @NonNull private native final ByteBuffer[] getBuffers(boolean input); Loading
media/java/android/media/MediaCodecInfo.java +25 −18 Original line number Diff line number Diff line Loading @@ -829,14 +829,24 @@ public final class MediaCodecInfo { /** @hide */ public CodecCapabilities dup() { return new CodecCapabilities( // clone writable arrays Arrays.copyOf(profileLevels, profileLevels.length), Arrays.copyOf(colorFormats, colorFormats.length), isEncoder(), mFlagsVerified, mDefaultFormat, mCapabilitiesInfo); CodecCapabilities caps = new CodecCapabilities(); // profileLevels and colorFormats may be modified by client. caps.profileLevels = Arrays.copyOf(profileLevels, profileLevels.length); caps.colorFormats = Arrays.copyOf(colorFormats, colorFormats.length); caps.mMime = mMime; caps.mMaxSupportedInstances = mMaxSupportedInstances; caps.mFlagsRequired = mFlagsRequired; caps.mFlagsSupported = mFlagsSupported; caps.mFlagsVerified = mFlagsVerified; caps.mAudioCaps = mAudioCaps; caps.mVideoCaps = mVideoCaps; caps.mEncoderCaps = mEncoderCaps; caps.mDefaultFormat = mDefaultFormat; caps.mCapabilitiesInfo = mCapabilitiesInfo; return caps; } /** Loading Loading @@ -898,13 +908,13 @@ public final class MediaCodecInfo { if (mMime.toLowerCase().startsWith("audio/")) { mAudioCaps = AudioCapabilities.create(info, this); mAudioCaps.setDefaultFormat(mDefaultFormat); mAudioCaps.getDefaultFormat(mDefaultFormat); } else if (mMime.toLowerCase().startsWith("video/")) { mVideoCaps = VideoCapabilities.create(info, this); } if (encoder) { mEncoderCaps = EncoderCapabilities.create(info, this); mEncoderCaps.setDefaultFormat(mDefaultFormat); mEncoderCaps.getDefaultFormat(mDefaultFormat); } final Map<String, Object> global = MediaCodecList.getGlobalSettings(); Loading Loading @@ -990,8 +1000,7 @@ public final class MediaCodecInfo { return caps; } /** @hide */ public void init(MediaFormat info, CodecCapabilities parent) { private void init(MediaFormat info, CodecCapabilities parent) { mParent = parent; initWithPlatformLimits(); applyLevelLimits(); Loading Loading @@ -1171,7 +1180,7 @@ public final class MediaCodecInfo { } /** @hide */ public void setDefaultFormat(MediaFormat format) { public void getDefaultFormat(MediaFormat format) { // report settings that have only a single choice if (mBitrateRange.getLower().equals(mBitrateRange.getUpper())) { format.setInteger(MediaFormat.KEY_BIT_RATE, mBitrateRange.getLower()); Loading Loading @@ -1585,8 +1594,7 @@ public final class MediaCodecInfo { return caps; } /** @hide */ public void init(MediaFormat info, CodecCapabilities parent) { private void init(MediaFormat info, CodecCapabilities parent) { mParent = parent; initWithPlatformLimits(); applyLevelLimits(); Loading Loading @@ -2707,8 +2715,7 @@ public final class MediaCodecInfo { return caps; } /** @hide */ public void init(MediaFormat info, CodecCapabilities parent) { private void init(MediaFormat info, CodecCapabilities parent) { // no support for complexity or quality yet mParent = parent; mComplexityRange = Range.create(0, 0); Loading Loading @@ -2789,7 +2796,7 @@ public final class MediaCodecInfo { } /** @hide */ public void setDefaultFormat(MediaFormat format) { public void getDefaultFormat(MediaFormat format) { // don't list trivial quality/complexity as default for now if (!mQualityRange.getUpper().equals(mQualityRange.getLower()) && mDefaultQuality != null) { Loading
media/jni/android_media_MediaCodec.cpp +153 −0 Original line number Diff line number Diff line Loading @@ -29,6 +29,7 @@ #include "android_util_Binder.h" #include "jni.h" #include <nativehelper/JNIHelp.h> #include <nativehelper/ScopedLocalRef.h> #include <android/hardware/cas/native/1.0/IDescrambler.h> Loading Loading @@ -98,6 +99,13 @@ static struct { jint AesCbc; } gCryptoModes; static struct { jclass capsClazz; jmethodID capsCtorId; jclass profileLevelClazz; jfieldID profileField; jfieldID levelField; } gCodecInfo; struct fields_t { jfieldID context; Loading Loading @@ -625,6 +633,103 @@ status_t JMediaCodec::getName(JNIEnv *env, jstring *nameStr) const { return OK; } static jobject getCodecCapabilitiesObject( JNIEnv *env, const char *mime, bool isEncoder, const sp<MediaCodecInfo::Capabilities> &capabilities) { Vector<MediaCodecInfo::ProfileLevel> profileLevels; Vector<uint32_t> colorFormats; sp<AMessage> defaultFormat = new AMessage(); defaultFormat->setString("mime", mime); capabilities->getSupportedColorFormats(&colorFormats); capabilities->getSupportedProfileLevels(&profileLevels); uint32_t flags = capabilities->getFlags(); sp<AMessage> details = capabilities->getDetails(); jobject defaultFormatObj = NULL; if (ConvertMessageToMap(env, defaultFormat, &defaultFormatObj)) { return NULL; } ScopedLocalRef<jobject> defaultFormatRef(env, defaultFormatObj); jobject detailsObj = NULL; if (ConvertMessageToMap(env, details, &detailsObj)) { return NULL; } ScopedLocalRef<jobject> detailsRef(env, detailsObj); ScopedLocalRef<jobjectArray> profileLevelArray(env, env->NewObjectArray( profileLevels.size(), gCodecInfo.profileLevelClazz, NULL)); for (size_t i = 0; i < profileLevels.size(); ++i) { const MediaCodecInfo::ProfileLevel &src = profileLevels.itemAt(i); ScopedLocalRef<jobject> srcRef(env, env->AllocObject( gCodecInfo.profileLevelClazz)); env->SetIntField(srcRef.get(), gCodecInfo.profileField, src.mProfile); env->SetIntField(srcRef.get(), gCodecInfo.levelField, src.mLevel); env->SetObjectArrayElement(profileLevelArray.get(), i, srcRef.get()); } ScopedLocalRef<jintArray> colorFormatsArray( env, env->NewIntArray(colorFormats.size())); for (size_t i = 0; i < colorFormats.size(); ++i) { jint val = colorFormats.itemAt(i); env->SetIntArrayRegion(colorFormatsArray.get(), i, 1, &val); } return env->NewObject( gCodecInfo.capsClazz, gCodecInfo.capsCtorId, profileLevelArray.get(), colorFormatsArray.get(), isEncoder, flags, defaultFormatRef.get(), detailsRef.get()); } status_t JMediaCodec::getCodecInfo(JNIEnv *env, jobject *codecInfoObject) const { sp<MediaCodecInfo> codecInfo; status_t err = mCodec->getCodecInfo(&codecInfo); if (err != OK) { return err; } ScopedLocalRef<jstring> nameObject(env, env->NewStringUTF(codecInfo->getCodecName())); bool isEncoder = codecInfo->isEncoder(); Vector<AString> mimes; codecInfo->getSupportedMimes(&mimes); ScopedLocalRef<jobjectArray> capsArrayObj(env, env->NewObjectArray(mimes.size(), gCodecInfo.capsClazz, NULL)); for (size_t i = 0; i < mimes.size(); i++) { const sp<MediaCodecInfo::Capabilities> caps = codecInfo->getCapabilitiesFor(mimes[i].c_str()); ScopedLocalRef<jobject> capsObj(env, getCodecCapabilitiesObject( env, mimes[i].c_str(), isEncoder, caps)); env->SetObjectArrayElement(capsArrayObj.get(), i, capsObj.get()); } ScopedLocalRef<jclass> codecInfoClazz(env, env->FindClass("android/media/MediaCodecInfo")); CHECK(codecInfoClazz.get() != NULL); jmethodID codecInfoCtorID = env->GetMethodID(codecInfoClazz.get(), "<init>", "(Ljava/lang/String;Z[Landroid/media/MediaCodecInfo$CodecCapabilities;)V"); *codecInfoObject = env->NewObject(codecInfoClazz.get(), codecInfoCtorID, nameObject.get(), isEncoder, capsArrayObj.get()); return OK; } status_t JMediaCodec::getMetrics(JNIEnv *, MediaAnalyticsItem * &reply) const { status_t status = mCodec->getMetrics(reply); Loading Loading @@ -1665,6 +1770,29 @@ static jobject android_media_MediaCodec_getName( return NULL; } static jobject android_media_MediaCodec_getOwnCodecInfo( JNIEnv *env, jobject thiz) { ALOGV("android_media_MediaCodec_getOwnCodecInfo"); sp<JMediaCodec> codec = getMediaCodec(env, thiz); if (codec == NULL) { throwExceptionAsNecessary(env, INVALID_OPERATION); return NULL; } jobject codecInfoObj; status_t err = codec->getCodecInfo(env, &codecInfoObj); if (err == OK) { return codecInfoObj; } throwExceptionAsNecessary(env, err); return NULL; } static jobject android_media_MediaCodec_native_getMetrics(JNIEnv *env, jobject thiz) { Loading Loading @@ -1877,6 +2005,28 @@ static void android_media_MediaCodec_native_init(JNIEnv *env) { field = env->GetFieldID(clazz.get(), "mPersistentObject", "J"); CHECK(field != NULL); gPersistentSurfaceClassInfo.mPersistentObject = field; clazz.reset(env->FindClass("android/media/MediaCodecInfo$CodecCapabilities")); CHECK(clazz.get() != NULL); gCodecInfo.capsClazz = (jclass)env->NewGlobalRef(clazz.get()); method = env->GetMethodID(clazz.get(), "<init>", "([Landroid/media/MediaCodecInfo$CodecProfileLevel;[IZI" "Ljava/util/Map;Ljava/util/Map;)V"); CHECK(method != NULL); gCodecInfo.capsCtorId = method; clazz.reset(env->FindClass("android/media/MediaCodecInfo$CodecProfileLevel")); CHECK(clazz.get() != NULL); gCodecInfo.profileLevelClazz = (jclass)env->NewGlobalRef(clazz.get()); field = env->GetFieldID(clazz.get(), "profile", "I"); CHECK(field != NULL); gCodecInfo.profileField = field; field = env->GetFieldID(clazz.get(), "level", "I"); CHECK(field != NULL); gCodecInfo.levelField = field; } static void android_media_MediaCodec_native_setup( Loading Loading @@ -2002,6 +2152,9 @@ static const JNINativeMethod gMethods[] = { { "getName", "()Ljava/lang/String;", (void *)android_media_MediaCodec_getName }, { "getOwnCodecInfo", "()Landroid/media/MediaCodecInfo;", (void *)android_media_MediaCodec_getOwnCodecInfo }, { "native_getMetrics", "()Landroid/os/PersistableBundle;", (void *)android_media_MediaCodec_native_getMetrics}, Loading
media/jni/android_media_MediaCodec.h +2 −0 Original line number Diff line number Diff line Loading @@ -120,6 +120,8 @@ struct JMediaCodec : public AHandler { status_t getName(JNIEnv *env, jstring *name) const; status_t getCodecInfo(JNIEnv *env, jobject *codecInfo) const; status_t getMetrics(JNIEnv *env, MediaAnalyticsItem * &reply) const; status_t setParameters(const sp<AMessage> ¶ms); Loading