dcerpc: Add rust registration function

Get rid of the C glue code and move registration completely to Rust.
pull/6139/head
Shivani Bhardwaj 5 years ago committed by Victor Julien
parent a0a09a102b
commit bac69af7e4

@ -23,6 +23,7 @@ use nom::error::ErrorKind;
use nom::number::Endianness;
use nom;
use std::cmp;
use std::ffi::CString;
// Constant DCERPC UDP Header length
pub const DCERPC_HDR_LEN: u16 = 16;
@ -108,6 +109,8 @@ pub const DCERPC_TYPE_ORPHANED: u8 = 19;
pub const DCERPC_TYPE_RTS: u8 = 20;
pub const DCERPC_TYPE_UNKNOWN: u8 = 99;
pub static mut ALPROTO_DCERPC: AppProto = ALPROTO_UNKNOWN;
pub fn dcerpc_type_string(t: u8) -> String {
match t {
DCERPC_TYPE_REQUEST => "REQUEST",
@ -1365,7 +1368,6 @@ fn probe(input: &[u8]) -> (bool, bool) {
}
}
#[no_mangle]
pub extern "C" fn rs_dcerpc_probe_tcp(_f: *const core::Flow, direction: u8, input: *const u8,
len: u32, rdir: *mut u8) -> AppProto
{
@ -1387,9 +1389,93 @@ pub extern "C" fn rs_dcerpc_probe_tcp(_f: *const core::Flow, direction: u8, inpu
if direction & (core::STREAM_TOSERVER|core::STREAM_TOCLIENT) != dir {
unsafe { *rdir = dir };
}
return 1;
return unsafe { ALPROTO_DCERPC };
}
return unsafe { core::ALPROTO_FAILED };
}
fn register_pattern_probe() -> i8 {
unsafe {
if AppLayerProtoDetectPMRegisterPatternCSwPP(IPPROTO_TCP as u8, ALPROTO_DCERPC,
b"|05 00|\0".as_ptr() as *const std::os::raw::c_char, 2, 0,
core::STREAM_TOSERVER, rs_dcerpc_probe_tcp, 0, 0) < 0 {
SCLogDebug!("TOSERVER => AppLayerProtoDetectPMRegisterPatternCSwPP FAILED");
return -1;
}
if AppLayerProtoDetectPMRegisterPatternCSwPP(IPPROTO_TCP as u8, ALPROTO_DCERPC,
b"|05 00|\0".as_ptr() as *const std::os::raw::c_char, 2, 0,
core::STREAM_TOCLIENT, rs_dcerpc_probe_tcp, 0, 0) < 0 {
SCLogDebug!("TOCLIENT => AppLayerProtoDetectPMRegisterPatternCSwPP FAILED");
return -1;
}
}
0
}
// Parser name as a C style string.
pub const PARSER_NAME: &'static [u8] = b"dcerpc\0";
#[no_mangle]
pub unsafe extern "C" fn rs_dcerpc_register_parser() {
let default_port = CString::new("[0:65355]").unwrap();
let parser = RustParser {
name: PARSER_NAME.as_ptr() as *const std::os::raw::c_char,
default_port: default_port.as_ptr(),
ipproto: IPPROTO_TCP,
probe_ts: None,
probe_tc: None,
min_depth: 0,
max_depth: 16,
state_new: rs_dcerpc_state_new,
state_free: rs_dcerpc_state_free,
tx_free: rs_dcerpc_state_transaction_free,
parse_ts: rs_dcerpc_parse_request,
parse_tc: rs_dcerpc_parse_response,
get_tx_count: rs_dcerpc_get_tx_cnt,
get_tx: rs_dcerpc_get_tx,
tx_comp_st_ts: 1,
tx_comp_st_tc: 1,
tx_get_progress: rs_dcerpc_get_alstate_progress,
get_de_state: rs_dcerpc_get_tx_detect_state,
set_de_state: rs_dcerpc_set_tx_detect_state,
get_events: None,
get_eventinfo: None,
get_eventinfo_byid : None,
localstorage_new: None,
localstorage_free: None,
get_files: None,
get_tx_iterator: None,
get_tx_data: rs_dcerpc_get_tx_data,
apply_tx_config: None,
flags: APP_LAYER_PARSER_OPT_ACCEPT_GAPS,
truncate: None,
};
let ip_proto_str = CString::new("tcp").unwrap();
if AppLayerProtoDetectConfProtoDetectionEnabled(
ip_proto_str.as_ptr(),
parser.name,
) != 0
{
let alproto = AppLayerRegisterProtocolDetection(&parser, 1);
ALPROTO_DCERPC = alproto;
if register_pattern_probe() < 0 {
return;
}
if AppLayerParserConfParserEnabled(
ip_proto_str.as_ptr(),
parser.name,
) != 0
{
let _ = AppLayerRegisterParser(&parser, alproto);
}
SCLogDebug!("Rust DCERPC parser registered.");
} else {
SCLogDebug!("Protocol detector and parser disabled for DCERPC.");
}
return 0;
}
#[cfg(test)]

@ -16,7 +16,6 @@ noinst_HEADERS = \
alert-prelude.h \
alert-syslog.h \
app-layer-dcerpc-common.h \
app-layer-dcerpc.h \
app-layer-dcerpc-udp.h \
app-layer-detect-proto.h \
app-layer-dnp3.h \
@ -600,7 +599,6 @@ libsuricata_c_a_SOURCES = \
alert-prelude.c \
alert-syslog.c \
app-layer.c \
app-layer-dcerpc.c \
app-layer-dcerpc-udp.c \
app-layer-detect-proto.c \
app-layer-dnp3.c \

@ -1,202 +0,0 @@
/* Copyright (C) 2007-2010 Open Information Security Foundation
*
* You can copy, redistribute or modify this Program under the terms of
* the GNU General Public License version 2 as published by the Free
* Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* version 2 along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
#include "suricata-common.h"
#include "suricata.h"
#include "debug.h"
#include "decode.h"
#include "threads.h"
#include "util-print.h"
#include "util-pool.h"
#include "util-debug.h"
#include "flow-util.h"
#include "detect-engine-state.h"
#include "stream-tcp-private.h"
#include "stream-tcp-reassemble.h"
#include "stream-tcp.h"
#include "stream.h"
#include "app-layer-protos.h"
#include "app-layer-parser.h"
#include "app-layer.h"
#include "util-spm.h"
#include "util-unittest.h"
#include "app-layer-dcerpc-common.h"
#include "app-layer-dcerpc.h"
static AppLayerResult DCERPCParseRequest(Flow *f, void *dcerpc_state,
AppLayerParserState *pstate,
const uint8_t *input, uint32_t input_len,
void *local_data, const uint8_t flags)
{
if (input == NULL && input_len > 0) {
AppLayerResult res = rs_parse_dcerpc_request_gap(dcerpc_state, input_len);
SCLogDebug("DCERPC request GAP of %u bytes, retval %d", input_len, res.status);
SCReturnStruct(res);
} else {
AppLayerResult res = rs_dcerpc_parse_request(
f, dcerpc_state, pstate, input, input_len, local_data, flags);
SCLogDebug("DCERPC request%s of %u bytes, retval %d",
(input == NULL && input_len > 0) ? " is GAP" : "", input_len, res.status);
SCReturnStruct(res);
}
}
static AppLayerResult DCERPCParseResponse(Flow *f, void *dcerpc_state,
AppLayerParserState *pstate,
const uint8_t *input, uint32_t input_len,
void *local_data, const uint8_t flags)
{
if (input == NULL && input_len > 0) {
AppLayerResult res = rs_parse_dcerpc_response_gap(dcerpc_state, input_len);
SCLogDebug("DCERPC response GAP of %u bytes, retval %d", input_len, res.status);
SCReturnStruct(res);
} else {
AppLayerResult res = rs_dcerpc_parse_response(
f, dcerpc_state, pstate, input, input_len, local_data, flags);
SCLogDebug("DCERPC response%s of %u bytes, retval %d",
(input == NULL && input_len > 0) ? " is GAP" : "", input_len, res.status);
SCReturnStruct(res);
}
}
static void *RustDCERPCStateNew(void *state_orig, AppProto proto_orig)
{
return rs_dcerpc_state_new(state_orig, proto_orig);
}
static void DCERPCStateFree(void *s)
{
return rs_dcerpc_state_free(s);
}
static int DCERPCSetTxDetectState(void *vtx, DetectEngineState *de_state)
{
return rs_dcerpc_set_tx_detect_state(vtx, de_state);
}
static DetectEngineState *DCERPCGetTxDetectState(void *vtx)
{
return rs_dcerpc_get_tx_detect_state(vtx);
}
static void DCERPCStateTransactionFree(void *state, uint64_t tx_id)
{
return rs_dcerpc_state_transaction_free(state, tx_id);
}
static void *DCERPCGetTx(void *state, uint64_t tx_id)
{
return rs_dcerpc_get_tx(state, tx_id);
}
static uint64_t DCERPCGetTxCnt(void *state)
{
return rs_dcerpc_get_tx_cnt(state);
}
static int DCERPCGetAlstateProgress(void *tx, uint8_t direction)
{
return rs_dcerpc_get_alstate_progress(tx, direction);
}
static uint16_t DCERPCTCPProbe(
Flow *f, uint8_t direction, const uint8_t *input, uint32_t len, uint8_t *rdir)
{
SCLogDebug("DCERPCTCPProbe");
const int r = rs_dcerpc_probe_tcp(f, direction, input, len, rdir);
switch (r) {
case 1:
return ALPROTO_DCERPC;
case 0:
return ALPROTO_UNKNOWN;
case -1:
default:
return ALPROTO_FAILED;
}
}
static int DCERPCRegisterPatternsForProtocolDetection(void)
{
if (AppLayerProtoDetectPMRegisterPatternCSwPP(IPPROTO_TCP, ALPROTO_DCERPC, "|05 00|", 2, 0,
STREAM_TOSERVER, DCERPCTCPProbe, 0, 0) < 0) {
return -1;
}
if (AppLayerProtoDetectPMRegisterPatternCSwPP(IPPROTO_TCP, ALPROTO_DCERPC, "|05 00|", 2, 0,
STREAM_TOCLIENT, DCERPCTCPProbe, 0, 0) < 0) {
return -1;
}
return 0;
}
void RegisterDCERPCParsers(void)
{
const char *proto_name = "dcerpc";
if (AppLayerProtoDetectConfProtoDetectionEnabled("tcp", proto_name)) {
AppLayerProtoDetectRegisterProtocol(ALPROTO_DCERPC, proto_name);
if (DCERPCRegisterPatternsForProtocolDetection() < 0)
return;
} else {
SCLogInfo("Protocol detection and parser disabled for %s protocol.",
proto_name);
return;
}
if (AppLayerParserConfParserEnabled("tcp", proto_name)) {
AppLayerParserRegisterParser(IPPROTO_TCP, ALPROTO_DCERPC, STREAM_TOSERVER,
DCERPCParseRequest);
AppLayerParserRegisterParser(IPPROTO_TCP, ALPROTO_DCERPC, STREAM_TOCLIENT,
DCERPCParseResponse);
AppLayerParserRegisterStateFuncs(IPPROTO_TCP, ALPROTO_DCERPC, RustDCERPCStateNew,
DCERPCStateFree);
AppLayerParserRegisterParserAcceptableDataDirection(IPPROTO_TCP, ALPROTO_DCERPC, STREAM_TOSERVER);
AppLayerParserRegisterTxFreeFunc(IPPROTO_TCP, ALPROTO_DCERPC, DCERPCStateTransactionFree);
AppLayerParserRegisterDetectStateFuncs(IPPROTO_TCP, ALPROTO_DCERPC,
DCERPCGetTxDetectState, DCERPCSetTxDetectState);
AppLayerParserRegisterGetTx(IPPROTO_TCP, ALPROTO_DCERPC, DCERPCGetTx);
AppLayerParserRegisterTxDataFunc(IPPROTO_TCP, ALPROTO_DCERPC, rs_dcerpc_get_tx_data);
AppLayerParserRegisterGetTxCnt(IPPROTO_TCP, ALPROTO_DCERPC, DCERPCGetTxCnt);
AppLayerParserRegisterGetStateProgressFunc(IPPROTO_TCP, ALPROTO_DCERPC, DCERPCGetAlstateProgress);
AppLayerParserRegisterStateProgressCompletionStatus(ALPROTO_DCERPC, 1, 1);
/* This parser accepts gaps. */
AppLayerParserRegisterOptionFlags(IPPROTO_TCP, ALPROTO_DCERPC, APP_LAYER_PARSER_OPT_ACCEPT_GAPS);
AppLayerParserRegisterTruncateFunc(IPPROTO_TCP, ALPROTO_DCERPC, rs_dcerpc_state_trunc);
} else {
SCLogInfo("Parsed disabled for %s protocol. Protocol detection"
"still on.", proto_name);
}
return;
}

