C++ windows32 winsock UDP routing? - c++

In C++ using Windows32 using windows socket library using UDP is there a way to give a client routing information to another client to establish a connection between clients without having to route through the server
Clarification:
server - waits for computers and gives routing info - a detached server
client - sends a ack request and waits for routing info - a normal user computer
but ok so its not posible to give routing info to clients to interconnect clients without requiring the data to be forwarded through the server?

Short answer: no.
Long answer: No matter what information you include in your UDP packet, at the transport layer it's just another IP packet, and your NIC will slap the appropriate headers on it and send it on its way. Unless the hosts are directly connected to each other, the network topology will dictate how many hops (routers/switches) it has to make to get there.
Addendum:
I'm not sure what you mean by server (I read it as "router" initially, but you could just as easily have been talking about a Domain Name Server (DNS)). If you are trying to avoid DNS lookup, you can easily do this by providing an IP address directly (assuming you know it). However, DNS lookup is a one-time process--once the IP address is known, the DNS host is not involved in routing your UDP packets in any way.

Short answer: no
Long answer: yes --- but you have to use IPPROTO_IP, not IPPROTO_UDP. Use IP_OPTIONS option in setsockopt() to set source routing.

Related

Uniquely Identify UDP Connection - Multiple Connections from same IP

I'll start by saying that currently my server identifies based on sender IP, that is the IP of the client.
Now I am programming a game server (just for practice) and this got me thinking how do I uniquely identify a client if they are on the same IP. (Two players open a connection on the same machine / same network so the outward IP is the same).
I've searched for an answer both on google and here and gamedev.net but am unable to find what I am looking for, likely because I do not know the correct terms to query for.
Any guidance on this would be appreciated, especially in regards to efficiency and best practice.
Thanks.
There is no "connection" term in all stuff related to UDP, but it is common that an application that initiates a UDP socket maintains the same source port over the time, so you could identify it by source IP-port.
There is some stuff related to maintain communication between a client inside a NAT router (in NAT-UDP the client is the first host that send a UDP datagram to another host and trigger a new connection tracking entry) and a server.
This "connection tracking" is only for allow traffic from outside to inside, making a "temporal" relationship (with a timeout), that probably will not be used anymore (only once) sometimes.
If the server doesn't use the same destination port in outcoming datagram as source port in incoming one, the router won't send the datagram to the host inside NAT.
Best regards.

C++ sockets: communication between PCs over internet

I'm writing a program on Windows using winsocks that can send messages to another computer. The client connects with the server in the other computer and begin exchanging data.
It works fine on my local network using local addresses(192.168.1.*), but I can't communicate with public addresses (216.185.45.129); not even my own. I can successfully connect to a website on port 80, but not to my laptop at home using its public IP address, regardless of what ports I use (unreserved ports).
So I did research online and the only solution that seems to work is port forwarding.
-But is there absolutely no other way to achieve this?
-How do other programs like Teamviewer connect to other computers on the network then?
-Is there an already open but typically unused port that I can use?
-At the very least, can I forward the ports on my router but not have the client do anything? Or maybe have my program forward the ports automatically.
The main problem is, that every router is using NAT to distinguish different computer in your lokal network against the WAN. He need to do this, because you got only one IP in the internet, but several devices in your home. To archive this, he uses groups of ports. That means, if you use to send maybe from port 2048 to a webserver in internet with two devices, the router gives one device another port (like 2049). The response has the Port of the requester, so the router can map it back. Unfortunately most router always map ports so you never now which port you have from the internet side.
There are two common ways to work around and archive your goal.
Port Fowarding
You can force most router not to map special ports but bind them to unique MAC addresses. You can use UPNP to config most router to do that, but I do not recommend that for security reasons and also it does not work in many enviroments where Router do not allow UPNP manipulation.
Most router have port forwarding abilities for gaming reasons (mostly it is used in P2P networks)
It works with TCP and UDP.
NAT Traversal
The common way is NAT traversal, also known as NAT hole punching. I will describe it in short for UDP. You can find a wiki explanation here for TCP and for UDP here. Unfortunately you need a server in the internet both clients can reach. Here the steps:
Both clients contact the server. The server now know IP and PORT of both clients.
Server send back the information to the clients.
Both(!) clients send now packages to each other on the known address.
It is necessary that both client send a UDP package and have to accept that the first package get lost. The reason is the router. Most router only accept packages from a source on a mapped PORT if a client has send a package to that source before.
UPDATE
Regarding to a comment of Remy Lebau I changed the Firewall piercing part to NAT Traversal as it was partly wrong.

0MQ - get message ip

