IP封包协议头/TCP协议头/TCP3次握手/TCP4次挥手/UDP协议头/ICMP协议头/HTTP协议(请求报文和响应报文)/IP地址/子网掩码(划分子网)/路由概念/MAC封包格式

Posted liliyang

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了IP封包协议头/TCP协议头/TCP3次握手/TCP4次挥手/UDP协议头/ICMP协议头/HTTP协议(请求报文和响应报文)/IP地址/子网掩码(划分子网)/路由概念/MAC封包格式相关的知识,希望对你有一定的参考价值。

IP协议头
IP包头格式:
技术分享图片

 

1、版本号:4个bit,用来标识IP版本号。这个4位字段的值设置为二进制的0100表示IPv4,设置为0110表示IPv6。目前使用的IP协议版本号是4。

2、首部长度:4个bit。标识包括选项在内的IP头部字段的长度。

3、服务类型:8个bit。服务类型字段被划分成两个子字段:3bit的优先级字段和4bit TOS字段,最后一位置为0。
4bit的TOS分别代表:最小时延,最大吞吐量,最高可靠性和最小花费。4bit中只能将其中一个bit位置1。如果4个bit均为0,则代表一般服务。

技术分享图片

4、总长度字段:16个bit。接收者用IP数据报总长度减去IP报头长度就可以确定数据包数据有效负荷的大小。IP数据报最长可达65535字节。

5、标识字段:16个bit。唯一的标识主机发送的每一份数据报。接收方根据分片中的标识字段是否相同来判断这些分片是否是同一个数据报的分片,从而进行分片的重组。通常每发送一份报文它的值就会加1。

6、标志字段:3个bit。用于标识数据报是否分片。第1位没有使用,第2位是不分段(DF)位。当DF位被设置为1时,表示路由器不能对数据包进行分段处理。如果数据包由于不能分段而未能被转发,那么路由器将丢弃该数据包并向源发送ICMP不可达。第3位是分段(MF)位。当路由器对数据包进行分段时,除了最后一个分段的MF位被设置为0外,其他的分段的MF位均设置为1,以便接收者直到收到MF位为0的分片为止。

7、位偏移:13个bit。在接收方进行数据报重组时用来标识分片的顺序。用于指明分段起始点相对于报头起始点的偏移量。由于分段到达时可能错序,所以位偏移字段可以使接收者按照正确的顺序重组数据包。
当数据包的长度超过它所要去的那个数据链路的MTU时,路由器要将它分片。数据包中的数据将被分成小片,每一片被封装在独立的数据包中。接收端使用标识符,分段偏移以及标记域的MF位来进行重组。

8、生存时间:8个bit。TTL域防止丢失的数据包在无休止的传播。该域包含一个8位整数,此数由产生数据包的主机设定。TTL值设置了数据报可以经过的最多的路由器数。TTL的初始值由源主机设置(通常为32或64),每经过一个处理它的路由器,TTL值减1。如果一台路由器将TTL减至0,它将丢弃该数据包并发送一个ICMP超时消息给数据包的源地址。注意:TTL值经过PIX时不减1。

9、协议字段:8个bit。用来标识是哪个协议向IP传送数据。ICMP为1,IGMP为2,TCP为6,UDP为17,GRE为47,ESP为50。

10、首部校验和:根据IP首部计算的校验和码。

11、Option选项:是数据报中的一个可变长的可选信息。选项字段以32bit为界,不足时插入值为0的填充字节。保证IP首部始终是32bit的整数倍

 

TCP协议头
格式:

技术分享图片

1).16位的源端口号和目的端口号,我们知道端口号就是标识特定主机上的唯一进程的,而IP地址是用来标识网络中的不同主机的,这两个源和目的端口号和IP首部中的源和目的IP地址则标识互联网上的唯一进程,所以套接字的定义说白了就是IP地址和端口号共同组成。

2).32位的序号,是用来标识从TCP发送端向TCP接收端发送的数据字节流的,是一个32位的无符号数。它表示在这个报文段中的的第一个数据字节在数据流中的序号。如果将字节流看作在两个应用程序间的单向流动,则TCP用序列号对每个字节进行计数。用来保证到达数据顺序的编号
3).32位的确认序号,上一个字段的序号是对数据的编号,所以确认序号是下一个期望接收的TCP分段号,相当于是对对方所发送的并且已经被本方所正确接受的分段的确认。确认序号应当是上次已成功收到数据字节序号加1。不过,只有当标志位中的ACK标志为1时该确认序列号的字段才有效。所以顺序号和确认号共同作用于TCP服务中的确认,差错控制,是用于确保TCP的安全性和可靠性的。
4).4位的报头长度,以32位字长为单位,需要这个值是因为任选字段的长度是可变的。这个字段占4bit(最多能表示15(四位全为1)个32bit的的字,即4*15=60个字节的首部长度),因此TCP最多有60字节的首部。不存在任选字段正常的报头长度是20字节。其实相当于给出数据在数据段中的开始位置。

5).保留位,占6比特,为将来的应用而保留,目前置为‘0‘。

