Bash script average of iperf result - linux

I'm running iperf multiple times via the following command
iperf -c 1.1.1.1 -t 60 -w 6400 -f m >> iperf.log
sometimes with different arguments. The resulting iperf.log may look like this:
[ 3] local 2.2.2.2 port 51129 connected with 1.1.1.1 port 5001
[ ID] Interval Transfer Bandwidth
[ 3] 0.0-20.0 sec 1869 MBytes 784 Mbits/sec
[ 3] local 2.2.2.2 port 51130 connected with 1.1.1.1 port 5001
[ ID] Interval Transfer Bandwidth
[ 3] 0.0-15.0 sec 1445 MBytes 808 Mbits/sec
what i'd like to able to do is once it completed to have the average transfer rate outputted ie
average ....... XXX Mbits/sec

awk is the way to go, you can try something like this:
iperf -c 1.1.1.1 -t 60 -w 6400 -f m|awk -F 'MBytes' {'print $2'} >> iperf.log
You just need to remove the empty lines now, that I will leave to you. :)

Do you need to start and stop it? You might just want to use interval reporting (-i ) You can set i to 15 and set -t to samples desired * 15.

Related

iperf 2 hangs with multiple udp streams

When I run iperf UDP test with multiple threads, it simply hangs. It never returns. But the same test always successfully completes with single stream. Here is my iperf version and details:
$ iperf --v
iperf version 2.0.5 (08 Jul 2010) pthreads
The client (10.20.32.50) command: $ iperf -c 10.20.32.52 -P 2 -t 10 -u -b 1g
The server (10.20.32.52) command: $ iperf -s -u
The client gives following output and never finishes
$ iperf -c 10.20.32.52 -P 2 -t 10 -u -b 1g
------------------------------------------------------------
Client connecting to 10.20.32.52, UDP port 5001
Sending 1470 byte datagrams
UDP buffer size: 208 KByte (default)
------------------------------------------------------------
[ 4] local 10.20.32.50 port 33635 connected with 10.20.32.52 port 5001
[ 3] local 10.20.32.50 port 56336 connected with 10.20.32.52 port 5001
[ ID] Interval Transfer Bandwidth
[ 4] 0.0-10.0 sec 483 MBytes 406 Mbits/sec
[ 4] Sent 344820 datagrams
[ 4] Server Report:
[ 4] 0.0-696.8 sec 483 MBytes 5.82 Mbits/sec 0.020 ms 229/344819 (0.066%)
[ 4] 0.0-696.8 sec 478 datagrams received out-of-order
The server output is following
$ iperf -s -u
------------------------------------------------------------
Server listening on UDP port 5001
Receiving 1470 byte datagrams
UDP buffer size: 208 KByte (default)
------------------------------------------------------------
[ 12] local 10.20.32.52 port 5001 connected with 10.20.32.50 port 60971
[ 10] local 10.20.32.52 port 5001 connected with 10.20.32.50 port 34388
[ 10] 0.0-823.4 sec 483 MBytes 4.92 Mbits/sec 0.018 ms 420/344819 (0.12%)
[ 10] 0.0-823.4 sec 365 datagrams received out-of-order
My both client/server machines are 32 cores with 10 Gbps. Note that client runs fine with the single thread/stream, i.e., $ iperf -c 10.20.32.52 -P 1 -t 10 -u -b 1g always completes. Any help is appreciated!
This question was originally asked as a response to similar question [1], but with iperf3. I made a separate question after receiving suggestions to do so.
Nodir
[1] https://stackoverflow.com/questions/31836985/iperf3-parallel-udp-not-running/32728777

Multipath TCP : Multiple connections Not Showing

I installed the mptcp kernel on my machine. I tried to test MPTCP by running iperf -c multipath-tcp.org (both end-ponts are MPTCP CAPABLE).
I tried to test if iperf lists the subflows created. I have an active wifi interface + active wired interface. But still iperf showed only the one with the wired interface:
Client connecting to multipath-tcp.org, TCP port 5001
TCP window size: 45.0 KByte (default)
------------------------------------------------------------
[ 3] local 192.168.42.123 port 52983 connected with 130.104.230.45 port 5001
[ ID] Interval Transfer Bandwidth
[ 3] 0.0-22.7 sec 384 KBytes 139 Kbits/sec
THis shouldn't be the case. My wired link was too slow so, even if the flow would have started here, surely subflow would be there in the wifi interface as well.
How could I actually see that MPTCP is in fact creating subflows ?
I saw the question here but my cat proc... file is showing
sl loc_tok rem_tok v6 local_address remote_address st ns tx_queue rx_queue inode
0: B491F32C CDF952DC 0 0B2BA8C0:8E9C 2DE66882:1389 01 02 00000000:00000000 203077
which doesn't relate to any subflows I guess.
Maybe you can check the mptcp setting with sysctl net.mptcp,the path manager should be setted to fullmesh rather than default to establish multiple flows.
sysctl -w net.mptcp.mptcp_path_manager=fullmesh
sysctl -w net.mptcp.mptcp_enabled=1
Further explanation of mptcp setting can be viewed at http://multipath-tcp.org/pmwiki.php/Users/ConfigureMPTCP

Does iperf have a bandwidth ceiling?

I am trying to run iperf and have a throughput of 1Gig. I'm using UDP so I expect the overhead to pretty much be minimal. Still, I see it capped at 600M despite my attempts.
I have been running:
iperf -c 172.31.1.1 -u -b 500M -l 1100
iperf -c 172.31.1.1 -u -b 1000M -l 1100
iperf -c 172.31.1.1 -u -b 1500M -l 1100
Yet Anything above 600 it seems to hit a limit of about 600. For example, the output for 1000M is:
[ 3] Server Report:
[ 3] 0.0-10.0 sec 716 MBytes 601 Mbits/sec 0.002 ms 6544/689154 (0.95%)
[ 3] 0.0-10.0 sec 1 datagrams received out-of-order
I'm running this on a server with a 10Gig port and even sending it right back to itself, so there should be no interface bottlenecks.
Unsure if I am running up against an iperf limit or if there is another way to get a true 1Gig test.

Linux - ping all devices in a file to check accessibility

I have a file with about 500 devices which I need to ping to check if they're currently accessible or not from various subnets around my network. It's essentially a basic test to check for routing/accessibility issue.
Not sure where to start really. I have a basic file in which I have put each individual IP in a file line-by-line.
For example, the file looks like this:
192.168.1.1
192.168.1.2
192.168.1.3
192.168.1.4
I'd need it to return something like the following, if the third in line didn't get a reply:
192.168.1.1 Accessible
192.168.1.2 Accessible
192.168.1.3 Inaccessible
192.168.1.4 Accessible
I'm running Ubuntu here. Apologies for not having any idea where to start !
Cheers
Steve.
You should use nmap in ping scan mode with:
nmap -sn -oG - -v -iL hosts_to_scan.txt
This will try to ping all hosts contained in the hosts_to_scan.txt file.
By the way, you can also specifify a subnet, if that is the case:
nmap -sn -oG - -v 192.168.1.0/24
And/or save the result to file:
nmap -sn -oG status.txt -v 192.168.1.0/24
nmap -sn -oG status.txt -v -iL hosts_to_scan.txt
I would use nmap probably for a long list, but if you are in a command line and need a quick one-liner, this will do also:
$ for i in `cat file.txt `;do ping -c 1 $i;done
PING 8.8.8.8 (8.8.8.8): 56 data bytes
64 bytes from 8.8.8.8: icmp_seq=0 ttl=50 time=16.271 ms
--- 8.8.8.8 ping statistics ---
1 packets transmitted, 1 packets received, 0.0% packet loss
round-trip min/avg/max/stddev = 16.271/16.271/16.271/0.000 ms
PING 8.8.4.4 (8.8.4.4): 56 data bytes
64 bytes from 8.8.4.4: icmp_seq=0 ttl=50 time=16.030 ms
--- 8.8.4.4 ping statistics ---
1 packets transmitted, 1 packets received, 0.0% packet loss
round-trip min/avg/max/stddev = 16.030/16.030/16.030/0.000 ms
On a positive note, this method it's quick and easy to remember. Works (probably) with all major shells (bash, zsh, *sh?).
On the other hand it's fairly verbose and you don't want that in say 200 IP's, even 10 might be hard to monitor.
I would write a script in ruby, or pytho or whatever language you like if nmap can't cut it.
EDIT: This one is cleaner and also has some additional stats:
for i in `cat file.txt `;do ping -c 1 $i|grep 64;done
64 bytes from 8.8.8.8: icmp_seq=0 ttl=50 time=15.397 ms
64 bytes from 8.8.4.4: icmp_seq=0 ttl=50 time=13.170 ms
There's virtually nothing that can't be done with gnu-tools.
Basic schema would be to ping each one of the servers and print the result.
If you store the IPs in a ips.txt file, you could do:
while read my_ip
do
test_ping $my_ip
done < ips.txt
And then create a function such as test_ping, that pings once to each IP:
test_ping () {
if ping -c 1 $1 &> /dev/null
then
echo "$1 Accessible"
else
echo "$1 Inaccessible"
fi
}

Efficiently test if a port is open on Linux?

