diff --git a/src/detect-nocase.c b/src/detect-nocase.c index fbb9ab06c3..040c117d2a 100644 --- a/src/detect-nocase.c +++ b/src/detect-nocase.c @@ -141,6 +141,9 @@ static int DetectNocaseSetup (DetectEngineCtx *de_ctx, Signature *s, char *nulls DetectUricontentData *ud = NULL; DetectContentData *cd = NULL; + DetectHttpClientBodyData *dhcb = NULL; + DetectHttpCookieData *dhcd = NULL; + switch (pm->type) { case DETECT_URICONTENT: ud = (DetectUricontentData *)pm->ctx; @@ -149,6 +152,8 @@ static int DetectNocaseSetup (DetectEngineCtx *de_ctx, Signature *s, char *nulls SCReturnInt(-1); } ud->flags |= DETECT_URICONTENT_NOCASE; + /* Recreate the context with nocase chars */ + BoyerMooreCtxToNocase(ud->bm_ctx, ud->uricontent, ud->uricontent_len); break; case DETECT_CONTENT: @@ -158,12 +163,18 @@ static int DetectNocaseSetup (DetectEngineCtx *de_ctx, Signature *s, char *nulls SCReturnInt(-1); } cd->flags |= DETECT_CONTENT_NOCASE; + /* Recreate the context with nocase chars */ + BoyerMooreCtxToNocase(cd->bm_ctx, cd->content, cd->content_len); break; case DETECT_AL_HTTP_CLIENT_BODY: - ((DetectHttpClientBodyData *)(pm->ctx))->flags |= DETECT_AL_HTTP_CLIENT_BODY_NOCASE; + dhcb =(DetectHttpClientBodyData *) pm->ctx; + dhcb->flags |= DETECT_AL_HTTP_CLIENT_BODY_NOCASE; + /* Recreate the context with nocase chars */ + BoyerMooreCtxToNocase(dhcb->bm_ctx, dhcb->content, dhcb->content_len); break; case DETECT_AL_HTTP_COOKIE: - ((DetectHttpCookieData *)(pm->ctx))->flags |= DETECT_AL_HTTP_COOKIE_NOCASE; + dhcd = (DetectHttpCookieData *) pm->ctx; + dhcd->flags |= DETECT_AL_HTTP_COOKIE_NOCASE; break; /* should never happen */ default: diff --git a/src/util-spm-bm.c b/src/util-spm-bm.c index 775021a248..98f5b1bcbf 100644 --- a/src/util-spm-bm.c +++ b/src/util-spm-bm.c @@ -20,6 +20,23 @@ #include #include +/** + * \brief Given a BmCtx structure, recreate the pre/suffixes for + * nocase + * + * \retval BmCtx pointer to the already created BmCtx (with BoyerMooreCtxInit()) + * \param str pointer to the pattern string + * \param size length of the string + */ +void BoyerMooreCtxToNocase(BmCtx *bm_ctx, uint8_t *needle, uint32_t needle_len) { + + /* Prepare bad chars with nocase chars */ + PreBmBcNocase(needle, needle_len, bm_ctx->bmBc); + + /* Prepare good Suffixes with nocase chars */ + PreBmGsNocase(needle, needle_len, bm_ctx->bmGs); +} + /** * \brief Setup a Booyer More context. * diff --git a/src/util-spm-bm.h b/src/util-spm-bm.h index 1d3db8f818..7e0ae1dfa7 100644 --- a/src/util-spm-bm.h +++ b/src/util-spm-bm.h @@ -15,6 +15,7 @@ typedef struct BmCtx_ { /** Prepare and return a Boyer Moore context */ BmCtx *BoyerMooreCtxInit(uint8_t *needle, uint32_t needle_len); +void BoyerMooreCtxToNocase(BmCtx *, uint8_t *, uint32_t); void PreBmBc(const uint8_t *x, int32_t m, int32_t *bmBc); void BoyerMooreSuffixes(const uint8_t *x, int32_t m, int32_t *suff); void PreBmGs(const uint8_t *x, int32_t m, int32_t *bmGs); diff --git a/src/util-spm.c b/src/util-spm.c index 2486299657..c1015401c4 100644 --- a/src/util-spm.c +++ b/src/util-spm.c @@ -487,6 +487,29 @@ int UtilSpmBoyerMooreSearchNocaseTest01() { return 0; } +/** + * \test issue 130 (@redmine) check to ensure that the + * problem is not the algorithm implementation + */ +int UtilSpmBoyerMooreSearchNocaseTestIssue130() { + uint8_t *needle = (uint8_t *)"WWW-Authenticate: "; + uint8_t *text = (uint8_t *)"Date: Mon, 23 Feb 2009 13:31:49 GMT" + "Server: Apache\r\n" + "Www-authenticate: Basic realm=\"Authentification user password\"\r\n" + "Vary: accept-language,accept-charset\r\n" + "Accept-ranges: bytes\r\n" + "Connection: close\r\n" + "Content-type: text/html; charset=iso-8859-1\r\n" + "Content-language: fr\r\n" + "Expires: Mon, 23 Feb 2009 13:31:49 GMT\r\n\r\n"; + uint8_t *found = BoyerMooreNocaseWrapper(text, needle, 1); + //printf("found: %s\n", found); + if (found != NULL) + return 1; + else + return 0; +} + /* Generic tests that should not match */ int UtilSpmBasicSearchTest02() { uint8_t *needle = (uint8_t *)"oPQRsT"; @@ -2253,6 +2276,7 @@ void UtilSpmSearchRegistertests(void) { UtRegisterTest("UtilSpmBoyerMooreSearchTest01", UtilSpmBoyerMooreSearchTest01, 1); UtRegisterTest("UtilSpmBoyerMooreSearchNocaseTest01", UtilSpmBoyerMooreSearchNocaseTest01, 1); + UtRegisterTest("UtilSpmBoyerMooreSearchNocaseTestIssue130", UtilSpmBoyerMooreSearchNocaseTestIssue130, 1); UtRegisterTest("UtilSpmBs2bmSearchTest02", UtilSpmBs2bmSearchTest02, 1); UtRegisterTest("UtilSpmBs2bmSearchNocaseTest02", UtilSpmBs2bmSearchNocaseTest02, 1);