use std::mem::transmute;
use crate::applayer::*;
-use crate::core::{self, sc_detect_engine_state_free};
+use crate::core::{self, *};
use crate::dcerpc::parser;
use nom::error::ErrorKind;
use nom::number::Endianness;
pub tc_ssn_gap: bool,
pub ts_ssn_trunc: bool, /// true if Truncated in this direction
pub tc_ssn_trunc: bool,
+ pub flow: Option<*const core::Flow>,
}
impl DCERPCState {
tc_ssn_gap: false,
ts_ssn_trunc: false,
tc_ssn_trunc: false,
+ flow: None,
};
}
tx.req_lost = true;
}
tx.req_done = true;
+ if let Some(flow) = self.flow {
+ sc_app_layer_parser_trigger_raw_stream_reassembly(flow, dir.into());
+ }
}
} else if self.tc_ssn_gap && dir == core::STREAM_TOCLIENT {
for tx in &mut self.transactions {
}
tx.req_done = true;
tx.resp_done = true;
+ if let Some(flow) = self.flow {
+ sc_app_layer_parser_trigger_raw_stream_reassembly(flow, dir.into());
+ }
}
}
}
let mut tx = self.create_tx(call_id);
tx.req_cmd = self.get_hdr_type().unwrap_or(0);
tx.req_done = true;
+ if let Some(flow) = self.flow {
+ sc_app_layer_parser_trigger_raw_stream_reassembly(flow, core::STREAM_TOSERVER.into());
+ }
tx.frag_cnt_ts = 1;
self.transactions.push(tx);
// Bytes parsed with `parse_dcerpc_bind` + (bytes parsed per bindctxitem [44] * number
);
tx.req_done = true;
tx.frag_cnt_ts = 1;
+ if let Some(flow) = self.flow {
+ sc_app_layer_parser_trigger_raw_stream_reassembly(flow, core::STREAM_TOSERVER.into());
+ }
}
DCERPC_TYPE_RESPONSE => {
retval = evaluate_stub_params(
);
tx.resp_done = true;
tx.frag_cnt_tc = 1;
+ if let Some(flow) = self.flow {
+ sc_app_layer_parser_trigger_raw_stream_reassembly(flow, core::STREAM_TOCLIENT.into());
+ }
}
_ => {
SCLogDebug!("Unrecognized packet type");
};
tx.resp_done = true;
tx.frag_cnt_tc = 1;
+ if let Some(flow) = self.flow {
+ sc_app_layer_parser_trigger_raw_stream_reassembly(flow, core::STREAM_TOCLIENT.into());
+ }
self.handle_bind_cache(current_call_id, false);
}
DCERPC_TYPE_REQUEST => {
#[no_mangle]
pub extern "C" fn rs_dcerpc_parse_request(
- _flow: *mut core::Flow, state: &mut DCERPCState, _pstate: *mut std::os::raw::c_void,
+ flow: *mut core::Flow, state: &mut DCERPCState, _pstate: *mut std::os::raw::c_void,
input: *const u8, input_len: u32, _data: *mut std::os::raw::c_void, flags: u8,
) -> AppLayerResult {
SCLogDebug!("Handling request: input {:p} input_len {} flags {:x} EOF {}",
}
if input_len > 0 && input != std::ptr::null_mut() {
let buf = build_slice!(input, input_len as usize);
+ state.flow = Some(flow);
return state.handle_input_data(buf, core::STREAM_TOSERVER);
}
AppLayerResult::err()
#[no_mangle]
pub extern "C" fn rs_dcerpc_parse_response(
- _flow: *mut core::Flow, state: &mut DCERPCState, _pstate: *mut std::os::raw::c_void,
+ flow: *mut core::Flow, state: &mut DCERPCState, _pstate: *mut std::os::raw::c_void,
input: *const u8, input_len: u32, _data: *mut std::os::raw::c_void, flags: u8,
) -> AppLayerResult {
if flags & core::STREAM_EOF != 0 && input_len == 0 {
if input_len > 0 {
if input != std::ptr::null_mut() {
let buf = build_slice!(input, input_len as usize);
+ state.flow = Some(flow);
return state.handle_input_data(buf, core::STREAM_TOCLIENT);
}
}
dce_state.ts_ssn_trunc = true;
for tx in &mut dce_state.transactions {
tx.req_done = true;
+ if let Some(flow) = dce_state.flow {
+ sc_app_layer_parser_trigger_raw_stream_reassembly(flow, core::STREAM_TOSERVER.into());
+ }
}
SCLogDebug!("dce_state.ts_ssn_trunc = true; txs {}", dce_state.transactions.len());
} else if direction & core::STREAM_TOCLIENT != 0 {
dce_state.tc_ssn_trunc = true;
for tx in &mut dce_state.transactions {
tx.resp_done = true;
+ if let Some(flow) = dce_state.flow {
+ sc_app_layer_parser_trigger_raw_stream_reassembly(flow, core::STREAM_TOCLIENT.into());
+ }
}
SCLogDebug!("dce_state.tc_ssn_trunc = true; txs {}", dce_state.transactions.len());
}