65.9K
CodeProject is changing. Read more.
Home

CAtlHttpClientT Bug Fixed

starIconstarIconstarIconstarIcon
emptyStarIcon
starIcon

4.91/5 (5 votes)

Mar 8, 2004

viewsIcon

46824

A fix of ATL 7 CAtlHttpClientT code

Introduction

This article provides a small but important fix to the ATL 7 CAtlHttpClientT class.

Background

The HTTP/1.1 specification supports chunked transfer encoding of the message body (see section 3.6 of RFC 2068). Chunked transfer encoding modifies the body of a message in order to transfer it as a series of chunks, each with its own size indicator. Unlike usual HTTP file transfer, chunked transfer does not specify the transfer length, i.e. there is no "Content-Length:" header transferred – the sender adds a "Transfer-Encoding: chunked" header instead.

ATL 7 Bug

In ATL 7 HTTP client transactions are performed with the CAtlHttpClientT class. This class supports, in particular, chunked-transfer encoding/decoding. It contains a protected method IsMsgBodyChunked() that checks whether the message body is chunked. The code of this method looks as following (ATLHTTP.INL, lines 1254 - 1263):

template<class TSocketClass>
inline bool CAtlHttpClientT<TSocketClass>::IsMsgBodyChunked()
{
  CString strValue;
  return (
    GetHeaderValue(_T("Transfer-Encoding"), strValue) &&
    strValue == _T("chunked") // m_HeaderMap lower cases 
                    // all values before storing
  );
}

Unfortunately, strValue here may end with CR/LF, i.e. be equal to "chunked\r\n" (I have met this situation while receiving files from the Microsoft IIS). In this case CAtlHttpClientT does not recognize chunked-transfer encoding and returns the raw response body. Below is a bug fix:

template<class TSocketClass>
inline bool CAtlHttpClientT<TSocketClass>::IsMsgBodyChunked()
{
  CString strValue;
  if (!GetHeaderValue(_T("Transfer-Encoding"), strValue))
    return false;
  if (strValue.Right(2) == _T("\r\n"))
    strValue = strValue.Left(strValue.GetLength() - 2);
  // m_HeaderMap lower cases all values before storing
  return strValue == _T("chunked");
}