10
votes

Just noticed that on Chrome only, RTCIceCandidate no longer returns an IP, but rather an obfuscated address.

RTCIceCandidate 
address: "a5b3ef18-2e66-4e24-91d2-893b93bbc1c1.local"
candidate: "candidate:169888242 1 udp 2113937151 a5b3ef18-2e66-4e24-91d2-893b93bbc1c1.local 47871 typ host generation 0 ufrag 7dHv network-cost 999"
component: "rtp"
foundation: "169888242"
port: 47871
priority: 2113937151
protocol: "udp"
relatedAddress: null
relatedPort: null
sdpMLineIndex: 0
sdpMid: "0"
tcpType: ""
type: "host"
usernameFragment: "7dHv"

Notice the first property of RTCIceCanadate is "address", and "ip" is no longer part of this object.

The following code determines the local IP address of a browser. Still works on MOZ.

function discover()
{
    try{
        //Get Local IP
        window.RTCPeerConnection = window.RTCPeerConnection || window.mozRTCPeerConnection || window.webkitRTCPeerConnection;   //compatibility for firefox and chrome

        if (pc)
            pc.close();

        pc = new RTCPeerConnection({iceServers:[]});   
        pc.onicecandidate = onIceCandidate;   
        pc.createDataChannel("");   
        pc.createOffer(pc.setLocalDescription.bind(pc), noop);   

    } catch (e)
    { console.log(e.message);}
}

function noop()
{
}

function onIceCandidate(ice)
{   
    console.log(ice.candidate);

    if(!ice || !ice.candidate || !ice.candidate.candidate)  return;

    var my_ip = /([0-9]{1,3}(\.[0-9]{1,3}){3}|[a-f0-9]{1,4}(:[a-f0-9]{1,4}){7})/.exec(ice.candidate.candidate)[1];

    this.onicecandidate = noop;

    ip = my_ip.split(".")[0]+'.'+my_ip.split(".")[1]+'.'+my_ip.split(".")[2];
}

Is WebRTC officially now a fractured standard? MOZ still lists "ip" as a member of RTCIceCandidate, with no mention of the "address" member that Chrome returns.

Is there a way to de-obfusucate the mDNS address back to an ip address without forcing users to mess around with browser settings they don't uderstand?

4
This has been changed back in beta, but the production version of Chrome still has fractured WebRTC. The Chrome-WebRTC bug forum already has complaints from intranet service providers about this. Services as basic as network printing are now broken.Dominic Cerisano
Thanks for raising this point.M.Hefny
Also noticed Google is discontinuing its own network printing service "Google Cloud Print", which relies on discovering local printer IPs.Dominic Cerisano
Firefox now also shows the obfuscated address.Alen Siljak

4 Answers

7
votes

Chrome is not broken, the WebRTC standard is evolving to prevent sites from collecting local addresses by diverting the WebRTC API. If you used this hack to obtain local addresses, you might need to find another approach.

Here are the corresponding issues for Chromium and Firefox, and the current IETF draft for WebRTC mDNS candidates.

4
votes

The ip field got renamed to address in the W3C webrtc specification at some point since these days the field can contain either an IP address or a mdns hostname. What you are seeing is part of the rollout of the WebRTC host candidate obfuscation which is described ħere which is happening in Chrome 75. You can not decode this mdns hostname in the browser.

If you have a legitimate use-case you might want to ask for it to be considered in that mailing list thread.

3
votes

You can disable this feature in Chrome goto chrome:://flags and disable "Anonymize local IPs exposed by WebRTC" enter image description here

0
votes

I noticed that this was happening, only returning an mDNS address (for more information about the obfuscation, read this great article completely explaining what happened).

However, I did find a new repository that seems to "fix" this (working, but not exposing the private ip, only the public). It can be found here, and the example can be found here.