From a bash script how can I quickly find out whether a port 445 is open/listening on a server.
I have tried a couple of options, but I want something quick:
1. lsof -i :445 (Takes seconds)
2. netstat -an |grep 445 |grep LISTEN (Takes seconds)
3. telnet (it doesn't return)
4. nmap, netcat are not available on the server
It will be nice to know of a way that doesn't enumerate first and greps after that.
A surprise I found out recently is that Bash natively supports tcp connections as file descriptors. To use:
exec 6<>/dev/tcp/ip.addr.of.server/445
echo -e "GET / HTTP/1.0\n" >&6
cat <&6
I'm using 6 as the file descriptor because 0,1,2 are stdin, stdout, and stderr. 5 is sometimes used by Bash for child processes, so 3,4,6,7,8, and 9 should be safe.
As per the comment below, to test for listening on a local server in a script:
exec 6<>/dev/tcp/127.0.0.1/445 || echo "No one is listening!"
exec 6>&- # close output connection
exec 6<&- # close input connection
To determine if someone is listening, attempt to connect by loopback. If it fails, then the port is closed or we aren't allowed access. Afterwards, close the connection.
Modify this for your use case, such as sending an email, exiting the script on failure, or starting the required service.
There's a very short with "fast answer" here : How to test if remote TCP port is opened from Shell script?
nc -z <host> <port>; echo $?
I use it with 127.0.0.1 as "remote" address.
this returns "0" if the port is open and "1" if the port is closed
e.g.
nc -z 127.0.0.1 80; echo $?
-z Specifies that nc should just scan for listening daemons,
without sending any data to them. It is an error to use this option
in conjunc-
tion with the -l option.
You can use netstat this way for much faster results:
On Linux:
netstat -lnt | awk '$6 == "LISTEN" && $4 ~ /\.445$/'
On Mac:
netstat -anp tcp | awk '$6 == "LISTEN" && $4 ~ /\.445$/'
This will output a list of processes listening on the port (445 in this example) or it will output nothing if the port is free.
You can use netcat for this.
nc ip port < /dev/null
connects to the server and directly closes the connection again. If netcat is not able to connect, it returns a non-zero exit code. The exit code is stored in the variable $?. As an example,
nc ip port < /dev/null; echo $?
will return 0 if and only if netcat could successfully connect to the port.
Based on Spencer Rathbun's answer, using bash:
true &>/dev/null </dev/tcp/127.0.0.1/$PORT && echo open || echo closed
they're listed in /proc/net/tcp.
it's the second column, after the ":", in hex:
> cat /proc/net/tcp
sl local_address rem_address st tx_queue rx_queue tr tm->when retrnsmt uid timeout inode
0: 00000000:0016 00000000:0000 0A 00000000:00000000 00:00000000 00000000 0 0 10863 1 ffff88020c785400 99 0 0 10 -1
1: 0100007F:0277 00000000:0000 0A 00000000:00000000 00:00000000 00000000 0 0 7983 1 ffff88020eb7b3c0 99 0 0 10 -1
2: 0500010A:948F 0900010A:2328 01 00000000:00000000 02:00000576 00000000 1000 0 10562454 2 ffff88010040f7c0 22 3 30 5 3
3: 0500010A:E077 5F2F7D4A:0050 01 00000000:00000000 02:00000176 00000000 1000 0 10701021 2 ffff880100474080 41 3 22 10 -1
4: 0500010A:8773 16EC97D1:0050 01 00000000:00000000 02:00000BDC 00000000 1000 0 10700849 2 ffff880104335440 57 3 18 10 -1
5: 0500010A:8772 16EC97D1:0050 01 00000000:00000000 02:00000BF5 00000000 1000 0 10698952 2 ffff88010040e440 46 3 0 10 -1
6: 0500010A:DD2C 0900010A:0016 01 00000000:00000000 02:0006E764 00000000 1000 0 9562907 2 ffff880104334740 22 3 30 5 4
7: 0500010A:AAA4 6A717D4A:0050 08 00000000:00000001 02:00000929 00000000 1000 0 10696677 2 ffff880106cc77c0 45 3 0 10 -1
so i guess one of those :50 in the third column must be stackoverflow :o)
look in man 5 proc for more details. and picking that apart with sed etc is left as an exercise for the gentle reader...
ss -tl4 '( sport = :22 )'
2ms is quick enough ?
Add the colon and this works on Linux
nc -l 8000
Where 8000 is the port number. If the port is free, it will start a server that you can close easily. If it isn't it will throw an error:
nc: Address already in use
Here's one that works for both Mac and Linux:
netstat -aln | awk '$6 == "LISTEN" && $4 ~ "[\\.\:]445$"'
I wanted to check if a port is open on one of our linux test servers.
I was able to do that by trying to connect with telnet from my dev machine to the test server. On you dev machine try to run:
$ telnet test2.host.com 8080
Trying 05.066.137.184...
Connected to test2.host.com
In this example I want to check if port 8080 is open on host test2.host.com
You can use netcat command as well
[location of netcat]/netcat -zv [ip] [port]
or
nc -zv [ip] [port]
-z – sets nc to simply scan for listening daemons, without actually sending any data to them.
-v – enables verbose mode.
tcping is a great tool with a very low overhead.It also has a timeout argument to make it quicker:
[root#centos_f831dfb3 ~]# tcping 10.86.151.175 22 -t 1
10.86.151.175 port 22 open.
[root#centos_f831dfb3 ~]# tcping 10.86.150.194 22 -t 1
10.86.150.194 port 22 user timeout.
[root#centos_f831dfb3 ~]# tcping 1.1.1.1 22 -t 1
1.1.1.1 port 22 closed.
nmap is the right tool.
Simply use nmap example.com -p 80
You can use it from local or remote server.
It also helps you identify if a firewall is blocking the access.
If you're using iptables try:
iptables -nL
or
iptables -nL | grep 445

Resources