# HG changeset patch # User Andreas Schiffler # Date 1357573186 28800 # Node ID a91717ac8ff1455b93b65aea3d85edcfa54757ba # Parent fbe83a6d10fa217d20b3885a6c0016194dc7cd9f# Parent 8a6b8ce976568afc59fd3240cd5f2f04af269cc8 Merged with tip diff -r fbe83a6d10fa -r a91717ac8ff1 android-project/src/org/libsdl/app/SDLActivity.java --- a/android-project/src/org/libsdl/app/SDLActivity.java Mon Jan 07 07:39:15 2013 -0800 +++ b/android-project/src/org/libsdl/app/SDLActivity.java Mon Jan 07 07:39:46 2013 -0800 @@ -353,8 +353,6 @@ } // Audio - private static Object buf; - public static Object audioInit(int sampleRate, boolean is16Bit, boolean isStereo, int desiredFrames) { int channelConfig = isStereo ? AudioFormat.CHANNEL_CONFIGURATION_STEREO : AudioFormat.CHANNEL_CONFIGURATION_MONO; int audioFormat = is16Bit ? AudioFormat.ENCODING_PCM_16BIT : AudioFormat.ENCODING_PCM_8BIT; @@ -373,13 +371,6 @@ audioStartThread(); Log.v("SDL", "SDL audio: got " + ((mAudioTrack.getChannelCount() >= 2) ? "stereo" : "mono") + " " + ((mAudioTrack.getAudioFormat() == AudioFormat.ENCODING_PCM_16BIT) ? "16-bit" : "8-bit") + " " + ((float)mAudioTrack.getSampleRate() / 1000f) + "kHz, " + desiredFrames + " frames buffer"); - - if (is16Bit) { - buf = new short[desiredFrames * (isStereo ? 2 : 1)]; - } else { - buf = new byte[desiredFrames * (isStereo ? 2 : 1)]; - } - return buf; } public static void audioStartThread() { diff -r fbe83a6d10fa -r a91717ac8ff1 src/core/android/SDL_android.cpp --- a/src/core/android/SDL_android.cpp Mon Jan 07 07:39:15 2013 -0800 +++ b/src/core/android/SDL_android.cpp Mon Jan 07 07:39:46 2013 -0800 @@ -120,7 +120,7 @@ midFlipBuffers = mEnv->GetStaticMethodID(mActivityClass, "flipBuffers","()V"); midAudioInit = mEnv->GetStaticMethodID(mActivityClass, - "audioInit", "(IZZI)Ljava/lang/Object;"); + "audioInit", "(IZZI)V"); midAudioWriteShortBuffer = mEnv->GetStaticMethodID(mActivityClass, "audioWriteShortBuffer", "([S)V"); midAudioWriteByteBuffer = mEnv->GetStaticMethodID(mActivityClass, @@ -433,13 +433,30 @@ audioBuffer16Bit = is16Bit; audioBufferStereo = channelCount > 1; - audioBuffer = env->CallStaticObjectMethod(mActivityClass, midAudioInit, sampleRate, audioBuffer16Bit, audioBufferStereo, desiredBufferFrames); + env->CallStaticObjectMethod(mActivityClass, midAudioInit, sampleRate, audioBuffer16Bit, audioBufferStereo, desiredBufferFrames); + + /* Allocating the audio buffer from the Java side and passing it as the return value for audioInit no longer works on + * Android >= 4.2 due to a "stale global reference" error. So now we allocate this buffer directly from this side. */ + + if (is16Bit) { + jshortArray audioBufferLocal = env->NewShortArray(desiredBufferFrames * (audioBufferStereo ? 2 : 1)); + if (audioBufferLocal) { + audioBuffer = env->NewGlobalRef(audioBufferLocal); + env->DeleteLocalRef(audioBufferLocal); + } + } + else { + jbyteArray audioBufferLocal = env->NewByteArray(desiredBufferFrames * (audioBufferStereo ? 2 : 1)); + if (audioBufferLocal) { + audioBuffer = env->NewGlobalRef(audioBufferLocal); + env->DeleteLocalRef(audioBufferLocal); + } + } if (audioBuffer == NULL) { - __android_log_print(ANDROID_LOG_WARN, "SDL", "SDL audio: didn't get back a good audio buffer!"); + __android_log_print(ANDROID_LOG_WARN, "SDL", "SDL audio: could not allocate an audio buffer!"); return 0; } - audioBuffer = env->NewGlobalRef(audioBuffer); jboolean isCopy = JNI_FALSE; if (audioBuffer16Bit) {