diff --git a/jicofo-common/src/main/kotlin/org/jitsi/jicofo/OctoConfig.kt b/jicofo-common/src/main/kotlin/org/jitsi/jicofo/OctoConfig.kt index 090e94b7ab..0046a9f4c5 100644 --- a/jicofo-common/src/main/kotlin/org/jitsi/jicofo/OctoConfig.kt +++ b/jicofo-common/src/main/kotlin/org/jitsi/jicofo/OctoConfig.kt @@ -29,6 +29,10 @@ class OctoConfig { "jicofo.octo.allow-mixed-versions".from(newConfig) } + val sctpDatachannels: Boolean by config { + "jicofo.octo.sctp-datachannels".from(newConfig) + } + companion object { @JvmField val config = OctoConfig() diff --git a/jicofo-selector/src/main/kotlin/org/jitsi/jicofo/bridge/colibri/Colibri2Session.kt b/jicofo-selector/src/main/kotlin/org/jitsi/jicofo/bridge/colibri/Colibri2Session.kt index 0a388167b8..f5e196fd67 100644 --- a/jicofo-selector/src/main/kotlin/org/jitsi/jicofo/bridge/colibri/Colibri2Session.kt +++ b/jicofo-selector/src/main/kotlin/org/jitsi/jicofo/bridge/colibri/Colibri2Session.kt @@ -17,6 +17,7 @@ */ package org.jitsi.jicofo.bridge.colibri +import org.jitsi.jicofo.OctoConfig import org.jitsi.jicofo.bridge.Bridge import org.jitsi.jicofo.bridge.CascadeLink import org.jitsi.jicofo.bridge.CascadeNode @@ -326,7 +327,8 @@ class Colibri2Session( private val useUniquePort = initiator private val iceControlling = initiator private val dtlsSetup = if (initiator) "active" else "passive" - private val websocketActive = initiator + private val bridgeChannelActive = initiator + private val sctpBridgeChannel = OctoConfig.config.sctpDatachannels private val logger = createChildLogger(this@Colibri2Session.logger).apply { addContext("relay", relayId) } @@ -382,10 +384,11 @@ class Colibri2Session( logger.info("Setting setup=$dtlsSetup for $relayId") it.setup = dtlsSetup } - // We always expect the bridge to advertise a websocket, but we want only one side to act as a client. + // The bridge always advertises a websocket if we're not using SCTP, but we want only one side to act as a + // client. // The bridge will always act as a client if the signaled transport includes a websocket, so here we make // sure it is only included to one of the sides. - if (!websocketActive) { + if (sctpBridgeChannel || !bridgeChannelActive) { transport.getChildExtensionsOfType(WebSocketPacketExtension::class.java).forEach { transport.removeChildExtension(it) } @@ -407,7 +410,8 @@ class Colibri2Session( put("use_unique_port", useUniquePort) put("ice_controlling", iceControlling) put("dtls_setup", dtlsSetup) - put("websocket_active", websocketActive) + put("bridge_channel_active", bridgeChannelActive) + put("sctp_bridge_channel", sctpBridgeChannel) meshId?.let { put("mesh_id", it) } } @@ -484,6 +488,11 @@ class Colibri2Session( Transport.getBuilder().apply { setUseUniquePort(useUniquePort) setIceControlling(iceControlling) + if (sctpBridgeChannel) { + val sctp = Sctp.Builder() + sctp.setRole(if (bridgeChannelActive) Sctp.Role.CLIENT else Sctp.Role.SERVER) + setSctp(sctp.build()) + } }.build() ) diff --git a/jicofo-selector/src/main/resources/reference.conf b/jicofo-selector/src/main/resources/reference.conf index 65b6c08c87..ade74e5576 100644 --- a/jicofo-selector/src/main/resources/reference.conf +++ b/jicofo-selector/src/main/resources/reference.conf @@ -320,6 +320,9 @@ jicofo { // Whether to allow bridges with different versions to be used in the same conference. Intended only for testing. allow-mixed-versions = false + + // Whether bridge-to-bridge communication should use SCTP datachannels (as opposed to websockets) + sctp-datachannels = false } rest {