1. 程式人生 > >服務端主動終止連線的情況分析

服務端主動終止連線的情況分析

正常退出情況

首先我們來看看一次伺服器和客戶端正常通訊的情況。
在這之前,讓我們看看TCP的三次握手與四次揮手的過程。

首先是三次握手過程。
三次握手

下來是四次揮手過程。
這裡寫圖片描述

下面我們結合著套接字程式設計,來看看TCP的這些過程(程式碼請點選上面的github連線).
這裡寫圖片描述
當我們只打開服務端時,此時由於客戶端沒有向服務端發出連線請求,所以服務端此時處在LISTEN狀態,這個狀態稱為監聽狀態,表示服務端在等待客戶端的連線請求報文。

這裡寫圖片描述
這次我們開啟客戶端,並且通過客戶端向服務端傳送資料,服務端頁正常接收到了資料,此時服務端和客戶端都處於ESTABLISHED

狀態,表示連線已經建立完成,即此時三次握手這個過程已經完畢,但是大家應該清楚,中間還有兩次狀態的切換客戶端的SYN-SENT 以及 服務端的SYN-RCV.由於我們是手動監視,所以我們不能顯示的看到這兩個狀態。

這裡寫圖片描述
上圖中,客戶端在資料通訊完成後想要結束掉與服務端的連線狀態,我們直接通過按Ctrl + C 鍵向客戶端傳送了訊號將客戶端終止,此時,服務端應該也會向客戶端傳送ACK 欄位的報文 相當於我們完成了四次揮手過程中的前兩次揮手,通過指令的檢視,我們發現結果確實也是那樣,隨後我們在Ctrl + C 掉服務端,完成了後兩次揮手,整個通訊過程也就完成了。

連線異常終止的情況

上面的正常過程中,我們是讓客戶端比服務端先退出,這樣滿足了四次揮手過程的要求;現在我們讓伺服器在客戶端前面退出,我們來看看這個過程發生了什麼。
由於我們研究的情況是連線的異常終止情況,所以三次握手狀態我們就不關心了,這裡我們這研究連線的異常終止情況。
這裡寫圖片描述


上圖中,我們讓服務端先退出,然後我們用netstat觀察埠的狀態,此時我們發現四次揮手過程中伺服器和客戶端的狀態顛倒了, 也就是說,服務端和客戶端的程序那個先向對方傳送FIN 欄位報文,那麼哪個就先進入FIN_WAIT2狀態。

這裡寫圖片描述

上圖發生的原因是這樣的,當伺服器程序被終止時,會關閉其開啟的所有檔案描述符,此時就會向客戶端傳送一個FIN 的報文,客戶端則響應一個ACK 報文,但是這樣只完成了“四次揮手”的前兩次揮手,也就是說這樣只實現了半關閉,客戶端仍然可以向伺服器寫入資料。
但是當客戶端向伺服器寫入資料時,由於伺服器端的套接字程序已經終止,此時連線的狀態已經異常了,所以服務端程序不會向客戶端傳送ACK

報文,而是傳送了一個RST 報文請求將處於異常狀態的連線復位; 如果客戶端此時還要向服務端傳送資料,將誘發服務端TCP向服務端傳送SIGPIPE訊號,因為向接收到RST的套介面寫資料都會收到此訊號. 所以說,這就是為什麼我們主動關閉服務端後,用客戶端向服務端寫資料,還必須是寫兩次後連線才會關閉的原因。

大家可以在自己的Linux系統實驗一下,用tcpdump去抓包效果會更好。

相關推薦

服務主動終止連線情況分析