6).编码位,占有6个比特位,他们中可以有多个为置为1,依次为:URG,ACK,PSH,RST,SYN,FIN。
URG:该位为1说明表示TCP包的紧急指针域有效,用来保证TCP连接不被中断,并且督促中间层设备要尽快处理这些数据。
ACK:该位为1时说明确认字段是有效,反之为0。
PSH:请求急迫操作,这个标志位表示Push操作。所谓Push操作就是指在数据包到达接收端以后,立即传送给应用程序,而不是在缓冲区中排队。

看到这里有的读者就会产生疑问了URG和PSH都是紧急时使用,那仫这两者有什仫区别和联系呢? 答:在一般的数据中都会存在PSH,而URG只有在紧急情况下才会触发TCP报文中的紧急指针字段,那仫什仫样的情况才是紧急情况呢?紧急方式是向对方发送紧急数据的一种方式,表示数据需要优先处理。它是一个正的偏移,与TCP首部中序号字段的值相加表示紧急数据后面的字节,紧急指针是数据最后一个字节,TCP首部中只有紧急指针指出紧急数据的位置,它所指的字节为紧急数据,但没有办法指定紧急数据的长度。

RST:连接复位,复位因主机奔溃或其他原因而出现的错误连接,也可以用于拒绝非法的分段或拒绝连接请求
SYN:是一个同步序号,通常与ACK合用用来建立连接。例如SYN=1,ACK=0表示连接请求;SYN=1,ACK=1则表示同意建立连接。
FIN:既然有建立连接那仫必然有拆除连接,这个字段表示发送端已经达到数据末尾,也就是说双方的数据传送完成,没有数据可以传送了,发送FIN标志位的TCP数据包后,连接将被断开。这个标志的数据包也经常被用于进行端口扫描。

7).16位的窗口大小,TCP的流量控制由连接的每一端通过声明的窗口大小来提供。窗口大小为字节数,起始于确认序号字段指明的值,这个值是接收端正期望接收的字节。这是一个16 bit字段,因而窗口大小最大为65535字节。

8).16位的校验和,用于对分段首部和数据进行校验。通过将所有16位的数据以补码的形式相加,然后再对相加和取补,正常情况下为0.

9).16位的紧急指针, 只有当URG标志置1时紧急指针才有效。紧急指针是一个正的偏移量,和序号字段中的值相加表示紧急数据最后一个字节的序号。TCP的紧急方式是发送端向另一端发送紧急数据的一种方式。


TCP的三次握手建立连接与四次挥手拆除连接
1.三次握手建立连接
TCP使用三次握手来建立连接,该连接可以由任意一方发起,也可以由双方同时发起!!!
三次握手建立连接的过程:
第一次握手:发送方首先发起TCP建立连接的请求,SYN=1,ACK=0,seq=x,此时发送方由CLOSED进入并进入SYN_SEND状态,等待服务器确认;
第二次握手:接收端收到SYN,同意建立连接,SYN=1,ACK=1,seq=y,ack=x+1(对发送方回应的确认字段),此时接收端进入此时服务器进入SYN_RECV状态;
第三次握手:发送方收到接收端发来的同意建立连接的分段,如果此时确认真的要建立连接,则想接收端发送确认字段,ACK=1,ack=y+1(对接收端做出的回应)。发送方和接收方进入ESTABLISHED状态,完成三次握手
技术分享图片

 

2.四次挥手拆除连接
在上面提到了TCP的三次握手建立连接,那仫如何拆除连接呢?就是四次挥手拆除连接。因为TCP的连接时全双工的,所以拆除连接需要拆除两个单向的连接
第一次挥手:当发送方的主机已经发送完毕的时候,在等待接收端的确认的同时,可以向另一端发送拆除连接的请求。FIN=1,ACK=1,seq=u;
第二次挥手:当接收端已经正确接受发送端的所有数据包,会发送一个ACK应答,同时通知本地相应的应用程序;如果此时对方要求关闭连接,此时再发送一个ACK的分段进行确认。ACK=1,FIN=0,ack=u+1;
第三次挥手:因为TCP的连接时全双工的所以也需要拆除接收方到发送方的连接,此时接收端发送一个FIN的报文段。FIN=1,ACK=1,seq=w;
第四次挥手:发送方收到这个FIN字段,发回一个ACK应答。ACK=1,FIN=0,seq=u+1,ack=w+1;

一个TCP连接是全双工的(即数据在两个方向上能同时传递),因此每个方向必须单独地进行关闭,所以正常的终止一个连接需要四次握手。收到一个FIN只意味着在这一方向上没有数据流动。一个TCP连接在收到一个FIN后仍能发送数据。首先进行关闭的一方(即发送第一个FIN)将执行主动关闭,而另一方(收到这个FIN)执行被动关闭。通常一方完成主动关闭而另一方完成被动关闭。

技术分享图片

 

3.TCP中的状态
首先需要了解TCP中有哪些状态每个状态都有什么意义?
1).CLOSED:表示初始状态.

2).LISTEN:表示服务器端的某个SOCKET处于监听状态,可以接受连接。
3).SYN_RCVD:这个状态表示接受到了SYN报文,在正常情况下,这个状态是服务器端的SOCKET在建立TCP连接时的三次握手会话过程中的一个中间状态,很短暂,基本上用netstat你是很难看到这种状态的,除非你特意写了一个客户端测试程序,故意将三次TCP握手 过程中最后一个ACK报文不予发送。因此这种状态时,当收到客户端的ACK报文后,它会进入到ESTABLISHED状态。

