腾讯一面面试官让我关闭连接
接着上一篇的四次挥手后说起,将会为你展示面试官的威武!
面试官:你刚才说了四次挥手,主动一方会进入 TIME_WAIT 状态,那么我问你,你了解半连接是啥不?
暖蓝:知道的面试官。因为 TCP 是全双工通信,意味着客户端和服务端需要都关闭了才能算关闭。举个例子来说,假设此时客户端想断开连接了,意味着不会再给服务端发任何消息,此时服务端自然也收不到任何数据,这并不能说明 TCP 连接已经完全关闭,因为作为服务端,可能正在处理客户端最后的报文比如说去访问数据库,然后通过套接字把结果返回给客户端,这个时候的套接字就叫做”半关闭“。
面试官:说的不错,这样是比较正常的关闭场景?哪还有其他的关闭方法?
暖蓝:在 Linux 环境编程中,可以使用 close 函数进行关闭(埋下伏笔,面试官可能会继续追问)
面试官:那具体说说 close 怎么关闭的吧
暖蓝:(我靠,很爽啊,真是按照我的套路来)。在 Linux 中,一切皆文件,套接字也不例外,也是描述符。我们在创建进程,可以想象套接字有个计数器,此时计数器会+1,当调用 close 的时候就会-1,当为 0 的时候,就会对套接字进行彻底的关闭,也就是 TCP 两个方向都关闭。(在 c++中是不是也有类似的操作)
面试官:那 close 是如何实现两个方向都能关闭的?
暖蓝:(很棒,真是一套接一套),先说说输入方向,既然要关闭,ok,内核可以帮助你并把你设置为不可读,你后续再想读操作我就抛出异常。对于输出方向,我们知道客户端发送数据给服务端,先会发送到缓冲区,此时将缓冲区的数据给服务端,服务端会发送 Fin 报文,接下来如果再对套接字进行写操作,对不起,抛出异常。那么问题来了,如果客户端没有接收到 fin 报文还要发报文,此时不好意思,会给与"rst"报文警告(我已经关闭,该说的不早点说现在晚勒,别再给我发送数据)
面试官:分析的不错,我现在如果指向关闭一个方向呢?
暖蓝:面试官,这个也可以的。Linux 中提供了 shutdown(int sockfd,int howto),成功返回 0,失败返回-1。
面试官:那你深入说一说吧
暖蓝:(天,您这是要让我将套接字选项啊)。其中 howto 有三个参数,分别代表的含义如下
SHUT_RD(0)
关闭连接的"读"方方向,如果对此方向进行读操作直接返回 EOF。此时缓冲区数据将被丢弃,但是如果有新数据会返回 ACK。
SHUT_WR(1)
关闭连接中的"写"方向,这也是之前说的"半关闭"连接。但是它不会使用计数器,意味着无论计数器值多少,直接关闭,套接字缓冲区数据被直接发送出去且发送 FIN 报文。如果对此套接字进行写操作,报错处理
SHUT_WR(2)
上述两个方向的整合
面试官: 你这么一说,如果参数是 SHUT_RDWR 岂不是和 close 一样了,为什么要这样?
暖蓝:(哈哈哈哈,我真的是故意让您问的),两着不一样勒
close 会关闭且释放资源,shutdown 不会
close 有计数器机制。shutdown 直接让套接字不可用,非常暴力
close 引用技术是不一定会发送 fin 报文,但是 shutdown 会立即发出
面试官:计算机网络这一部分还行,今天就到这吧,请问还有什么问题问我?
暖蓝:谢谢面试官,请问下面试官对这一块的学习有什么推荐的学习方法?
总结:
很多时间,面试时间固定,那么如果对某一块比较熟悉,尽量往深一点的地方讲,引导面试官的同时也引导自己,何乐而不为
码字不易,感谢转发和点击在看!我们下一期再见。。
唠嗑
今年虽难,但是大家也是幸运的,踏踏实实备战,抱团取暖,多多分享会助你成长的。
小蓝准备 5T+共享资源,其中包括 python 爬虫,数据分析,机器学习,c/c++基础实践,java 基础,Spring 企业实战,微服务应用等资源。只需关注"我是程序员小贱"回复关键字即可(失效请联系我)。支持暖蓝,点击文末"在看"。
Linux后台开发必看![c/c++后台开发面经系列]3 bigo/映客面经(含答案)
persist
版权声明: 本文为 InfoQ 作者【我是程序员小贱】的原创文章。
原文链接:【http://xie.infoq.cn/article/ed524e3d591b7b2a963f1bb02】。文章转载请联系作者。
评论