@ -1,24 +0,0 @@
/* Copyright (C) 2020 Open Information Security Foundation
*
* You can copy, redistribute or modify this Program under the terms of
* the GNU General Public License version 2 as published by the Free
* Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* version 2 along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
#ifndef __APP_LAYER_DCERPC_RUST_H__
#define __APP_LAYER_DCERPC_RUST_H__
void RegisterDCERPCParsers(void);
#endif /* __APP_LAYER_DCERPC_H__ */

@ -46,7 +46,6 @@
#include "app-layer.h"
#include "app-layer-protos.h"
#include "app-layer-parser.h"
#include "app-layer-dcerpc.h"
#include "app-layer-dcerpc-udp.h"
#include "app-layer-smb.h"
#include "app-layer-htp.h"
@ -1581,7 +1580,7 @@ void AppLayerParserRegisterProtocolParsers(void)
RegisterHTPParsers();
RegisterSSLParsers();
RegisterDCERPCParsers();
rs_dcerpc_register_parser();
RegisterDCERPCUDPParsers();
RegisterSMBParsers();
RegisterFTPParsers();

@ -38,7 +38,6 @@
#include "flow-util.h"
#include "app-layer.h"
#include "app-layer-dcerpc.h"
#include "queue.h"
#include "stream-tcp-reassemble.h"

