网络包排错指南-类linux 平台

背景信息

最近一直在测试k8s,如果你了解或者解接触过docker,那你一定知道docker 相关的网络很大部分在桥接、路由、Iptables 上做文章。如果你凑巧接触过k8s,并且了解其后面的原理,那你一定知道kube-proxy 把iptables 玩的简直要飞起来。当然你可能会想到一些排错工具,比如我之前常用的抓包工具,或者路由跟踪工具,但这些工具在目前这样复杂的环境下,是不太趁手的,特别是包在本机的多个网卡或者虚拟网卡里转来转去,还有很多个iptables策略,路由等让包在内核空间中转来转去。抓包工具抓不到这些信息,traceroute 跟踪路由时你会发现你需要跟踪一个src,dst 还有port的包的路由信息是没有法达成的。

这里介绍一些新的排错工具:

  • IPTables 跟踪排错
  • 本地路由 排错
  • 一些网络相关的内核参数设置。

Iptables 跟踪排错

说到Iptables 排错,我不得不拿出这张逻辑非常清晰的图出来,建议Iptables 排错时常常对照下这张图,看下数据包的传递路径。在我之前的IPtables 知识范畴里,我以为它多个表之间传递时是没有路由选择这个操作的,结果实际的排错加上这样图来看。原来在不同的table 之间可能经过Routing decision.

请参考我的这篇K8s Issue 中的排错过程。

然后我不得不说下Iptables 的TRACE Target,没有了解到这个Target之前,我用LOG Target,结果发现要写好多个IPtables你也不一定能跟踪的全每个包经过的策略,以及策略如何处理的。

我目前演示的在ubuntu 上面:

