linux page size is 4096 bytes
MTU:最大传输单元,以太网的MTU为1500Bytes
MSS:最大分解大小,为每次TCP数据包每次传输的最大数据的分段大小,由发送端通知接收端,发送大于MTU就会被分片。
MSS默认最小为536B,最小的MTU576B,MSS = MTU - IP头(20B)- TCP头(20B)
MSL,即Maximum Segment Lifetime,一个数据分片(报文)在网络中能够生存的最长时间
TTL是 time to live的缩写,中文可以译为“生存时间”,这个生存时间是由源主机设置初始值但不是存的具体时间
RTT是客户到服务器往返所花时间(round-trip time,简称RTT),TCP含有动态估算RTT的算法
查看默认的MSL值(60s):
cat /proc/sys/net/ipv4/tcp_fin_timeout
TCP粘包是指发送方发送的若干包数据到接收方接收时粘成一包,从接收缓冲区看,后一包数据的头紧接着前一包数据的尾。
(1)发送方原因
我们知道,TCP默认会使用Nagle算法。而Nagle算法主要做两件事:1)只有上一个分组得到确认,才会发送下一个分组;2)收集多个小分组,在一个确认到来时一起发送。
所以,正是Nagle算法造成了发送方有可能造成粘包现象。
(2)接收方原因
TCP接收到分组时,并不会立刻送至应用层处理,或者说,应用层并不一定会立即处理;实际上,TCP将收到的分组保存至接收缓存里,然后应用程序主动从缓存里读收到的分组。这样一来,如果TCP接收分组的速度大于应用程序读分组的速度,多个包就会被存至缓存,应用程序读时,就会读到多个首尾相接粘到一起的包。
(1)如果发送方发送的多个分组本来就是同一个数据的不同部分,比如一个很大的文件被分成多个分组发送,这时,当然不需要处理粘包的现象;
(2)但如果多个分组本毫不相干,甚至是并列的关系,我们就一定要处理粘包问题了。比如,我当时要接收的每个分组都是一个有固定格式的商品信息,如果不处理粘包问题,每个读进来的分组我只会处理最前边的那个商品,后边的就会被丢弃。这显然不是我要的结果。
(1)发送方
对于发送方造成的粘包现象,我们可以通过关闭Nagle算法来解决,使用TCP_NODELAY选项来关闭Nagle算法。
(2)接收方
遗憾的是TCP并没有处理接收方粘包现象的机制,我们只能在应用层进行处理。
(3)应用层处理
应用层的处理简单易行!并且不仅可以解决接收方造成的粘包问题,还能解决发送方造成的粘包问题。
解决方法就是循环处理:应用程序在处理从缓存读来的分组时,读完一条数据时,就应该循环读下一条数据,直到所有的数据都被处理;但是如何判断每条数据的长度呢?
主要有三种策略,其利弊也有简单说明:
(1)发送固定长度的消息
我们首先假设总长度 1000,如果我发送一个”hi”,长度不足 1000, 其他地方补全即可。但是会浪费资源,同时不能传输长度超过 1000 的报文。
(2)使用特殊标记来区分消息间隔
回车换行符就是一种特殊的结束分隔符
这种方法虽然解决了长度固定的问题,但是有分隔符被使用了怎么办的问题。当然了你的系统如果不存在"#@!"三个字符转化为字节的这样的顺序,那么你就可以使用这些字节作为分隔符。但是像微信就不可以用这种方式,因为用户可能什么都会发,万一发送了个跟"#@!"字节一样的消息,就会发生混乱。
(3)把消息的尺寸与消息一块发送
这个就是最常规和正常的方式。dubbo 等协议都是基于这些的,因为 dubbo 也是基于 netty 来实现底层通讯的,所以速度可能会比 spring 等速度好点。
举个简单的实现例子,我们把报文的前 4 个字节永远固定,就是一个长整数,用来声明这条报文的总长度,后面的字节当成 body。每次一方接收到报文,取出前 4 个字节进行解码,得知总长度,然后进行这个包的处理就可以了。
如果把前面的 4 个字节,扩展到 16 字节,那就是 dubbo 协议的长度了。
Netty 中的解决方案:
netty 中的 decode 和 encode 已经有了很多接口,想个性化自己实现可以,也可以直接采用他们提供的。
FixedLengthFrameDecoder。主要对应上一节中的策略 1,使用很简单。
DelimiterBasedFrameDecoder。主要对应上一节中的策略 2,可以自定义输入自己的分隔符。
编写自己的协议的话,主要就是约定好报头就好啦。可以参考 dubbo 的协议。
简单说来,page cache用来缓存文件数据,buffer cache用来缓存磁盘数据。在有文件系统的情况下,对文件操作,那么数据会缓存到page cache,如果直接采用dd等工具对磁盘进行读写,那么数据会缓存到buffer cache。
开源实现:cachingbe
常用操作 https://linuxtools-rst.readthedocs.io/zh_CN/latest/index.html
命令手册 https://wangchujiang.com/linux-command/c/sed.html
cat /etc/centos-release
uname -a
cat /proc/version
lsb_release -a
hostnamectl
cat /proc/cpuinfo| grep "cpu cores"| uniq
cat /proc/cpuinfo| grep "processor"| wc -l
time curl -v "http://uat-apollometa:10080" -o /dev/null
“rpm -ql 包名”来查看具体的安装路径
Ctrl+f:向文件尾翻一屏
Ctrl+b;向文件首翻一屏
b或B :光标左移一个字至字首
e或E :光标右移一个字至字尾
:s/p1/p2/g:将当前行中所有p1均用p2替代
:set number
:set nonumber
grep -rn redis -9
# -r 递归
# -n 显示行号
# -9 显示查找下面9行
more +3223947 tcp.log
/ - 使用一个模式进行搜索,并定位到下一个匹配的文本
/ - 使用一个模式进行搜索,并定位到下一个匹配的文本
n - 向前查找下一个匹配的文本
N - 向后查找前一个匹配的文本
unlink 软连接
ln -sfn dev_20190522131339 latest
rm latest
du -ah --max-depth=1
rz -bye,并且去掉弹出的对话框中“Upload files as ASCII”前的勾选。
/etc/resolv.conf
ab -n 100 -c 10 http://test.com/
ab -n 100 -H “Cookie: Key1=Value1; Key2=Value2” http://test.com/
移到行道有两个,0 和 ^ (shift+6),在行首第一个字符是空白字符时有点区别。
移到行尾是 $ (shift+4)
到结尾是G
到开头是gg
复制yy
yum install java-1.8.0-openjdk-devel.x86_64
yum install locate
updatedb
grep -a
less -f -r
strings file|grep 'abc'
解压到指定目录
tar -xvf a.gz -C ./dir
Ctrl + 左右键:在单词之间跳转
Ctrl + A:跳到本行的行首
Ctrl + E:跳到页尾
Ctrl + U:删除当前光标前面的所有文字(还有剪切功能)
Ctrl + K:删除当前光标后面的所有文字(还有剪切功能)
Ctrl + L:进行清屏操作
Ctrl + Y:粘贴Ctrl + U或Ctrl + K剪切的内容
Ctrl + W和Alt + D:对于当前的单词进行删除操作,W删除光标前面的单词的字符,D则删除后面的字符
Alt + Backsapce:删除当前光标后面的单词
[root@localhost ~]# strings /lib64/libc.so.6 |grep GLIBC_
[root@localhost ~]# rpm -qa |grep glibc
如下升级glibc版本到2.17做法
# wget http://ftp.gnu.org/gnu/glibc/glibc-2.17.tar.gz
# tar -xvf glibc-2.17.tar.gz
# cd glibc-2.17
# mkdir build; cd build
# ../configure --prefix=/usr --disable-profile --enable-add-ons --with-headers=/usr/include --with-binutils=/usr/bin
# make -j 8
# make install
查看版本,发现已升级到2.17版本
# ldd --version
# strings /lib64/libc.so.6 |grep GLIBC_
supervisorctl stop ssserver
ssserver -c /etc/shadowsocks.json -d start
supervisorctl restart kcptun
./shell-scripts/kcptun/kcptun.sh log
/Users/jonny/Downloads/kcptun-darwin-amd64-20190109/client_darwin_amd64 -c config.json
鲸鱼加速器
SetupVpn
谷歌访问助手
* tcp检查
nc -z -w2 10.244.0.8 31389
* udp检查
nc -u 127.0.0.1 7777
nc -ul -p 7777
查看端口:
netstat –apn
lsof -i:port
连接状态列表:
netstat -n | awk '/^tcp/ {++S[$NF]} END {for(a in S) print a, S[a]}'
杀进程:
kill -9 processId
pidstat -u -p 7249
pidstat -r -p 7249 1
pidstat -d -p 7249 1 2
- curl --connect-timeout 2 -i http://install.ren
- wget http://install.ren
netstat -nltp
netstat -tunpl | grep 端口号
netstat –anp | grep 8080 或者 名称
lsof -i tcp:port
netstat -nat | grep -iw "8989" | wc -l
netstat -anp | grep ESTABLISHED | wc -l
当服务器维持30000个socket连接时,使用netstat和ss命令统计连接数的耗时情况如下:
[root@wang ~]# netstat -at | wc -l //耗时15.60秒
[root@wang ~]# ss -atr | wc -l //耗时5.40秒(未利用tcp_diag)
ss -a 查看机器的socket连接数
ss -l 查看机器的端口情况
ss -s 查看机器的网络连接数
tcpdump -s0
tcpdump -i eth0 dst host 172.20.49.153 -A -s0
tcpdump -i eth0 dst host 10.69.10.27 and port 10080 and 'ip[2:2] > 10240' -A
更多:https://www.cnblogs.com/ggjucheng/archive/2012/01/14/2322659.html
sudo cat /proc/sys/fs/file-nr
lsof -p 20262 |wc -l
[root@master1] ~$ lsof -n |awk '{print $10}'|sort |uniq -c |sort -nr|head -10
可以用下面的命令将 cpu 占用率高的线程找出来:
ps H -eo user,pid,ppid,tid,time,%cpu,cmd --sort=%cpu
cat /proc/cpuinfo
物理CPU个数: cat /proc/cpuinfo |grep "physical id"|sort |uniq|wc -l
每个CPU物理核数: cat /proc/cpuinfo |grep "cpu cores"|uniq
每个CPU逻辑核数: cat /proc/cpuinfo |grep "siblings"|uniq
总CPU逻辑核数: cat /proc/cpuinfo |grep -c "processor"
我的服务器是两个芯片组,每个芯片组是10核,支持超线程,所以逻辑CPU是40。
超线程指物理内核+逻辑内核,芯片上只存在一个物理内核,但是这个物理内核可以模拟出一个逻辑内核,于是系统信息就显示了两个内核,一真一假。
free -h
pidstat -u -p 7249
pidstat -r -p 7249 1
pidstat -d -p 7249 1 2
使用pidstat进行问题定位时,以下命令常被用到:
pidstat -u 1
pidstat -r 1
pidstat -d 1
以上命令以1秒为信息采集周期,分别获取cpu、内存和磁盘IO的统计信息。
sync
To free pagecache:
echo 1 > /proc/sys/vm/drop_caches
To free dentries and inodes:
echo 2 > /proc/sys/vm/drop_caches
To free pagecache, dentries and inodes:
echo 3 > /proc/sys/vm/drop_caches
vmstat - 内存,进程和分页等的简要信息。
iostat - CPU统计信息,设备和分区的输入/输出统计信息。
strace -o output.txt -T -tt -e trace=all -p 28979
上面的含义是 跟踪28979进程的所有系统调用(-e trace=all),并统计系统调用的花费时间,以及开始时间(并以可视化的时分秒格式显示),最后将记录结果存在output.txt文件里面。
iostat属于sysstat软件包。可以直接安装。
yum install sysstat
https://www.cnblogs.com/ftl1012/p/iostat.html
yum install epel-release
yum update
yum install iperf
1.在需要测试的电脑上,以服务器模式启动iperf
iperf -s
2.在第二台电脑上,以客户端模式启动iperf连接到第一台电脑,替换198.51.100.5为地台电脑的ip地址
iperf -c 198.51.100.5
3.这时可以在第一步中的服务端终端看到连接和结果,类似下图
Server listening on TCP port 5001
TCP window size: 85.3 KByte (default)
------------------------------------------------------------
[ 4] local 198.51.100.5 port 5001 connected with 198.51.100.6 port 50616
[ ID] Interval Transfer Bandwidth
[ 4] 0.0-10.1 sec 1.27 GBytes 1.08 Gbits/sec
HTTP协议头里面加上connection:keep-alive当然能解决这个问题。
还有的方法就是系统参数调优:
sysctl net.ipv4.tcp_tw_reuse=1
sysctl net.ipv4.tcp_tw_recycle=1
sysctl net.ipv4.tcp_timestamps=1
tcp_tw_reuse
这个参数作用是当新的连接进来的时候,可以复用处于TIME_WAIT的socket。默认值是0。
tcp_tw_recycle和tcp_timestamps
默认TIME_WAIT的超时时间是2倍的MSL,但是MSL一般会设置的非常长。如果tcp_timestamps是关闭的,开启tcp_tw_recycle是没用的。但是一般情况下tcp_timestamps是默认开启的,所以直接开启就有用了。
for i in {1..1000}
do
curl --location --request GET 'http://fat-bff-admin.d.cn/general/bffApiDebug' --data-raw '{"platformCode":"Android"}'
done