How can I control the source port of a TCP packet? - tcp

To test my implementation of a NAT, I want to send TCP packets from one internal host to two different external hosts, and make sure that the source port for both streams of packets that leave the NAT have the same source port. How can I control the source port? wget uses different source ports for separate TCP connections.

Maybe you want to try netcat with -p option, if you don't want to write code by yourself, example:
$ nc -p 31337 www.google.com 80
Here is the explanation for "-p" option from man page:
Specifies the source port nc should use, subject to privilege restrictions and availability. It is an error to use this option in conjunction with the -l option.
Note though to use any port under 1024 requires root permission.

Bind the socket to a specific local port before you connect it.

Related

Copying UDP traffic from a bound port

I have two applications that both bind to the same port to receive UDP traffic. I am able to change the listen port of one of the programs but not the other. I need both to be able to see the traffic.
I have tried using socat for this but have been unable to figure out how to get it to send a copy of the traffic to a different port without interfering with the program bound to the original port.
A few tricks come to mind, but when you are not able to change both receiving ports or the target port of the sender, you will need to use iptables to modify the port of the incoming packets. On that port Socat with sniffing (option -r) to a pipe and another Socat instance could solve your problem.

Failing to perform TCP hole punching using STUN

I have two hosts A and B. They're in different networks, behind different NATs and ISPs. I'm trying to set up a p2p connection between them by using hole punching. I use a STUN server to obtain mapped IP addresses and ports for both A and B. It goes on like this:
For A:
.\stunclient.exe --mode behavior stunserver.stunprotocol.org 3478
Binding test: success
Local address: 192.168.0.110:54709
Mapped address: 186.233.160.141:28769
Behavior test: success
Nat behavior: Endpoint Independent Mapping
For B:
.\stunclient.exe --mode behavior stunserver.stunprotocol.org 3478
Binding test: success
Local address: 192.168.3.1:57015
Mapped address: 45.70.35.52:12870
Behavior test: success
Nat behavior: Endpoint Independent Mapping
Then I try to perform the TCP hole punching technique (using netcat) by executing these two lines simultaneously and multiple times on A and B:
On A:
ncat -p 54709 45.70.35.52 12870
Ncat: TIMEOUT.
On B:
ncat -p 57015 186.233.160.141 28769
Ncat: TIMEOUT.
I always get "Ncat: Timeout" as output (not immediatelly, it takes some time), however, I could make a direct connection between A and B via UDP hole punching by running the following commands three times:
On A:
ncat -u -p 54709 45.70.35.52 12870
On B:
ncat -u -p 57015 186.233.160.141 28769
So the problem is TCP hole punching isn't working. Any ideas why?
Many issues that might be making this a challenge.
First, stunclient defaults to UDP whereas ncat defaults to TCP. So your first issue is that you aren't passing the flag (-u on most systems) to tell ncat to run as UDP. Or, you can try running stunclient in tcp mode. (e.g. stunclient --protocol tcp stunserver.stunclient.org), but TCP NAT traversal is much less reliable than UDP - especially with rudimentary command line tools )
I don't understand how your output above can have Host A and Host B behind the same NAT, yet both machines appear to have the same local IP address, using the same local port, but printing the same local ip address 192.168.3.3. How is this a thing? Is this just a typo? Or is one machine a VM host of the other and they are sharing an IP?
The behavior you are trying to achieve, having two hosts behind the same NAT connect via the public ip address is called hairpinning. This relies on the NAT to be smart enough to see that an outbound packet is really meant for a host behind the router itself and to loop it back through its own routing table instead of going out on the WAN adapter. Not all NATs support hairpinning. So what you have to do is try connecting through to both the local and remote ip addresses.
Also, try to avoid picking hardcoded ports like 20000. Let stunclient.exe pick a randomly available port for you. (i.e. don't specify --localport parameter). Then when you issue the ncat command, use the local port it picked to connect to the remote mapped port of the other ip address.
Hypothetical usage:
Host A
stunclient.exe stunserver.stunprotocol.org
Binding test: success
Local address: 192.168.1.2:1111
Mapped address: 45.70.35.52:2222
Host B
stunclient.exe stunserver.stunprotocol.org
Binding test: success
Local address: 192.168.1.3:3333
Mapped address: 45.70.35.52:4444
Address candidates passed from A to B: {45.70.35.52:2222, 192.168.1.2:1111}
Address candidates passed from B to A: {45.70.35.52:4444, 192.168.1.3:3333}
Host A then runs these command in parallel. But oops, ncat may not allow sharing the socket port between two running programs. Look at the documentation to see if the SO_REUSEADDR flag is exposed implicitly as a command line param. It may do this implicitly.
ncat -u -p 1111 45.70.35.52 4444
ncat -u -p 1111 192.168.1.3:3333
Host B then does this in two separate consoles:
ncat -u -p 3333 45.70.35.52 2222
ncat -u -p 3333 192.168.1.2:1111
In other words, try all 4 combinations of A to B and B to A.
I was about to mention making sure you don't have address dependent mapping by running the behavior test. (i.e. "symmetric NAT"). Symmetric NATs make p2p connectivity very difficult for the connection to "go direct". But you've got endpoint independent, which is good.

Verifying that a communication is happening over IPSec?

Is there a way one could test whether the communication between two hosts is happening over the IPSec protocol?
I have two different hosts running the OpenSource Peer2PeerVPN solution. And I have one host listening for messages via the net-cat tool.
nc -v -l -p 9999
And the other host connected to this via the VPN tunnel
nc -v 192.168.188.2 9999
I want to verify or check whether the communication is actually happening over the IPSec protocol. Also, I would like to see the values of the IPSec Protocol's Authentication and Encapsulation Headers.
I tried tcpdump but I'm guessing it only provides a capture on the layer above the Network level - Transport.
EDIT:
Based on a comment below I downloaded a sample pcap file to view how headers look in a IPSec communication. I see that these traces have ESP headers of the IPSec protocol.
However, when I try the same with the VPN Tool I'm using I don't see any packets with ESP header on the tcpdump. I was listening on the VPN interface (peervpn0) that the tool creates.
To check if this was a problem with the tool, I connected to a remote server to which I usually connect using VPN and sent some data via netcat to my machine from inside the remote-machine (I ssh'ed in). I listened for all packets on the VPN interface created by the Cisco VPN Tool (utun0) with filter esp
tcpdump -vvv -i utun0 esp
Still, I did not see any traces.
What am I missing here?
Should I listen on the default interface (my wifi interface) via which the VPN tunnel is created to see the ESP Headers?
Or have understood something wrong here?
Thank You
Shabir
With some further reading I was able to find out that PeerVPN does not communicate over IPSec but using encryption and sends the data as UDP payload over the underlying interface.
I also saw that many of the VPN tools indeed do this and does encrypt the tunnel interface packets and forwards them over UDP in the underlying interface. Besides some VPN solutions have a separate option to enable IPSec protocol specifically.
Thank You.

Is there a command line tool for all the incoming traffic in different protocol?

I found netcat is very useful for listening TCP connection by using -l port-number, but I'm wondering if there is a more powerful tool available to analysis all incoming protocol, like RADIUS client request, so I can check out what the request are made of and if server get the request
netstat maybe the way to go with the -c flag, but it doesn't show even tcp connection with custom port number
any idea?
Wireshark offers a command line tool as well as a GUI (http://www.wireshark.org/)
Why don't you use netstat and grep the output to filter only the ports that you need?
The output is similar to this:
Proto Recv-Q Send-Q Local Address Foreign Address (state)
tcp4 0 0 192.168.1.7.63364 64.34.119.101.80 ESTABLISHED
tcp4 0 0 192.168.1.7.63357 64.34.119.13.80 ESTABLISHED
and it is very simple to grep results by protocol, port, address and state.
Bro is a (command-line) tool that extracts a wide range of information from network traffic. It is port agnostic, e.g., can detect HTTP on non-standard ports and features a application parsers for a variety of protocols. The connection log provides a lot of useful information at flow granularity, including:
Timestamp
Connection 5-tuple (source host, source port, destination host, destination port, transport protocol)
Application-layer protocol
Duration
Transport-layer bytes sent (source and destination)
Connection status
Number of packets (source and destination)
See this answer for example output.

Monitoring multiple ports in tcpdump

I am trying to find a way to read multiple ports using tcpdump. Suppose I have two ports, p1 and p2, and I want to read the traffic moving through both ports simultaneously. Is there any way to do it using tcpdump or will I have to use some other tool?
Basically I am running a proxy server which is running on some port. I want to read the traffic moving through this port as well traffic moving through port 80(HTTP).
tcpdump port 80 or port 3128
or, alternatively,
tcpdump port '(80 or 443)'
if you want to filter ports based on the range then use portrange.
E.g:
tcpdump -an portrange 1-25
You can also select an interface (change -i any to -i en0 for example) and the communication protocol :
tcpdump -i any 'udp port 1812 or tcp port 1813'

Resources