From 35e884f30353097895765bb59be23ca564764fb2 Mon Sep 17 00:00:00 2001 From: Victor Julien Date: Thu, 31 Dec 2009 01:43:34 +0100 Subject: [PATCH] Make sure offset modifies depth. --- src/detect-content.c | 38 +++++++++++++++----------- src/detect-depth.c | 58 +++++++++++++++++---------------------- src/detect-offset.c | 64 +++++++++++++++++++------------------------- src/detect.c | 4 +-- 4 files changed, 77 insertions(+), 87 deletions(-) diff --git a/src/detect-content.c b/src/detect-content.c index f2944f0e3e..145dbf5c37 100644 --- a/src/detect-content.c +++ b/src/detect-content.c @@ -105,6 +105,8 @@ static void DetectContentPrintMatches(DetectEngineThreadCtx *det_ctx, DetectCont static inline int TestOffsetDepth(MpmMatch *m, DetectContentData *co, uint16_t pktoff) { + SCEnter(); + if (m->offset >= pktoff) { if (co->offset == 0 || (m->offset >= co->offset)) { if (co->depth == 0 || ((m->offset + co->content_len) <= co->depth)) { @@ -116,9 +118,9 @@ TestOffsetDepth(MpmMatch *m, DetectContentData *co, uint16_t pktoff) { * offset match, which indicates that we have a FAILURE if the * content is negated, and SUCCESS if the content is not negated */ if (co->negated == 1) - return 0; + SCReturnInt(0); else - return 1; + SCReturnInt(1); } else { /* We have success so far with offset, but a failure with * depth. We can return a match at the bottom of this function @@ -127,28 +129,33 @@ TestOffsetDepth(MpmMatch *m, DetectContentData *co, uint16_t pktoff) { * a no match here. If the content is not negated, we have a no * match, which we return at the end of this function. */ if (co->offset && co->negated == 1) - return 0; + SCReturnInt(0); } } else { /* If offset fails, and if the content is negated, we check if depth * succeeds. If it succeeds, we have a no match for negated content. * Else we have a success for negated content. If the content is * not negated, we go down till the end and return a no match. */ - if (co->negated == 1 && - (co->depth && (m->offset+co->content_len) <= co->depth)) { - return 0; + if (co->negated == 1) { + if (co->offset != 0) { + SCReturnInt(1); + } else if (co->depth && (m->offset+co->content_len) <= co->depth) { + SCLogDebug("depth %" PRIu32 ", offset %" PRIu32 ", m->offset %" PRIu32 ", " + "return 0", co->depth, co->offset, m->offset); + SCReturnInt(0); + } } } } SCLogDebug("depth %" PRIu32 ", offset %" PRIu32 ", m->offset %" PRIu32 ", " - "return 0", co->depth, co->offset, m->offset); + "return 0 (or 1 if negated)", co->depth, co->offset, m->offset); /* If we reach this point, we have a match for negated content and no match * otherwise */ if (co->negated == 1) - return 1; + SCReturnInt(1); else - return 0; + SCReturnInt(0); } /** @@ -771,6 +778,7 @@ void DetectContentPrint(DetectContentData *cd) SCLogDebug("Distance: %u ", cd->distance); SCLogDebug("Isdataat: %u ", cd->isdataat); SCLogDebug("flags: %u ", cd->flags); + SCLogDebug("negated %u ", cd->negated); /** If it's a chunk, print the data related */ if (cd->flags & DETECT_CONTENT_IS_CHUNK) { @@ -2048,7 +2056,7 @@ int DetectContentChunkModifiersTest01 (void) { goto end; /** Check modifiers for the first chunk */ - if (cd->offset != 10 || cd->depth != 39 || cd->isdataat != 21 || + if (cd->offset != 10 || cd->depth != 42 || cd->isdataat != 21 || cd->within != 0 || cd->distance != 0) { SCLogDebug("First Chunk has bad modifiers"); goto end; @@ -2083,7 +2091,7 @@ int DetectContentChunkModifiersTest01 (void) { goto end; /** Check modifiers for the second chunk */ - if (cd->offset != 42 || cd->depth != 50 || cd->isdataat != 10 || + if (cd->offset != 42 || cd->depth != 53 || cd->isdataat != 10 || cd->within != 11 || cd->distance != 0) { SCLogDebug("Second Chunk has bad modifiers"); goto end; @@ -2168,7 +2176,7 @@ int DetectContentChunkModifiersTest02 (void) { goto end; /** Check modifiers for the first chunk */ - if (cd->offset != 10 || cd->depth != 39 || cd->isdataat != 21 || + if (cd->offset != 10 || cd->depth != 42 || cd->isdataat != 21 || cd->within != 39 || cd->distance != 1) { SCLogDebug("First Chunk has bad modifiers"); goto end; @@ -2203,7 +2211,7 @@ int DetectContentChunkModifiersTest02 (void) { goto end; /** Check modifiers for the second chunk */ - if (cd->offset != 42 || cd->depth != 50 || cd->isdataat != 10 || + if (cd->offset != 42 || cd->depth != 53 || cd->isdataat != 10 || cd->within != 11 || cd->distance != 0) { SCLogDebug("Second Chunk has bad modifiers"); goto end; @@ -2767,7 +2775,7 @@ static int SigTest41TestNegatedContent(void) * the negated content within the specified depth */ static int SigTest42TestNegatedContent(void) -{ +{ // 01 5 10 15 20 24 return SigTestPositiveTestContent("alert tcp any any -> any any (msg:\"HTTP URI cap\"; content:!twentythree; depth:22; offset:35; sid:1;)", (uint8_t *)"one four nine fourteen twentythree thirtyfive fourtysix fiftysix"); } @@ -2789,7 +2797,7 @@ static int SigTest43TestNegatedContent(void) */ static int SigTest44TestNegatedContent(void) { - return SigTestNegativeTestContent("alert tcp any any -> any any (msg:\"HTTP URI cap\"; content:!twentythree; offset:40; depth:35; sid:1;)", (uint8_t *)"one four nine fourteen twentythree thirtyfive fourtysix fiftysix"); + return SigTestPositiveTestContent("alert tcp any any -> any any (msg:\"HTTP URI cap\"; content:!twentythree; offset:40; depth:35; sid:1;)", (uint8_t *)"one four nine fourteen twentythree thirtyfive fourtysix fiftysix"); } /** diff --git a/src/detect-depth.c b/src/detect-depth.c index eb00735ca0..97aebbb207 100644 --- a/src/detect-depth.c +++ b/src/detect-depth.c @@ -6,6 +6,7 @@ #include "flow-var.h" #include "detect-content.h" #include "detect-pcre.h" +#include "util-debug.h" int DetectDepthSetup (DetectEngineCtx *, Signature *s, SigMatch *m, char *depthstr); @@ -33,44 +34,33 @@ int DetectDepthSetup (DetectEngineCtx *de_ctx, Signature *s, SigMatch *m, char * dubbed = 1; } - SigMatch *pm = m; - if (pm != NULL) { - if (pm->type == DETECT_PCRE) { - DetectPcreData *pe = (DetectPcreData *)pm->ctx; - pe->depth = (uint32_t)atoi(str); - //printf("DetectDepthSetup: set depth %" PRIu32 " for previous pcre\n", pe->depth); - - } else if (pm->type == DETECT_CONTENT) { - /** Search for the first previous DetectContent - * SigMatch (it can be the same as this one) */ - pm = DetectContentFindPrevApplicableSM(m); - if (pm == NULL) { - printf("DetectDepthSetup: Unknown previous keyword!\n"); - return -1; - } - - DetectContentData *cd = (DetectContentData *)pm->ctx; - if (cd == NULL) { - printf("DetectDepthSetup: Unknown previous keyword!\n"); - return -1; - } + /** Search for the first previous DetectContent + * SigMatch (it can be the same as this one) */ + SigMatch *pm = DetectContentFindPrevApplicableSM(m); + if (pm == NULL) { + printf("DetectDepthSetup: Unknown previous keyword!\n"); + return -1; + } - cd->depth = (uint32_t)atoi(str); + DetectContentData *cd = (DetectContentData *)pm->ctx; + if (cd == NULL) { + printf("DetectDepthSetup: Unknown previous keyword!\n"); + return -1; + } - /** Propagate the modifiers through the first chunk - * (SigMatch) if we're dealing with chunks */ - if (cd->flags & DETECT_CONTENT_IS_CHUNK) - DetectContentPropagateDepth(pm); + cd->depth = (uint32_t)atoi(str); + if (cd->content_len + cd->offset > cd->depth) { + SCLogDebug("depth increased to %"PRIu32" to match pattern len and offset", cd->content_len + cd->offset); + cd->depth = cd->content_len + cd->offset; + } - //DetectContentPrint(cd); - //printf("DetectDepthSetup: set depth %" PRIu32 " for previous content\n", cd->depth); + /** Propagate the modifiers through the first chunk + * (SigMatch) if we're dealing with chunks */ + if (cd->flags & DETECT_CONTENT_IS_CHUNK) + DetectContentPropagateDepth(pm); - } else { - printf("DetectDepthSetup: Unknown previous keyword!\n"); - } - } else { - printf("DetectDepthSetup: No previous match!\n"); - } + //DetectContentPrint(cd); + //printf("DetectDepthSetup: set depth %" PRIu32 " for previous content\n", cd->depth); if (dubbed) free(str); return 0; diff --git a/src/detect-offset.c b/src/detect-offset.c index 963e7b0628..0204b657cc 100644 --- a/src/detect-offset.c +++ b/src/detect-offset.c @@ -9,6 +9,8 @@ #include "detect-content.h" #include "detect-pcre.h" +#include "util-debug.h" + int DetectOffsetSetup (DetectEngineCtx *, Signature *s, SigMatch *m, char *offsetstr); void DetectOffsetRegister (void) { @@ -35,45 +37,35 @@ int DetectOffsetSetup (DetectEngineCtx *de_ctx, Signature *s, SigMatch *m, char dubbed = 1; } - SigMatch *pm = m; - if (pm != NULL) { - if (pm->type == DETECT_PCRE) { - //DetectPcreData *pe = (DetectPcreData *)pm->ctx; - //pe->offset = (uint32_t)atoi(str); /* XXX */ - //printf("DetectOffsetSetup: set offset %" PRIu32 " for previous pcre\n", pe->offset); - - } else if (pm->type == DETECT_CONTENT) { - /** Search for the first previous DetectContent - * SigMatch (it can be the same as this one) */ - pm = DetectContentFindPrevApplicableSM(m); - if (pm == NULL) { - printf("DetectOffsetSetup: Unknown previous keyword!\n"); - return -1; - } - - DetectContentData *cd = (DetectContentData *)pm->ctx; - if (cd == NULL) { - printf("DetectOffsetSetup: Unknown previous keyword!\n"); - return -1; - } - - cd->offset = (uint32_t)atoi(str); /* XXX */ - - /** Propagate the modifiers through the first chunk - * (SigMatch) if we're dealing with chunks */ - if (cd->flags & DETECT_CONTENT_IS_CHUNK) - DetectContentPropagateOffset(pm); - - //DetectContentPrint(cd); - //printf("DetectOffsetSetup: set offset %" PRIu32 " for previous content\n", cd->offset); - - } else { - printf("DetectOffsetSetup: Unknown previous keyword!\n"); + /** Search for the first previous DetectContent + * SigMatch (it can be the same as this one) */ + SigMatch *pm = DetectContentFindPrevApplicableSM(m); + if (pm == NULL) { + printf("DetectOffsetSetup: Unknown previous keyword!\n"); + return -1; + } + + DetectContentData *cd = (DetectContentData *)pm->ctx; + if (cd == NULL) { + printf("DetectOffsetSetup: Unknown previous keyword!\n"); + return -1; + } + + cd->offset = (uint32_t)atoi(str); + + /* check if offset and depth make sense with the pattern len */ + if (cd->depth != 0) { + if (cd->content_len + cd->offset > cd->depth) { + SCLogDebug("depth increased to %"PRIu32" to match pattern len and offset", cd->content_len + cd->offset); + cd->depth = cd->content_len + cd->offset; } - } else { - printf("DetectOffsetSetup: No previous match!\n"); } + /** Propagate the modifiers through the first chunk + * (SigMatch) if we're dealing with chunks */ + if (cd->flags & DETECT_CONTENT_IS_CHUNK) + DetectContentPropagateOffset(pm); + if (dubbed) free(str); return 0; } diff --git a/src/detect.c b/src/detect.c index 81e8469ee5..89380426be 100644 --- a/src/detect.c +++ b/src/detect.c @@ -3212,7 +3212,7 @@ static int SigTest03Real (int mpm_type) { de_ctx->mpm_matcher = mpm_type; de_ctx->flags |= DE_QUIET; - de_ctx->sig_list = SigInit(de_ctx,"alert tcp any any -> any any (msg:\"HTTP TEST\"; content:\"Host: one.example.org\"; offset:20; depth:40; sid:1;)"); + de_ctx->sig_list = SigInit(de_ctx,"alert tcp any any -> any any (msg:\"HTTP TEST\"; content:\"Host: one.example.org\"; offset:20; depth:39; sid:1;)"); if (de_ctx->sig_list == NULL) { result = 0; goto end; @@ -3223,7 +3223,7 @@ static int SigTest03Real (int mpm_type) { DetectEngineThreadCtxInit(&th_v, (void *)de_ctx, (void *)&det_ctx); SigMatchSignatures(&th_v, de_ctx, det_ctx, &p); - if (!PacketAlertCheck(&p, 1)) + if (PacketAlertCheck(&p, 1)) result = 1; SigGroupCleanup(de_ctx);