######### 检查是TRACE相关的mod 是否载入
modprobe nf_log_ipv4########## TRACE Target 只能应用于RAW Tablesudo iptables -t raw -I PREROUTING -p tcp -m tcp --dport 8081   -j TRACE
sudo iptables -t raw -I OUTPUT -p tcp -m tcp --dport 8081   -j TRACE########### grep TRACE in /var/log/kern.loggrep TRACE /var/log/kern.logubuntu@ceph3:~$ grep TRACE /var/log/kern.log|grep 2213090174
May  8 16:30:29 ceph3 kernel: [324781.838361] TRACE: raw:OUTPUT:policy:2 IN= OUT=enp3s0 SRC=192.168.235.13 DST=10.43.206.251 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=57266 DF PROTO=TCP SPT=18130 DPT=8081 SEQ=2213090174 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04D5CCCC0000000001030307) UID=1000 GID=1000
May  8 16:30:29 ceph3 kernel: [324781.838389] TRACE: nat:OUTPUT:rule:1 IN= OUT=enp3s0 SRC=192.168.235.13 DST=10.43.206.251 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=57266 DF PROTO=TCP SPT=18130 DPT=8081 SEQ=2213090174 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04D5CCCC0000000001030307) UID=1000 GID=1000
May  8 16:30:29 ceph3 kernel: [324781.838417] TRACE: nat:KUBE-SERVICES:rule:9 IN= OUT=enp3s0 SRC=192.168.235.13 DST=10.43.206.251 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=57266 DF PROTO=TCP SPT=18130 DPT=8081 SEQ=2213090174 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04D5CCCC0000000001030307) UID=1000 GID=1000
May  8 16:30:29 ceph3 kernel: [324781.838439] TRACE: nat:KUBE-SVC-ZP4VKUJYTBCROZYY:rule:1 IN= OUT=enp3s0 SRC=192.168.235.13 DST=10.43.206.251 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=57266 DF PROTO=TCP SPT=18130 DPT=8081 SEQ=2213090174 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04D5CCCC0000000001030307) UID=1000 GID=1000
May  8 16:30:29 ceph3 kernel: [324781.838454] TRACE: nat:KUBE-SEP-OR6JECCPPINGGGRC:rule:2 IN= OUT=enp3s0 SRC=192.168.235.13 DST=10.43.206.251 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=57266 DF PROTO=TCP SPT=18130 DPT=8081 SEQ=2213090174 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04D5CCCC0000000001030307) UID=1000 GID=1000
May  8 16:30:29 ceph3 kernel: [324781.838479] TRACE: filter:OUTPUT:rule:1 IN= OUT=enp3s0 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=57266 DF PROTO=TCP SPT=18130 DPT=8081 SEQ=2213090174 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04D5CCCC0000000001030307) UID=1000 GID=1000
May  8 16:30:29 ceph3 kernel: [324781.838493] TRACE: filter:KUBE-SERVICES:return:2 IN= OUT=enp3s0 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=57266 DF PROTO=TCP SPT=18130 DPT=8081 SEQ=2213090174 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04D5CCCC0000000001030307) UID=1000 GID=1000
May  8 16:30:29 ceph3 kernel: [324781.838505] TRACE: filter:OUTPUT:rule:2 IN= OUT=enp3s0 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=57266 DF PROTO=TCP SPT=18130 DPT=8081 SEQ=2213090174 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04D5CCCC0000000001030307) UID=1000 GID=1000
May  8 16:30:29 ceph3 kernel: [324781.838518] TRACE: filter:KUBE-FIREWALL:return:2 IN= OUT=enp3s0 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=57266 DF PROTO=TCP SPT=18130 DPT=8081 SEQ=2213090174 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04D5CCCC0000000001030307) UID=1000 GID=1000
May  8 16:30:29 ceph3 kernel: [324781.838531] TRACE: filter:OUTPUT:rule:4 IN= OUT=enp3s0 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=57266 DF PROTO=TCP SPT=18130 DPT=8081 SEQ=2213090174 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04D5CCCC0000000001030307) UID=1000 GID=1000
May  8 16:30:29 ceph3 kernel: [324781.838551] TRACE: filter:OUTPUT:policy:6 IN= OUT=enp3s0 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=57266 DF PROTO=TCP SPT=18130 DPT=8081 SEQ=2213090174 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04D5CCCC0000000001030307) UID=1000 GID=1000
May  8 16:30:29 ceph3 kernel: [324781.838564] TRACE: nat:POSTROUTING:rule:1 IN= OUT=enp5s0 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=57266 DF PROTO=TCP SPT=18130 DPT=8081 SEQ=2213090174 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04D5CCCC0000000001030307) UID=1000 GID=1000
May  8 16:30:29 ceph3 kernel: [324781.838577] TRACE: nat:KUBE-POSTROUTING:return:2 IN= OUT=enp5s0 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=57266 DF PROTO=TCP SPT=18130 DPT=8081 SEQ=2213090174 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04D5CCCC0000000001030307) UID=1000 GID=1000
May  8 16:30:29 ceph3 kernel: [324781.838589] TRACE: nat:POSTROUTING:rule:8 IN= OUT=enp5s0 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=57266 DF PROTO=TCP SPT=18130 DPT=8081 SEQ=2213090174 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04D5CCCC0000000001030307) UID=1000 GID=1000
May  8 16:30:29 ceph3 kernel: [324781.838609] TRACE: nat:POSTROUTING:policy:10 IN= OUT=enp5s0 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=57266 DF PROTO=TCP SPT=18130 DPT=8081 SEQ=2213090174 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04D5CCCC0000000001030307) UID=1000 GID=1000

解释一下,每个trace 会记录表名字比如raw:OUTPUT:policy:2或者nat:OUTPUT:rule:1,表明为Table:Chain:显式策略为Rule,Table默认策略为Policy:rule 编号。我一般用grep ID=57266 这种方法去过滤同一个包。

以上都抓取的iptables 的日志,如果中间遇到路由问题呢,比如我这个问题包日志如下,包到了nat:PREROUTING:policy:3 就没有下文了,本来应该继续进mangle:INPUT 或者filter:INPUT,结果都没有,参考以上数据包图,可以发现这里有个route decision的过程。那么接下来我看看如果排除本地路由的问题。

