mirror of
https://github.com/wownero/wownero.git
synced 2026-10-17 07:31:35 +02:00
epee: prevent log injection from malformed HTTP headers
(cherry picked from commit 281c1d41aae7b579fa1307d82622e18abcd038ff)
This commit is contained in:
@@ -594,7 +594,7 @@ namespace net_utils
|
||||
}
|
||||
if(!get_chunk_head(m_chunked_cache, m_len_in_remain, is_matched))
|
||||
{
|
||||
LOG_ERROR("http_stream_filter::handle_chunked(*) Failed to get length from chunked head:" << m_chunked_cache);
|
||||
LOG_ERROR("http_stream_filter::handle_chunked(*) Failed to get length from chunked head (" << m_chunked_cache.size() << " bytes)");
|
||||
m_state = reciev_machine_state_error;
|
||||
return false;
|
||||
}
|
||||
@@ -660,7 +660,7 @@ namespace net_utils
|
||||
while(cur < m_cache_to_process.size())
|
||||
{
|
||||
const size_t line_end = m_cache_to_process.find('\n', cur);
|
||||
CHECK_AND_ASSERT_MES(line_end != std::string::npos, false, "http_stream_filter::parse_cached_header() invalid header in: " << m_cache_to_process);
|
||||
CHECK_AND_ASSERT_MES(line_end != std::string::npos, false, "http_stream_filter::parse_cached_header() invalid header (" << m_cache_to_process.size() << " bytes)");
|
||||
|
||||
boost::string_view line(m_cache_to_process.data() + cur, line_end - cur);
|
||||
cur = line_end + 1;
|
||||
@@ -670,7 +670,7 @@ namespace net_utils
|
||||
|
||||
boost::string_view name;
|
||||
boost::string_view value;
|
||||
CHECK_AND_ASSERT_MES(detail::parse_header_line(line, name, value), false, "http_stream_filter::parse_cached_header() invalid header in: " << m_cache_to_process);
|
||||
CHECK_AND_ASSERT_MES(detail::parse_header_line(line, name, value), false, "http_stream_filter::parse_cached_header() invalid header (" << m_cache_to_process.size() << " bytes)");
|
||||
|
||||
std::string key(name.data(), name.size());
|
||||
std::string val(value.data(), value.size());
|
||||
@@ -704,25 +704,25 @@ namespace net_utils
|
||||
{
|
||||
//First line response, look like this: "HTTP/1.1 200 OK"
|
||||
const char *ptr = m_header_cache.c_str();
|
||||
CHECK_AND_ASSERT_MES(!memcmp(ptr, "HTTP/", 5), false, "Invalid first response line: " + m_header_cache);
|
||||
CHECK_AND_ASSERT_MES(!memcmp(ptr, "HTTP/", 5), false, "Invalid first response line (" << m_header_cache.size() << " header bytes)");
|
||||
ptr += 5;
|
||||
CHECK_AND_ASSERT_MES(epee::misc_utils::parse::isdigit(*ptr), false, "Invalid first response line: " + m_header_cache);
|
||||
CHECK_AND_ASSERT_MES(epee::misc_utils::parse::isdigit(*ptr), false, "Invalid first response line (" << m_header_cache.size() << " header bytes)");
|
||||
unsigned long ul;
|
||||
char *end;
|
||||
ul = strtoul(ptr, &end, 10);
|
||||
CHECK_AND_ASSERT_MES(ul <= INT_MAX && *end =='.', false, "Invalid first response line: " + m_header_cache);
|
||||
CHECK_AND_ASSERT_MES(ul <= INT_MAX && *end =='.', false, "Invalid first response line (" << m_header_cache.size() << " header bytes)");
|
||||
m_response_info.m_http_ver_hi = ul;
|
||||
ptr = end + 1;
|
||||
CHECK_AND_ASSERT_MES(epee::misc_utils::parse::isdigit(*ptr), false, "Invalid first response line: " + m_header_cache + ", ptr: " << ptr);
|
||||
CHECK_AND_ASSERT_MES(epee::misc_utils::parse::isdigit(*ptr), false, "Invalid first response line (" << m_header_cache.size() << " header bytes)");
|
||||
ul = strtoul(ptr, &end, 10);
|
||||
CHECK_AND_ASSERT_MES(ul <= INT_MAX && isblank(*end), false, "Invalid first response line: " + m_header_cache + ", ptr: " << ptr);
|
||||
CHECK_AND_ASSERT_MES(ul <= INT_MAX && isblank(*end), false, "Invalid first response line (" << m_header_cache.size() << " header bytes)");
|
||||
m_response_info.m_http_ver_lo = ul;
|
||||
ptr = end + 1;
|
||||
while (isblank(*ptr))
|
||||
++ptr;
|
||||
CHECK_AND_ASSERT_MES(epee::misc_utils::parse::isdigit(*ptr), false, "Invalid first response line: " + m_header_cache);
|
||||
CHECK_AND_ASSERT_MES(epee::misc_utils::parse::isdigit(*ptr), false, "Invalid first response line (" << m_header_cache.size() << " header bytes)");
|
||||
ul = strtoul(ptr, &end, 10);
|
||||
CHECK_AND_ASSERT_MES(ul >= 100 && ul <= 999 && isspace(*end), false, "Invalid first response line: " + m_header_cache);
|
||||
CHECK_AND_ASSERT_MES(ul >= 100 && ul <= 999 && isspace(*end), false, "Invalid first response line (" << m_header_cache.size() << " header bytes)");
|
||||
m_response_info.m_response_code = ul;
|
||||
ptr = end;
|
||||
// ignore the optional text, till the end
|
||||
@@ -730,7 +730,7 @@ namespace net_utils
|
||||
++ptr;
|
||||
if (*ptr == '\r')
|
||||
++ptr;
|
||||
CHECK_AND_ASSERT_MES(*ptr == '\n', false, "Invalid first response line: " << m_header_cache);
|
||||
CHECK_AND_ASSERT_MES(*ptr == '\n', false, "Invalid first response line (" << m_header_cache.size() << " header bytes)");
|
||||
++ptr;
|
||||
|
||||
m_header_cache.erase(0, ptr - m_header_cache.c_str());
|
||||
@@ -762,7 +762,7 @@ namespace net_utils
|
||||
std::string fake_str; //gcc error workaround
|
||||
|
||||
bool res = parse_header(m_response_info.m_header_info, m_header_cache);
|
||||
CHECK_AND_ASSERT_MES(res, false, "http_stream_filter::analize_cached_reply_header_and_invoke_state(): failed to anilize reply header: " << m_header_cache);
|
||||
CHECK_AND_ASSERT_MES(res, false, "http_stream_filter::analize_cached_reply_header_and_invoke_state(): failed to anilize reply header (" << m_header_cache.size() << " bytes)");
|
||||
|
||||
set_reply_content_encoder();
|
||||
|
||||
@@ -784,7 +784,7 @@ namespace net_utils
|
||||
string_tools::trim(m_response_info.m_header_info.m_transfer_encoding);
|
||||
if(string_tools::compare_no_case(m_response_info.m_header_info.m_transfer_encoding, "chunked"))
|
||||
{
|
||||
LOG_ERROR("Wrong Transfer-Encoding:" << m_response_info.m_header_info.m_transfer_encoding);
|
||||
LOG_ERROR("Wrong Transfer-Encoding (" << m_response_info.m_header_info.m_transfer_encoding.size() << " bytes)");
|
||||
m_state = reciev_machine_state_error;
|
||||
return false;
|
||||
}
|
||||
@@ -797,7 +797,7 @@ namespace net_utils
|
||||
//In the response header the length was specified
|
||||
if(!content_len_valid)
|
||||
{
|
||||
LOG_ERROR("http_stream_filter::analize_cached_reply_header_and_invoke_state(): Failed to get_len_from_content_lenght();, m_query_info.m_content_length="<<m_response_info.m_header_info.m_content_length);
|
||||
LOG_ERROR("http_stream_filter::analize_cached_reply_header_and_invoke_state(): Failed to get_len_from_content_lenght() (" << m_response_info.m_header_info.m_content_length.size() << " bytes)");
|
||||
m_state = reciev_machine_state_error;
|
||||
return false;
|
||||
}
|
||||
@@ -823,7 +823,7 @@ namespace net_utils
|
||||
}else
|
||||
{ //Apparently there are no signs of the form of transfer, will receive data until the connection is closed
|
||||
m_state = reciev_machine_state_error;
|
||||
MERROR("Undefined transfer type, consider http_body_transfer_connection_close method. header: " << m_header_cache);
|
||||
MERROR("Undefined transfer type, consider http_body_transfer_connection_close method (" << m_header_cache.size() << " header bytes)");
|
||||
return false;
|
||||
}
|
||||
return false;
|
||||
@@ -854,7 +854,7 @@ namespace net_utils
|
||||
boundary = result[7];
|
||||
else
|
||||
{
|
||||
LOG_ERROR("Failed to match boundary in content-type=" << head_info.m_content_type);
|
||||
LOG_ERROR("Failed to match boundary in content-type (" << head_info.m_content_type.size() << " bytes)");
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
|
||||
@@ -101,7 +101,7 @@ namespace net_utils
|
||||
entry.m_etc_header_fields.push_back(std::pair<std::string, std::string>(result[field_etc_name], result[field_val]));
|
||||
else
|
||||
{
|
||||
LOG_ERROR("simple_http_connection_handler::parse_header() not matched last entry in:"<<std::string(it_current_bound, it_end));
|
||||
LOG_ERROR("simple_http_connection_handler::parse_header() not matched last entry (" << std::distance(it_current_bound, it_end) << " bytes)");
|
||||
}
|
||||
|
||||
it_current_bound = result[(int)result.size()-1].first;
|
||||
@@ -122,7 +122,7 @@ namespace net_utils
|
||||
|
||||
if(!parse_header(it_begin, end_header_it+4, entry))
|
||||
{
|
||||
LOG_ERROR("Failed to parse header:" << std::string(it_begin, end_header_it+2));
|
||||
LOG_ERROR("Failed to parse header (" << std::distance(it_begin, end_header_it + 2) << " bytes)");
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -139,7 +139,7 @@ namespace net_utils
|
||||
std::string boundary;
|
||||
if(!match_boundary(content_type, boundary))
|
||||
{
|
||||
MERROR("Failed to match boundary in content type: " << content_type);
|
||||
MERROR("Failed to match boundary in content type (" << content_type.size() << " bytes)");
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -430,7 +430,7 @@ namespace net_utils
|
||||
}else
|
||||
{
|
||||
m_state = http_state_error;
|
||||
LOG_ERROR_CC(m_conn_context, "simple_http_connection_handler<t_connection_context>::handle_invoke_query_line(): Failed to match first line: " << m_cache);
|
||||
LOG_ERROR_CC(m_conn_context, "simple_http_connection_handler<t_connection_context>::handle_invoke_query_line(): Failed to match first line (" << m_cache.size() << " bytes)");
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -454,14 +454,14 @@ namespace net_utils
|
||||
template<class t_connection_context>
|
||||
bool simple_http_connection_handler<t_connection_context>::analize_cached_request_header_and_invoke_state(size_t pos)
|
||||
{
|
||||
LOG_PRINT_L3("HTTP HEAD:\r\n" << m_cache.substr(0, pos));
|
||||
LOG_PRINT_L3("HTTP HEAD: " << pos << " bytes");
|
||||
|
||||
m_query_info.m_full_request_buf_size = pos;
|
||||
m_query_info.m_request_head.assign(m_cache.begin(), m_cache.begin()+pos);
|
||||
|
||||
if(!parse_cached_header(m_query_info.m_header_info, m_cache, pos))
|
||||
{
|
||||
LOG_ERROR_CC(m_conn_context, "simple_http_connection_handler<t_connection_context>::analize_cached_request_header_and_invoke_state(): failed to anilize request header: " << m_cache);
|
||||
LOG_ERROR_CC(m_conn_context, "simple_http_connection_handler<t_connection_context>::analize_cached_request_header_and_invoke_state(): failed to anilize request header (" << pos << " bytes)");
|
||||
m_state = http_state_error;
|
||||
return false;
|
||||
}
|
||||
@@ -477,7 +477,7 @@ namespace net_utils
|
||||
m_body_transfer_type = http_body_transfer_measure;
|
||||
if(!get_len_from_content_lenght(m_query_info.m_header_info.m_content_length, m_len_summary))
|
||||
{
|
||||
LOG_ERROR_CC(m_conn_context, "simple_http_connection_handler<t_connection_context>::analize_cached_request_header_and_invoke_state(): Failed to get_len_from_content_lenght();, m_query_info.m_content_length="<<m_query_info.m_header_info.m_content_length);
|
||||
LOG_ERROR_CC(m_conn_context, "simple_http_connection_handler<t_connection_context>::analize_cached_request_header_and_invoke_state(): Failed to get_len_from_content_lenght() (" << m_query_info.m_header_info.m_content_length.size() << " bytes)");
|
||||
m_state = http_state_error;
|
||||
return false;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user