4).SYN_SENT:这个状态与SYN_RCVD有关,当客户端发送SYN报文,因此也随即会进入到了SYN_SENT状态,并等待服务端的发送三次握手中的第2个报文。SYN_SENT状态表示客户端已发送SYN报文。

5).ESTABLISHED:表示连接已经建立了。
6).FIN_WAIT_1:其实FIN_WAIT_1和FIN_WAIT_2状态的真正含义都是表示等待对方的FIN报文。而这两种状态有什仫区别呢?FIN_WAIT_1状态实际上是当SOCKET在ESTABLISHED状态时,它想主动关闭连接,向对方发送了FIN报文,此时该SOCKET即进入到FIN_WAIT_1状态。而当接受到对方回应ACK报文后,则进入到FIN_WAIT_2状态,当然在实际的正常情况下,无论对方何种情况下,都应该马上回应ACK报文,所以FIN_WAIT_1状态一般是比较难见到的,而FIN_WAIT_2状态还有时常常可以用netstat看到。

7).FIN_WAIT_2:实际上FIN_WAIT_2状态下的SOCKET,表示半连接,也即有一方要求关闭连接,但另外还告诉对方,我暂时还有点数据需要传送给你,稍后再关闭连接。

8).TIME_WAIT:表示收到了对方的FIN报文,并发送出了ACK报文,就等2MSL后即可回到CLOSED可用状态了。如果FIN_WAIT_1状态下,收到了对方同时带FIN标 志和ACK标志的报文时,可以直接进入到TIME_WAIT状态,而无须经过FIN_WAIT_2状态。
9).CLOSE_WAIT:这种状态的含义其实是表示在等待关闭。怎么理解呢?当对方close一个SOCKET后发送FIN报文给自己,系统毫无疑问地会回应一个ACK报文给对方,此时则进入到CLOSE_WAIT状态。接下来呢,实际上你真正需要考虑的事情是察看你是否还有数据发送给对方,如果没有的话, 那么你也就可以close这个SOCKET,发送FIN报文给对方,也即关闭连接。所以你在CLOSE_WAIT状态下,需要完成的事情是等待你去关闭连接。

10).LAST_ACK: 它是被动关闭一方在发送FIN报文后,最后等待对方的ACK报文。当收到ACK报文后,也即可以进入到CLOSED可用状态了
11).CLOSING:这种状态比较特殊,实际情况中应该是很少见,属于一种比较罕见的例外状态。正常情况下,当你发送FIN报文后,按理来说是应该先收到(或同时收到)对方的ACK报文,再收到对方的FIN报文。但是CLOSING状态表示你发送FIN报文后,并没有收到对方的ACK报文,反而却收到了对方的FIN报文。什么情况下会出现此种情况呢?其实细想一下,也不难得出结论:那就是如果双方几乎在同时close一 个SOCKET的话,那么就出现了双方同时发送FIN报文的情况,也即会出现CLOSING状态,表示双方都正在关闭SOCKET连接。

为什么在拆除连接后要等待该2*MSL的时间?
答:我们知道在发送方和接收方拆除连接后会等该一定的时间,这是为了防止刚被释放的端口立即被释放,在RFC中该超时时间一般为120s。如果在两倍最大分组生存期内FIN的应答没有到达的话,FIN的发送方就会直接释放连接;而接收方也会注意到,对方已经不再监听了,于是不再发送,连接拆除

 

UDP协议头

技术分享图片

 


ICMP协议:
ICMP是Internet控制报文协议。它是TCP/IP协议族的一个子协议,用于在IP主机、路由器之间传递控制消息。控制消息是指网络通不通、主机是否可达、路由是否可用等网络本身的消息。这些控制消息虽然并不传输用户数据,但是对于用户数据的传递起着重要的作用。
ICMP协议是一种面向无连接的协议,用于传输出错报告控制信息

ICMP报文格式:
技术分享图片

ICMP常用的类型:

TYPE CODE Description Query Error
0 0 Echo Reply——回显应答(Ping应答) x  
3 0 Network Unreachable——网络不可达 x
3 1 Host Unreachable——主机不可达 x
3 2 Protocol Unreachable——协议不可达 x
3 3 Port Unreachable——端口不可达 x
3 4 Fragmentation needed but no frag. bit set——需要进行分片但设置不分片比特 x
3 5 Source routing failed——源站选路失败 x
3 6 Destination network unknown——目的网络未知 x
3 7 Destination host unknown——目的主机未知 x
3 8 Source host isolated (obsolete)——源主机被隔离(作废不用) x
3 9 Destination network administratively prohibited——目的网络被强制禁止 x
3 10 Destination host administratively prohibited——目的主机被强制禁止 x
3 11 Network unreachable for TOS——由于服务类型TOS,网络不可达 x
3 12 Host unreachable for TOS——由于服务类型TOS,主机不可达 x
3 13 Communication administratively prohibited by filtering——由于过滤,通信被强制禁止 x
3 14 Host precedence violation——主机越权 x
3 15 Precedence cutoff in effect——优先中止生效 x
4 0 Source quench——源端被关闭(基本流控制)
5 0 Redirect for network——对网络重定向
5 1 Redirect for host——对主机重定向
5 2 Redirect for TOS and network——对服务类型和网络重定向
5 3 Redirect for TOS and host——对服务类型和主机重定向
8 0 Echo request——回显请求(Ping请求) x
9 0 Router advertisement——路由器通告
10 0 Route solicitation——路由器请求
11 0 TTL equals 0 during transit——传输期间生存时间为0 x
11 1 TTL equals 0 during reassembly——在数据报组装期间生存时间为0 x
12 0 IP header bad (catchall error)——坏的IP首部(包括各种差错) x
12 1 Required options missing——缺少必需的选项 x
13 0 Timestamp request (obsolete)——时间戳请求(作废不用) x
14   Timestamp reply (obsolete)——时间戳应答(作废不用) x
15 0 Information request (obsolete)——信息请求(作废不用) x
16 0 Information reply (obsolete)——信息应答(作废不用) x
17 0 Address mask request——地址掩码请求 x
18 0 Address mask reply——地址掩码应答

