detect: initialization optimization

A lot of time was spent in `SigMatchListSMBelongsTo` for the `mpm_sm`.

Optimize this by keeping the value at hand during Signature parsing and
detection engine setup.
pull/7204/head
Victor Julien 3 years ago
parent b804a84c93
commit 3352c0bee4

@ -153,8 +153,9 @@ void EngineAnalysisFP(const DetectEngineCtx *de_ctx, const Signature *s, char *l
int fast_pattern_set = 0;
int fast_pattern_only_set = 0;
int fast_pattern_chop_set = 0;
DetectContentData *fp_cd = NULL;
SigMatch *mpm_sm = s->init_data->mpm_sm;
const DetectContentData *fp_cd = NULL;
const SigMatch *mpm_sm = s->init_data->mpm_sm;
const int mpm_sm_list = s->init_data->mpm_sm_list;
if (mpm_sm != NULL) {
fp_cd = (DetectContentData *)mpm_sm->ctx;
@ -186,7 +187,7 @@ void EngineAnalysisFP(const DetectEngineCtx *de_ctx, const Signature *s, char *l
}
fprintf(fp_engine_analysis_FD, " Fast pattern matcher: ");
int list_type = SigMatchListSMBelongsTo(s, mpm_sm);
int list_type = mpm_sm_list;
if (list_type == DETECT_SM_LIST_PMATCH)
fprintf(fp_engine_analysis_FD, "content\n");
else {
@ -473,8 +474,9 @@ int PerCentEncodingMatch (uint8_t *content, uint8_t content_len)
static void EngineAnalysisRulesPrintFP(const DetectEngineCtx *de_ctx, const Signature *s)
{
DetectContentData *fp_cd = NULL;
SigMatch *mpm_sm = s->init_data->mpm_sm;
const DetectContentData *fp_cd = NULL;
const SigMatch *mpm_sm = s->init_data->mpm_sm;
const int mpm_sm_list = s->init_data->mpm_sm_list;
if (mpm_sm != NULL) {
fp_cd = (DetectContentData *)mpm_sm->ctx;
@ -511,7 +513,7 @@ static void EngineAnalysisRulesPrintFP(const DetectEngineCtx *de_ctx, const Sign
fprintf(rule_engine_analysis_FD, "\" on \"");
int list_type = SigMatchListSMBelongsTo(s, mpm_sm);
const int list_type = mpm_sm_list;
if (list_type == DETECT_SM_LIST_PMATCH) {
int payload = 0;
int stream = 0;
@ -1559,7 +1561,7 @@ void EngineAnalysisRules(const DetectEngineCtx *de_ctx,
warn_offset_depth_alproto = 1;
}
if (s->init_data->mpm_sm != NULL && s->alproto == ALPROTO_HTTP1 &&
SigMatchListSMBelongsTo(s, s->init_data->mpm_sm) == DETECT_SM_LIST_PMATCH) {
s->init_data->mpm_sm_list == DETECT_SM_LIST_PMATCH) {
rule_warning += 1;
warn_non_alproto_fp_for_alproto_sig = 1;
}

@ -607,7 +607,7 @@ static int RuleGetMpmPatternSize(const Signature *s)
{
if (s->init_data->mpm_sm == NULL)
return -1;
int mpm_list = SigMatchListSMBelongsTo(s, s->init_data->mpm_sm);
int mpm_list = s->init_data->mpm_sm_list;
if (mpm_list < 0)
return -1;
const DetectContentData *cd = (const DetectContentData *)s->init_data->mpm_sm->ctx;
@ -620,7 +620,7 @@ static int RuleMpmIsNegated(const Signature *s)
{
if (s->init_data->mpm_sm == NULL)
return 0;
int mpm_list = SigMatchListSMBelongsTo(s, s->init_data->mpm_sm);
int mpm_list = s->init_data->mpm_sm_list;
if (mpm_list < 0)
return 0;
const DetectContentData *cd = (const DetectContentData *)s->init_data->mpm_sm->ctx;
@ -723,7 +723,7 @@ static json_t *RulesGroupPrintSghStats(const DetectEngineCtx *de_ctx, const SigG
}
} else {
int mpm_list = SigMatchListSMBelongsTo(s, s->init_data->mpm_sm);
int mpm_list = s->init_data->mpm_sm_list;
BUG_ON(mpm_list < 0);
const DetectContentData *cd = (const DetectContentData *)s->init_data->mpm_sm->ctx;
uint32_t size = cd->content_len < 256 ? cd->content_len : 255;
@ -1150,15 +1150,13 @@ static int RuleSetWhitelist(Signature *s)
/* one byte pattern in packet/stream payloads */
} else if (s->init_data->mpm_sm != NULL &&
SigMatchListSMBelongsTo(s, s->init_data->mpm_sm) == DETECT_SM_LIST_PMATCH &&
RuleGetMpmPatternSize(s) == 1)
{
s->init_data->mpm_sm_list == DETECT_SM_LIST_PMATCH &&
RuleGetMpmPatternSize(s) == 1) {
SCLogDebug("Rule %u No MPM. Payload inspecting. Whitelisting SGH's.", s->id);
wl = 55;
} else if (DetectFlagsSignatureNeedsSynPackets(s) &&
DetectFlagsSignatureNeedsSynOnlyPackets(s))
{
DetectFlagsSignatureNeedsSynOnlyPackets(s)) {
SCLogDebug("Rule %u Needs SYN, so inspected often. Whitelisting SGH's.", s->id);
wl = 33;
}

@ -1012,7 +1012,7 @@ static void PopulateMpmHelperAddPattern(MpmCtx *mpm_ctx,
#define SGH_DIRECTION_TS(sgh) ((sgh)->init->direction & SIG_FLAG_TOSERVER)
#define SGH_DIRECTION_TC(sgh) ((sgh)->init->direction & SIG_FLAG_TOCLIENT)
static void SetMpm(Signature *s, SigMatch *mpm_sm)
static void SetMpm(Signature *s, SigMatch *mpm_sm, const int mpm_sm_list)
{
if (s == NULL || mpm_sm == NULL)
return;
@ -1035,6 +1035,7 @@ static void SetMpm(Signature *s, SigMatch *mpm_sm)
}
}
cd->flags |= DETECT_CONTENT_MPM;
s->init_data->mpm_sm_list = mpm_sm_list;
s->init_data->mpm_sm = mpm_sm;
return;
}
@ -1080,7 +1081,7 @@ void RetrieveFPForSig(const DetectEngineCtx *de_ctx, Signature *s)
if (s->init_data->mpm_sm != NULL)
return;
SigMatch *mpm_sm = NULL, *sm = NULL;
SigMatch *sm = NULL;
const int nlists = s->init_data->smlists_array_size;
int nn_sm_list[nlists];
int n_sm_list[nlists];
@ -1105,7 +1106,7 @@ void RetrieveFPForSig(const DetectEngineCtx *de_ctx, Signature *s)
const DetectContentData *cd = (DetectContentData *)sm->ctx;
/* fast_pattern set in rule, so using this pattern */
if ((cd->flags & DETECT_CONTENT_FAST_PATTERN)) {
SetMpm(s, sm);
SetMpm(s, sm, list_id);
return;
}
@ -1175,15 +1176,29 @@ void RetrieveFPForSig(const DetectEngineCtx *de_ctx, Signature *s)
}
}
SigMatch *mpm_sm = NULL;
int mpm_sm_list = -1;
for (int i = 0; i < count_final_sm_list; i++) {
if (final_sm_list[i] >= (int)s->init_data->smlists_array_size)
continue;
/* GetMpmForList may keep `mpm_sm` the same, so track if it changed */
SigMatch *prev_mpm_sm = mpm_sm;
mpm_sm = GetMpmForList(s, final_sm_list[i], mpm_sm, max_len, skip_negated_content);
if (mpm_sm != prev_mpm_sm) {
mpm_sm_list = final_sm_list[i];
}
}
#ifdef DEBUG
if (mpm_sm != NULL) {
BUG_ON(mpm_sm_list == -1);
int check_list = SigMatchListSMBelongsTo(s, mpm_sm);
BUG_ON(check_list != mpm_sm_list);
}
#endif
/* assign to signature */
SetMpm(s, mpm_sm);
SetMpm(s, mpm_sm, mpm_sm_list);
return;
}
@ -1500,7 +1515,7 @@ static void MpmStoreSetup(const DetectEngineCtx *de_ctx, MpmStore *ms)
}
if (s->init_data->mpm_sm == NULL)
continue;
int list = SigMatchListSMBelongsTo(s, s->init_data->mpm_sm);
int list = s->init_data->mpm_sm_list;
if (list < 0)
continue;
if (list != ms->sm_list)
@ -1609,7 +1624,7 @@ MpmStore *MpmStorePrepareBuffer(DetectEngineCtx *de_ctx, SigGroupHead *sgh,
if (s->init_data->mpm_sm == NULL)
continue;
int list = SigMatchListSMBelongsTo(s, s->init_data->mpm_sm);
int list = s->init_data->mpm_sm_list;
if (list < 0)
continue;
@ -1704,7 +1719,7 @@ static MpmStore *MpmStorePrepareBufferAppLayer(DetectEngineCtx *de_ctx,
if ((s->flags & am->direction) == 0)
continue;
int list = SigMatchListSMBelongsTo(s, s->init_data->mpm_sm);
int list = s->init_data->mpm_sm_list;
if (list < 0)
continue;
@ -1778,7 +1793,7 @@ static MpmStore *MpmStorePrepareBufferPkt(DetectEngineCtx *de_ctx,
if (s->init_data->mpm_sm == NULL)
continue;
int list = SigMatchListSMBelongsTo(s, s->init_data->mpm_sm);
int list = s->init_data->mpm_sm_list;
if (list < 0)
continue;
@ -1851,7 +1866,7 @@ static MpmStore *MpmStorePrepareBufferFrame(
if ((s->flags & am->direction) == 0)
continue;
int list = SigMatchListSMBelongsTo(s, s->init_data->mpm_sm);
int list = s->init_data->mpm_sm_list;
if (list < 0)
continue;
@ -2134,7 +2149,7 @@ int DetectSetFastPatternAndItsId(DetectEngineCtx *de_ctx)
for (s = de_ctx->sig_list; s != NULL; s = s->next) {
if (s->init_data->mpm_sm != NULL) {
int sm_list = SigMatchListSMBelongsTo(s, s->init_data->mpm_sm);
int sm_list = s->init_data->mpm_sm_list;
BUG_ON(sm_list == -1);
DetectContentData *cd = (DetectContentData *)s->init_data->mpm_sm->ctx;

@ -538,7 +538,7 @@ static void AppendStreamInspectEngine(Signature *s, SigMatchData *stream, int di
if (unlikely(new_engine == NULL)) {
exit(EXIT_FAILURE);
}
if (SigMatchListSMBelongsTo(s, s->init_data->mpm_sm) == DETECT_SM_LIST_PMATCH) {
if (s->init_data->mpm_sm_list == DETECT_SM_LIST_PMATCH) {
SCLogDebug("stream is mpm");
prepend = true;
new_engine->mpm = true;
@ -583,9 +583,7 @@ int DetectEngineAppInspectionEngine2Signature(DetectEngineCtx *de_ctx, Signature
SigMatchData *ptrs[nlists];
memset(&ptrs, 0, (nlists * sizeof(SigMatchData *)));
const int mpm_list = s->init_data->mpm_sm ?
SigMatchListSMBelongsTo(s, s->init_data->mpm_sm) :
-1;
const int mpm_list = s->init_data->mpm_sm ? s->init_data->mpm_sm_list : -1;
const int files_id = DetectBufferTypeGetByName("files");
@ -1830,7 +1828,7 @@ static int DetectEnginePktInspectionAppend(Signature *s, InspectionBufferPktInsp
if (e == NULL)
return -1;
e->mpm = (SigMatchListSMBelongsTo(s, s->init_data->mpm_sm) == list_id);
e->mpm = s->init_data->mpm_sm_list == list_id;
e->sm_list = list_id;
e->sm_list_base = list_id;
e->v1.Callback = Callback;

@ -1273,6 +1273,7 @@ Signature *SigAlloc (void)
SCFree(sig);
return NULL;
}
sig->init_data->mpm_sm_list = -1;
sig->init_data->smlists_array_size = DetectBufferTypeMaxId();
SCLogDebug("smlists size %u", sig->init_data->smlists_array_size);

@ -514,6 +514,8 @@ typedef struct SignatureInitData_ {
/* used at init to determine max dsize */
SigMatch *dsize_sm;
/* list id for `mpm_sm`. Should always match `SigMatchListSMBelongsTo(s, mpm_sm)`. */
int mpm_sm_list;
/* the fast pattern added from this signature */
SigMatch *mpm_sm;
/* used to speed up init of prefilter */

Loading…
Cancel
Save