First, I want to give thanks for that amazing lib! I love it. A client is connecting himself to a server. The server should save the IP and do stuff with it later on (I really need the IP). I found that answer: http://lists.zeromq.org/pipermail/zeromq-dev/2010-September/006381.html but I don't understand how I get the IP out of the message (a XREP)... I think I am only able to read the ID, but the IP is managed internally by 0MQ. His second solution suggests to send the IP as part of the message, but I don't understand how to get the "public"-IP. I found that post: Get TCP address information in ZeroMQ
is pass bind a service to an ephemeral port, get a full connection endpoint ("tcp://ipaddress:port")
I don't get how this works. Does he mean something like a web-service?
In my opinion, it would be best to get the IP out of 0MQ (it has the IP already). I would even adjust 0MQ for that, if somebody could point to the place where the IP is saved, couldn't find it. The socket types are not that important, at the moment. I would prefer smth REQ-REP like. Thank you!
Summary:
TL;DR answer to your question is: you can't get IP address of the peer that sent a message, using ZeroMQ API.
Explanation:
ZeroMQ does not expose peer IP address because it is irrelevant for the message based communication that ZeroMQ is designed for. When it is possible for ZeroMQ to get IP address of client that is connecting to server (in example using method described here), it is useless. For a longer explanation here is how it works inside ZeroMQ and any other server implementation.
Server side of the connection does not handle connected clients by the means of the hashtable that maps IP to client, but by keeping track of connected "sockets" (socket descriptors) - when a server accepts (using accept()) a connection, it receives from operating system socket descriptor to use to communicate with connected peer. All server has to do is keep that descriptor around to read() from and write() to that client. Another client that connects to server receives another socket descriptor.
To summarize: even if ZeroMQ would be able to provide you with IP of connected peer, you should not depend on it. ZeroMQ hides from you connection management so you can focus on messaging. Connection management includes reconnections, which may result in a change of IP without changing the actual ZeroMQ socket connected on the other side.
So here's an example of why you might want to get the ip address a message was delivered from: we have a server whose job it is to synchronize updates onto occasionally-connected clients (think mobile devices here, though this is an extreme example of a mobile deivce.)
When the mobile unit comes onto the network, it sends a list of it's firmware files to the server via a dealer-router connection. The server has a list of all applicable firmware files; if the client needs an update it will initiate an update via a separate mechanism.
Since the IPs for the devices can (and do) change, we need to know the IP address associated with the mobile device FOR THIS CONNECTION, i.e. right now.
Yes, we absolutely can have the client send it's IP address in the message, but that's a waste of another n bytes of valuable satellite air time, and while not pure evil, is sure annoying. Zmq already has this information, if it didn't have it, it wouldn't be able to generate replies. The address is in the socket data, there's no reason the message couldn't (optionally, for all you guys who use wired networks and think disconnects are the exception) include a reference to the socket structure so you can get the address out of it. Other than pedantic religiosity, which is far too common in zmq.
The way ZeroMQ is designed there's no information provided on the remote IP. As far as I know you have to manage this through your application by sending that information as a message of some sort.
The messages themselves use an IP-agnostic ID which has more to do with the instance of ZeroMQ running than any particular interface. This is because there may be more than one transport method and interface connecting the two instances.

TCP three way handshake fails

I have a C++ application which accepts TCP connections and then reads the traffic sent to it. It has worked very well until I moved it to a new machine. It seems like winsock never accepts the inbound tcp connection. In my code it never returns from the select statement. I can see using netstat/tcpview that the application is listening on port 14005.
I can connect to this port if I just telnet in locally. However, when someone tries to connect in via an outside IP address the TCP 3 way handshake never finishes. I can see the inbound SYN packet in wireshark. It is going to the correct port, 14005. However my system never sends the SYN-ACK back. This is just something that winsock is suppose to handle right? The machine does have multiple NIC cards, but I'm binding with INADDR_ANY so this shouldn't matter. Is there some way I can dig deeper to see why this handshake never takes place?
per ways to dig deeper: nothing more than wireshark / tshark (which you already use, however if you want to play with packets, look at scapy)
what happens if you reduce headache - only use one nic and network, put the client on the same network (ie, no router or smart switch between), (last resort) disable unneeded network services.

UDP hole Punching

I've got some questions regarding hole punching with UDP. Based on the wiki http://en.wikipedia.org/wiki/UDP_hole_punching
1) To set up a UDP session between two parties (the client which is behind NAT, server which is non-NAT) does the client simply have to send a packet to the server and then the session is allowed both ways (send & receieve) through the firewall? Meaning the client can receive too from the server.
2) UDP Hole punching: Two clients first conenct to the server, then the server gives a client port / ip on to other clients, so the clients send packets to each other on those ports. Is this coorrect?
3) if #2 is true, Why would firewalls allow data to be received from another IP than the one used in making the connection on that very port? Sounds like a big security hole that should easly be filtered? I understand that source IP spoofing would trick it, but this?
Thanks in advance,
Johan
1) Yes, with most reasonable firewalls, unless you configure it in extremely paranoid mode.
2) Not exactly. This article explains it in more detail, but the idea is that one of the clients first sends a datagram to the other's public IP. Then this datagram is discarded, but the other client knows that it was sent because the first one told it through the server. Then the other client sends a datagram back to the first one to the same port from which the first datagram originated. Since NAT at the first client remembers that there was a packet from that port, it considers the incoming datagram to be a reply to the first one. The problem here is to figure out which public port NAT will choose to send the first datagram, but most NATs do it in a predictable way so it almost always works fine, sometimes just not from the first try.
1) Yes. However, you don't need hole punching if you're contacting a non-NATted server. Your client application just behaves normally.
2) Yes.
3) Some NATs do indeed restrict a public port to just one sender-receiver pair. If you need to hole-punch in such a scenario, your only chance is to guess the public port the NAT will choose for the direct connection.
However, NAT is not a security feature. Therefore, accepting any packets to the public port is not a security hole as there is no difference to the simple case of a client directly connected to the internet.