分类 Ubuntu 下的文章

“Ubuntu是以桌面应用为主的Linux发行版,基于Debian。Ubuntu有三个正式版本,包括桌面版、服务器版及用于物联网设备和机器人的Core版。从17.10版本开始,Ubuntu以GNOME为默认桌面环境。 Ubuntu是著名的Linux发行版之一,也是目前最多用户的Linux版本。 ”

The file has a global header containing some global information followed by zero or more records for each captured packet, looking like this:

  • Global Header
  • Packet Header
  • Packet Data

Global Header

typedef struct pcap_hdr_s {
          guint32 magic_number;   /* magic number */
          guint16 version_major;  /* major version number */
          guint16 version_minor;  /* minor version number */
          gint32  thiszone;       /* GMT to local correction */
          guint32 sigfigs;        /* accuracy of timestamps */
          guint32 snaplen;        /* max length of captured packets, in octets */
          guint32 network;        /* data link type */
  } pcap_hdr_t;

示例:
xd4xc3xb2xa1x02x00x04x00x00x00x00x00x00x00x00x00x00x00x04x00x01x00x00x00
Record (Packet) Header

typedef struct pcaprec_hdr_s {
          guint32 ts_sec;         /* timestamp seconds */
          guint32 ts_usec;        /* timestamp microseconds */
          guint32 incl_len;       /* number of octets of packet saved in file */
          guint32 orig_len;       /* actual length of packet */
  } pcaprec_hdr_t;

Packet Data
The actual packet data will immediately follow the packet header as a data blob of incl_len bytes without a specific byte alignment.
查看tcpdump 数据

sudo tcpdump -c 1 -w test.pcap tcp

查看Global Header

hexdump -C -n 24 test.pcap 

00000000 d4 c3 b2 a1 02 00 04 00 00 00 00 00 00 00 00 00 |................|
00000010 00 00 04 00 01 00 00 00 |........|
00000018

查看Record (Packet) Header

 hexdump -C -s 24 -n 16 test.pcap 

00000018 54 f0 69 63 ab 52 0b 00 42 00 00 00 42 00 00 00 |T.ic.R..B...B...|
00000028

查看包数据Packet Data

