I'm trying to set up a cost-effective home security camera site where I can login and view the stream with very low latency. WebRTC seemed like a great solution to get very low latency and keep the connection peer to peer.
I am looking to view this from a mobile device and as a client device I am often behind a symmetric NAT. Since I know the static public IP the camera is behind and control that network I believe I should be able to create a peer connection for video without the need for a turn server I am struggling to figure out how to manage the ICE portion in this case. When I try to connect with just STUN video does not work.
Given my control of the serving peer's network, should this be possible without TURN? If so is there a way for me to sidestep/implement ICE to establish video with my known server peer IP and configuration? Or is there a better technology to use altogether that would allow very low latency?
Knowing the IP address of the camera isn't going to help you any. Since you are dealing with a symmetric NAT, the NAT device is going to bind every IP:port from inside the network reaching to an IP:port in the external network.
This means that if you pin-hole the data via a STUN server, the NAT device won't be impressed enough by that feat to let you connect into the internal network from any other machine other than that STUN server.
Which leads to the fact that you'll probably need a TURN server...
That said, you might have some issues with how you've set up the STUN server and its configuration.
An easy and rather cheap approach can be to use Twilio NAT traversal service - https://www.twilio.com/stun-turn
Related
I've written a small WebRTC demo that streams a video file to the other peer and everything works fine (it's a real P2P connection without using the TURN server) except for this:
One client connects via a mobile network and one via wifi. When the mobile client creates the offer and kicks off the ICE candidate back-and-forth, they settle on srflx candidates and create a real P2P connection.
But when the wifi-client creates the offer, they fall back to the TURN server as a relay.
This happens in Firefox and Chromium on Ubuntu.
Does this behavior point to an obvious problem in my code?
If not, how can this be? Shouldn't the ICE protocol produce the same two candidates no matter which client is the controller?
NATs have two attributes influence if a connection will succeed between two WebRTC Agents. Those attributes are filtering and mapping.
When you send a packet to an address outside your NAT you create a mapping. A mapping is your IP:Port and people usually call it your Public IP. This is the Public IP that others can send into. A STUN server is just an echo server that responds with your mapping.
The first mapping type is an Address Independent NAT. This is the one you want. In this configuration you re-use a mapping everytime you contact an IP outside your NAT. You can give out your mapping to remote peers and they can send to you.
The second mapping type is Address Dependent. In this configuration you create a new mapping for each remote address. This means that the IP/Port you got back from the STUN server can NOT be used by other peers. In this case you may have to use a TURN server.
filtering controls who is allowed to send in. Some NATs allow anyone to send traffic in. Like mapping behavior this is called Address Independent. Other NATs only allow someone to send traffic in that you have attempted to contact, knows as a Address Dependent NAT.
Check out WebRTC for the Curious's Connecting Chapter I try to explain this in more depth. Pion also has a tool stun-nat-behavior that prints out the details of your NAT like so.
connecting to STUN server: stun.voip.blackberry.com:3478
=> NAT mapping behavior: endpoint independent
=> NAT filtering behavior: address and port dependent
Recently i've been choosen as backend lider for course on my studies. We are suppossed to write BE for chat app that will allow users to communicate p2p without any server code (i know it means that there's no BE, but my proffessor isn't technical person). I've asked him if it could use webrtc, but he didn't like the idea of using STUN and TURN servers. So my main question is, is this possible at all? We are talking about an app that will run in browser, not directly in OS. And if it is, what protocols/apis can we use to achieve that?
I am not sure if I get your question right, so here are some general informations:
WebRTC as a P2P API relies heavily on servers.
"ICE":
To connect one Peer to the other Peer, the peers need to know their IP address to exchange data. They can "ask" their OS for the registered IP, but this will only yield 127.0.0.1 and their local Network IP. This works for connections on the same computer or between computers in the same local network, but it will fail for everything else.
The ICE Servers STUN and TURN are necessary, since your browser clients are behind your Routers Network Address Translation (NAT). STUN gets the NATs IP Address and Port and TURN forwards Packets as a known, public IP Address if STUN fails.
"Signaling":
Let's assume, that your Peers know their own reachable IP-Addresses (- probably the NATs IP and Port by using STUN and maybe even TURN). Even IF (!) they know their reachable IP, they have to tell the other Peer that this IP is in fact, their IP and the IP to use to contact them. They also have to tell the other Peer some other technical information to make the transmission of data work. To use WebRTC, you need to have a WebSocket-Server (or a combination of Server-Sent-Events and HTTP Post Messages), which forward this information.
After everything is established (they know their respective IPs and Ports, technical information, etc.), you can then send data over WebRTCs DataChannels.
My Advice:
Do not use WebRTC for the given use case. If you do not want to use a Backend-Server, you have to search for "serverless" Web-Apps. P2P will always rely on some sort of server to start the connection. If you use a "serverless" architecture, someone else is hosting the server / chat service you want to use (also commonly referred as "cloud based"). If it is about hosting costs for a prototype app, you may have a look at heroku.com, aws.amazon.com, zeit.co, firebase.google.com or other hosting providers with free, limited (test) plans.
WebRTC signalling is driving me crazy. My use-case is quite simple: a bidirectional audio intercom between a kiosk and to a control room webapp. Both computers are on the same network. Neither has internet access, all machines have known static IPs.
Everything I read wants me to use STUN/TURN/ICE servers. The acronyms for this is endless, contributing to my migraine but if this were a standard application, I'd just open a port, tell the other client about it (I can do this via the webapp if I need to) and have the other connect.
Can I do this with WebRTC? Without running a dozen signalling servers?
For the sake of examples, how would you connect a browser running on 192.168.0.101 to one running on 192.168.0.102?
STUN/TURN is different from signaling.
STUN/TURN in WebRTC are used to gather ICE candidates. Signaling is used to transmit between these two PCs the session description (offer and answer).
You can use free STUN server (like stun.l.google.com or stun.services.mozilla.org). There are also free TURN servers, but not too many (these are resource expensive). One is numb.vigenie.ca.
Now there's no signaling server, because these are custom and can be done in many ways. Here's an article that I wrote. I ended up using Stomp now on client side and Spring on server side.
I guess you can tamper with SDP and inject the ICE candidates statically, but you'll still need to exchange SDP (and that's dinamycally generated each session) between these two PCs somehow. Even though, taking into account that the configuration will not change, I guess you can exchange it once (through the means of copy-paste :) ), stored it somewhere and use it every time.
If your end-points have static IPs then you can ignore STUN, TURN and ICE, which are just power-tools to drill holes in firewalls. Most people aren't that lucky.
Due to how WebRTC is structured, end-points do need a way to exchange call setup information (SDP) like media ports and key information ahead of time. How you get that information from A to B and back to A, is entirely up to you ("signaling server" is just a fancy word for this), but most people use something like a web socket server, the tic-tac-toe of client-initiated communication.
I think the simplest way to make this work on a private network without an internet connection is to install a basic web socket server on one of the machines.
As an example I recommend the very simple https://github.com/emannion/webrtc-web-socket which worked on my private network without an internet connection.
Follow the instructions to install the web socket server on e.g. 192.168.1.101, then have both end-points connect to 192.168.0.101:1337 with Chrome or Firefox. Share camera on both ends in the basic demo web UI, and hit Connect and you should be good to go.
If you need to do this entirely without any server, then this answer to a related question at least highlights the information you'd need to send across (in a cut'n'paste demo).
i have a problem. I've developed a web-app using WebRtc for one-to-one videocall via browser using WebRtc with signalling server on node js (listening e.g. on 8181 port).
Now i would implement MITM attack. I was thinking that, wheen Peer_1 should invoke two rtc peer connection, one for the second peer (Peer_2), one to the MITM. The same thing for the second peer.
Now, i was thinking that signalling server needs to listen on another port, for each rtc peer connection received from the two peers (e.g. 8282 for Peer_1 and 8383 for Peer_2).
Am i right? I think that because signalling server's implementation is to one-to-one communication.
In this way, signalling server on port 8181 allows end-to-end communication for Peer_1 and Peer_2, on 8282 there is the signalling path for Peer_1 and the MITM, and on 8383 for MITM and Peer_2.
Am i right or not? Thanks for the support.
Man in the middle refers to interception during transmission, which WebRTC itself is secured against using DTLS and key exchange, so the weak point is usually the signaling server chosen by an application instead.
But what you describe however sounds like Man on both ends. You have to trust the service (the server) to guarantee whom you're being connected to. If that server is compromised, or either client is compromised - say by injection - then there's no guarantee whom you're talking to, since a client can easily forward a transmission to another party.
How do you send a UDP Packet using Web RTC?
You can't send a UDP packet directly with WebRTC. That would violate the basic security constraints required by the browser.
You can send SRTP to an ICE-enabled host. That is probably not what you are looking for.
If a browser permitted sending arbitrary UDP packets, then malicious applications could send packets to any host.
This might not sound so bad, after all, hosts on the Internet need to be able to deal with that right? The problem is that some browsers are in protected environments where access to the network is restricted. Within those networks, some hosts are far less protected than a host on the public Internet might be. This would be OK, since access to the network is controlled.
If it were possible for a browser to send arbitrary packets, a user on a browser in that environment could be convinced to send specifically crafted packets to one of these poorly protected hosts. Likely, that would result in the network operator banning the browser, which is something browser-makers want very much to avoid.
WebRTC only sends certain types of UDP packet under specific conditions. If the host that you are interested in talking to understands ICE and is able to consume RTP with SRTP or SCTP over DTLS (unlikely methinks). Then perhaps you could force the browser to send something.
You should check sipml5, http://code.google.com/p/sipml5/
get the code and look into the folder:
sipml5/src/tinySIP/src/transports
#Martin Thomson has explained the problem very well. By taking
motivation from his post, this post might provide guidance to some
geeks and newbies.
It is being said that WebRtc is Real-time, Bi-directional, Secure communication between two or more peers. I will more focus on the word: Secure.
Security policies of enterprise networks typically require filtering of incoming unsolicited traffic, blocking certain protocols, and doing application-level filtering and scanning for spam, malware, and intellectual property.
Now two new questions come to mind;
Why is TCP traversal not problematic?
Why is UDP traversal problematic?
Why is TCP traversal not problematic?
TCP clearly indicates two things;
The beginning of a flow (SYN) and,
The end of a flow (FIN or RST).
This is used by firewalls to open and close pinholes. Exceptionally, a TCP connection that has received no traffic for a long time also has its pinhole closed (to accommodate network topology changes or failure of both TCP peers). Firewalls also perform protocol validation to clean up problems with
Out-of-window TCP segments and,
Overlapping TCP segments
This allows the firewall to protect the network and protect hosts from
several attack vectors (replay attacks, host IP address probing, DDOS
attack, etc.).
Why is UDP traversal problematic?
For UDP flows, the first outgoing packet on a 5-tuple will be used by the firewall as a start-of-session indicator. But UDP does not have an end-of-session indicator, so the firewall has only two ways to close a pinhole:
Timing out the pinhole after the interior host does not send traffic
for several seconds or
The interior host generates a fatal ICMP error.
Because there is no reliable way to determine that a session is being stopped, the firewall has a much harder job. It could implement an Application-level Gateway (ALG) and be aware of whatever semantics are imposed by the higher-level code on top of UDP.
It could also rely on a set of well-known application servers to inform it of sessions as they start and end, but that suffers from many challenges as application servers are hosted independently of the network on which they are used.
Using an ALG, a firewall can determine when the call is terminated and
close any dynamic mappings created for the media session. But the
problem is session signaling between the WebRTC application running in
the browser and the Web server that could be using TLS, in which case
the ALG no longer has access to the signaling.
Conclusion:
So, at the Application-Level Gateway, Webrtc utilizes a combination of SDP and ICE. WebRtc basically wraps UDP in such a way that
For Audio, Video Channels, WebRtc uses combinations of RTP, RTCP, SRTP over DTLS.
For Data Channels, webrtc uses the Stream Control Transmission Protocol (SCTP), defined in RFC 2960.
SCTP is a transport layer protocol that was intended as an alternative
to TCP or UDP. For WebRtc, we use it as an application layer
protocol that runs over our DTLS connection.
These protocols also come with some new protocols such as STUN, TURN. For the basic implementations of WebRtc Please follow;
WebRtc Experiments by Mauz Khan
WebRtc Experiments by Muhammad Usman Bashir
I hope this explanation might help some of the geeks. Thanks