上一次說到通過
WinHTTP
來接收網(wǎng)絡數(shù)據(jù),但沒有具體介紹怎么樣接收,現(xiàn)在就來分析這方面的代碼。首先是通過函數(shù)
WinHttpQueryHeaders
來查詢
HTTP
協(xié)議頭的大小,接著還是通過函數(shù)
WinHttpQueryHeaders
把數(shù)據(jù)接收到緩沖區(qū)里。下面這段代碼,就是做這樣的事情:
#001
?
int HttpTransactionWinHttp::DidReceiveHeaders() {
#002
???
session_callback_->set_load_state(LOAD_STATE_IDLE);
#003
?
第一次調用函數(shù)
WinHttpQueryHeaders
查看接收到協(xié)議頭的大小。
#004
???
DWORD size = 0;
#005
???
if (!WinHttpQueryHeaders(request_handle_,
#006
????????????????????????????
WINHTTP_QUERY_RAW_HEADERS,
#007
????????????????????????????
WINHTTP_HEADER_NAME_BY_INDEX,
#008
????????????????????????????
NULL,
#009
????????????????????????????
&size,
#010
????????????????????????????
WINHTTP_NO_HEADER_INDEX)) {
#011
?????
DWORD error = GetLastError();
#012
?????
if (error != ERROR_INSUFFICIENT_BUFFER) {
#013
???????
DLOG(ERROR) << "WinHttpQueryHeaders failed: " << GetLastError();
#014
???????
return TranslateLastOSError();
#015
?????
}
#016
?????
// OK, size should tell us how much to allocate...
#017
?????
DCHECK(size > 0);
#018
???
}
#019
?
第二次調用函數(shù)
WinHttpQueryHeaders
來接收協(xié)議頭的數(shù)據(jù)。
#020
???
std::wstring raw_headers;
#021
?
#022
???
// 'size' is the number of bytes rather than the number of characters.
#023
???
DCHECK(size % 2 == 0);
#024
???
if (!WinHttpQueryHeaders(request_handle_,
#025
????
????????????????????????
WINHTTP_QUERY_RAW_HEADERS,
#026
????????????????????????????
WINHTTP_HEADER_NAME_BY_INDEX,
#027
????????????????????????????
WriteInto(&raw_headers, size/2 + 1),
#028
????????????????????????????
&size,
#029
????????????????????????????
WINHTTP_NO_HEADER_INDEX)) {
#030
?????
DLOG(ERROR) << "WinHttpQueryHeaders failed: " << GetLastError();
#031
?????
return TranslateLastOSError();
#032
???
}
#033
?
設置回應的一些狀態(tài)。
#034
???
response_.response_time = Time::Now();
#035
?
#036
???
// From experimentation, it appears that WinHttp translates non-ASCII bytes
#037
???
// found in the response headers to UTF-16 assuming that they are encoded
#038
???
// using the default system charset.
?
We attempt to undo that here.
#039
???
response_.headers =
#040
???????
new HttpResponseHeaders(base::SysWideToNativeMB(raw_headers));
#041
?
#042
???
// WinHTTP truncates a response longer than 2GB.
?
Perhaps it stores the
#043
???
// response's content length in a signed 32-bit integer.
?
We fail rather
#044
??
?
// than reading a truncated response.
#045
???
if (response_.headers->GetContentLength() > 0x80000000)
#046
?????
return ERR_FILE_TOO_BIG;
#047
?
#048
???
response_.vary_data.Init(*request_, *response_.headers);
#049
???
PopulateAuthChallenge();
#050
?
#051
?
??
// Unfortunately, WinHttp does not close the connection when a non-keepalive
#052
???
// response is _not_ followed by the server closing the connection.
?
So, we
#053
???
// attempt to hack around this bug.
#054
???
if (!response_.headers->IsKeepAlive())
#055
?????
content_length_remaining_ = response_.headers->GetContentLength();
#056
?
#057
???
return OK;
#058
?
}
通過上面的函數(shù)處理,就可以收到
HTTP
協(xié)議頭的數(shù)據(jù),這樣就可以進一步處理了。那么接著下來就是收到
HTTP
協(xié)議里的數(shù)據(jù),這個主要通過下面的函數(shù)來接收到的,如下:
#001
?
BOOL HttpTransactionWinHttp::SessionCallback::ReadData(
#002
?????
HINTERNET request_handle) {
#003
???
DCHECK(bytes_available_ >= 0);
#004
???
char* buf = read_buf_;
#005
???
read_buf_ = NULL;
#006
???
int bytes_to_read = std::min(bytes_available_, read_buf_len_);
#007
???
read_buf_len_ = 0;
#008
???
if (!bytes_to_read)
#009
?????
bytes_to_read = 1;
#010
?
#011
???
// Because of how WinHTTP fills memory when used asynchronously, Purify isn't
#012
???
// able to detect that it's been initialized, so it scans for 0xcd in the
#013
???
// buffer and reports UMRs (uninitialized memory reads) for those individual
#014
???
// bytes. We override that to avoid the false error reports.
#015
???
// See http://b/issue?id=1173916.
#016
???
base::MemoryDebug::MarkAsInitialized(buf, bytes_to_read);
#017
???
return
WinHttpReadData
(request_handle, buf, bytes_to_read, NULL);
#018
?
}
上面通過判斷可以接收到多少字節(jié),然后通過函數(shù)
WinHttpReadData
把數(shù)據(jù)保存到緩沖區(qū)
read_buf_
里,在這個緩沖區(qū)里保存了所有網(wǎng)絡接收到的數(shù)據(jù),那么這些數(shù)據(jù)又將要流向何方呢?下一次再來分析這個問題。
更多文章、技術交流、商務合作、聯(lián)系博主
微信掃碼或搜索:z360901061

微信掃一掃加我為好友
QQ號聯(lián)系: 360901061
您的支持是博主寫作最大的動力,如果您喜歡我的文章,感覺我的文章對您有幫助,請用微信掃描下面二維碼支持博主2元、5元、10元、20元等您想捐的金額吧,狠狠點擊下面給點支持吧,站長非常感激您!手機微信長按不能支付解決辦法:請將微信支付二維碼保存到相冊,切換到微信,然后點擊微信右上角掃一掃功能,選擇支付二維碼完成支付。
【本文對您有幫助就好】元
