From 4ba639ac7f0ee788ccea2e70610eda7d02c0dc4f Mon Sep 17 00:00:00 2001 From: Anoop Saldanha Date: Sat, 4 Feb 2012 07:02:21 +0530 Subject: [PATCH 1/2] bug #412 - Unify SigInit() and SigInitReal(). Remove any use of SigInitReal() --- src/detect-parse.c | 418 +++++++++++++++++++++++++++++----------------------- 1 files changed, 230 insertions(+), 188 deletions(-) diff --git a/src/detect-parse.c b/src/detect-parse.c index 97b5701..82a50cb 100644 --- a/src/detect-parse.c +++ b/src/detect-parse.c @@ -1468,19 +1468,12 @@ static int SigValidate(Signature *s) { } /** - * \brief Parses a signature and adds it to the Detection Engine Context - * This function is going to be deprecated. Should use DetectEngineAppendSig() - * or SigInitReal() if you want to control the sig_list building. - * - * \param de_ctx Pointer to the Detection Engine Context - * \param sigstr Pointer to a character string containing the signature to be - * parsed - * - * \retval Pointer to the Signature instance on success; NULL on failure + * \internal + * \brief Helper function for SigInit(). */ -Signature *SigInit(DetectEngineCtx *de_ctx, char *sigstr) { - SCEnter(); - +static Signature *SigInitHelper(DetectEngineCtx *de_ctx, char *sigstr, + uint8_t dir) +{ Signature *sig = SigAlloc(); if (sig == NULL) goto error; @@ -1488,7 +1481,7 @@ Signature *SigInit(DetectEngineCtx *de_ctx, char *sigstr) { /* default gid to 1 */ sig->gid = 1; - if (SigParse(de_ctx, sig, sigstr, SIG_DIREC_NORMAL) < 0) + if (SigParse(de_ctx, sig, sigstr, dir) < 0) goto error; /* signature priority hasn't been overwritten. Using default priority */ @@ -1591,7 +1584,7 @@ Signature *SigInit(DetectEngineCtx *de_ctx, char *sigstr) { goto error; } - SCReturnPtr(sig, "Signature"); + return sig; error: if (sig != NULL) { @@ -1599,210 +1592,259 @@ error: } if (de_ctx->failure_fatal == 1) { - SCLogError(SC_ERR_INVALID_SIGNATURE,"Signature parsing failed: \"%s\"", sigstr); + SCLogError(SC_ERR_INVALID_SIGNATURE, "Signature parsing failed: " + "\"%s\"", sigstr); exit(EXIT_FAILURE); } - SCReturnPtr(NULL,"Signature"); + return NULL; } /** - * \brief Parses a signature and assign a unique number from the Detection - * Engine Context. If the signature is bidirectional it should return - * two Signatures linked. Look if flag Bidirec is set and if the pointer - * sig->next is set (!= NULL). + * \brief Parses a signature and adds it to the Detection Engine Context. * - * \param de_ctx Pointer to the Detection Engine Context + * \param de_ctx Pointer to the Detection Engine Context. * \param sigstr Pointer to a character string containing the signature to be - * parsed + * parsed. * - * \retval Pointer to the Signature instance on success; NULL on failure + * \retval Pointer to the Signature instance on success; NULL on failure. */ -Signature *SigInitReal(DetectEngineCtx *de_ctx, char *sigstr) { - Signature *sig = SigAlloc(); - uint32_t oldsignum = de_ctx->signum; +Signature *SigInit(DetectEngineCtx *de_ctx, char *sigstr) +{ + SCEnter(); - if (sig == NULL) - goto error; + uint32_t oldsignum = de_ctx->signum; - /* default gid to 1 */ - sig->gid = 1; + Signature *sig; - if (SigParse(de_ctx, sig, sigstr, SIG_DIREC_NORMAL) < 0) + if ((sig = SigInitHelper(de_ctx, sigstr, SIG_DIREC_NORMAL)) == NULL) { goto error; - - /* signature priority hasn't been overwritten. Using default priority */ - if (sig->prio == -1) - sig->prio = 3; - - /* assign an unique id in this de_ctx */ - sig->num = de_ctx->signum; - de_ctx->signum++; - - SigMatch *sm; - /* set mpm_content_len */ - - /* determine the length of the longest pattern in the sig */ - if (sig->sm_lists[DETECT_SM_LIST_PMATCH] != NULL) { - sig->mpm_content_maxlen = 0; - - for (sm = sig->sm_lists[DETECT_SM_LIST_PMATCH]; sm != NULL; sm = sm->next) { - if (sm->type == DETECT_CONTENT) { - DetectContentData *cd = (DetectContentData *)sm->ctx; - if (cd == NULL) - continue; - - if (sig->mpm_content_maxlen == 0) - sig->mpm_content_maxlen = cd->content_len; - if (sig->mpm_content_maxlen < cd->content_len) - sig->mpm_content_maxlen = cd->content_len; - } - } } - if (sig->sm_lists[DETECT_SM_LIST_UMATCH] != NULL) { - sig->mpm_uricontent_maxlen = 0; - for (sm = sig->sm_lists[DETECT_SM_LIST_UMATCH]; sm != NULL; sm = sm->next) { - if (sm->type == DETECT_URICONTENT) { - DetectContentData *ud = (DetectContentData *)sm->ctx; - if (ud == NULL) - continue; - if (sig->mpm_uricontent_maxlen == 0) - sig->mpm_uricontent_maxlen = ud->content_len; - if (sig->mpm_uricontent_maxlen < ud->content_len) - sig->mpm_uricontent_maxlen = ud->content_len; - } - } - } if (sig->init_flags & SIG_FLAG_INIT_BIDIREC) { - /* Allocate a copy of this signature with the addresses siwtched - This copy will be installed at sig->next */ - sig->next = SigAlloc(); - sig->next->prio = sig->prio; - sig->next->gid = sig->gid; - - if (sig->next == NULL) + sig->next = SigInitHelper(de_ctx, sigstr, SIG_DIREC_SWITCHED); + if (sig->next == NULL) { goto error; - - if (SigParse(de_ctx, sig->next, sigstr, SIG_DIREC_SWITCHED) < 0) - goto error; - - /* assign an unique id in this de_ctx */ - sig->next->num = de_ctx->signum; - de_ctx->signum++; - - /* set mpm_content_len */ - - /* determine the length of the longest pattern in the sig */ - if (sig->next->sm_lists[DETECT_SM_LIST_PMATCH] != NULL) { - sig->next->mpm_content_maxlen = 0; - - SigMatch *sm; - for (sm = sig->next->sm_lists[DETECT_SM_LIST_PMATCH]; sm != NULL; sm = sm->next) { - if (sm->type == DETECT_CONTENT) { - DetectContentData *cd = (DetectContentData *)sm->ctx; - if (cd == NULL) - continue; - - if (sig->next->mpm_content_maxlen == 0) - sig->next->mpm_content_maxlen = cd->content_len; - if (sig->next->mpm_content_maxlen < cd->content_len) - sig->next->mpm_content_maxlen = cd->content_len; - } - } - } - if (sig->next->sm_lists[DETECT_SM_LIST_UMATCH] != NULL) { - sig->next->mpm_uricontent_maxlen = 0; - - for (sm = sig->next->sm_lists[DETECT_SM_LIST_UMATCH]; sm != NULL; sm = sm->next) { - if (sm->type == DETECT_URICONTENT) { - DetectContentData *ud = (DetectContentData *)sm->ctx; - if (ud == NULL) - continue; - - if (sig->next->mpm_uricontent_maxlen == 0) - sig->next->mpm_uricontent_maxlen = ud->content_len; - if (sig->next->mpm_uricontent_maxlen < ud->content_len) - sig->next->mpm_uricontent_maxlen = ud->content_len; - } - } } } - /* set the packet and app layer flags, but only if the - * app layer flag wasn't already set in which case we - * only consider the app layer */ - if (!(sig->flags & SIG_FLAG_APPLAYER)) { - if (sig->sm_lists[DETECT_SM_LIST_MATCH] != NULL) { - SigMatch *sm = sig->sm_lists[DETECT_SM_LIST_MATCH]; - for ( ; sm != NULL; sm = sm->next) { - if (sigmatch_table[sm->type].AppLayerMatch != NULL) - sig->flags |= SIG_FLAG_APPLAYER; - if (sigmatch_table[sm->type].Match != NULL) - sig->init_flags |= SIG_FLAG_INIT_PACKET; - } - } else { - sig->init_flags |= SIG_FLAG_INIT_PACKET; - } - } - - if (sig->sm_lists[DETECT_SM_LIST_UMATCH]) - sig->flags |= SIG_FLAG_STATE_MATCH; - if (sig->sm_lists[DETECT_SM_LIST_DMATCH]) - sig->flags |= SIG_FLAG_STATE_MATCH; - if (sig->sm_lists[DETECT_SM_LIST_AMATCH]) - sig->flags |= SIG_FLAG_STATE_MATCH; - if (sig->sm_lists[DETECT_SM_LIST_HCBDMATCH]) - sig->flags |= SIG_FLAG_STATE_MATCH; - if (sig->sm_lists[DETECT_SM_LIST_HSBDMATCH]) - sig->flags |= SIG_FLAG_STATE_MATCH; - if (sig->sm_lists[DETECT_SM_LIST_HHDMATCH]) - sig->flags |= SIG_FLAG_STATE_MATCH; - if (sig->sm_lists[DETECT_SM_LIST_HRHDMATCH]) - sig->flags |= SIG_FLAG_STATE_MATCH; - if (sig->sm_lists[DETECT_SM_LIST_HMDMATCH]) - sig->flags |= SIG_FLAG_STATE_MATCH; - if (sig->sm_lists[DETECT_SM_LIST_HCDMATCH]) - sig->flags |= SIG_FLAG_STATE_MATCH; - if (sig->sm_lists[DETECT_SM_LIST_FILEMATCH]) - sig->flags |= SIG_FLAG_STATE_MATCH; - - if (!(sig->init_flags & SIG_FLAG_INIT_FLOW)) { - sig->flags |= SIG_FLAG_TOSERVER; - sig->flags |= SIG_FLAG_TOCLIENT; - } - - SigBuildAddressMatchArray(sig); - - SCLogDebug("sig %"PRIu32" SIG_FLAG_APPLAYER: %s, SIG_FLAG_PACKET: %s", - sig->id, sig->flags & SIG_FLAG_APPLAYER ? "set" : "not set", - sig->init_flags & SIG_FLAG_INIT_PACKET ? "set" : "not set"); - - /* validate signature, SigValidate will report the error reason */ - if (SigValidate(sig) == 0) { - goto error; - } - - /** - * In SigInitReal, the signature returned will point from the ptr next - * to the cloned signatures with the switched addresses if it has - * the bidirectional operator set - */ - return sig; + SCReturnPtr(sig, "Signature"); error: if (sig != NULL) { - if (sig->next != NULL) { - SigFree(sig->next); - } SigFree(sig); } + + if (de_ctx->failure_fatal == 1) { + SCLogError(SC_ERR_INVALID_SIGNATURE, "Signature parsing failed: " + "\"%s\"", sigstr); + exit(EXIT_FAILURE); + } + /* if something failed, restore the old signum count * since we didn't install it */ de_ctx->signum = oldsignum; - return NULL; + + SCReturnPtr(NULL, "Signature"); } /** + * \brief Parses a signature and assign a unique number from the Detection + * Engine Context. If the signature is bidirectional it should return + * two Signatures linked. Look if flag Bidirec is set and if the pointer + * sig->next is set (!= NULL). + * + * \param de_ctx Pointer to the Detection Engine Context + * \param sigstr Pointer to a character string containing the signature to be + * parsed + * + * \retval Pointer to the Signature instance on success; NULL on failure + */ +//Signature *SigInitReal(DetectEngineCtx *de_ctx, char *sigstr) { +// Signature *sig = SigAlloc(); +// uint32_t oldsignum = de_ctx->signum; +// +// if (sig == NULL) +// goto error; +// +// /* default gid to 1 */ +// sig->gid = 1; +// +// if (SigParse(de_ctx, sig, sigstr, SIG_DIREC_NORMAL) < 0) +// goto error; +// +// /* signature priority hasn't been overwritten. Using default priority */ +// if (sig->prio == -1) +// sig->prio = 3; +// +// /* assign an unique id in this de_ctx */ +// sig->num = de_ctx->signum; +// de_ctx->signum++; +// +// SigMatch *sm; +// /* set mpm_content_len */ +// +// /* determine the length of the longest pattern in the sig */ +// if (sig->sm_lists[DETECT_SM_LIST_PMATCH] != NULL) { +// sig->mpm_content_maxlen = 0; +// +// for (sm = sig->sm_lists[DETECT_SM_LIST_PMATCH]; sm != NULL; sm = sm->next) { +// if (sm->type == DETECT_CONTENT) { +// DetectContentData *cd = (DetectContentData *)sm->ctx; +// if (cd == NULL) +// continue; +// +// if (sig->mpm_content_maxlen == 0) +// sig->mpm_content_maxlen = cd->content_len; +// if (sig->mpm_content_maxlen < cd->content_len) +// sig->mpm_content_maxlen = cd->content_len; +// } +// } +// } +// if (sig->sm_lists[DETECT_SM_LIST_UMATCH] != NULL) { +// sig->mpm_uricontent_maxlen = 0; +// +// for (sm = sig->sm_lists[DETECT_SM_LIST_UMATCH]; sm != NULL; sm = sm->next) { +// if (sm->type == DETECT_URICONTENT) { +// DetectContentData *ud = (DetectContentData *)sm->ctx; +// if (ud == NULL) +// continue; +// if (sig->mpm_uricontent_maxlen == 0) +// sig->mpm_uricontent_maxlen = ud->content_len; +// if (sig->mpm_uricontent_maxlen < ud->content_len) +// sig->mpm_uricontent_maxlen = ud->content_len; +// } +// } +// } +// if (sig->init_flags & SIG_FLAG_INIT_BIDIREC) { +// /* Allocate a copy of this signature with the addresses siwtched +// This copy will be installed at sig->next */ +// sig->next = SigAlloc(); +// sig->next->prio = sig->prio; +// sig->next->gid = sig->gid; +// +// if (sig->next == NULL) +// goto error; +// +// if (SigParse(de_ctx, sig->next, sigstr, SIG_DIREC_SWITCHED) < 0) +// goto error; +// +// /* assign an unique id in this de_ctx */ +// sig->next->num = de_ctx->signum; +// de_ctx->signum++; +// +// /* set mpm_content_len */ +// +// /* determine the length of the longest pattern in the sig */ +// if (sig->next->sm_lists[DETECT_SM_LIST_PMATCH] != NULL) { +// sig->next->mpm_content_maxlen = 0; +// +// SigMatch *sm; +// for (sm = sig->next->sm_lists[DETECT_SM_LIST_PMATCH]; sm != NULL; sm = sm->next) { +// if (sm->type == DETECT_CONTENT) { +// DetectContentData *cd = (DetectContentData *)sm->ctx; +// if (cd == NULL) +// continue; +// +// if (sig->next->mpm_content_maxlen == 0) +// sig->next->mpm_content_maxlen = cd->content_len; +// if (sig->next->mpm_content_maxlen < cd->content_len) +// sig->next->mpm_content_maxlen = cd->content_len; +// } +// } +// } +// if (sig->next->sm_lists[DETECT_SM_LIST_UMATCH] != NULL) { +// sig->next->mpm_uricontent_maxlen = 0; +// +// for (sm = sig->next->sm_lists[DETECT_SM_LIST_UMATCH]; sm != NULL; sm = sm->next) { +// if (sm->type == DETECT_URICONTENT) { +// DetectContentData *ud = (DetectContentData *)sm->ctx; +// if (ud == NULL) +// continue; +// +// if (sig->next->mpm_uricontent_maxlen == 0) +// sig->next->mpm_uricontent_maxlen = ud->content_len; +// if (sig->next->mpm_uricontent_maxlen < ud->content_len) +// sig->next->mpm_uricontent_maxlen = ud->content_len; +// } +// } +// } +// } +// +// /* set the packet and app layer flags, but only if the +// * app layer flag wasn't already set in which case we +// * only consider the app layer */ +// if (!(sig->flags & SIG_FLAG_APPLAYER)) { +// if (sig->sm_lists[DETECT_SM_LIST_MATCH] != NULL) { +// SigMatch *sm = sig->sm_lists[DETECT_SM_LIST_MATCH]; +// for ( ; sm != NULL; sm = sm->next) { +// if (sigmatch_table[sm->type].AppLayerMatch != NULL) +// sig->flags |= SIG_FLAG_APPLAYER; +// if (sigmatch_table[sm->type].Match != NULL) +// sig->init_flags |= SIG_FLAG_INIT_PACKET; +// } +// } else { +// sig->init_flags |= SIG_FLAG_INIT_PACKET; +// } +// } +// +// if (sig->sm_lists[DETECT_SM_LIST_UMATCH]) +// sig->flags |= SIG_FLAG_STATE_MATCH; +// if (sig->sm_lists[DETECT_SM_LIST_DMATCH]) +// sig->flags |= SIG_FLAG_STATE_MATCH; +// if (sig->sm_lists[DETECT_SM_LIST_AMATCH]) +// sig->flags |= SIG_FLAG_STATE_MATCH; +// if (sig->sm_lists[DETECT_SM_LIST_HCBDMATCH]) +// sig->flags |= SIG_FLAG_STATE_MATCH; +// if (sig->sm_lists[DETECT_SM_LIST_HSBDMATCH]) +// sig->flags |= SIG_FLAG_STATE_MATCH; +// if (sig->sm_lists[DETECT_SM_LIST_HHDMATCH]) +// sig->flags |= SIG_FLAG_STATE_MATCH; +// if (sig->sm_lists[DETECT_SM_LIST_HRHDMATCH]) +// sig->flags |= SIG_FLAG_STATE_MATCH; +// if (sig->sm_lists[DETECT_SM_LIST_HMDMATCH]) +// sig->flags |= SIG_FLAG_STATE_MATCH; +// if (sig->sm_lists[DETECT_SM_LIST_HCDMATCH]) +// sig->flags |= SIG_FLAG_STATE_MATCH; +// if (sig->sm_lists[DETECT_SM_LIST_FILEMATCH]) +// sig->flags |= SIG_FLAG_STATE_MATCH; +// +// if (!(sig->init_flags & SIG_FLAG_INIT_FLOW)) { +// sig->flags |= SIG_FLAG_TOSERVER; +// sig->flags |= SIG_FLAG_TOCLIENT; +// } +// +// SigBuildAddressMatchArray(sig); +// +// SCLogDebug("sig %"PRIu32" SIG_FLAG_APPLAYER: %s, SIG_FLAG_PACKET: %s", +// sig->id, sig->flags & SIG_FLAG_APPLAYER ? "set" : "not set", +// sig->init_flags & SIG_FLAG_INIT_PACKET ? "set" : "not set"); +// +// /* validate signature, SigValidate will report the error reason */ +// if (SigValidate(sig) == 0) { +// goto error; +// } +// +// /** +// * In SigInitReal, the signature returned will point from the ptr next +// * to the cloned signatures with the switched addresses if it has +// * the bidirectional operator set +// */ +// return sig; +// +//error: +// if (sig != NULL) { +// if (sig->next != NULL) { +// SigFree(sig->next); +// } +// SigFree(sig); +// } +// /* if something failed, restore the old signum count +// * since we didn't install it */ +// de_ctx->signum = oldsignum; +// return NULL; +//} + +/** * \brief The hash free function to be the used by the hash table - * DetectEngineCtx->dup_sig_hash_table. * @@ -2043,7 +2085,7 @@ end: */ Signature *DetectEngineAppendSig(DetectEngineCtx *de_ctx, char *sigstr) { - Signature *sig = SigInitReal(de_ctx, sigstr); + Signature *sig = SigInit(de_ctx, sigstr); if (sig == NULL) { return NULL; } -- 1.7.1