Skip to content

Commit 3613946

Browse files
committed
detect/integers: add support for negated strings when enum is used
function detect_parse_uint_enum can parse strings like !bind_request Ticket: #7513
1 parent d63ad75 commit 3613946

File tree

2 files changed

+17
-4
lines changed

2 files changed

+17
-4
lines changed

doc/userguide/rules/integer-keywords.rst

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -55,14 +55,17 @@ Enumerations
5555

5656
Some integers on the wire represent an enumeration, that is, some values
5757
have a string/meaning associated to it.
58-
Rules can be written using one of these strings to check for equality.
58+
Rules can be written using one of these strings to check for equality or inequality.
5959
This is meant to make rules more human-readable and equivalent for matching.
6060

6161
Examples::
6262

6363
websocket.opcode:text;
6464
websocket.opcode:1; # behaves the same
6565

66+
websocket.opcode:!ping;
67+
websocket.opcode:!9; # behaves the same
68+
6669
Bitmasks
6770
--------
6871

rust/src/detect/uint.rs

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@ use nom7::branch::alt;
1919
use nom7::bytes::complete::{is_a, tag, tag_no_case, take_while};
2020
use nom7::character::complete::{char, digit1, hex_digit1};
2121
use nom7::combinator::{all_consuming, map_opt, opt, value, verify};
22-
use nom7::error::{make_error, ErrorKind};
22+
use nom7::error::{make_error, Error, ErrorKind};
2323
use nom7::Err;
2424
use nom7::IResult;
2525

@@ -58,15 +58,25 @@ pub struct DetectUintData<T> {
5858
/// And if this fails, will resort to using the enumeration strings.
5959
///
6060
/// Returns Some DetectUintData on success, None on failure
61-
pub fn detect_parse_uint_enum<T1: DetectIntType, T2: EnumString<T1>>(s: &str) -> Option<DetectUintData<T1>> {
61+
pub fn detect_parse_uint_enum<T1: DetectIntType, T2: EnumString<T1>>(
62+
s: &str,
63+
) -> Option<DetectUintData<T1>> {
6264
if let Ok((_, ctx)) = detect_parse_uint::<T1>(s) {
6365
return Some(ctx);
6466
}
67+
68+
// we need to precise the Error type, we get error[E0283]: type annotations needed
69+
let (s, neg) = opt(char::<_, Error<_>>('!'))(s).ok()?;
70+
let mode = if neg.is_some() {
71+
DetectUintMode::DetectUintModeNe
72+
} else {
73+
DetectUintMode::DetectUintModeEqual
74+
};
6575
if let Some(enum_val) = T2::from_str(s) {
6676
let ctx = DetectUintData::<T1> {
6777
arg1: enum_val.into_u(),
6878
arg2: T1::min_value(),
69-
mode: DetectUintMode::DetectUintModeEqual,
79+
mode,
7080
};
7181
return Some(ctx);
7282
}

0 commit comments

Comments
 (0)