Winsock開發網路通訊程式的經典入門

2021-04-13 13:48:17 字數 2727 閱讀 2943

對於許多初學者來說,網路通訊程式的開發,普遍的

乙個現象就是覺得難以入手。許多概念,諸如:

同步(sync)/非同步(async),阻塞(block)/非阻塞(unblock)

等,初學者往往迷惑不清,只知其所以而不知起所以然。 

同步方式指的是傳送方不等接收方響應,便接著發下

個資料報的通訊方式;而非同步指傳送方發出資料後,等收到接收方發回的響應,才發下乙個資料報的通訊方式。

阻塞套接字是指執行此套接字的網路呼叫時,直到成功才返回,否則一直阻塞在此網路呼叫上,比如呼叫recv()函式讀取網路緩衝區中的資料,如果沒有資料到達,將一直掛在recv()這個函式呼叫上,直到讀到一些資料,此函式呼叫才返回;而非阻塞套接字是指執行此套接字的網路呼叫時,不管是否執行成功,都立即返回。比如呼叫recv()函式讀取網路緩衝區中資料,不管是否讀到資料都立即返回,而不會一直掛在此函式呼叫上。在實際windows網路通訊軟體開發中,非同步非阻塞套接字是用的最多的。平常所說的c/s(客戶端/伺服器)結構的軟體就是非同步非阻塞模式的。

對於這些概念,初學者的理解也許只能似是而非,我將用乙個最簡單的例子說明非同步非阻塞socket的基本原理和工作機制。目的是讓初學者不僅對socket非同步非阻塞的概念有個非常透徹的理解,而且也給他們提供乙個用socket開發網路通訊應用程式的快速入門方法。作業系統是windows 98(或nt4.0),開發工具是visual c++6.0。

mfc提供了乙個非同步類casyncsocket,它封裝了非同步、非阻塞socket的基本功能,用它做常用的網路通訊軟體很方便。但它遮蔽了socket的非同步、非阻塞等概念,開發人員無需了解非同步、非阻塞socket的原理和工作機制。因此,建議初學者學習編網路通訊程式時,暫且不要用mfc提供的類,而先用winsock2  api,這樣有助於對非同步、非阻塞socket程式設計機制的理解。

為了簡單起見,伺服器端和客戶端的應用程式均是基於mfc的標準對話方塊,網路通訊部分基於winsock2 api實現。

先做伺服器端應用程式。

用mfc嚮導做乙個基於對話方塊的應用程式socketsever,注意第三步中不要選上windwos sockets選項。在做好工程後,建立乙個seversock,將它設定為非同步非阻塞模式,並為它註冊各種網路非同步事件,然後與自定義的網路非同步事件聯絡上,最後還要將它設定為監聽模式。在自定義的網路非同步事件的**函式中,你可以得到各種網路非同步事件,根據它們的型別,做不同的處理。下面將詳細介紹如何編寫相關**。

在socketseverdlg.h檔案的類定義之前增加如下定義:

#define  network_event  wm_user+166  file://定義網路事件

socket serversock; file://伺服器端socket

在類定義中增加如下定義:

class csocketseverdlg : cdialog

; 在socketseverdlg.cpp檔案中增加訊息對映,其中onnetevent是非同步事件**函式名:

on_message(network_event,onnetevent)

定義初始化網路函式,在socketseverdlg.cpp檔案的oninitdialog()中調此函式即可。

bool csocketseverdlg::initnetwork()

file://建立伺服器端套接字

serversock = socket(af_inet, sock_stream, ipproto_tcp);

if(serversock == invalid_socket)

file://繫結到本地乙個埠上

sockaddr_in localaddr;

localaddr.sin_family = af_inet;

localaddr.sin_port = htons(8888);  file://埠號不要與其他應用程式衝突

localaddr.sin_addr.s_addr = 0;

if(bind(serversock ,(struct sockaddr*)&localaddr,sizeof(sockaddr))

= = socket_error)

file://將seversock設定為非同步非阻塞模式,並為它註冊各種網路非同步事件,其 中   m_hwnd      

file://為應用程式的主對話方塊或主視窗的控制代碼

if(wsaasyncselect(serversock, m_hwnd, network_event,

fd_accept | fd_close | fd_read | fd_write) == socket_error)

listen(serversock, 5); file://設定偵聽模式

return true;

} 下面定義網路非同步事件的**函式

void csocketseverdlg::onnetevent(wparam wparam, lparam lparam) }

以下是發生在相應socket上的各種網路非同步事件的處理函式,其中onaccept傳進來的引數是伺服器端建立的套接字,onclose()、onreceive()和onsend()傳進來的引數均是伺服器端在接受客戶端連線時新建立的用與此客戶端通訊的socket。

void csocketseverdlg::onaccept(socket cursock)

void csocketseverdlg::onclose(socet cursock)

void csocketseverdlg::onsend(socet cursock)

Winsock開發網路通訊程式的經典入門

對於許多初學者來說,網路通訊程式的開發,普遍的乙個現象就是覺得難以入手。許多概念,諸如 同步 sync 非同步 async 阻塞 block 非阻塞 unblock 等,初學者往往迷惑不清,只知其所以而不知起所以然。同步方式指的是傳送方不等接收方響應,便接著發下個資料報的通訊方式 而非同步指傳送方發...

Winsock開發網路通訊程式的經典入門

對於許多初學者來說,網路通訊程式的開發,普遍的乙個現象就是覺得難以入手。許多概念,諸如 同步 sync 非同步 async 阻塞 block 非阻塞 unblock 等,初學者往往迷惑不清,只知其所以而不知起所以然。同步方式指的是傳送方不等接收方響應,便接著發下個資料報的通訊方式 而非同步指傳送方發...

用ACE開發網路通訊程式

該程式將演示如何將乙個簡單結構序列化後傳送到網路上,如何從網路上接收到資料後反序列化回結構。首先使用ace sock connector connect連線某個伺服器 使用ip位址和埠號 該伺服器上使用ace sock acceptor accept等待外部的連線請求。ace inet addr類進...