ubuntu@ceph2:~$ grep TRACE /var/log/kern.log|grep 1726587944
May  8 15:51:07 ceph2 kernel: [309854.514762] TRACE: raw:PREROUTING:policy:2 IN=enp5s0 OUT= MAC=00:23:7d:5b:96:ec:00:21:5a:ef:39:fe:08:00 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=28265 DF PROTO=TCP SPT=14024 DPT=8081 SEQ=1726587944 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04CCCA410000000001030307)
May  8 15:51:07 ceph2 kernel: [309854.514799] TRACE: nat:PREROUTING:rule:1 IN=enp5s0 OUT= MAC=00:23:7d:5b:96:ec:00:21:5a:ef:39:fe:08:00 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=28265 DF PROTO=TCP SPT=14024 DPT=8081 SEQ=1726587944 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04CCCA410000000001030307)
May  8 15:51:07 ceph2 kernel: [309854.514841] TRACE: nat:KUBE-SERVICES:rule:13 IN=enp5s0 OUT= MAC=00:23:7d:5b:96:ec:00:21:5a:ef:39:fe:08:00 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=28265 DF PROTO=TCP SPT=14024 DPT=8081 SEQ=1726587944 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04CCCA410000000001030307)
May  8 15:51:07 ceph2 kernel: [309854.514861] TRACE: nat:KUBE-NODEPORTS:return:1 IN=enp5s0 OUT= MAC=00:23:7d:5b:96:ec:00:21:5a:ef:39:fe:08:00 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=28265 DF PROTO=TCP SPT=14024 DPT=8081 SEQ=1726587944 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04CCCA410000000001030307)
May  8 15:51:07 ceph2 kernel: [309854.514881] TRACE: nat:KUBE-SERVICES:return:14 IN=enp5s0 OUT= MAC=00:23:7d:5b:96:ec:00:21:5a:ef:39:fe:08:00 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=28265 DF PROTO=TCP SPT=14024 DPT=8081 SEQ=1726587944 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04CCCA410000000001030307)
May  8 15:51:07 ceph2 kernel: [309854.514897] TRACE: nat:PREROUTING:rule:2 IN=enp5s0 OUT= MAC=00:23:7d:5b:96:ec:00:21:5a:ef:39:fe:08:00 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=28265 DF PROTO=TCP SPT=14024 DPT=8081 SEQ=1726587944 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04CCCA410000000001030307)
May  8 15:51:07 ceph2 kernel: [309854.514914] TRACE: nat:DOCKER:return:2 IN=enp5s0 OUT= MAC=00:23:7d:5b:96:ec:00:21:5a:ef:39:fe:08:00 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=28265 DF PROTO=TCP SPT=14024 DPT=8081 SEQ=1726587944 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04CCCA410000000001030307)
May  8 15:51:07 ceph2 kernel: [309854.514930] TRACE: nat:PREROUTING:policy:3 IN=enp5s0 OUT= MAC=00:23:7d:5b:96:ec:00:21:5a:ef:39:fe:08:00 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=28265 DF PROTO=TCP SPT=14024 DPT=8081 SEQ=1726587944 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04CCCA410000000001030307)

本地路由 排错

一般情况下本地路由并没有多少条,所以一般传统方法是逐条对下路由条目,然后人工判断最终会丢到那里,如果没有发现路由能处理,就会被DROP了。新版本的linux 上用ip rule 和ip route 显示和操作路由表,ip 属于iproute2 包中的套件,后面大致看了下文档,才发现有种还有这种操作的的感觉。

######## ip rule to list ip route tables
ubuntu@ceph2:~$ ip rule
0:      from all lookup local
32766:  from all lookup main
32767:  from all lookup default######## 这里有三个table ,先查0编号的local,然后查32766的main,然后查32767的default
######## 列出每个table 中的rule
ubuntu@ceph2:~$ ip route list table local
broadcast 10.0.1.0 dev enp5s0  proto kernel  scope link  src 10.0.1.12
local 10.0.1.12 dev enp5s0  proto kernel  scope host  src 10.0.1.12
broadcast 10.0.1.255 dev enp5s0  proto kernel  scope link  src 10.0.1.12
local 10.42.2.0 dev flannel.1  proto kernel  scope host  src 10.42.2.0
broadcast 10.42.2.0 dev cni0  proto kernel  scope link  src 10.42.2.1
local 10.42.2.1 dev cni0  proto kernel  scope host  src 10.42.2.1
broadcast 10.42.2.255 dev cni0  proto kernel  scope link  src 10.42.2.1
broadcast 127.0.0.0 dev lo  proto kernel  scope link  src 127.0.0.1
local 127.0.0.0/8 dev lo  proto kernel  scope host  src 127.0.0.1
local 127.0.0.1 dev lo  proto kernel  scope host  src 127.0.0.1
broadcast 127.255.255.255 dev lo  proto kernel  scope link  src 127.0.0.1
broadcast 172.17.0.0 dev docker0  proto kernel  scope link  src 172.17.0.1 linkdown
local 172.17.0.1 dev docker0  proto kernel  scope host  src 172.17.0.1
broadcast 172.17.255.255 dev docker0  proto kernel  scope link  src 172.17.0.1 linkdown
broadcast 192.168.235.0 dev enp3s0  proto kernel  scope link  src 192.168.235.12
local 192.168.235.12 dev enp3s0  proto kernel  scope host  src 192.168.235.12
broadcast 192.168.235.255 dev enp3s0  proto kernel  scope link  src 192.168.235.12ubuntu@ceph2:~$ ip route list table main
default via 192.168.235.2 dev enp3s0 onlink
10.0.1.0/24 dev enp5s0  proto kernel  scope link  src 10.0.1.12
10.42.0.0/24 via 10.42.0.0 dev flannel.1 onlink
10.42.1.0/24 via 10.42.1.0 dev flannel.1 onlink
10.42.2.0/24 dev cni0  proto kernel  scope link  src 10.42.2.1
10.42.3.0/24 via 10.42.3.0 dev flannel.1 onlink
10.42.4.0/24 via 10.42.4.0 dev flannel.1 onlink
172.17.0.0/16 dev docker0  proto kernel  scope link  src 172.17.0.1 linkdown
192.168.235.0/24 dev enp3s0  proto kernel  scope link  src 192.168.235.12ubuntu@ceph2:~$ ip route list table default
ubuntu@ceph2:~$

前面说了一般方法是逐条对路由来看路由条目对特定的包是否有规则对应,但这种方法需要你对路由规则非常熟悉,而且人工容易判断漏。那么这里介绍一个测试路由规则的命令ip route get

###### 偷懒摘抄下man 8 ip 里的说明
ip route get - get a single routethis command gets a single route to a destination and prints its contents exactly as the kernel sees it.to ADDRESS (default) #the destination address.
from ADDRESS #the source address.
tos TOS
dsfield TOS # TOS=the Type Of Service.
iif NAME #the device from which this packet is expected to arrive.
oif NAME #force the output device on which this packet will be routed.

以上面iptables 跟踪部分的这条日志为例

May  8 15:51:07 ceph2 kernel: [309854.514930] TRACE: nat:PREROUTING:policy:3 IN=enp5s0 OUT= MAC=00:23:7d:5b:96:ec:00:21:5a:ef:39:fe:08:00 SRC=192.168.235.13 DST=10.0.1.12 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=28265 DF PROTO=TCP SPT=14024 DPT=8081 SEQ=1726587944 ACK=0 WINDOW=29200 RES=0x00 SYN URGP=0 OPT (020405B40402080A04CCCA410000000001030307)

假设我们要判断这个包的路由选择会匹配哪条路由,我们可以下面命令来看,初一看结果会第一反应是不是我命令语法有问题报错呢?来看看我当时参考了rp_filter_kernel_setting后的运行结果

ubuntu@ceph2:~$ ip route get from 192.168.235.13 to 10.0.1.12 iif enp5s0 tos 0x00
RTNETLINK answers: Invalid cross-device link######### change rp_filter kernel setting
ubuntu@ceph2:~$ sudo bash
root@ceph2:~# echo 2 > /proc/sys/net/ipv4/conf/default/rp_filter
root@ceph2:~# echo 2 > /proc/sys/net/ipv4/conf/all/rp_filter######### Ok 在更改rp_filter 内核参数后,我们的同样的命令有匹配结果了。root@ceph2:~# ip route get from 192.168.235.13 to 10.0.1.12 iif enp5s0 tos 0x00
local 10.0.1.12 from 192.168.235.13 dev locache <local>  iif enp5s0
root@ceph2:~#

到这里我想你可以再尝试一些其他的ip route get 命令来连连手,看看输出结果,比如

ubuntu@ceph2:~$ ip route get from 172.18.0.3 to 10.0.1.12
RTNETLINK answers: Invalid argument # 本机根本没法从172.18.0.3 路由到10.0.1.12
ubuntu@ceph2:~$ ip route get from 192.168.235.3 to 10.0.1.12
RTNETLINK answers: Invalid argument # 本机也没法从192.168.235.3 路由到10.0.1.12
ubuntu@ceph2:~$ ip route get from 192.168.235.12 to 10.0.1.12 #从本地的一个卡为192.168.235.12 可以从lo 上路由到10.0.1.12
local 10.0.1.12 from 192.168.235.12 dev locache <local>
ubuntu@ceph2:~$ ip route get from 192.168.235.12 to 10.0.1.13 #从本地的一个卡为192.168.235.12 可以从enp5s0 上路由到10.0.1.13(另外一个主机)
10.0.1.13 from 192.168.235.12 dev enp5s0cache

最后我们详细解读下路由规则的显示意思,具体可以参考【iproute2 doc】

以这条比较长的broadcast 10.0.1.0 dev enp5s0 proto kernel scope link src 10.0.1.12为例

  • broadcast 10.0.1.0 第一个为路由类型,可以为broadcast,unicast,local等等,如果不写,则为unicast,10.0.1.0 为目的网络。
  • dev enp5s0 这代表出去的时候走网卡enp5s0
  • via 10.42.3.0 你可能在有些规则中看到这句,代表下一跳网关是10.42.3.0
  • proto kernel 路由协议是kernel,由kernel 生成。
  • scope link 该地址只在该link 上有效
  • src 10.0.1.12 源Ip为10.0.1.12, 这里的10.0.1.12 必须在本地的网卡地址上能找到
  • onlink 假装下一跳的网关在这个link上 。

一些网络相关的内核参数设置

OK,快到最后不得不提下linux 的内核参数设置,这些参数能在内核中可以设置,往往是提炼了又提炼的精华部分。那么问题来了?

  • Q : 我怎么知道哪些参数是我需要的呢?

    A : linux的内核文档中会对这些参数加以详细描述,因此我们可以阅读内核文档,比如和IP相关的参数,来寻找我们可能需要的参数,我的思路是通过自己觉得有可能的内核参数名去搜索互联网,然后看结果中别人使用这个参数具体解决了什么问题。

  • Q: 那里找到linux 内核文档?

    A: 以ubuntu 为例,linux-doc 是当前kernel的文档包,安装后的文件在/usr/share/doc/linux-doc/主目录下,可以 dpkg -L linux-doc查看寻找所需文档。比如zcat /usr/share/doc/linux-doc/networking/ip-sysctl.txt.gz可以阅读网络相关内核参数的文档。

几个重要的内核参数

  • rp_filter 设置为2时会针对所有网卡匹配包的src,如果匹配则路由,设置为1时,如果包经过的网卡发现返回路径不是最优,则丢弃包。

    net.ipv4.conf.default.rp_filter = 2

    net.ipv4.conf.all.rp_filter=2

  • log_martians Boolean 设置为enable 时,上面这种被内核认为是不可能的地址的时候,可以在内核日志中记录信息。

其他补充

  • 跨主机时,抓包工具是补充。
  • 知识需要扩散、深挖,欢迎补充。

转载于:https://blog.51cto.com/yoke88/2114923

