上一篇,通过抓包,我们总结了两者在效率和可靠性上的差别.这一篇,我们将认识socket如何处理多个请求
1、代码
这里使用之前tcp服务的代码
1.1、运行流程
- 启动tcp服务
- 使用tcpdump进行抓包
![7379413131354ef7e11a2bb0f8b51003.png](https://i-blog.csdnimg.cn/blog_migrate/b924d74206f40ad4330a52c4a5e8d0be.jpeg)
- 使用telnet连接tcp服务
![2800ca3565c7ddd55a708bcaecee22d2.png](https://i-blog.csdnimg.cn/blog_migrate/b2b0b6fda40d42ad0aaae7fc30933f9f.jpeg)
- 执行tcp客户端脚本
![be7daa482ec921f8f293e1d26fd5cf7c.png](https://i-blog.csdnimg.cn/blog_migrate/7faf7cc1101fd75853e103353459861a.jpeg)
1.2、查看目前的执行结果
- tcp服务端
![e62888b749cdd13505aa67fd64cc708d.png](https://i-blog.csdnimg.cn/blog_migrate/02c0aec283fdc099313f06b171cbf491.jpeg)
- tcpdump抓包结果1
![9192908887825a99639edf7f052ddbd4.png](https://i-blog.csdnimg.cn/blog_migrate/020b34028d90cb8677f5b2c52e515a6c.jpeg)
1.3、分析抓包结果1
- 序号1-4的数据包,是telnet客户端与tcp服务端建立三次握手
- 序号5-8的数据包,是tcp客户端与tcp服务端建立的三次握手
- 序号9-10数据包,则是tcp客户端往服务端发送数据"hello world"
1.4、telnet的终端输入数据“iamasb”
- telnet终端输出结果
![90232ec4cec7ce5b6984c18d02c1f662.png](https://i-blog.csdnimg.cn/blog_migrate/f19a21d6339446df2767981a32ffc014.jpeg)
- tcp客户端输出结果
![213c759ac3aba537c25472eb615502f1.png](https://i-blog.csdnimg.cn/blog_migrate/558938b4663c1ffc196df8f18ab1d6e3.jpeg)
- tcp服务端输出结果
![f59a4c8ab0b2c16b118868b1cc294f7e.png](https://i-blog.csdnimg.cn/blog_migrate/fd2a52100153fe692224ed2fa5da02c1.jpeg)
- tcpdump抓包结果2
![c5892f321ca610014f699eb7a340ca6d.png](https://i-blog.csdnimg.cn/blog_migrate/ff55db0b34cb867890d743e3115f1a65.jpeg)
1.5、分析抓包结果2
- 序号11-12,则是telnet客户端往服务端发送数据"iamasb"
- 序号13-14,则是服务端往telnet客户端发送数据"iamasb"
- 序号15、16、23、24,则是服务端与telnet客户端释放连接的四次握手
- 序号17、19,则是服务端往tcp客户端发送数据"hello world"
- 序号18、20、21、22则是服务端与tcp客户端释放连接的四次握手
备注: 由于是在shell终端发送数据需要按回车,因此telnet客户端在发送数据时,追加了两个字符
2、案例分析
整个案例,以telnet客户端是否输入数据为分界点
2.1、输入数据前
从抓包结果1的截图中,可以看出:
- telnet和tcp客户端都与服务端通过三次握手,建立好连接
- tcp客户端往服务端发送数据,而服务端也接收完毕。从这个环节可以看出socket存在"缓冲区",来临时存放客户端发来的数据。但无法马上进行处理,是因为"服务端"处于阻塞状态。
从输入数据前,服务端的输出结果来看:
- 服务端在socket_read调用处,阻塞。等待telnet客户端发送数据,导致无法处理其它请求
2.2、输入数据后
服务端在socket_read调用处,获取数据"iamasb"后,向telnet客户端发送数据,并释放此socket连接。开始下一个循环。
服务端调用socket_accept获取新的socket连接,再次执行read/write操作,并释放此socket连接。
3、总结
- socket_accept和socket_read在调用时会进行阻塞
- 再处理多个客户端请求时,只能串行处理。即一个接着一个进行
- 在socket_accept获取新的socket连接前,此socket连接已在内核中建立好
- socket存在缓存区