程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> C語言 >> C++ >> C++入門知識 >> windows下的C++ socket服務器(4)

windows下的C++ socket服務器(4)

編輯:C++入門知識

 handleAccept( buf[] = { (buf), );
    stringstream sstream;
    sstream <<>>>><< cmd <<   << filename << (cmd=== filename.substr(, filename.length() - 
         head = ;
         (!<<  << (filename.find()!=::npos|| filename.find()!==  (filename.find()!==  (filename.find()!==  (!file.eof())
 buf[, (buf)- n =

1 recv(socket_fd, buf, sizeof(buf), 0)和send(socket_fd, buf,n,0);

recv用於接收從客戶端發送來的消息,send用於向服務端發送消息

recv/send函數原型如下

int recv(SOCKET s,char FAR * buf,int len,int flags)/int send(SOCKET s,const char FAR * buf,int len,int flags);

第一個參數表示代表對方的socket,

第二個參數為接收讀取的信息的字符串

第三個參數為該字符串的大小

第四個參數可以用來控制讀寫操作

該值可以為一下幾種

0

MSG_DONTROUTE:不查找路由表/* send without using routing tables */
MSG_OOB:接受或發送帶外數據 /* process out-of-band data */

MSG_PEEK:查看數據,並不從系統緩沖區移走數據/* peek at incoming message */
MSG_WAITALL :等待任何數據/* do not complete until packet is completely filled */

etc…

解釋:
MSG_DONTROUTE:是send函數使用的標志.這個標志告訴IP協議.目的主機在本地網絡上面,沒有必要查找路由表.這個標志一般用網絡診斷和路由程式裡面。
MSG_OOB:表示能夠接收和發送帶外的數據.關於帶外數據我們以後會解釋的.
MSG_PEEK:是recv函數的使用標志,表示只是從系統緩沖區中讀取內容,而不清除系統緩沖區的內容。這樣下次讀的時候,仍然是相同的內容。一般在有多個進程讀寫數據時能夠使用這個標志。

MSG_WAITALL:是recv函數的使用標志,表示等到任何的信息到達時才返回。使用這個標志的時候recv會一直阻塞,直到指定的條件滿足,或是發生了錯誤。

    1)當讀到了指定的字節時,函數正常返回,返回值等於len

    2)當讀到了文檔的結尾時,函數正常返回.返回值小於len

    3)當操作發生錯誤時,返回-1,且配置錯誤為相應的錯誤號(errno)
其他的幾個選項,但是我們實際上用的很少.

 

關於其他的發送和接收函數

recvfrom/sendto

這兩個函數一般用在UDP中。

函數原型如下

int  recvfrom(SOCKET s,char FAR * buf,int len,int flags,struct sockaddr FAR * from,int FAR * fromlen);

int  sendto(SOCKET s,const char FAR * buf,int len,int flags,const struct sockaddr FAR * to,int tolen);

 

2 stringstream sstream;

字符串讀寫流,這裡用於將char buf[1024]的數據按默認的間隔符讀到cmd和filename中,關於cmd和filename的具體含義見3

也可以用來將數字轉換為字符串

例如

stringstream sstream;

sstream <<123456789;
string a;
sstream >> a;
cout << a << endl;

將數字123456789轉換為了字符串

 

 

3 HTTP協議請求

當客戶端連接到服務端時,會發出一個http請求

http請求由三部分組成,分別是:請求行、消息報頭、請求正文

這裡只對請求行進行介紹

請求行以一個方法符號開頭,以空格分開,後面跟著請求的URI和協議的版本,格式如下:Method Request-URI HTTP-Version CRLF  

其中 Method表示請求方法;Request-URI是一個統一資源標識符;HTTP-Version表示請求的HTTP協議版本;CRLF表示回車和換行(除了作為結尾的CRLF外,不允許出現單獨的CR或LF字符)。

請求方法(所有方法全為大寫)有多種,各個方法的解釋如下:
GET     請求獲取Request-URI所標識的資源
POST    在Request-URI所標識的資源後附加新的數據
HEAD    請求獲取由Request-URI所標識的資源的響應消息報頭
PUT     請求服務器存儲一個資源,並用Request-URI作為其標識
DELETE  請求服務器刪除Request-URI所標識的資源
TRACE   請求服務器回送收到的請求信息,主要用於測試或診斷
CONNECT 保留將來使用
OPTIONS 請求查詢服務器的性能,或者查詢與資源相關的選項和需求

在本程序中只對GET請求進行處理,將請求方法讀入cmd中,和Request-URL讀入filename中,判斷是否為GET,並獲請求的資源名稱

 

4 file.open(filename ,ifstream::binary);

打開客戶所請求的文件,這裡使用二進制的方式打開是為了方便對圖片進行傳輸

 

 

5 string head = "HTTP/1.0 200 OK\r\nContent - type:text/plain\r\n\r\n";

在接收和解釋請求消息後,服務器返回一個HTTP響應消息。

HTTP響應也是由三個部分組成,分別是:狀態行、消息報頭、響應正文

1)、狀態行格式如下:
HTTP-Version Status-Code Reason-Phrase CRLF

其中,HTTP-Version表示服務器HTTP協議的版本;Status-Code表示服務器發回的響應狀態代碼;Reason-Phrase表示狀態代碼的文本描述。

常見狀態代碼、狀態描述、說明:

200 OK      //客戶端請求成功
400 Bad Request  //客戶端請求有語法錯誤,不能被服務器所理解
401 Unauthorized //請求未經授權,這個狀態代碼必須和WWW-Authenticate報頭域一起使用 
403 Forbidden  //服務器收到請求,但是拒絕提供服務
404 Not Found  //請求資源不存在,eg:輸入了錯誤的URL
500 Internal Server Error //服務器發生不可預期的錯誤
503 Server Unavailable  //服務器當前不能處理客戶端的請求,一段時間後可能恢復正常

 

Content-Type表示正在傳輸的類型

Content - type:text/plain:普通文本

Content - type:text/html:html網頁

Content - type:image/png:png圖片

Content - type:image/jpg:jpg圖片

2)響應報頭允許服務器傳遞不能放在狀態行中的附加響應信息,以及關於服務器的信息和對Request-URI所標識的資源進行下一步訪問的信息。在這不做詳細介紹

3)響應正文就是服務器返回的資源的內容

 關於http協議更詳細的部分可以參照http://blog.csdn.net/gueter/article/details/1524447 HTTP協議詳解

 

 

6 獲得響應正文並寫到客戶端

char buf[1024];
memset(buf, 0, sizeof(buf));//初始化

file.read(buf,sizeof(buf)-1);//由於我們使用二進制的方式打開的文件所以使用了read方法

int n = file.gcount();//gcount()返回最後一個非格式化的抽取方法讀取的字符數,因為有時候讀到的會小於1023個

send(socket_fd, buf,n,0);//將buf中的n個字符發送到客戶端

 

7

file.close()和closesocket(socket_fd)

關閉打開的文件和socket_fd

 

 程序代碼下載:http://files.cnblogs.com/magicsoar/WebServer.rar

p.s

程序做的還不是很完善,對一些情況比如send,reve是否正在執行也沒有進行檢查,客戶端請求的文件不存在也沒有返回404,

我會在以後對程序進行完善的,並將一些新的心得寫出來。

第一次寫博客,希望大家能指出我的不足來,我會虛心接受並改進的。

接下來可能會將自己大一大二做的軟件,游戲拿出來,寫一寫,與大家分享,或者是讀書的心得等,也可能會是我目前正在學習C++網絡爬蟲。

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved