Картинка взята из телнет-видео «Звёздных войн»: telnet towel.blinkenlights.nl
Недавно был пост о том, нужны ли сетевики. До тех пор, пока проверка доступности tcp/ip порта кажется чем-то сложным даже для администраторов БД и AD, сетевики несомненно нужны. Они особенно полезны в тех случаях, когда необходимо понять почему так плохо работает некое клиент-серверное приложение ценой в пароход.
Иногда мало знать ping и traceroute для того, чтобы понять и устранить проблему в сети. Необходимо понимать как работают все звенья в цепи, а сделать это может лишь сетевик. Рассмотрим несколько таких примеров.
(1:1004)$ ncat -v -w3 -z some.server 1111
Ncat: Version 7.80 ( https://nmap.org/ncat )
Ncat: Connection refused.
(1:1005)$ ncat -v -w3 -z another.server 1521
Ncat: Version 7.80 ( https://nmap.org/ncat )
Ncat: No route to host.
Test-NetConnection -ComputerName "www.contoso.com" -Port 80
(1:1006)$ netstat -s
(1:1007)$ nstat -s
(1:1008)$ netstat -s |grep prune
873 packets pruned from receive queue because of socket buffer overrun
(1:1009)$ nstat -s |grep Prune
TcpExtPruneCalled 873 0.0
(1:1010)$ cat /proc/sys/net/ipv4/tcp_rmem
4096 16384 4194304
(1:1011)$ cat /proc/sys/net/ipv4/wcp_rmem
4096 16384 4194304
(1:1012)$ grep -e tcp_rmem -e tcp_wmem /etc/sysctl.conf
net.ipv4.tcp_rmem = 4096 87380 16777216
net.ipv4.tcp_wmem = 4096 65536 16777216
(1:1013)$ /usr/share/bcc/tools/tcpdrop
TIME PID IP SADDR:SPORT > DADDR:DPORT STATE (FLAGS)
16:31:07 3103 4 93.184.216.34:443 > 192.168.11.32:36222 ESTABLISHED (PSH|ACK)
b'tcp_drop+0x1'
b'tcp_data_queue+0x1e7'
b'tcp_rcv_established+0x1df'
b'tcp_v4_do_rcv+0x131'
b'tcp_v4_rcv+0xad3'
b'ip_protocol_deliver_rcu+0x2b'
b'ip_local_deliver_finish+0x55'
b'ip_local_deliver+0xe8'
b'ip_rcv+0xcf'
b'__netif_receive_skb_core+0x429'
b'__netif_receive_skb_list_core+0x10a'
b'netif_receive_skb_list_internal+0x1bf'
b'netif_receive_skb_list+0x26'
b'iwl_pcie_rx_handle+0x447'
b'iwl_pcie_irq_handler+0x4d5'
b'irq_thread_fn+0x20'
b'irq_thread+0xdc'
b'kthread+0x113'
b'ret_from_fork+0x35'
(1:1014)$ /usr/share/bcc/tools/tcplife -h
...
examples:
./tcplife # trace all TCP connect()s
./tcplife -T # include time column (HH:MM:SS)
./tcplife -w # wider columns (fit IPv6)
./tcplife -stT # csv output, with times & timestamps
./tcplife -p 181 # only trace PID 181
./tcplife -L 80 # only trace local port 80
./tcplife -L 80,81 # only trace local ports 80 and 81
./tcplife -D 80 # only trace remote port 80
# ./tcplife -D 80
PID COMM LADDR LPORT RADDR RPORT TX_KB RX_KB MS
27448 curl 100.66.11.247 54146 54.154.224.174 80 0 1 263.85
27450 curl 100.66.11.247 20618 54.154.164.22 80 0 1 243.62
27452 curl 100.66.11.247 11480 54.154.43.103 80 0 1 231.16
27454 curl 100.66.11.247 31382 54.154.15.7 80 0 1 249.95
bcc-tools
.getnameinfo(getaddrinfo(HOSTNAME)) = HOSTMANE
int getnameinfo(const struct sockaddr *addr, socklen_t addrlen,
char *host, socklen_t hostlen,
char *serv, socklen_t servlen, int flags);
int getaddrinfo(const char *node, const char *service,
const struct addrinfo *hints, struct addrinfo **res);
(1:1015)$ host lib.ru
lib.ru has address 81.176.66.163
...
(1:1016)$ host 81.176.66.163
163.66.176.81.in-addr.arpa domain name pointer lib.ru.
Отрицательный пример - example.com.
(1:1017)$ host example.com
example.com has address 93.184.216.34
(1:1018)$ host 93.184.216.34
Host 34.216.184.93.in-addr.arpa. not found: 3(NXDOMAIN)
(1:1019)$ strace -f -e trace=openat host my.router 2>&1 |grep -e "^openat" -e address
openat(AT_FDCWD, "/etc/ld.so.cache", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/usr/lib64/libcrypto.so.1.1", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/usr/lib64/libuv.so.1", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/lib64/libpthread.so.0", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/usr/lib64/libidn2.so.0", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/lib64/libc.so.6", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/lib64/libz.so.1", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/lib64/libdl.so.2", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/usr/lib64/libunistring.so.2", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/proc/self/task/7164/comm", O_RDWR) = 3
(1:1020)$ strace -f -e trace=openat getent ahosts my.router
openat(AT_FDCWD, "/etc/ld.so.cache", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/lib64/libc.so.6", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/usr/lib64/locale/locale-archive", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/usr/lib64/gconv/gconv-modules.cache", O_RDONLY) = 3
openat(AT_FDCWD, "/etc/nsswitch.conf", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/etc/host.conf", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/etc/resolv.conf", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/etc/ld.so.cache", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/lib64/libnss_files.so.2", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/etc/hosts", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/etc/ld.so.cache", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/usr/lib64/libidn2.so.0", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/usr/lib64/libunistring.so.2", O_RDONLY|O_CLOEXEC) = 3
openat(AT_FDCWD, "/usr/lib64/charset.alias", O_RDONLY|O_NOFOLLOW) = -1 ENOENT (No such file or directory)
192.168.10.10 STREAM my.router
192.168.10.10 DGRAM
192.168.10.10 RAW
+++ exited with 0 +++
К сожалению, не доступен сервер mySQL