Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 0 additions & 4 deletions webrtc-jni/src/main/cpp/include/api/PeerConnectionObserver.h
Original file line number Diff line number Diff line change
Expand Up @@ -72,10 +72,6 @@ namespace jni
};

private:
// Reports a Java exception thrown by a callback without letting it
// unwind through WebRTC.
void ReportException(JNIEnv * env) noexcept;

JavaGlobalRef<jobject> observer;

const std::shared_ptr<JavaPeerConnectionObserverClass> javaClass;
Expand Down
8 changes: 7 additions & 1 deletion webrtc-jni/src/main/cpp/include/api/WebRTCUtils.h
Original file line number Diff line number Diff line change
Expand Up @@ -82,7 +82,13 @@ namespace jni
// uncaught exception handler, as the JVM does for an exception escaping a
// Java thread. Callbacks that WebRTC invokes use it, because a C++
// exception must not unwind through WebRTC's frames.
void ReportUncaughtException(JNIEnv * env, jthrowable exception);
void ReportUncaughtException(JNIEnv * env, jthrowable exception) noexcept;

// Clears the Java exception pending on the calling thread, if any, and
// reports it as uncaught. A callback that WebRTC invokes ends with this
// instead of ExceptionCheck(), which throws, after turning any C++
// exception of its own into a Java one with ThrowCxxJavaException().
void ReportPendingException(JNIEnv * env) noexcept;
}

#endif
26 changes: 18 additions & 8 deletions webrtc-jni/src/main/cpp/src/JNI_CustomVideoSource.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -67,10 +67,15 @@ JNIEXPORT void JNICALL Java_dev_onvoid_webrtc_media_video_CustomVideoSource_push
CHECK_HANDLE(source);

if (javaFrame != nullptr) {
auto frame = jni::JavaLocalRef<jobject>(env, javaFrame);
webrtc::VideoFrame nativeFrame = jni::VideoFrame::toNative(env, frame);

source->PushFrame(nativeFrame);
try {
auto frame = jni::JavaLocalRef<jobject>(env, javaFrame);
webrtc::VideoFrame nativeFrame = jni::VideoFrame::toNative(env, frame);

source->PushFrame(nativeFrame);
}
catch (...) {
ThrowCxxJavaException(env);
}
}
}

Expand All @@ -81,9 +86,14 @@ JNIEXPORT void JNICALL Java_dev_onvoid_webrtc_media_video_CustomVideoSource_push
CHECK_HANDLE(source);

if (javaFrame != nullptr) {
auto frame = jni::JavaLocalRef<jobject>(env, javaFrame);
webrtc::VideoFrame nativeFrame = jni::VideoFrame::toNative(env, frame);

source->PushFrame(nativeFrame, timestampUs);
try {
auto frame = jni::JavaLocalRef<jobject>(env, javaFrame);
webrtc::VideoFrame nativeFrame = jni::VideoFrame::toNative(env, frame);

source->PushFrame(nativeFrame, timestampUs);
}
catch (...) {
ThrowCxxJavaException(env);
}
}
}
6 changes: 1 addition & 5 deletions webrtc-jni/src/main/cpp/src/api/AddIceCandidateObserver.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -79,11 +79,7 @@ namespace jni
}

// A Java exception must not escape into WebRTC's signaling thread.
if (env->ExceptionCheck()) {
JavaLocalRef<jthrowable> exception(env, env->ExceptionOccurred());
env->ExceptionClear();
ReportUncaughtException(env, exception.get());
}
ReportPendingException(env);
}

AddIceCandidateObserver::JavaAddIceCandidateObserverClass::JavaAddIceCandidateObserverClass(JNIEnv * env)
Expand Down
15 changes: 10 additions & 5 deletions webrtc-jni/src/main/cpp/src/api/AudioTrackSink.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,9 @@
*/

#include "api/AudioTrackSink.h"
#include "api/WebRTCUtils.h"
#include "JavaClasses.h"
#include "JavaUtils.h"
#include "JNI_WebRTC.h"

namespace jni
Expand All @@ -37,12 +39,15 @@ namespace jni
const jbyte * buffer = static_cast<const jbyte *>(data);
jsize dataSize = static_cast<jsize>(frames * channels * (bitsPerSample / 8));

jbyteArray dataArray = env->NewByteArray(dataSize);
env->SetByteArrayRegion(dataArray, 0, dataSize, buffer);
JavaLocalRef<jbyteArray> dataArray(env, env->NewByteArray(dataSize));

env->CallVoidMethod(sink, javaClass->onData, dataArray, bitsPerSample, sampleRate, channels, frames);
ExceptionCheck(env);
env->DeleteLocalRef(dataArray);
if (dataArray.get() != nullptr) {
env->SetByteArrayRegion(dataArray.get(), 0, dataSize, buffer);
env->CallVoidMethod(sink, javaClass->onData, dataArray.get(), static_cast<jint>(bitsPerSample),
static_cast<jint>(sampleRate), static_cast<jint>(channels), static_cast<jint>(frames));
}

ReportPendingException(env);
}

AudioTrackSink::JavaAudioTrackSinkClass::JavaAudioTrackSinkClass(JNIEnv * env)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
#include "api/RTCSessionDescription.h"
#include "api/WebRTCUtils.h"
#include "JavaString.h"
#include "JavaUtils.h"
#include "JNI_WebRTC.h"

namespace jni
Expand All @@ -36,11 +37,16 @@ namespace jni
return;
}

JavaLocalRef<jobject> javaDesc = jni::RTCSessionDescription::toJava(env, desc);
try {
JavaLocalRef<jobject> javaDesc = jni::RTCSessionDescription::toJava(env, desc);

env->CallVoidMethod(observer, javaClass->onSuccess, javaDesc.get());
env->CallVoidMethod(observer, javaClass->onSuccess, javaDesc.get());
}
catch (...) {
ThrowCxxJavaException(env);
}

ExceptionCheck(env);
ReportPendingException(env);
}

void CreateSessionDescriptionObserver::OnFailure(webrtc::RTCError error)
Expand All @@ -51,11 +57,16 @@ namespace jni
return;
}

JavaLocalRef<jstring> errorMessage = JavaString::toJava(env, RTCErrorToString(error));
try {
JavaLocalRef<jstring> errorMessage = JavaString::toJava(env, RTCErrorToString(error));

env->CallVoidMethod(observer, javaClass->onFailure, errorMessage.get());
env->CallVoidMethod(observer, javaClass->onFailure, errorMessage.get());
}
catch (...) {
ThrowCxxJavaException(env);
}

ExceptionCheck(env);
ReportPendingException(env);
}

CreateSessionDescriptionObserver::JavaCreateSessionDescObserverClass::JavaCreateSessionDescObserverClass(JNIEnv * env)
Expand Down
Loading
Loading