1 year ago
#355940
David
Android WebRTC connection is not established in non-local network
I'm developing an Android app with a P2P call feature with WebRTC. I've faced a strange problem and cannot find a solution for already several days.
The problem is that the side A cannot connect to the side B if the side A is connected to the network N1 and the side B is connected to the network N2. When both the sides are connected to the same network N then everything works fine.
In case of different networks the devices generate candidates, exchange but cannot find the best pair...
The connection establishment algorithm is:
- Side A creates an offer, sets a local description and sends SDP to the side B via signalling server
- Side B sets a remote description, creates an answer and sends SDP the the side A
- Side A sets a remote desscription
- Side A and side B generate ICE candidates, sends them to each other and apply them.
I guarantee that the ICE candidates generated from the side A are delivered to the side B.
I guess the problem is related to TURN server. I know that non-local connection establishment needs a TURN server so I've added it.
The most useful webrtc native library log I've got in the logcat is:
(line 848): Port[e6cb70c0:0:1:0:relay:Net[lo:127.0.0.x/8:Loopback:id=1]]: Failed to send TURN message, error: 22
The local logs:
2022-03-30 20:58:29.303 26318-31936/org.hedwig D/Log: On renegotiation needed
2022-03-30 20:58:29.311 26318-31936/org.hedwig D/Log: On signaling change HAVE_LOCAL_OFFER
2022-03-30 20:58:29.314 26318-31936/org.hedwig D/Log: On ice gathering change GATHERING
2022-03-30 20:58:29.322 26318-31936/org.hedwig D/Log: On ice candidate 0:0:candidate:1460998643 1 udp 2122260223 *hidden* 46575 typ host generation 0 ufrag iUAZ network-id 3 network-cost 900::UNKNOWN
2022-03-30 20:58:29.326 26318-31936/org.hedwig D/Log: On ice candidate 0:0:candidate:559267639 1 udp 2122202367 ::1 49813 typ host generation 0 ufrag iUAZ network-id 2::UNKNOWN
2022-03-30 20:58:29.327 26318-31936/org.hedwig D/Log: On ice candidate 0:0:candidate:1510613869 1 udp 2122129151 127.0.0.1 42709 typ host generation 0 ufrag iUAZ network-id 1::UNKNOWN
2022-03-30 20:58:29.349 26318-31936/org.hedwig D/Log: On ice candidate 0:0:candidate:3596425031 1 udp 1686052607 *hidden* typ srflx raddr *hidden* rport 46575 generation 0 ufrag iUAZ network-id 3 network-cost 900:stun:*hidden*:UNKNOWN
2022-03-30 20:58:29.426 26318-31936/org.hedwig D/Log: On ice candidate 0:0:candidate:429321475 1 tcp 1518280447 *hidden* typ host tcptype passive generation 0 ufrag iUAZ network-id 3 network-cost 900::UNKNOWN
2022-03-30 20:58:29.426 26318-31936/org.hedwig D/Log: On ice candidate 0:0:candidate:1876313031 1 tcp 1518222591 ::1 37467 typ host tcptype passive generation 0 ufrag iUAZ network-id 2::UNKNOWN
2022-03-30 20:58:29.429 26318-31936/org.hedwig D/Log: On ice candidate 0:0:candidate:344579997 1 tcp 1518149375 127.0.0.1 40083 typ host tcptype passive generation 0 ufrag iUAZ network-id 1::UNKNOWN
2022-03-30 20:58:29.664 26318-31936/org.hedwig D/Log: On signaling change STABLE
2022-03-30 20:58:29.723 26318-31936/org.hedwig D/Log: On ice connection change CHECKING
2022-03-30 20:58:29.727 26318-31936/org.hedwig D/Log: On standardized ice con change: CHECKING
2022-03-30 20:58:29.728 26318-31936/org.hedwig D/Log: On connection change CONNECTING
2022-03-30 20:58:30.921 26318-31936/org.hedwig D/Log: On selected candidate pair changed $Candidate pair change event:
remote: :-1:candidate:3011219415 1 udp 1686052607 *hidden* 56205 typ srflx raddr ***hidden*** rport 56205 generation 0 ufrag rv+a network-id 1 network-cost 50::UNKNOWN
local: :-1:candidate:3596425031 1 udp 1686052607 *hidden* 37170 typ srflx raddr ***hidden*** rport 46575 generation 0 ufrag iUAZ network-id 3 network-cost 900::CELLULAR
last data received ms: 0
reason: candidate pair state changed
estimatedDisconnectedTimeMs: 0
2022-03-30 20:58:30.923 26318-31936/org.hedwig D/Log: On standardized ice con change: CONNECTED
2022-03-30 20:58:30.927 26318-31936/org.hedwig D/Log: On ice gathering change COMPLETE
2022-03-30 20:58:34.840 26318-31936/org.hedwig D/Log: On selected candidate pair changed $Candidate pair change event:
remote: :-1:candidate:2623950527 1 udp 41885439 ***hidden*** 61645 typ relay raddr ***hidden*** rport 56205 generation 0 ufrag rv+a network-id 1 network-cost 50::UNKNOWN
local: :-1:candidate:3596425031 1 udp 1686052607 ***hidden*** 37170 typ srflx raddr ***hidden*** rport 46575 generation 0 ufrag iUAZ network-id 3 network-cost 900::CELLULAR
last data received ms: 0
reason: candidate pair state changed (after delay: 1000)
estimatedDisconnectedTimeMs: 3881
2022-03-30 20:58:40.866 26318-31936/org.hedwig D/Log: On selected candidate pair changed $Candidate pair change event:
remote: :-1:candidate:3011219415 1 udp 1686052607 ***hidden*** 56205 typ srflx raddr ***hidden*** rport 56205 generation 0 ufrag rv+a network-id 1 network-cost 50::UNKNOWN
local: :-1:candidate:3596425031 1 udp 1686052607 *hidden* 37170 typ srflx raddr ***hidden*** rport 46575 generation 0 ufrag iUAZ network-id 3 network-cost 900::CELLULAR
last data received ms: 0
reason: candidate pair state changed
estimatedDisconnectedTimeMs: 6013
2022-03-30 20:58:40.867 26318-31936/org.hedwig D/Log: On standardized ice con change: DISCONNECTED
2022-03-30 20:58:40.867 26318-31936/org.hedwig D/Log: On connection change DISCONNECTED
2022-03-30 20:58:46.952 26318-31936/org.hedwig D/Log: On selected candidate pair changed $Candidate pair change event:
remote: :-1:candidate:2623950527 1 udp 41885439 ***hidden*** 61645 typ relay raddr ***hidden*** rport 56205 generation 0 ufrag rv+a network-id 1 network-cost 50::UNKNOWN
local: :-1:candidate:3596425031 1 udp 1686052607 ***hidden*** 37170 typ srflx raddr ***hidden*** rport 46575 generation 0 ufrag iUAZ network-id 3 network-cost 900::CELLULAR
last data received ms: 0
reason: candidate pair state changed
estimatedDisconnectedTimeMs: 15994
2022-03-30 20:58:50.900 26318-31936/org.hedwig D/Log: On ice connection change FAILED
2022-03-30 20:58:50.901 26318-31936/org.hedwig D/Log: On standardized ice con change: FAILED
2022-03-30 20:58:50.901 26318-31936/org.hedwig D/Log: On connection change FAILED
2022-03-30 20:58:52.585 26318-31936/org.hedwig D/Log: On ice connection change CLOSED
2022-03-30 20:58:52.585 26318-31936/org.hedwig D/Log: On connection change CLOSED
2022-03-30 20:58:52.585 26318-31936/org.hedwig D/Log: On signaling change CLOSED
I've checked my TURN server in the Trickle ICE and it seems to work
Here is connection factory creating code:
private fun createPeerConnectionFactory(): PeerConnectionFactory {
initializeFactoryOptions()
val eglBase = EglBase.create()
this.eglBase = eglBase
val encoderFactory =
DefaultVideoEncoderFactory(eglBase.eglBaseContext, true, true)
val decoderFactory = DefaultVideoDecoderFactory(eglBase.eglBaseContext)
val options = PeerConnectionFactory
.Options()
.apply {
disableNetworkMonitor = true
}
return PeerConnectionFactory
.builder()
.setOptions(options)
.setVideoDecoderFactory(decoderFactory)
.setVideoEncoderFactory(encoderFactory)
.createPeerConnectionFactory()
}
private fun initializeFactoryOptions() {
val initOptions = PeerConnectionFactory
.InitializationOptions
.builder(context)
.setEnableInternalTracer(true)
.setFieldTrials("WebRTC-H264HighProfile/Enabled/")
.setInjectableLogger(WebRtcLoggable(), Logging.Severity.LS_VERBOSE)
.createInitializationOptions()
PeerConnectionFactory.initialize(initOptions)
}
Here is the peer connection creating code:
val stunUrl = PeerConnection.IceServer
.builder("stun:${webRtcConfig.stunUrl}")
.createIceServer()
val username = generateUsername()
val password = generatePassword(username)
val turnUrl = PeerConnection
.IceServer
.builder("turn:${webRtcConfig.turnUrl}")
.setUsername(username)
.setPassword(password)
.createIceServer()
val rtcConfig = PeerConnection
.RTCConfiguration(listOf(stunUrl, turnUrl))
.also {
it.sdpSemantics = PeerConnection.SdpSemantics.UNIFIED_PLAN
}
val connection = createPeerConnection(
factory = peerConnectionFactory,
config = rtcConfig
)
@Suppress("DEPRECATION")
private fun createPeerConnection(
factory: PeerConnectionFactory,
config: PeerConnection.RTCConfiguration
): PeerConnection? {
val constraints = MediaConstraints()
constraints.optional.add(MediaConstraints.KeyValuePair("DtlsSrtpKeyAgreement", "true"))
return factory
.createPeerConnection(config, constraints, object : WebRtcConnectionObserver() {
override fun onIceCandidate(p0: IceCandidate?) {
super.onIceCandidate(p0)
infoLog("On Web RTC ice candidate: $p0", tag = LOG_TAG_WEB_RTC_CONTROLLER)
p0
?.let { candidate ->
onNewCandidateGenerated(candidate)
}
}
override fun onIceConnectionChange(p0: PeerConnection.IceConnectionState?) {
super.onIceConnectionChange(p0)
infoLog("On Ice connection change: $p0", tag = LOG_TAG_WEB_RTC_CONTROLLER)
}
})
}
Here is remote ICE candidate apply code: If remote description is null the candidate is added to a pending list remoteCandidates. When the remote description is set all the candidates from the pending list are added to the connection.
private fun onNewCandidateFromOtherSide(
sdp: String,
sdpMid: String,
sdpMLineIndex: Int
) {
infoLog(
"Got new candidate from the other side. SDP: $sdp\nsdpMid: $sdpMid\nsdpMLineIndex: $sdpMLineIndex",
tag = LOG_TAG_WEB_RTC_CONTROLLER
)
val candidate = IceCandidate(
sdpMid, sdpMLineIndex, sdp
)
if (peerConnection?.remoteDescription != null) {
requirePeerConnection().addIceCandidate(candidate)
} else {
remoteCandidates.add(candidate)
}
}
The WebRTC library I use:
implementation 'org.webrtc:google-webrtc:1.0.32006'
FYI: TURN server URL is an IP address (may be useful).
My team has developed an iOS version of the same app and everything works fine on the iPhone. I cannot understand the reason of the failure on Android devices...
Thank you in advance!
android
kotlin
webrtc
p2p
0 Answers
Your Answer