diff --git a/talk/app/webrtc/java/jni/peerconnection_jni.cc b/talk/app/webrtc/java/jni/peerconnection_jni.cc index 75f230f928..9bb84ac24f 100644 --- a/talk/app/webrtc/java/jni/peerconnection_jni.cc +++ b/talk/app/webrtc/java/jni/peerconnection_jni.cc @@ -195,22 +195,18 @@ static JNIEnv* AttachCurrentThreadIfNeeded() { return jni; } -// Return a |jlong| that will automatically convert back to |ptr| when assigned -// to a |uint64| +// Return a |jlong| that will correctly convert back to |ptr|. This is needed +// because the alternative (of silently passing a 32-bit pointer to a vararg +// function expecting a 64-bit param) picks up garbage in the high 32 bits. static jlong jlongFromPointer(void* ptr) { - COMPILE_ASSERT(sizeof(intptr_t) <= sizeof(uint64), + COMPILE_ASSERT(sizeof(intptr_t) <= sizeof(jlong), Time_to_rethink_the_use_of_jlongs); - // Guaranteed to fit by the COMPILE_ASSERT above. - uint64 u64 = reinterpret_cast(ptr); - // If the unsigned value fits in the signed type, return it directly. - if (u64 <= std::numeric_limits::max()) - return u64; - // Otherwise, we need to get move u64 into the range of [int64min, -1] subject - // to the constraints of remaining equal to |u64| modulo |2^64|. - u64 = std::numeric_limits::max() - u64; // In [0,int64max]. - int64 i64 = -u64; // In [-int64max, 0]. - i64 -= 1; // In [int64min, -1], and i64+2^64==u64. - return i64; + // Going through intptr_t to be obvious about the definedness of the + // conversion from pointer to integral type. intptr_t to jlong is a standard + // widening by the COMPILE_ASSERT above. + jlong ret = reinterpret_cast(ptr); + assert(reinterpret_cast(ret) == ptr); + return ret; } // Android's FindClass() is trickier than usual because the app-specific @@ -1104,7 +1100,7 @@ JOW(jlong, DataChannel_registerObserverNative)( talk_base::scoped_ptr observer( new DataChannelObserverWrapper(jni, j_observer)); ExtractNativeDC(jni, j_dc)->RegisterObserver(observer.get()); - return reinterpret_cast(observer.release()); + return jlongFromPointer(observer.release()); } JOW(void, DataChannel_unregisterObserverNative)( diff --git a/talk/app/webrtc/javatests/src/org/webrtc/PeerConnectionTest.java b/talk/app/webrtc/javatests/src/org/webrtc/PeerConnectionTest.java index d7380e02c3..dfed4bf022 100644 --- a/talk/app/webrtc/javatests/src/org/webrtc/PeerConnectionTest.java +++ b/talk/app/webrtc/javatests/src/org/webrtc/PeerConnectionTest.java @@ -533,9 +533,11 @@ public class PeerConnectionTest extends TestCase { factory, offeringPC, videoSource, "oLMS", "oLMSv0", "oLMSa0", offeringExpectations); - offeringExpectations.setDataChannel(offeringPC.createDataChannel( - "offeringDC", new DataChannel.Init())); + DataChannel offeringDC = offeringPC.createDataChannel( + "offeringDC", new DataChannel.Init()); + assertEquals("offeringDC", offeringDC.label()); + offeringExpectations.setDataChannel(offeringDC); SdpObserverLatch sdpLatch = new SdpObserverLatch(); offeringPC.createOffer(sdpLatch, new MediaConstraints()); assertTrue(sdpLatch.await()); diff --git a/talk/examples/android/src/org/appspot/apprtc/AppRTCDemoActivity.java b/talk/examples/android/src/org/appspot/apprtc/AppRTCDemoActivity.java index c1dff74cd1..6d864e4860 100644 --- a/talk/examples/android/src/org/appspot/apprtc/AppRTCDemoActivity.java +++ b/talk/examples/android/src/org/appspot/apprtc/AppRTCDemoActivity.java @@ -171,11 +171,26 @@ public class AppRTCDemoActivity extends Activity } } + + // Just for fun (and to regression-test bug 2302) make sure that DataChannels + // can be created, queried, and disposed. + private static void createDataChannelToRegressionTestBug2302( + PeerConnection pc) { + DataChannel dc = pc.createDataChannel("dcLabel", new DataChannel.Init()); + abortUnless("dcLabel".equals(dc.label()), "WTF?"); + dc.dispose(); + } + @Override public void onIceServers(List iceServers) { factory = new PeerConnectionFactory(); - pc = factory.createPeerConnection( - iceServers, appRtcClient.pcConstraints(), pcObserver); + + MediaConstraints pcConstraints = appRtcClient.pcConstraints(); + pcConstraints.optional.add( + new MediaConstraints.KeyValuePair("RtpDataChannels", "true")); + pc = factory.createPeerConnection(iceServers, pcConstraints, pcObserver); + + createDataChannelToRegressionTestBug2302(pc); // See method comment. // Uncomment to get ALL WebRTC tracing and SENSITIVE libjingle logging. // NOTE: this _must_ happen while |factory| is alive!