Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit c371a02e authored by James Dong's avatar James Dong
Browse files

Media JNI code cleanup

o Don't throw exception again because an exception was already thrown
o Check on return values from FindClass() and GetMethodID

Change-Id: Id92bb8228f1f0d2798d1cdf7de73cbb43816060b
related-to-bug: 4139926
parent fcdebf88
Loading
Loading
Loading
Loading
+43 −10
Original line number Diff line number Diff line
@@ -34,11 +34,11 @@ using namespace android;

struct fields_t {
    jfieldID context;
    jclass bitmapClazz;
    jclass bitmapClazz;  // Must be a global ref
    jfieldID nativeBitmap;
    jmethodID createBitmapMethod;
    jmethodID createScaledBitmapMethod;
    jclass configClazz;
    jclass configClazz;  // Must be a global ref
    jmethodID createConfigMethod;
};

@@ -120,33 +120,71 @@ android_media_MediaMetadataRetriever_setDataSourceAndHeaders(
    if (headers) {
        // Get the Map's entry Set.
        jclass mapClass = env->FindClass("java/util/Map");
        if (mapClass == NULL) {
            return;
        }

        jmethodID entrySet =
            env->GetMethodID(mapClass, "entrySet", "()Ljava/util/Set;");
        if (entrySet == NULL) {
            return;
        }

        jobject set = env->CallObjectMethod(headers, entrySet);
        if (set == NULL) {
            return;
        }

        // Obtain an iterator over the Set
        jclass setClass = env->FindClass("java/util/Set");
        if (setClass == NULL) {
            return;
        }

        jmethodID iterator =
            env->GetMethodID(setClass, "iterator", "()Ljava/util/Iterator;");
        if (iterator == NULL) {
            return;
        }

        jobject iter = env->CallObjectMethod(set, iterator);
        if (iter == NULL) {
            return;
        }

        // Get the Iterator method IDs
        jclass iteratorClass = env->FindClass("java/util/Iterator");
        if (iteratorClass == NULL) {
            return;
        }
        jmethodID hasNext = env->GetMethodID(iteratorClass, "hasNext", "()Z");
        if (hasNext == NULL) {
            return;
        }

        jmethodID next =
            env->GetMethodID(iteratorClass, "next", "()Ljava/lang/Object;");
        if (next == NULL) {
            return;
        }

        // Get the Entry class method IDs
        jclass entryClass = env->FindClass("java/util/Map$Entry");
        if (entryClass == NULL) {
            return;
        }

        jmethodID getKey =
            env->GetMethodID(entryClass, "getKey", "()Ljava/lang/Object;");
        if (getKey == NULL) {
            return;
        }

        jmethodID getValue =
            env->GetMethodID(entryClass, "getValue", "()Ljava/lang/Object;");
        if (getValue == NULL) {
            return;
        }

        // Iterate over the entry Set
        while (env->CallBooleanMethod(iter, hasNext)) {
@@ -161,6 +199,7 @@ android_media_MediaMetadataRetriever_setDataSourceAndHeaders(

            const char* valueStr = env->GetStringUTFChars(value, NULL);
            if (!valueStr) {  // Out of memory
                env->ReleaseStringUTFChars(key, keyStr);
                return;
            }

@@ -173,12 +212,6 @@ android_media_MediaMetadataRetriever_setDataSourceAndHeaders(
            env->DeleteLocalRef(value);
        }

      env->DeleteLocalRef(entryClass);
      env->DeleteLocalRef(iteratorClass);
      env->DeleteLocalRef(iter);
      env->DeleteLocalRef(setClass);
      env->DeleteLocalRef(set);
      env->DeleteLocalRef(mapClass);
    }

    process_media_retriever_call(
+49 −32
Original line number Diff line number Diff line
/* //device/libs/android_runtime/android_media_MediaPlayer.cpp
/*
**
** Copyright 2007, The Android Open Source Project
**
@@ -185,45 +185,87 @@ android_media_MediaPlayer_setDataSourceAndHeaders(
        return;
    }

    const char *pathStr = env->GetStringUTFChars(path, NULL);
    if (pathStr == NULL) {  // Out of memory
        jniThrowException(env, "java/lang/RuntimeException", "Out of memory");
    const char *tmp = env->GetStringUTFChars(path, NULL);
    if (tmp == NULL) {  // Out of memory
        return;
    }

    String8 pathStr(tmp);
    env->ReleaseStringUTFChars(path, tmp);
    tmp = NULL;

    // headers is a Map<String, String>.
    // We build a similar KeyedVector out of it.
    KeyedVector<String8, String8> headersVector;
    if (headers) {
        // Get the Map's entry Set.
        jclass mapClass = env->FindClass("java/util/Map");
        if (mapClass == NULL) {
            return;
        }

        jmethodID entrySet =
            env->GetMethodID(mapClass, "entrySet", "()Ljava/util/Set;");
        if (entrySet == NULL) {
            return;
        }

        jobject set = env->CallObjectMethod(headers, entrySet);
        if (set == NULL) {
            return;
        }

        // Obtain an iterator over the Set
        jclass setClass = env->FindClass("java/util/Set");
        if (setClass == NULL) {
            return;
        }

        jmethodID iterator =
            env->GetMethodID(setClass, "iterator", "()Ljava/util/Iterator;");
        if (iterator == NULL) {
            return;
        }

        jobject iter = env->CallObjectMethod(set, iterator);
        if (iter == NULL) {
            return;
        }

        // Get the Iterator method IDs
        jclass iteratorClass = env->FindClass("java/util/Iterator");
        if (iteratorClass == NULL) {
            return;
        }

        jmethodID hasNext = env->GetMethodID(iteratorClass, "hasNext", "()Z");
        if (hasNext == NULL) {
            return;
        }

        jmethodID next =
            env->GetMethodID(iteratorClass, "next", "()Ljava/lang/Object;");
        if (next == NULL) {
            return;
        }

        // Get the Entry class method IDs
        jclass entryClass = env->FindClass("java/util/Map$Entry");
        if (entryClass == NULL) {
            return;
        }

        jmethodID getKey =
            env->GetMethodID(entryClass, "getKey", "()Ljava/lang/Object;");
        if (getKey == NULL) {
            return;
        }

        jmethodID getValue =
            env->GetMethodID(entryClass, "getValue", "()Ljava/lang/Object;");
        if (getValue == NULL) {
            return;
        }

        // Iterate over the entry Set
        while (env->CallBooleanMethod(iter, hasNext)) {
@@ -233,15 +275,12 @@ android_media_MediaPlayer_setDataSourceAndHeaders(

            const char* keyStr = env->GetStringUTFChars(key, NULL);
            if (!keyStr) {  // Out of memory
                jniThrowException(
                        env, "java/lang/RuntimeException", "Out of memory");
                return;
            }

            const char* valueStr = env->GetStringUTFChars(value, NULL);
            if (!valueStr) {  // Out of memory
                jniThrowException(
                        env, "java/lang/RuntimeException", "Out of memory");
                env->ReleaseStringUTFChars(key, keyStr);
                return;
            }

@@ -254,23 +293,14 @@ android_media_MediaPlayer_setDataSourceAndHeaders(
            env->DeleteLocalRef(value);
        }

      env->DeleteLocalRef(entryClass);
      env->DeleteLocalRef(iteratorClass);
      env->DeleteLocalRef(iter);
      env->DeleteLocalRef(setClass);
      env->DeleteLocalRef(set);
      env->DeleteLocalRef(mapClass);
    }

    LOGV("setDataSource: path %s", pathStr);
    status_t opStatus =
        mp->setDataSource(
                String8(pathStr),
                pathStr,
                headers ? &headersVector : NULL);

    // Make sure that local ref is released before a potential exception
    env->ReleaseStringUTFChars(path, pathStr);

    process_media_player_call(
            env, thiz, opStatus, "java/io/IOException",
            "setDataSource failed." );
@@ -628,62 +658,49 @@ android_media_MediaPlayer_native_init(JNIEnv *env)

    clazz = env->FindClass("android/media/MediaPlayer");
    if (clazz == NULL) {
        jniThrowException(env, "java/lang/RuntimeException", "Can't find android/media/MediaPlayer");
        return;
    }

    fields.context = env->GetFieldID(clazz, "mNativeContext", "I");
    if (fields.context == NULL) {
        jniThrowException(env, "java/lang/RuntimeException", "Can't find MediaPlayer.mNativeContext");
        return;
    }

    fields.post_event = env->GetStaticMethodID(clazz, "postEventFromNative",
                                               "(Ljava/lang/Object;IIILjava/lang/Object;)V");
    if (fields.post_event == NULL) {
        jniThrowException(env, "java/lang/RuntimeException", "Can't find MediaPlayer.postEventFromNative");
        return;
    }

    fields.surface = env->GetFieldID(clazz, "mSurface", "Landroid/view/Surface;");
    if (fields.surface == NULL) {
        jniThrowException(env, "java/lang/RuntimeException", "Can't find MediaPlayer.mSurface");
        return;
    }

    jclass surface = env->FindClass("android/view/Surface");
    if (surface == NULL) {
        jniThrowException(env, "java/lang/RuntimeException", "Can't find android/view/Surface");
        return;
    }

    fields.surface_native = env->GetFieldID(surface, ANDROID_VIEW_SURFACE_JNI_ID, "I");
    if (fields.surface_native == NULL) {
        jniThrowException(env, "java/lang/RuntimeException",
                "Can't find Surface." ANDROID_VIEW_SURFACE_JNI_ID);
        return;
    }

    fields.surfaceTexture = env->GetFieldID(clazz, "mSurfaceTexture",
            "Landroid/graphics/SurfaceTexture;");
    if (fields.surfaceTexture == NULL) {
        jniThrowException(env, "java/lang/RuntimeException",
                "Can't find MediaPlayer.mSurfaceTexture");
        return;
    }

    jclass surfaceTexture = env->FindClass("android/graphics/SurfaceTexture");
    if (surfaceTexture == NULL) {
        jniThrowException(env, "java/lang/RuntimeException",
                "Can't find android/graphics/SurfaceTexture");
        return;
    }

    fields.surfaceTexture_native = env->GetFieldID(surfaceTexture,
            ANDROID_GRAPHICS_SURFACETEXTURE_JNI_ID, "I");
    if (fields.surfaceTexture_native == NULL) {
        jniThrowException(env, "java/lang/RuntimeException",
                "Can't find SurfaceTexture." ANDROID_GRAPHICS_SURFACETEXTURE_JNI_ID);
        return;
    }

+1 −4
Original line number Diff line number Diff line
@@ -213,7 +213,6 @@ android_media_MediaScanner_processDirectory(

    const char *pathStr = env->GetStringUTFChars(path, NULL);
    if (pathStr == NULL) {  // Out of memory
        jniThrowException(env, kRunTimeException, "Out of memory");
        return;
    }

@@ -243,15 +242,14 @@ android_media_MediaScanner_processFile(

    const char *pathStr = env->GetStringUTFChars(path, NULL);
    if (pathStr == NULL) {  // Out of memory
        jniThrowException(env, kRunTimeException, "Out of memory");
        return;
    }

    const char *mimeTypeStr =
        (mimeType ? env->GetStringUTFChars(mimeType, NULL) : NULL);
    if (mimeType && mimeTypeStr == NULL) {  // Out of memory
        // ReleaseStringUTFChars can be called with an exception pending.
        env->ReleaseStringUTFChars(path, pathStr);
        jniThrowException(env, kRunTimeException, "Out of memory");
        return;
    }

@@ -281,7 +279,6 @@ android_media_MediaScanner_setLocale(
    }
    const char *localeStr = env->GetStringUTFChars(locale, NULL);
    if (localeStr == NULL) {  // Out of memory
        jniThrowException(env, kRunTimeException, "Out of memory");
        return;
    }
    mp->setLocale(localeStr);