versatica / mediasoup

Cutting Edge WebRTC Video Conferencing

Home Page:https://mediasoup.org

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Maybe using an useless extra ICE candidate?

piranna opened this issue · comments

(Not sure if I should ask this in the forum).

At

listenIps :
[
{ ip: '127.0.0.1', announcedIp: '9.9.9.1' },
{ ip: '0.0.0.0', announcedIp: '9.9.9.2' },
{ ip: '127.0.0.1', announcedIp: undefined }
],
the tests are providing 3 listenIPs, and later the test expect to have 6 ICE candidates: 2 for announced 9.9.9.1, 2 for announced 9.9.9.2, and 2 for IP 127.0.0.1. Thing is, that the 9.9.9.2 announced one has an IP of 0.0.0.0, it's said, the INADDR_ANY address, meaning "all addresses in the local machine". Due to that, we could be able to safely ignore any other IP after this entry and generate just only 4 ICE candidates. I don't remember the exact details I was filtering that but seems to be an optimization based on the docs (don't remember the exact place), so I'm asking, is there a bug on Mediasoup by creating more ICE candidates that needed ones, or I misunderstood something and I'm missing the point and should not remove the listenIPs after the INADDR_ANY address?

We don't care about INADDR_ANY addresses. The user passes N listen IPs and, in case UDP and TCP are enabled, num listen IPs x 2 candidates are created. The user is free to just create a listenIp with ip 0.0.0.0 and later signal N candidates with different announced IPs to the clients. But internally we want to keep things simple.

BTW listenIps will be soon deprecated once listenInfos (for now just in flatbuffers branch) is merged in v3.

We don't care about INADDR_ANY addresses. The user passes N listen IPs and, in case UDP and TCP are enabled, num listen IPs x 2 candidates are created. The user is free to just create a listenIp with ip 0.0.0.0 and later signal N candidates with different announced IPs to the clients. But internally we want to keep things simple.

Fair enough, just only that based on some spec (sorry, I really forgot where I read that, and just only have a comment about that topic on my code), once we get to the INADDR_ANY address, any subsequent listenIp will not be used because the INADDR_ANY will accept everything, so any ICE candidate generated after it will be useless and we can remove them. It can be something like this:

/**
 * Find the "all addresses in the local machine" entry
 * @param listenIp
 */
function findINADDR_ANY(listenIp)
{
  return listenIp    === '0.0.0.0' || listenIp    === '::'
      || listenIp.ip === '0.0.0.0' || listenIp.ip === '::'
}

/**
 *
 * @param listenIps
 * @param localListenIps
 */
function genListenIps(listenIps, localListenIps)
{
  const result = [...listenIps, ...localListenIps]

  // Remove all entries after the "all addresses in the local machine" entry
  const index = result.findIndex(findINADDR_ANY)
  if(index !== -1) result.length = index + 1

  return result
}

BTW listenIps will be soon deprecated once listenInfos (for now just in flatbuffers branch) is merged in v3.

Can we consider on not generating useless ICE candidates with listenInfos after they get merged? This will save resources and bandwidth...

The user may want to generate ICE candidates with different announced public (or private) IPs so we must honor those. If the user wants to just allocate a single port then he can pass a single listenIp with ip 0.0.0.0 and then construct N ICE candidates with different announced IPs as told in my previous message. We don't want to do this magic within mediasoup. The user can easily do it depending on the server network setup.

The user may want to generate ICE candidates with different announced public (or private) IPs so we must honor those. If the user wants to just allocate a single port then he can pass a single listenIp with ip 0.0.0.0 and then construct N ICE candidates with different announced IPs as told in my previous message. We don't want to do this magic within mediasoup. The user can easily do it depending on the server network setup.

So, are you saying about having several entries with INADDR_ANY (0.0.0.0), allowing connections from all the network interfaces, but using different announce IPs, for example one server with several ISPs? Interesting use case, and yes, makes sense. In that case, maybe the entries that would be useless and could be removed would be the non-INADDR_ANY after the first sequence of INADDR_ANY ones, isn't it? Would in that case makes sense to remove them (I think that by Mediasoup itself, but also by app code)?

As told above we don't want to play with networking assumptions. The user can set up the addresses he needs and do whatever in JS or Rust to bind a single socket and expose different announced IPs to devices or whatever. We don't want to inspect IP addresses and be aware of INADDR_ANY addresses, etc. This is a low level library. It's like if you ask OpenSSL authors to do the same when a user app binds twice in 0.0.0.0.