最常用的类型为0和8

HTTP协议

TCP HTTP UDP三者的关系:
TCP/IP是个协议组,可分为四个层次:网络接口层、网络层、传输层和应用层。
在网络层有: IP协议、ICMP协议、ARP协议、RARP协议和BOOTP协议。
在传输层中有: TCP协议与UDP协议。
在应用层有: FTP、HTTP、TELNET、SMTP、DNS等协议。
因此,HTTP本身就是一个协议,是从Web服务器传输超文本到本地浏览器的传送协议。

socket:
这是为了实现以上的通信过程而建立成来的通信管道,其真实的代表是客户端和服务器端的一个通信进程,双方进程通过socket进行通信,而通信的规则采用指定的协议。socket只是一种连接模式,不是协议。
tcp,udp,简单的说是两个最基本的协议,很多其它协议都是基于这两个协议。
如,http就是基于tcp的,
用socket可以创建tcp连接,也可以创建udp连接,
这意味着,用socket可以创建任何协议的连接,因为其它协议都是基于此的。

HTTP协议:
HTTP全称是HyperText Transfer Protocol(超文本传输协议)是应用层协议,是现今在WWW上应用最多的协议, ,当你上网浏览网页的时候,浏览器和Web服务器之间就会通过HTTP协议在Internet上进行数据的发送和接收。
Http是一个基于请求/响应模式的、无状态的协议。即我们通常所说的Request(请求)/Response(响应)。

URL:
URL(Uniform Resource Locator) 网络资源统一定位器。
用于描述一个网络上的资源, 基本格式如下:
schema://host[:port#]/path/.../[?query-string][#anchor]

scheme 指定低层使用的协议(例如:http, https, ftp)
host HTTP服务器的IP地址或者域名
port# HTTP服务器的默认端口是80,这种情况下端口号可以省略。如果使用了别的端口,必须指明,例如 http://www.cnblogs.com:8080/
path 访问资源的路径
query-string 发送给http服务器的数据
anchor- 锚

示例:
http://www.mywebsite.com/sj/test/test.aspx?name=sviergn&x=true#stuff
Schema http
host www.mywebsite.com
path /sj/test/test.aspx
Query String name=sviergn&x=true
Anchor stuff

HTTP的请求头和响应头

Request请求头结构:
Request 消息分为4部分:
第一部分叫Request line(请求行)
第二部分叫Request header(请求头)
第三部分是空白行,告诉服务器,请求头部分已经结束
第四部分是body(请求体),一般情况使用get、head等方法是为空,使用post(上传数据),put(资源替换)等方法时才有内容

---request begin---
GET / HTTP/1.1 第一部分请求行
User-Agent: Wget/1.14 (linux-gnu) 第二部分请求头开始
Accept: */*
Host: www.baidu.com
Connection: Keep-Alive 第二部分请求头结束
第三部分空白行
---request end--- 第四部分无

常见的请求头(第二部分):
Accept
作用: 浏览器端可以接受的媒体类型,
例如: Accept: text/html 代表浏览器可以接受服务器回发的类型为 text/html 也就是我们常说的html文档,
如果服务器无法返回text/html类型的数据,服务器应该返回一个406错误(non acceptable)
通配符 * 代表任意类型
例如 Accept: / 代表浏览器可以处理所有类型,(一般浏览器发给服务器都是发这个)

Referer
作用: 提供了Request的上下文信息的服务器,告诉服务器我是从哪个链接过来的,比如从我主页上链接到一个朋友那里,他的服务器就能够从HTTP Referer中统计出每天有多少用户点击我主页上的链接访问他的网站。
例如: Referer:http://translate.google.cn/?hl=zh-cn&tab=wT

Accept-Language
作用: 浏览器申明自己接收的语言。
语言跟字符集的区别:中文是语言,中文有多种字符集,比如big5,gb2312,gbk等等;
例如: Accept-Language: en-us

Accept-Charset
作用:浏览器申明自己接收的字符集,这就是本文前面介绍的各种字符集和字符编码,如gb2312,utf-8(通常我们说Charset包括了相应的字符编码方案)

Accept-Encoding:
作用: 浏览器申明自己接收的编码方法,通常指定压缩方法,是否支持压缩,支持什么压缩方法(gzip,deflate)(注意:这不是只字符编码);
例如: Accept-Encoding: gzip, deflate

Content-Type
作用:指明请求内容的类型
例如:Content-Type: application/x-www-form-urlencoded


User-Agent
作用:告诉HTTP服务器, 客户端使用的操作系统和浏览器的名称和版本.
我们上网登陆论坛的时候,往往会看到一些欢迎信息,其中列出了你的操作系统的名称和版本,你所使用的浏览器的名称和版本,这往往让很多人感到很神奇,实际上,服务器应用程序就是从User-Agent这个请求报头域中获取到这些信息User-Agent请求报头域允许客户端将它的操作系统、浏览器和其它属性告诉服务器。
例如:
User-Agent: Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 5.1; Trident/4.0; CIBA; .NET CLR 2.0.50727; .NET CLR 3.0.4506.2152; .NET CLR 3.5.30729; .NET4.0C; InfoPath.2; .NET4.0E)

Connection
作用:指明是否支持持久连接
例如: Connection: keep-alive 当一个网页打开完成后,客户端和服务器之间用于传输HTTP数据的TCP连接不会关闭,如果客户端再次访问这个服务器上的网页,会继续使用这一条已经建立的连接
例如:
Connection: close 代表一个Request完成后,客户端和服务器之间用于传输HTTP数据的TCP连接会关闭, 当客户端再次发送Request,需要重新建立TCP连接。

Content-Length
作用:发送给HTTP服务器数据的长度。
例如: Content-Length: 38

Host(发送请求时,该报头域是必需的)
作用: 请求报头域主要用于指定被请求资源的Internet主机和端口号,它通常从HTTP URL中提取出来的
例如: 我们在浏览器中输入:http://www.guet.edu.cn/index.html
浏览器发送的请求消息中,就会包含Host请求报头域,如下:
Host:http://www.guet.edu.cn
此处使用缺省端口号80,若指定了端口号,则变成:Host:指定端口号

Pragma
作用: 防止页面被缓存, 在HTTP/1.1版本中,它和Cache-Control:no-cache作用一模一样
Pargma只有一个用法, 例如: Pragma: no-cache

Cookie:
作用: 最重要的header, 将cookie的值发送给HTTP 服务器


响应头:
响应头同样分为4个部分
第一部分叫Response line(响应行或状态信息行)
第二部分叫Response header(响应头)
第三部分是空行,告诉到这里响应头部分结束
第四部分是body响应体(返回给用户的数据)

[[email protected] scripts]# curl -I www.baidu.com
HTTP/1.1 200 OK 第一部分叫Response line(响应行或状态信息行)
Server: bfe/1.0.8.18 第二部分,响应头开始
Date: Thu, 22 Mar 2018 03:08:44 GMT
Content-Type: text/html
Content-Length: 277
Last-Modified: Mon, 13 Jun 2016 02:50:37 GMT
Connection: Keep-Alive
ETag: "575e1f7d-115"
Cache-Control: private, no-cache, no-store, proxy-revalidate, no-transform
Pragma: no-cache
Accept-Ranges: bytes 第二部分响应头结束
第三部分空行
[[email protected] scripts]#

常见的响应头:

Cache-Control
作用: 这个是非常重要的规则。 这个用来指定Response-Request遵循的缓存机制。各个指令含义如下:
Cache-Control:Public 可以被任何缓存所缓存()
Cache-Control:Private 内容只缓存到私有缓存中
Cache-Control:no-cache 所有内容都不会被缓存

Content-Type
作用:WEB服务器告诉浏览器自己响应的对象的类型和字符集,
例如:
Content-Type: text/html; charset=utf-8
Content-Type:text/html;charset=GB2312
Content-Type: image/jpeg

Expires
作用: 浏览器会在指定过期时间内使用本地缓存
例如: Expires: Tue, 08 Feb 2022 11:35:14 GMT

Last-Modified:
作用: 用于指示资源的最后修改日期和时间。(实例请看上节的If-Modified-Since的实例)
例如: Last-Modified: Wed, 21 Dec 2011 09:09:10 GMT

Server:
作用:指明HTTP服务器的软件信息
例如:Server: Microsoft-IIS/7.5

X-AspNet-Version:
作用:如果网站是用ASP.NET开发的,这个header用来表示ASP.NET的版本
例如: X-AspNet-Version: 4.0.30319

X-Powered-By:
作用:表示网站是用什么技术开发的
例如: X-Powered-By: ASP.NET

Connection
作用:指明服务端是否支持持久连接
例如:Connection: keep-alive 当一个网页打开完成后,客户端和服务器之间用于传输HTTP数据的TCP连接不会关闭,如果客户端再次访问这个服务器上的网页,会继续使用这一条已经建立的连接
例如: Connection: close 代表一个Request完成后,客户端和服务器之间用于传输HTTP数据的TCP连接会关闭, 当客户端再次发送Request,需要重新建立TCP连接。

Content-Length
指明实体正文的长度,以字节方式存储的十进制数字来表示。在数据下行的过程中,Content-Length的方式要预先在服务器中缓存所有数据,然后所有数据再发给客户端。
例如: Content-Length: 19847

Date
作用: 生成消息的具体时间和日期
例如: Date: Sat, 11 Feb 2012 11:35:14 GM

HTTP协议中常用的请求方法:Post、Delete、Put、Get(Head)
Http协议定义了很多与服务器交互的方法,
最基本的有4种,分别是Post(增)、Delete(删)、Put(改)、Get(查)
一个URL地址用于描述一个网络上的资源,而HTTP中的GET, POST, PUT, DELETE就对应着对这个资源的查,改,增,删4个操作。
其中最常用的是GET和POST

 


IP地址
一个完整的IP地址,由2个部分组成:网络位+主机位
技术分享图片

分类:

公有IP地址:
A类:1.0.0.0 ~ 127.255.255.255 #主要分配 给大量主机而局域网网络数量较少的大型网络
B类:128.0.0.0 ~ 191.255.255.255 #一般用于国际性大公司和政府机构
C类:192.0.0.0 ~ 223.255.255.255 #用于一般小公司校园网研究机构等
D类:224.0.0.0 ~ 239.255.255.255 #用于特殊用途,又称做广播地址
E类:240.0.0.0 ~ 255.255.255.255 #暂时保留
私有地址:
A类 10.0.0.0--10.255.255.255
B类 172.16.0.0--172.31.255.255
C类 192.168.0.0--192.168.255.255

其中127.0.0.0 到127.255.255.255 为系统回环地址


子网掩码:
子网掩码不能单独存在,它必须结合IP地址一起使用。
子网掩码只有一个作用,就是将某个IP地址划分成网络地址和主机地址两部分,即切分子网

以 192.168.0.0 ~ 192.168.0.255 这个网域为范例好了,如下所示,这个 IP 网段可以分为 Net_ID 与 Host_ID,既然 Net_ID 是不可变的,那就假设他所占据的 bits 已经被用光了 (全部为 1),而 Host_ID 是可变的,就将他想成是保留着 (全部为 0),所以, Netmask 的表示就成为:
192.168.0.0~192.168.0.255 这个 C Class 的 Netmask 说明
技术分享图片

                   :                       255 .               255 .               255 . 0                    <== Netmask 十进制 特别注意,netmask 也是 32 位,在数值上,位于 Net_ID 的为 1 而 Host_ID 为 0

A, B, C Class 的 Netmask 表示就成为这样:
Class A : 11111111.00000000.00000000.00000000 ==> 255. 0. 0. 0
Class B : 11111111.11111111.00000000.00000000 ==> 255.255. 0. 0
Class C : 11111111.11111111.11111111.00000000 ==> 255.255.255. 0

192.168.0.0 ~ 192.168.0.255这个Class C 的网域中他的Netmask就是 255.255.255.0
刚刚提到了当Host_ID全部为0以及全部为1时,该 IP是不可以使用的,
因为Host_ID全部为 0的时后,表示 IP是该网段的Network,
至于全部为1的时后就表示该网段最后一个 IP,也称为Broadcast,
所以说,在192.168.0.0 ~ 192.168.0.255 这个IP网段里面的相关网络参数就有:

Netmask: 255.255.255.0 <==网域定义中,最重要的参数
Network: 192.168.0.0 <==第一个 IP
Broadcast: 192.168.0.255 <==最后一个 IP
可设定成为主机IP的范围: 192.168.0.1 ~ 192.168.0.254


子网切分
刚提到Class C还可以继续进行子域(Subnet)的切分,以192.168.0.0 ~192.168.0.255这个情况为例,他要如何再细分为两个子域呢?
已经知道Host_ID可以拿来当作Net_ID,那么 Net_ID使用了25 bits时,就会如下所示:

原本的C Class的 Net_ID与Host_ID如下
技术分享图片

切成两个子网之后的 Net_ID 与 Host_ID 为何? 

技术分享图片

技术分享图片

所以,当再细分下去时,就会得到两个子域,而两个子域还可以再细分下去(Net_ID用掉26 bits)

例题:
计算172.16.0.0,但 Net_ID占用23个位时,这个网域的 Netmask, Network, Broadcast 等参数
答:
由于172.16.xxx.xxx是在Class B的等级当中,亦即Net_ID 应该是16位才对。不过题目给的Net_ID占用了23个位!等于是向Host_ID借了(23-16)7个位用在Net_ID中。所以整个 IP 的地址会变成这样:
技术分享图片

技巧:

子网的计算是有技巧的,IP是二进制,每个位就是 2的次方。又由于 IP数量都是平均分配到每个子网去,所以,如果我们以 192.168.0.0 ~ 192.168.0.255这个网段来说,要是给予Net_ID是26位时,总共分为几段? 因为26-24=2,所以总共享掉两个位,因此有2的2次方,得到4个网段。再将256个IP平均分配到4个网段去,那我们就可以知道这四个网段分别是:
192.168.0.0 ~ 192.168.0.63 第一个是Network不可用
192.168.0.64 ~ 192.168.0.127
192.168.0.128 ~ 192.168.0.191
192.168.0.192 ~ 192.168.0.255 最后一个是Broadcast不可用


无层级IP:CIDR (Classless Interdomain Routing)
一般来说,如果我们知道了Network以及Netmask之后,就可以定义出该网域的所有 IP 了!
因为由Netmask就可以推算出来Broadcast的IP!
因此,我们常常会以Network以及Netmask来表示一个网域,写法如下:

Network/Netmask
192.168.0.0/255.255.255.0
192.168.0.0/24 <==因为 Net_ID 共有 24 个 bits
上面的4个网段可写成:
192.168.0.0/26
192.168.0.64/26
192.168.0.128/26
192.168.0.192/26


路由概念
在同一个区网里面,可以透过IP广播的方式来达到资料传递的目的。但如果是非区网内的数据呢?这时就得要透过那个所谓的邮局(路由器,即网关)的帮忙了!
每一部主机都有自己的路由表,也就是说,你必须要透过你自己的路由表来传递你主机的封包到下一个路由器上头。若传送出去后,该封包就得要透过下一个路由器的路由表来传送了,此时与你自己主机的路由表就没有关系!
traceroute指令可以跟踪封包途径的路由
路由的观察:route -n #使用route设定静态路由,见单独文档
[[email protected] ~]# route -n
Kernel IP routing table
Destination Gateway Genmask Flags Metric Ref Use Iface
10.8.0.2 0.0.0.0 255.255.255.255 UH 0 0 0 tun0
10.0.0.0 0.0.0.0 255.255.255.0 U 0 0 0 eth0
169.254.0.0 0.0.0.0 255.255.0.0 U 1002 0 0 eth0
169.254.0.0 0.0.0.0 255.255.0.0 U 1003 0 0 eth1
0.0.0.0 10.0.0.2 0.0.0.0 UG 0 0 0 eth0
从上面可以看出,Linux系统下的路由表是由小网域排列到大网域(封包发送是就是根据上述的路由表从小到大开始测试使用哪条路由可将数据发送出去)

重复路由的问题
由上面知道,封包发送是按照路由表中从小到大的进行的,如果封包能够从其中一条路由将封包传送出去,就不会继续后续的测试,因此如果设置了两条相同的路由,并不能增加网络流量,上面的:
169.254.0.0 0.0.0.0 255.255.0.0 U 1002 0 0 eth0
169.254.0.0 0.0.0.0 255.255.0.0 U 1003 0 0 eth1
发送数据时,封包只会从第一条发送出去

1、依据网络接口产生的 IP 而存在的路由
主机上面有几个网络接口的存在时,该网络接口就会存在一个路由(与自己所在网段的主机进行通信)
[[email protected] scripts]# route -n
Kernel IP routing table
Destination Gateway Genmask Flags Metric Ref Use Iface
0.0.0.0 10.0.91.1 0.0.0.0 UG 100 0 0 em1
10.0.91.0 0.0.0.0 255.255.255.0 U 100 0 0 em1 #em1网卡IP地址为100.0.91.5
172.17.0.0 0.0.0.0 255.255.0.0 U 0 0 0 docker0

2、手动或预设路由(default route),即使用route手动设定静态路由
3、动态路由的学习(使用zebra等服务,其能够自动学习添加路由)

封包转递:
主机想要将数据传送到不同的网域时需要透过路由器的帮忙,所以,路由器的主要功能就是:『转递网络封包』 也就是说,路由器会分析来源端封包的 IP 表头,在表头内找出要送达的目标IP后,透过路由器本身的路由表(routing table) 来将这个封包向下一个目标(next hop)传送。这就是路由器的功能。

Linux系统本身具有封包转递的功能,打开后,linux充当路由器(网关)来使用(实际设定时,必须在指令中明确指定gw,即明确指定使用某个网关才会进行转发)
[[email protected] ~]# vim /etc/sysctl.conf # 将底下这个设定值修改正确即可! (本来值为 0 ,将它改为 1 即可)
net.ipv4.ip_forward = 1
[[email protected] ~]# sysctl -p # 立刻让该设定生效

 


注意:路由和路由器是不同的概念(可将路由器与网关逻辑上等同)

判断多个地址是否位于同一网段内,主要看他们的Net_ID是否相同,如果相同就位于同一网段
两个不同网段的数据无法透过广播来达到数据的传递,那怎办?此时就得要经过IP的路径选择(routing)功能

两个不同网段的主机要相互通信,必须要经过路由器进行转发(路由器通常有2块网卡,一块网卡上的IP地址和其中一个网段中的主机处于同一网段;而另一块网卡上的IP地址和另一个网段中主机处于同一网段。而路由器上的2张网卡,分别称之为各自网段的网关)
同一网段的所有主机要和另一个网段的主机进行通信,该网段中所有主机的网关必须相同,都设置成路由器上和本网段处于同一网段的IP。

 

 

MAC 的封装格式:

CSMA/CD 发送出去的数据帧,其实就是 MAC。MAC 就是我们上面一直讲到的数据帧(frame)。只是这个数据帧上面有两个很重要的数据,就是目标与来源的网卡卡号,因此我们又简称网卡卡号为 MAC 地址。简单地说,你可以把 MAC 想成是一个在网线上面传递的包裹,而这个包裹是整个网络硬件上面传送数据的最小单位。也就是说,网线可想成是一条“一次仅可通过一个人”的独木桥,而 MAC 就是在这个独木桥上面走动的人。

技术分享图片

 

OSI 7层模型:
PL(物理层) :传送0或1这种位串
DLL(数据链路层):包括2个子层,偏向硬件部分的MAC层和偏向软件部分的逻辑连接控制层(LLC)
MAC子层:MAC 是网络媒体所能处理的主要数据报裹,也是最终被物理层编码成位串的数据。MAC 必须要经由通讯协议来取得媒体的使用权,目前最常使用的则是 IEEE 802.3 的以太网络协议
LLC子层:处理来自上层的封包数据 (packet) 并转成 MAC 的格式, 负责的工作包括讯息交换、流量控制、失误问题的处理等

NL(网络层) :IP协议位于这一层,封包是否可以达到目的地路由
TL(传输层) :TCP和UDP协议位于这一层,封包格式,数据封包的传送、流程的控制、传输过程的侦测检查与复原重新传。判断资料封包是否可以正确的到达目标
SL(会话层) :定义了两个地址之间的联机信道的连接与挂断。确定网络服务建立联机的确认
PL(表现层) :数据的加密和解密
AL(应用层) :以将数据接收或传送给应用程序最终展示给用户。


IP与MAC:链结层的ARP与RARP协定
Internet上最重要的就是IP,也会计算所谓的局域网络与路由。但事实上在传递数据时却是以太网络!
而以太网络则要是用网卡卡号(MAC地址)!
这就有问题,那这两者(IP与MAC)势必有一个关连性存在?
是的就是ARP(Address Resolution Protocol, 网络地址解析)协议,及RARP(Revers ARP, 反向网络地址解析)

当我们想要了解某个IP是设定于哪张以太网卡上时,我们的主机会对整个区网发送出ARP封包,对方收到ARP封包后就会回传他的MAC,我们的主机就会知道对方所在的网卡,那接下来就能够开始传递数据!!

执行arp指令,会向本机所在网段内的所有IP发送广播包,(因为Dest MAC为:ff:ff:ff:ff:ff:ff),其他主机接收到后会返回自己的IP地址和MAC地址

如果每次要传送都得要重新通过ARP协议获得远程主机的MAC地址,效率较低。
因此,当使用ARP协议取得目标IP与MAC后,就会将该记录写入本机的ARP table中(内存内的数据),默认记录20分钟


取得本机的ARP表格内的IP/MAC对应数据,透过arp指令
arp 选项
-n 将主机名以IP显示
-d 将hostname的hardware_address由ARP table当中删除掉
-s 设定某个IP或hostname的MAC到ARP table当中。 即建立静态 ARP
[[email protected] ~]# arp -n
Address HWtype HWaddress Flags Mask Iface
10.0.0.2 ether 00:50:56:fc:31:a6 C eth0
10.0.0.25 ether 00:0c:29:2a:1d:d4 C eth0
10.0.0.1 ether 00:50:56:c0:00:08 C eth0
10.0.0.26 ether 00:0c:29:68:85:1a C eth0
[[email protected] ~]# arp -s 192.168.1.100 01:00:2D:23:A1:0E #将192.168.1.100那部主机的网卡卡号直接写入ARP表格中
[[email protected] ~]# arp -d 192.168.1.100 01:00:2D:23:A1:0E #将ARP表格中上述添加的记录删除


IP地址是属于逻辑信息,无法以光电信号呈现,而实体层的寻址方式是用MAC地址来识别(假设实体层是以太网,实体层网络技术不同实现的方式也不同,也导致了各种技术的MTU也不相同,以太网实体层技术是通过MAC实现),因此,当数据发送到实体层时,会在该数据中附加上发送端和接收端的MAC地址,这样便可以将数据传输到正确的目的地

MAC地址是以太网的地址形式,在其他网络实体层技术中都会有其特有的地址形式,因此“MAC地址只在以太网上有效,MAC地址是不会跨越路由器设备的”,也因此,当初TCP/IP网络模型并没有定义立实体层技术一定要使用哪一种(这样的话TCP/IP网络模型可用于各种不同的实体层技术之上)。

 

 

 


各个封包之间的相关性:
技术分享图片

 

端口分类:
特权端口: 0 ~ 1023 #其中80端口分配给WWW服务,21端口分配给FTP服务等。
注册端口: 1024 ~ 49151 #许多服务绑定于这些端口,这些端口同样可用于其它目的,在没有被服务器资源占用的时候,可以用用户端动态选用为源端口。
动态端口: 49152 ~ 65535 #一般不固定分配某种服务,只是临时使用,而是动态分配,但不是绝对

特权端口的启动需要root权限,而注册端口和动态端口不需要
Linux系统中的/etc/services文件记录本机上各个端口对应的协议。

 









































































































































































































































































































































以上是关于IP封包协议头/TCP协议头/TCP3次握手/TCP4次挥手/UDP协议头/ICMP协议头/HTTP协议(请求报文和响应报文)/IP地址/子网掩码(划分子网)/路由概念/MAC封包格式的主要内容,如果未能解决你的问题,请参考以下文章

http请求与响应,tcp3次握手&四次挥手

tcp协议

TCP/IP协议全解析 三次握手与四次挥手[转]

抓包三次握手

TCP协议:头部结构三次握手与四次挥手

TCP UPD详解