正常退出情況 首先我們來看看一次伺服器和客戶端正常通訊的情況。 在這之前,讓我們看看TCP的三次握手與四次揮手的過程。 首先是三次握手過程。 下來是四次揮手過程。 下面我們結合著套接字程式設計,來看看TCP的這些過程(程

伺服器主動關閉連線, 產生的TIME_WAIT狀態為什麼會佔用服務大量埠?

1. 理解認為accep() 返回的socket_new, 其源埠和目的埠與 listen() 的socket 是一置的,accept() 返回並未佔用伺服器新的埠。 2. 如果伺服器端主動關閉 socket_new, 產生的TIME_WAIT狀態為什麼會在伺服器端佔用除監聽埠以外的其餘埠,還是其實並沒有佔

WebSocket安卓客戶實現詳解(三)–服務主動通知

this override 連接 繼續 true www. 格式 代碼 ati   WebSocket安卓客戶端實現詳解(三)–服務端主動通知    本篇依舊是接著上一篇繼續擴展,還沒看過之前博客的小夥伴,這裏附上前幾篇地址    WebSocket安卓客戶端實現詳解(一)

11-服務程序終止

  這一篇我們將討論伺服器程序終止的問題。   先啟動服務端,再啟動客戶端,然後殺死服務端子程序,以此來模擬伺服器程序終止的情況。如果客戶端再向服務端傳送資料,這將會發生什麼情況? 伺服器程式: #include <stdio.h> #

mina保持android\服務的長連線

更多幹貨 一.mina簡介 Apache Mina是一個能夠幫助使用者開發高效能和高伸縮性網路應用程式的框架。與Netty出自同一人之手,都是一個介於應用程式與網路之間的NIO框架,通過Java nio技術基於TCP/IP和UDP/IP協議提供了抽象的、事件驅動的、非同步

Netty框架服務主動向客戶通訊

專案場景: 一個車聯網專案,很多很多臺車輛會定時像服務端發包,所以都是使用TCP長連線的方式。現在有一個需求是,服務端需要向客戶端主動的傳送升級命令,由於使用的事件驅動的Netty框架,我們怎麼才能由服務端主動的向客服端通訊呢? 解決方案: pac

SpringBoot2.x服務主動推送SSE

講解SpringBoot2.x服務端主動推送Sever-Send-Events              1、localhost:8080/index.html     2、需要把

[netty原始碼分析]--服務啟動的工作流程分析

服務端 1.首先是例項化boss執行緒池和worker執行緒池 例項化的就是 NioEventLoopGroup;這裡我假設boss執行緒池初始化為1個執行緒,worker執行緒初始化為 2*CPU個數的執行緒數。 說一下主要做了什麼工作: (1)指

Asp.Net Core 2.1 中 利用SignalR 服務主動推送資料

最近正在學習 SignalR 在Asp.Net Core中的應用(資料推送等等。。。)。以下為個人學習時遇到問題的記錄和解決方法。對於Asp.Net Core我也是剛剛學習,所以不保證完全正確。如果有錯誤還請大家指正,多謝多謝!!!在完整版(傳統版)的 Asp.Net  程式

本地同時安裝oracle客戶服務(通過plSql連線)

前期準備 之前本站已經分享了oracle伺服器端(資料庫)的安裝,接下來只需要下個oracle的客戶端以及PLSQL Developer資料庫管理軟體,即能實現本地操控自己電腦上的oracle資料庫。 可以從我的百度雲連結:http://pan.baidu.com/s/1

3、客戶服務發訊息和服務主動推送訊息

index.html <!-- 客戶端 --> <!DOCTYPE html> <html lang="en"> <head>

android中對服務的長連線【socket】

    我們有時候有這種需求,即我們的android客戶端要始終保持與服務端的連線,當服務端有任務或訊息傳送到android客戶端的時候就傳送,沒有任務或訊息的時候不傳送但要保持這個連線,一旦有任務則開發傳送,而我們的android客戶端則要保持一個時刻接收任務或訊息的狀態

Netty服務啟動過程相關原始碼分析

1、Netty 是怎麼建立服務端Channel的呢? 我們在使用ServerBootstrap.bind(埠)方法時,最終呼叫其父類AbstractBootstrap中的doBind方法,相關原始碼如下: private ChannelFuture doBind(final SocketAddress lo

TCP狀態機:當服務主動發FIN進TIME_WAIT,客戶源埠複用會發生什麼

0X01 正常情況下TCP連線會通過4次揮手進行拆鏈(也有通過RST拆除連線的可能,見為什麼伺服器突然回覆RST——小心網路中的安全裝置),下圖TCP狀態機展示了TCP連線的狀態變化過程: 我們重點看4次揮手的過程: 想要拆除連線的一方A傳送FIN報文,自身進入到FIN_WAIT_1狀態; 被拆除連線

結合實際需求,在webapi內利用WebSocket建立單向的訊息推送平臺,讓A頁面和服務建立WebSocket連線,讓其他頁面可以及時給A頁面推送訊息

1.需求示意圖     2.需求描述 原本是為了給做unity3d客戶端開發的同事提供不定時的訊息推送,比如商城購買道具後服務端將道具資訊推送給客戶端。 本篇文章簡化理解,用“相關部門開展活動,向全市人民徵集社會服務改善意見”為例子。但核心想法一致:單向推送(指這個需求上只需要單向)。所

Netty4.x原始碼分析服務接受客戶Channel連線

引包 <dependency> <groupId>io.netty</groupId> <artifactId>netty-all</artifactId> &l

穩定性 耗時 監控原因分析-- dubbo rpc 框架 的線程池,io 連接模型. 客戶,服務

情況 現在 src tcp協議 時間 .cn 關系 1.0 繼續 上次 提到的Nagle算法特性有可能是dubbo調用”網絡耗時高“的始作俑者,後來又仔細看了下dubbo的代碼,發現dubbo在consumer端已經將tcp設置成非延遲(即關閉Nag

愛創課堂每日一題第五十五天- WEB應用從服務主動推送Data到客戶有那些方式?

前端 前端學習 前端入門Javascript數據推送Commet:基於HTTP長連接的服務器推送技術基於WebSocket的推送方案SSE(Server-Send Event):服務器推送數據新方式愛創課堂每日一題第五十五天- WEB應用從服務器主動推送Data到客戶端有那些方式?

netty服務實現心跳超時的主動拆鏈

use ctx out apt ket cond else pipeline ali 一、服務器啟動示例: public class MySocketServer { protected static Logger logger = LoggerFactory.g

FTP的主動與被動模式,及linux服務的配置

阻塞 pre 兩種模式 文件中 linux服務 文件傳輸協議 服務端 linu 固定 FTP作為一種簡單的明文文件傳輸協議,其工作過程有兩個工作進程--(命令進程(默認21端口)與數據傳輸進程); 而數據傳輸進程又分為主動與被動兩種模式: 主動FTP: 命令連接:客戶端