From: Hui Cao (huica) Date: Tue, 22 Nov 2016 21:39:29 +0000 (-0500) Subject: Merge pull request #717 in SNORT/snort3 from file_reg to master X-Git-Tag: 3.0.0-233~177 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=8b848817b0a202fd10bc3f6a7fb0da226cf19c8b;p=thirdparty%2Fsnort3.git Merge pull request #717 in SNORT/snort3 from file_reg to master Squashed commit of the following: commit 692030b8b6e8bee8ed0ca083cb74c2f5faa10dbd Author: huica Date: Mon Nov 21 15:30:07 2016 -0500 Fixed uu and qp decode issue Fixed file signature calculation for ftp Fixed file resume blocking --- diff --git a/src/hash/sfhashfcn.cc b/src/hash/sfhashfcn.cc index 349e381a8..f203025f2 100644 --- a/src/hash/sfhashfcn.cc +++ b/src/hash/sfhashfcn.cc @@ -158,3 +158,45 @@ void mix_str( } } +size_t str_to_hash(const uint8_t *str, int length ) +{ + size_t a,b,c,tmp; + int i,j,k,m; + a = b = c = 0; + for (i = 0, j = 0; i < length; i += 4) + { + tmp = 0; + k = length - i; + if (k > 4) + k=4; + + for (m = 0; m < k; m++) + { + tmp |= *(str + i + m) << m*8; + } + + switch (j) + { + case 0: + a += tmp; + break; + case 1: + b += tmp; + break; + case 2: + c += tmp; + break; + } + j++; + + if (j == 3) + { + mix(a,b,c); + j = 0; + } + } + + finalize(a,b,c); + return c; +} + diff --git a/src/hash/sfhashfcn.h b/src/hash/sfhashfcn.h index b23b37fb0..cd6287d66 100644 --- a/src/hash/sfhashfcn.h +++ b/src/hash/sfhashfcn.h @@ -55,6 +55,8 @@ SO_PUBLIC void mix_str( // n == 0 => strlen(s) const char* s, unsigned n = 0); +SO_PUBLIC size_t str_to_hash(const uint8_t *str, int length); + struct SFHASHFCN { unsigned seed; diff --git a/src/mime/decode_b64.cc b/src/mime/decode_b64.cc index 3e64f1f9a..75d6eda8a 100644 --- a/src/mime/decode_b64.cc +++ b/src/mime/decode_b64.cc @@ -29,7 +29,7 @@ void B64Decode::reset_decode_state() { reset_decoded_bytes(); - buffer->reset(); + buffer->reset_saved(); } DecodeResult B64Decode::decode_data(const uint8_t* start, const uint8_t* end) @@ -63,6 +63,8 @@ DecodeResult B64Decode::decode_data(const uint8_t* start, const uint8_t* end) act_encode_size = act_encode_size - i; buffer->save_buffer(buffer->get_encode_buff() + act_encode_size, i); } + else + buffer->reset_saved(); if (sf_base64decode(buffer->get_encode_buff(), act_encode_size, buffer->get_decode_buff(), buffer->get_decode_avail(), &act_decode_size) != 0) diff --git a/src/mime/decode_buffer.cc b/src/mime/decode_buffer.cc index 19483512e..98047265f 100644 --- a/src/mime/decode_buffer.cc +++ b/src/mime/decode_buffer.cc @@ -21,7 +21,7 @@ #include "decode_buffer.h" #include "utils/util.h" -void DecodeBuffer::reset() +void DecodeBuffer::reset_saved() { prev_encoded_bytes = 0; prev_encoded_buf = nullptr; diff --git a/src/mime/decode_buffer.h b/src/mime/decode_buffer.h index 81972884b..818f671a7 100644 --- a/src/mime/decode_buffer.h +++ b/src/mime/decode_buffer.h @@ -40,7 +40,7 @@ public: // Move forward buffer pointer void update_buffer(uint32_t act_encode_size, uint32_t act_decode_size); - void reset(); + void reset_saved(); uint8_t* get_decode_buff() { return decodeBuf; } uint8_t* get_encode_buff() { return encodeBuf; } uint32_t get_decode_bytes_read() { return decode_bytes_read; } diff --git a/src/mime/decode_qp.cc b/src/mime/decode_qp.cc index f5daea186..bf602cc19 100644 --- a/src/mime/decode_qp.cc +++ b/src/mime/decode_qp.cc @@ -28,7 +28,7 @@ void QPDecode::reset_decode_state() { reset_decoded_bytes(); - buffer->reset(); + buffer->reset_saved(); } DecodeResult QPDecode::decode_data(const uint8_t* start, const uint8_t* end) @@ -70,6 +70,8 @@ DecodeResult QPDecode::decode_data(const uint8_t* start, const uint8_t* end) buffer->save_buffer(buffer->get_encode_buff() + bytes_read, (act_encode_size - bytes_read)); act_encode_size = bytes_read; } + else + buffer->reset_saved(); decoded_bytes = act_decode_size; decodePtr = buffer->get_decode_buff(); diff --git a/src/mime/decode_uu.cc b/src/mime/decode_uu.cc index a31f3f414..2a8b503ea 100644 --- a/src/mime/decode_uu.cc +++ b/src/mime/decode_uu.cc @@ -33,7 +33,7 @@ void UUDecode::reset_decode_state() reset_decoded_bytes(); if (buffer) - buffer->reset(); + buffer->reset_saved(); begin_found = end_found = false; } @@ -96,6 +96,8 @@ DecodeResult UUDecode::decode_data(const uint8_t* start, const uint8_t* end) buffer->save_buffer(buffer->get_encode_buff() + bytes_read, (act_encode_size - bytes_read)); act_encode_size = bytes_read; } + else + buffer->reset_saved(); decoded_bytes = act_decode_size; decodePtr = buffer->get_decode_buff(); diff --git a/src/service_inspectors/ftp_telnet/ftp_data.cc b/src/service_inspectors/ftp_telnet/ftp_data.cc index 5f458a35f..f9adb2c9d 100644 --- a/src/service_inspectors/ftp_telnet/ftp_data.cc +++ b/src/service_inspectors/ftp_telnet/ftp_data.cc @@ -215,13 +215,6 @@ void FtpDataFlowData::handle_eof(Packet* p) initFilePosition(&data_ssn->position, get_file_processed_size(p->flow)); finalFilePosition(&data_ssn->position); - Stream::flush_request(p); - - if (!(data_ssn->packet_flags & FTPDATA_FLG_STOP)) - { - data_ssn->packet_flags |= FTPDATA_FLG_STOP; - FTPDataProcess(p, data_ssn, (uint8_t*)p->data, p->dsize); - } } //------------------------------------------------------------------------- diff --git a/src/service_inspectors/http_inspect/http_msg_body.cc b/src/service_inspectors/http_inspect/http_msg_body.cc index ed85bb778..cb3996580 100644 --- a/src/service_inspectors/http_inspect/http_msg_body.cc +++ b/src/service_inspectors/http_inspect/http_msg_body.cc @@ -141,15 +141,23 @@ void HttpMsgBody::do_file_processing() FileFlows* file_flows = FileFlows::get_file_flows(flow); const bool download = (source_id == SRC_SERVER); + HttpMsgRequest* request = transaction->get_request(); + + size_t file_index = 0; + + if ((request != nullptr) and (request->get_http_uri() != nullptr)) + { + file_index = request->get_http_uri()->get_file_proc_hash(); + } + if (file_flows->file_process(file_data.start, fp_length, - file_position, !download)) + file_position, !download, file_index)) { session_data->file_depth_remaining[source_id] -= fp_length; // With the first piece of the file we must provide the "name" which means URI if (front) { - HttpMsgRequest* request = transaction->get_request(); if (request != nullptr) { const Field& tranaction_uri = request->get_uri_norm_classic(); diff --git a/src/service_inspectors/http_inspect/http_stream_splitter_scan.cc b/src/service_inspectors/http_inspect/http_stream_splitter_scan.cc index 3d055702e..d861fb8d3 100644 --- a/src/service_inspectors/http_inspect/http_stream_splitter_scan.cc +++ b/src/service_inspectors/http_inspect/http_stream_splitter_scan.cc @@ -23,6 +23,7 @@ #include "file_api/file_flows.h" #include "http_enum.h" #include "http_field.h" +#include "http_msg_request.h" #include "http_test_manager.h" #include "http_test_input.h" #include "http_cutter.h" @@ -257,7 +258,19 @@ bool HttpStreamSplitter::finish(Flow* flow) { FileFlows* file_flows = FileFlows::get_file_flows(flow); const bool download = (source_id == SRC_SERVER); - file_flows->file_process(nullptr, 0, SNORT_FILE_END, !download); + + size_t file_index = 0; + + if (session_data->transaction[source_id] != nullptr) + { + HttpMsgRequest* request = session_data->transaction[source_id]->get_request(); + if ((request != nullptr) and (request->get_http_uri() != nullptr)) + { + file_index = request->get_http_uri()->get_file_proc_hash(); + } + } + + file_flows->file_process(nullptr, 0, SNORT_FILE_END, !download, file_index); } else { diff --git a/src/service_inspectors/http_inspect/http_uri.cc b/src/service_inspectors/http_inspect/http_uri.cc index 80878edd3..94a7878fe 100644 --- a/src/service_inspectors/http_inspect/http_uri.cc +++ b/src/service_inspectors/http_inspect/http_uri.cc @@ -26,6 +26,8 @@ #include "http_module.h" #include "http_uri.h" +#include "hash/sfhashfcn.h" + using namespace HttpEnums; HttpUri::~HttpUri() @@ -319,3 +321,15 @@ void HttpUri::normalize() classic_norm_allocated = true; } +size_t HttpUri::get_file_proc_hash() +{ + if (abs_path_hash) + return abs_path_hash; + + if (abs_path.length > 0 ) + { + abs_path_hash = str_to_hash(abs_path.start, abs_path.length); + } + + return abs_path_hash; +} diff --git a/src/service_inspectors/http_inspect/http_uri.h b/src/service_inspectors/http_inspect/http_uri.h index ce8f009f7..d1beb86ab 100644 --- a/src/service_inspectors/http_inspect/http_uri.h +++ b/src/service_inspectors/http_inspect/http_uri.h @@ -57,6 +57,7 @@ public: const Field& get_norm_query() { return query_norm; } const Field& get_norm_fragment() { return fragment_norm; } const Field& get_norm_classic() { return classic_norm; } + size_t get_file_proc_hash(); private: const Field uri; @@ -81,6 +82,7 @@ private: Field fragment_norm; Field classic_norm; bool classic_norm_allocated = false; + size_t abs_path_hash = 0; void normalize(); void parse_uri();