@ -37,7 +37,6 @@
#include "flow-util.h"
#include "app-layer.h"
#include "app-layer-dcerpc.h"
#include "queue.h"
#include "stream-tcp-reassemble.h"
#include "detect-dce-opnum.h"

@ -40,7 +40,6 @@
#include "flow-util.h"
#include "app-layer.h"
#include "app-layer-dcerpc.h"
#include "queue.h"
#include "stream-tcp-reassemble.h"

@ -49,8 +49,6 @@
#include "detect-dataset.h"
#include "detect-datarep.h"
#include "app-layer-dcerpc.h"
#include "util-spm.h"
#include "util-debug.h"
#include "util-print.h"

@ -41,7 +41,6 @@
#include "stream-tcp.h"
#include "app-layer.h"
#include "app-layer-dcerpc.h"
#include "flow-util.h"
#include "util-debug.h"

@ -43,7 +43,6 @@
#include "app-layer-protos.h"
#include "app-layer-htp.h"
#include "app-layer-dcerpc-common.h"
#include "app-layer-dcerpc.h"
#include "app-layer-smtp.h"
#include "util-unittest.h"

@ -57,7 +57,6 @@
#include "app-layer-protos.h"
#include "app-layer-htp.h"
#include "app-layer-dcerpc-common.h"
#include "app-layer-dcerpc.h"
#include "util-unittest.h"
#include "util-unittest-helper.h"

@ -56,7 +56,6 @@
#include "app-layer-detect-proto.h"
#include "app-layer-parser.h"
#include "app-layer.h"
#include "app-layer-dcerpc.h"
#include "app-layer-dcerpc-udp.h"
#include "app-layer-htp.h"
#include "app-layer-ftp.h"

@ -122,7 +122,6 @@
#include "app-layer-enip.h"
#include "app-layer-dnp3.h"
#include "app-layer-smb.h"
#include "app-layer-dcerpc.h"
#include "output-filestore.h"

Loading…
Cancel
Save