网络包排错指南-类linux 平台相关推荐

  1. Linux网络包接收过程的监控与调优

    Linux内核对网络包的接收过程大致可以分为接收到RingBuffer.硬中断处理.ksoftirqd软中断处理几个过程.其中在ksoftirqd软中断处理中,把数据包从RingBuffer中摘下来, ...

  2. linux 开发设计软件,在Linux平台下开发和设计聊天软件

    在网络无所不在的今天,在Internet上,有ICQ.MSN.Gtalk.OICQ等网络聊天软件,极大程度上方便了处于在世界各地的友人之间的相互联系,也使世界好像一下子缩小了,不管你在哪里,只要你上了 ...

  3. RK3399平台开发系列讲解(网络篇)7.11、图解Linux网络包接收过程

    文章目录 一.Linux网络收包概况 二.Linux启动:网络接收准备工作 2.1 创建ksoftirqd内核进程 2.2 网络子系统初始化 2.3 协议栈注册 2.4 网卡驱动初始化 2.5 启动网 ...

  4. Linux下使用Java调用Hikvision设备网络SDK使用指南

    1 简介  由于在开发过程中,本来以为抓图项目会部署在Windows服务器上,但随着项目的进行发现项目需要部署在Linux系统,甚至是国产化平台银河麒麟上,但在部署时发现在国产化平台部署时出现缺包的问 ...

  5. Linux平台:Alexa语音服务快速入门指南

    原文地址 译者:远方的自由 转载请注明出处: http://blog.csdn.net/z2066411585 概述 用于C++的AVS设备SDK为Alexa语音服务提供了一个现代化的C++(11或更 ...

  6. Linux网络协议栈:网络包接收过程

    目录 一 Linux网络收包总览 二 Linux启动 2.1 创建ksoftirqd内核线程 2.2 网络子系统初始化 2.3 协议栈注册 2.4 网卡驱动初始化 2.5 启动网卡 三 迎接数据的到来 ...

  7. 《Linux/UNIX OpenLDAP实战指南》——2.3 Linux平台安装

    本节书摘来自异步社区<Linux/UNIX OpenLDAP实战指南>一书中的第2章,第2.3节,作者:郭大勇著,更多章节内容可以访问云栖社区"异步社区"公众号查看 2 ...

  8. Linux平台网络配置-----C语言

    上一期我们已经介绍了VM虚拟机安装CentOS 7系统的步骤过程,这次就来看看使用Linux对初学者有什么障碍? 零基础学习C语言---Linux平台配置网络 用VM虚拟机启动Linux系统时出现的问 ...

  9. Linux平台开发技术指南

    以下技术和工具是Linux平台下工作的基础,熟练掌握: C++ 工作语言,重要性不言而喻: 入门: <C++ Primer>http://book.douban.com/subject/1 ...

最新文章

  1. 图算法在斗鱼反作弊中的实践
  2. 由SELECT *引发的多个生产故障,问题藏太深了吧……
  3. python安装位置是固定的吗_pip指定python位置安装软件包的方法
  4. 大唐联仪推出下一代移动通信测试解决方案
  5. ubuntu mysql5.6 编译安装_Ubuntu14.04编译安装mysql5.6.26
  6. eclipse 插件开发过程中遇到的一堆问题(急待解决)
  7. java fx消息通知,Java的FX 2警报声
  8. Codeforces Round #698 (Div. 2)
  9. HDU-3998 Sequence LIS统计
  10. 千橡CEO给应聘者的信
  11. React基础篇(四)之创建组件方式分析
  12. Nginx安装及配置反向代理
  13. 8.运输层(2)---TCP
  14. C++ - 操作运算符
  15. 即时通讯 音视频 开发技术
  16. 水光半导体于2017 CES展示全方位通讯网络、多媒体及消费性电子芯片解决方案
  17. 开发板实战篇4 RGB565 LCD刷颜色数据
  18. OutLook邮件中设计添加个性签名
  19. Python图片文字提取
  20. 获取 AWS 免费套餐

热门文章

  1. MYSQL 5.7 INNODB 表空间
  2. Dubbo(十四) dubbo的服务降级与集群容错
  3. senchaTouch 给组件传参的两种方式
  4. java extends 继承的一些小结。
  5. spark KafkaRDD的理解
  6. c++什么时候数组溢出_C语言,营养丰富的C语言五,变长数组不是动态数组
  7. 关于一个跨域的小问题
  8. Protobuf 的 import 功能在 Go 项目中的实践
  9. Redis的三种集群原理
  10. 面试题:双重检验锁⽅式实现 单例模式