hexdump -C -s 40 test.pcap
00000028 b8 ac 6f 3b 20 d0 38 f3 ab 09 44 1c 08 00 45 00 |..o; .8...D...E.|
00000038 00 34 3e c0 40 00 40 06 76 6b c0 a8 02 40 c0 a8 |.4>.@.@.vk...@..|
00000048 02 08 9c 08 1f 92 5e 7b f8 00 12 7f 1e 3e 80 11 |......^{.....>..|
00000058 01 f5 85 bf 00 00 01 01 08 0a 20 82 fb f2 d0 6a |.......... ....j|
00000068 41 0e |A.|
0000006a

How to Keep Alive SSH Sessions
To enable the keep alive system-wide (root access required), edit /etc/ssh/ssh_config; to set the settings for just your user, edit ~/.ssh/config (create the file if it doesn’t exist). Insert the following:

Host *
    ServerAliveInterval 300
    ServerAliveCountMax 2

You can also make your OpenSSH server keep alive all connections with clients by adding the following to /etc/ssh/sshd_config:

ClientAliveInterval 300
ClientAliveCountMax 2

Add timestamp to SSH verbose logs

ssh -v 192.168.0.151 exit 2>&1 | while read line; do printf '[%s] %s\n' "$(date '+%Y-%m-%d %H:%M:%S')" "$line"; done

Store SSH client VERBOSE logs into log file

ssh -v 192.168.0.151 exit 2>&1 | while read line; do printf '[%s] %s\n' "$(date '+%Y-%m-%d %H:%M:%S')" "$line"; done > "/tmp/ssh-debug.log"

ssh exit

How does 'ssh <destination> exit' terminate the session?

The exit executed by the remote shell would terminate that shell. In
the case when true is executed, the remote shell would terminate due
to not having any further commands to execute, but exit would
terminate it even if there were further commands afterwards (as in any
script).

In the simple case where the SSH session is only for executing a set
of commands (where it does not set up tunnels or use connection
sharing), the session would terminate when the remote shell
terminates, no matter how the remote shell terminates (either by exit
or by some error, or receiving a HUP signal, or by simply reaching the
end of the script).

Note that the manual says "[...] and all X11 and TCP connections have
been closed". This means that the connection may not terminate just
because the remote shell has terminated. This will be the case when
you, for example, are using connection sharing with ssh -M and ssh -S
(or the ControlMaster setting in ~/.ssh/config; see man ssh and man
ssh_config). I assume that SSH tunnels would also keep the SSH session
alive until they are explicitly closed.

To truly terminate the SSH connection, you may send the exit control
command using ssh -O exit user@host. This would terminate all shared
SSH sessions to user@host.

linux sshfs

SSHFS is available for most Linux distributions. On Ubuntu, you can install it using apt.

First, use apt update to refresh your package sources:

sudo apt update

Then, use apt install to install the sshfs package.

sudo apt install sshfs

Mounting the Remote Filesystem
Create a subdirectory within /mnt called droplet using the mkdir command:

sudo mkdir /mnt/droplet

You can now mount a remote directory using sshfs.

sudo sshfs -o allow_other,default_permissions sammy@your_other_server:~/ /mnt/droplet

If you no longer need this mount, you can unmount it with the umount command:

sudo umount /mnt/droplet

sshfs remote host has disconnected
修改/etc/sshd/sshd_config中的

Subsystem sftp /usr/lib/openssh/sftp-server

Subsystem sftp internal-sftp

Both sftp-server and internal-sftp are part of OpenSSH. The sftp-server is a standalone binary. The internal-sftp is just a configuration keyword that tells sshd to use the SFTP server code built-into the sshd, instead of running another process (what would typically be the sftp-server).

The internal-sftp was added much later (OpenSSH 4.9p1 in 2008?) than the standalone sftp-server binary. But it is the default by now. The sftp-server is now redundant and is kept probably for a backward compatibility.

I believe there's no reason to use the sftp-server for new installations.

tcpdump 官方说明文档
https://www.tcpdump.org/manpages/tcpdump.1.html
tcpdump 保存文件
tcpdump -i lo -w temp.pcap -C 10 -W 3
只显示除push和ack外的网络包

 tcpdump -i lo tcp port 31009 and 'tcp[tcpflags] & tcp-push==0' and 'tcp[tcpflags] & tcp-ack==0' -nnvvx

也可以使用

tcpdump -i lo tcp port 31009 and 'tcp[13] & 8 == 0' and 'tcp[13] & 16 == 0'

Show all URG packets:

tcpdump 'tcp[13] & 32 != 0'

Show all ACK packets:

tcpdump 'tcp[13] & 16 != 0'

Show all PSH packets:

tcpdump 'tcp[13] & 8 != 0'

Show all RST packets:

tcpdump 'tcp[13] & 4 != 0'

Show all SYN packets:

tcpdump 'tcp[13] & 2 != 0'

Show all FIN packets:

tcpdump 'tcp[13] & 1 != 0'

Show all SYN-ACK packets:

tcpdump 'tcp[13] = 18'

Show icmp echo request and reply

tcpdump -n icmp and 'icmp[0] != 8 and icmp[0] != 0'

Show all IP packets with a non-zero TOS field (one byte TOS field is at offset 1 in IP header):

tcpdump -v -n ip and ip[1]!=0

Show all IP packets with TTL less than some value (on byte TTL field is at offset 8 in IP header):

tcpdump -v ip and 'ip[8]<2'

Show TCP SYN packets:

tcpdump -n tcp and port 80 and 'tcp[tcpflags] & tcp-syn == tcp-syn'
tcpdump tcp and port 80 and 'tcp[tcpflags] == tcp-syn'
tcpdump -i <interface> "tcp[tcpflags] & (tcp-syn) != 0"

Show TCP ACK packets:

tcpdump -i <interface> "tcp[tcpflags] & (tcp-ack) != 0"

Show TCP SYN/ACK packets (typically, responses from servers):

tcpdump -n tcp and 'tcp[tcpflags] & (tcp-syn|tcp-ack) == (tcp-syn|tcp-ack)'
tcpdump -n tcp and 'tcp[tcpflags] & tcp-syn == tcp-syn' and 'tcp[tcpflags] & tcp-ack == tcp-ack'
tcpdump -i <interface> "tcp[tcpflags] & (tcp-syn|tcp-ack) != 0"

Show TCP FIN packets:

tcpdump -i <interface> "tcp[tcpflags] & (tcp-fin) != 0"

Show ARP Packets with MAC address

tcpdump -vv -e -nn ether proto 0x0806

Show packets of a specified length (IP packet length (16 bits) is located at offset 2 in IP header):

tcpdump -l icmp and '(ip[2:2]>50)' -w - |tcpdump -r - -v ip and '(ip[2:2]<60)'

tcpdump常用命令补充

Basic communication (very verbose) // see a good amount of traffic, with verbosity and no name help

tcpdump -nnvvS

A deeper look at the traffic // adds -X for payload but doesn’t grab any more of the packet

tcpdump -nnvvXS

Heavy packet viewing // the final “s” increases the snaplength, grabbing the whole packet

tcpdump -nnvvXSs 1514

host // look for traffic based on IP address (also works with hostname if you’re not using -n)

tcpdump host 1.2.3.4

src, dst // find traffic from only a source or destination (eliminates one side of a host conversation)

tcpdump src 2.3.4.5
tcpdump dst 3.4.5.6

net // capture an entire network using CIDR notation

tcpdump net 1.2.3.0/24

proto // works for tcp, udp, and icmp. Note that you don’t have to type proto

tcpdump icmp

port // see only traffic to or from a certain port

tcpdump port 3389

src, dst port // filter based on the source or destination port

tcpdump src port 1025 
tcpdump dst port 389

src/dst, port, protocol // combine all three

tcpdump src port 1025 and tcp
tcpdump udp and src port 53

You also have the option to filter by a range of ports instead of declaring them individually, and to only see packets that are above or below a certain size.

Port Ranges // see traffic to any port in a range

tcpdump port range 21–23

Packet Size Filter // only see packets below or above a certain size (in bytes)

tcpdump less 32
tcpdump greater 128

[ You can use the symbols for less than, greater than, and less than or equal / greater than or equal signs as well. ]

// filtering for size using symbols

tcpdump > 32
tcpdump <= 128

[ Note: Only the PSH, RST, SYN, and FIN flags are displayed in tcpdump‘s flag field output. URGs and ACKs are displayed, but they are shown elsewhere in the output rather than in the flags field ]

Keep in mind the reasons these filters work. The filters above find these various packets because tcp[13] looks at offset 13 in the TCP header, the number represents the location within the byte, and the !=0 means that the flag in question is set to 1, i.e. it’s on.

Show all URG packets:

tcpdump ‘tcp[13] & 32 != 0’

Show all ACK packets:

tcpdump ‘tcp[13] & 16 != 0’

Show all PSH packets:

tcpdump ‘tcp[13] & 8 != 0’

Show all RST packets:

tcpdump ‘tcp[13] & 4 != 0’

Show all SYN packets:

tcpdump ‘tcp[13] & 2 != 0’

Show all FIN packets:

tcpdump ‘tcp[13] & 1 != 0’

Show all SYN-ACK packets:

tcpdump ‘tcp[13] = 18’

Show icmp echo request and reply

tcpdump -n icmp and ‘icmp[0] != 8 and icmp[0] != 0’

Show all IP packets with a non-zero TOS field (one byte TOS field is at offset 1 in IP header):

tcpdump -v -n ip and ip[1]!=0

Show all IP packets with TTL less than some value (on byte TTL field is at offset 8 in IP header):

tcpdump -v ip and ‘ip[8]<2’

Show TCP SYN packets:

tcpdump -n tcp and port 80 and ‘tcp[tcpflags] & tcp-syn == tcp-syn’
tcpdump tcp and port 80 and ‘tcp[tcpflags] == tcp-syn’
tcpdump -i <interface> “tcp[tcpflags] & (tcp-syn) != 0”

Show TCP ACK packets:

tcpdump -i <interface> “tcp[tcpflags] & (tcp-ack) != 0”

Show TCP SYN/ACK packets (typically, responses from servers):

tcpdump -n tcp and ‘tcp[tcpflags] & (tcp-syn|tcp-ack) == (tcp-syn|tcp-ack)’
tcpdump -n tcp and ‘tcp[tcpflags] & tcp-syn == tcp-syn’ and ‘tcp[tcpflags] & tcp-ack == tcp-ack’
tcpdump -i <interface> “tcp[tcpflags] & (tcp-syn|tcp-ack) != 0”

Show TCP FIN packets:

tcpdump -i <interface> “tcp[tcpflags] & (tcp-fin) != 0”

Show ARP Packets with MAC address

tcpdump -vv -e -nn ether proto 0x0806

Show packets of a specified length (IP packet length (16 bits) is located at offset 2 in IP header):

tcpdump -l icmp and ‘(ip[2:2]>50)’ -w — |tcpdump -r — -v ip and ‘(ip[2:2]<60)’

apt -o Acquire::socks::proxy="socks5h://192.168.4.64:10008/" update
apt -o Acquire::http::proxy="socks5h://192.168.4.64:10008/" upgrade
apt -o Acquire::http::proxy="socks5h://192.168.4.64:10008/" install inetutils-telnet

export http_proxy="socks5://192.168.4.64:10008"
export https_proxy="socks5://192.168.4.64:10008"

unset HTTP_PROXY HTTPS_PROXY FTP_PROXY ALL_PROXY NO_PROXY

Writing an apt proxy conf file /etc/apt/apt.conf.d/proxy.conf as below.

Acquire::http::Proxy "socks5h://127.0.0.1:1080";
Acquire::https::Proxy "socks5h://127.0.0.1:1080";
Acquire::socks::Proxy "socks5h://127.0.0.1:1080";

D状态,往往是由于 I/O 资源得不到满足,而引发等待

不可中断状态,表示进程正在跟硬件交互,为了保护进程数据和硬件的一致性,系统不 允许其他进程或中断打断这个进程。进程长时间处于不可中断状态,通常表示系统有 I/O 性能问题。

僵尸进程表示进程已经退出,但它的父进程还没有回收子进程占用的资源。短暂的僵尸 状态我们通常不必理会,但进程长时间处于僵尸状态,就应该注意了,可能有应用程序 没有正常处理子进程的退出。

在内核源码 fs/proc/array.c 里,其文字定义为“ "D (disk sleep)", / 2 / ”(由此可知 D 原是Disk的打头字母),对应着 include/linux/sched.h 里的“ #define TASK_UNINTERRUPTIBLE 2 ”。举个例子,当 NFS 服务端关闭之时,若未事先 umount 相关目录,在 NFS 客户端执行 df 就会挂住整个登录会话,按 Ctrl+C 、Ctrl+Z 都无济于事。断开连接再登录,执行 ps axf 则看到刚才的 df 进程状态位已变成了 D ,kill -9 无法杀灭。正确的处理方式,是马上恢复 NFS 服务端,再度提供服务,刚才挂起的 df 进程发现了其苦苦等待的资源,便完成任务,自动消亡。若 NFS 服务端无法恢复服务,在 reboot 之前也应将 /etc/mtab 里的相关 NFS mount 项删除,以免 reboot 过程例行调用 netfs stop 时再次发生等待资源,导致系统重启过程挂起。

Linux进程状态:D (TASK_UNINTERRUPTIBLE),不可中断的睡眠状态。

与TASK_INTERRUPTIBLE状态类似,进程处于睡眠状态,但是此刻进程是不可中断的。不可中断,指的并不是CPU不响应外部硬件的中断,而是指进程不响应异步信号。
绝大多数情况下,进程处在睡眠状态时,总是应该能够响应异步信号的。否则你将惊奇的发现,kill -9竟然杀不死一个正在睡眠的进程了!于是我们也很好理解,为什么ps命令看到的进程几乎不会出现TASK_UNINTERRUPTIBLE状态,而总是TASK_INTERRUPTIBLE状态。

而TASK_UNINTERRUPTIBLE状态存在的意义就在于,内核的某些处理流程是不能被打断的。如果响应异步信号,程序的执行流程中就会被插入一段用于处理异步信号的流程(这个插入的流程可能只存在于内核态,也可能延伸到用户态),于是原有的流程就被中断了。(参见《linux内核异步中断浅析》)
在进程对某些硬件进行操作时(比如进程调用read系统调用对某个设备文件进行读操作,而read系统调用最终执行到对应设备驱动的代码,并与对应的物理设备进行交互),可能需要使用TASK_UNINTERRUPTIBLE状态对进程进行保护,以避免进程与设备交互的过程被打断,造成设备陷入不可控的状态。这种情况下的TASK_UNINTERRUPTIBLE状态总是非常短暂的,通过ps命令基本上不可能捕捉到。

当 iowait 升高时,进程很可能因为得不到硬件的响应,而长时间处于不可中断状态。从 ps 或者 top 命令的输出中,你可以发现它们都处于 D 状态,也就是不可中断状态 (Uninterruptible Sleep)。

top 和 ps 是最常用的查看进程状态的工具,我们就从 top 的输出开始。下面是一个 top 命令输出的示例,S 列(也就是 Status 列)表示进程的状态。从这个示例里,你可以看到 R、D、Z、S、I 等几个状态,它们分别是什么意思呢?

R 是 Running 或 Runnable 的缩写,表示进程在 CPU 的就绪队列中,正在运行或者正 在等待运行。

D 是 Disk Sleep 的缩写,也就是不可中断状态睡眠(Uninterruptible Sleep),一般 表示进程正在跟硬件交互,并且交互过程不允许被其他进程或中断打断。

Z 是 Zombie 的缩写,如果你玩过“植物大战僵尸”这款游戏,应该知道它的意思。它 表示僵尸进程,也就是进程实际上已经结束了,但是父进程还没有回收它的资源(比如进程的描述符、PID 等)。

S 是 Interruptible Sleep 的缩写,也就是可中断状态睡眠,表示进程因为等待某个事件 而被系统挂起。当进程等待的事件发生时,它会被唤醒并进入 R 状态。

I 是 Idle 的缩写,也就是空闲状态,用在不可中断睡眠的内核线程上。前面说了,硬件 交互导致的不可中断进程用 D 表示,但对某些内核线程来说,它们有可能实际上并没有 任何负载,用 Idle 正是为了区分这种情况。要注意,D 状态的进程会导致平均负载升 高, I 状态的进程却不会。

当然了,上面的示例并没有包括进程的所有状态。除了以上 5 个状态,进程还包括下面这 2 个状态。

第一个是 T 或者 t,也就是 Stopped 或 Traced 的缩写,表示进程处于暂停或者跟踪状态。

向一个进程发送 SIGSTOP 信号,它就会因响应这个信号变成暂停状态(Stopped);再 向它发送 SIGCONT 信号,进程又会恢复运行(如果进程是终端里直接启动的,则需要你 用 fg 命令,恢复到前台运行)。

而当你用调试器(如 gdb)调试一个进程时,在使用断点中断进程后,进程就会变成跟踪 状态,这其实也是一种特殊的暂停状态,只不过你可以用调试器来跟踪并按需要控制进程 的运行。

另一个是 X,也就是 Dead 的缩写,表示进程已经消亡,所以你不会在 top 或者 ps 命令 中看到它。