首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> 關於C語言

Linux C語言Socket網絡編程入門:TCP服務端/客戶端完整實現與關鍵調用詳解

     編輯:關於C語言

實驗環境與架構

  • 協議:TCP(面向連接、可靠傳輸)
  • 模型:單進程阻塞 I/O,服務端循環 accept,客戶端單次連接收發後退出
  • 固定參數:端口 0x8888 (34952),服務端綁定 INADDR_ANY,客戶端連接 192.168.1.104(實際部署請修改為真實服務器 IP)

服務端核心流程(server.c)

  1. socket(AF_INET, SOCK_STREAM, 0) 創建監聽套接字
  2. bind() 綁定 IP:PORT,listen(sfp, 5) 啟動監聽,backlog=5
  3. 進入 while(1) 循環 accept() 阻塞等待客戶端連接
  4. 連接建立後 write() 發送歡迎消息,close() 關閉該連接套接字,繼續循環等待下一個

關鍵代碼片段

sfp = socket(AF_INET, SOCK_STREAM, 0);
bzero(&s_add, sizeof(struct sockaddr_in));
s_add.sin_family = AF_INET;
s_add.sin_addr.s_addr = htonl(INADDR_ANY);  // 綁定所有本地網卡
s_add.sin_port = htons(portnum);

bind(sfp, (struct sockaddr*)&s_add, sizeof(struct sockaddr));
listen(sfp, 5);

while (1) {
    sin_size = sizeof(struct sockaddr_in);
    nfp = accept(sfp, (struct sockaddr*)&c_add, &sin_size);  // 阻塞點
    // 獲取客戶端 IP:PORT
    printf("Server get connect from %#x : %#x\n", ntohl(c_add.sin_addr.s_addr), ntohs(c_add.sin_port));
    write(nfp, "hello,welcome to my server \r\n", 32);
    close(nfp);
}

客戶端核心流程(client.c)

  1. socket() 創建套接字
  2. 構造服務端地址結構體:inet_addr("192.168.1.104") 將點分十進制 IP 轉網絡序整數
  3. connect() 主動發起連接
  4. read() 接收服務端數據並打印,getchar() 暫停以便 netstat 觀察連接狀態,最後 close()

關鍵代碼片段

cfd = socket(AF_INET, SOCK_STREAM, 0);
bzero(&s_add, sizeof(struct sockaddr_in));
s_add.sin_family = AF_INET;
s_add.sin_addr.s_addr = inet_addr("192.168.1.104");  // ★修改為實際服務端IP
s_add.sin_port = htons(portnum);

connect(cfd, (struct sockaddr*)&s_add, sizeof(struct sockaddr));
recbytes = read(cfd, buffer, 1024);
buffer[recbytes] = '\0';
printf("%s\n", buffer);
getchar();  // 方便 netstat -an | grep 34952 觀察 ESTABLISHED 狀態
close(cfd);

編譯與運行驗證

# 服務端
gcc server.c -o server
./server
# 輸出: Hello,welcome to my server! ... listen ok

# 客戶端(另一終端/機器)
gcc client.c -o client
./client
# 輸出: connect ok! read ok REC: hello,welcome to my server

字節序深度解析:為什麼要 htons/htonl?

  • 網絡傳輸統一使用大端序(高位字節在前)
  • x86 CPU 為小端序(低位字節在前)
  • htons (Host TO Network Short) 將 2 字節端口號轉為網絡序;htonl 處理 4 字節 IP
  • 接收端對應使用 ntohs/ntohl 轉回主機序
  • 口訣:「發送前 hton,接收後 ntoh,跨平台不崩潰」

常見坑點與調試技巧

現象原因解決
bind 失敗 "Address already in use"端口被佔用或 TIME_WAIT 狀態修改端口、設 SO_REUSEADDR、等待 1-2 分鐘
connect 超時IP 錯誤、防火牆攔截、服務端未啟動ping 測通、關閉防火牆/開放端口、確認 server 進程
read 返回 0對端正常關閉連接 (FIN)屬正常行為,處理 EOF 邏輯
write 返回 -1, errno=EPIPE對端已關閉,本端繼續寫入捕獲 SIGPIPE 信號或檢查連接狀態

進階擴展方向

  • 多進程/多線程併發服務端(fork() / pthread_create())
  • I/O 多路復用(select/poll/epoll)支撐高併發
  • 應用層協議設計:定長包頭+消息體、心跳保活、優雅關閉
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved