From 1a39ab99f330710311216e6bee657d263da393b7 Mon Sep 17 00:00:00 2001 From: Victor Julien Date: Sat, 4 Mar 2017 13:40:39 +0100 Subject: [PATCH] detect: don't rescan when just distance is used Content inspection optimization: when just distance is used without within we don't need to search recursively. E.g. content:"a"; content:"b"; distance:1; will scan the buffer for 'a' and when it finds 'a' it will scan the remainder for 'b'. Until now, the failure to find 'b' would lead to looking for the next 'a' and then for 'b' after that. However, we already inspected the entire buffer for 'b', so we know this will fail. --- src/detect-byte-extract.c | 4 ++-- src/detect-content.h | 10 +++++++--- src/detect-distance.c | 6 +++++- src/detect-engine-content-inspection.c | 2 +- src/detect-within.c | 2 +- 5 files changed, 16 insertions(+), 8 deletions(-) diff --git a/src/detect-byte-extract.c b/src/detect-byte-extract.c index a4549a1d6d..917315c301 100644 --- a/src/detect-byte-extract.c +++ b/src/detect-byte-extract.c @@ -3031,7 +3031,7 @@ int DetectByteExtractTest48(void) if (strncmp((char *)cd->content, "four", cd->content_len) != 0 || cd->flags != (DETECT_CONTENT_DISTANCE_BE | DETECT_CONTENT_DISTANCE | - DETECT_CONTENT_RELATIVE_NEXT) || + DETECT_CONTENT_DISTANCE_NEXT) || cd->distance != bed1->local_id || cd->depth != 0 || cd->offset != 0) { @@ -3260,7 +3260,7 @@ int DetectByteExtractTest50(void) if (strncmp((char *)cd->content, "four", cd->content_len) != 0 || cd->flags != (DETECT_CONTENT_WITHIN_BE | DETECT_CONTENT_WITHIN| - DETECT_CONTENT_RELATIVE_NEXT) || + DETECT_CONTENT_WITHIN_NEXT) || cd->within != bed1->local_id || cd->depth != 0 || cd->offset != 0 || diff --git a/src/detect-content.h b/src/detect-content.h index 5976adb868..0b0d2eaf46 100644 --- a/src/detect-content.h +++ b/src/detect-content.h @@ -39,8 +39,7 @@ /** content is negated */ #define DETECT_CONTENT_NEGATED (1 << 9) -/** a relative match to this content is next, used in matching phase */ -#define DETECT_CONTENT_RELATIVE_NEXT (1 << 10) +// bit 10 unused /* BE - byte extract */ #define DETECT_CONTENT_OFFSET_BE (1 << 11) @@ -53,7 +52,12 @@ /* this flag is set during the staging phase. It indicates that a content * has been added to the mpm phase and requires no further inspection inside * the inspection phase */ -#define DETECT_CONTENT_NO_DOUBLE_INSPECTION_REQUIRED (1 << 16) +#define DETECT_CONTENT_NO_DOUBLE_INSPECTION_REQUIRED BIT_U32(16) + +#define DETECT_CONTENT_WITHIN_NEXT BIT_U32(17) +#define DETECT_CONTENT_DISTANCE_NEXT BIT_U32(18) +/** a relative match to this content is next, used in matching phase */ +#define DETECT_CONTENT_RELATIVE_NEXT (DETECT_CONTENT_WITHIN_NEXT|DETECT_CONTENT_DISTANCE_NEXT) #define DETECT_CONTENT_IS_SINGLE(c) (!( ((c)->flags & DETECT_CONTENT_DISTANCE) || \ ((c)->flags & DETECT_CONTENT_WITHIN) || \ diff --git a/src/detect-distance.c b/src/detect-distance.c index 8be8219bab..dc89ea8456 100644 --- a/src/detect-distance.c +++ b/src/detect-distance.c @@ -163,7 +163,11 @@ static int DetectDistanceSetup (DetectEngineCtx *de_ctx, Signature *s, "only content"); goto end; } - prev_cd->flags |= DETECT_CONTENT_RELATIVE_NEXT; + if ((cd->flags & DETECT_CONTENT_NEGATED) == 0) { + prev_cd->flags |= DETECT_CONTENT_DISTANCE_NEXT; + } else { + prev_cd->flags |= DETECT_CONTENT_RELATIVE_NEXT; + } } else if (prev_pm->type == DETECT_PCRE) { DetectPcreData *pd = (DetectPcreData *)prev_pm->ctx; pd->flags |= DETECT_PCRE_RELATIVE_NEXT; diff --git a/src/detect-engine-content-inspection.c b/src/detect-engine-content-inspection.c index 32d6350612..b41b880447 100644 --- a/src/detect-engine-content-inspection.c +++ b/src/detect-engine-content-inspection.c @@ -339,7 +339,7 @@ int DetectEngineContentInspection(DetectEngineCtx *de_ctx, DetectEngineThreadCtx } /* no match and no reason to look for another instance */ - if ((cd->flags & DETECT_CONTENT_RELATIVE_NEXT) == 0) { + if ((cd->flags & DETECT_CONTENT_WITHIN_NEXT) == 0) { SCLogDebug("'next sm' does not depend on me, so we can give up"); det_ctx->discontinue_matching = 1; goto no_match; diff --git a/src/detect-within.c b/src/detect-within.c index f10b0275c6..fd9bd99d70 100644 --- a/src/detect-within.c +++ b/src/detect-within.c @@ -178,7 +178,7 @@ static int DetectWithinSetup(DetectEngineCtx *de_ctx, Signature *s, char *within "only content"); goto end; } - prev_cd->flags |= DETECT_CONTENT_RELATIVE_NEXT; + prev_cd->flags |= DETECT_CONTENT_WITHIN_NEXT; } else if (prev_pm->type == DETECT_PCRE) { DetectPcreData *pd = (DetectPcreData *)prev_pm->ctx; pd->flags |= DETECT_PCRE_RELATIVE_NEXT;