fix for bug 115

remotes/origin/master-1.0.x
Anoop Saldanha 16 years ago committed by Victor Julien
parent 2d45a5994a
commit 47037ef9ec

@ -1536,6 +1536,42 @@ int SCPerfUpdateCounterArray(SCPerfCounterArray *pca, SCPerfContext *pctx,
return 1;
}
/*
* \brief Get the value of the local copy of the counter that hold this id.
*
* \param id The counter id.
* \param pca Pointer to the SCPerfCounterArray.
*
* \retval 0 on success.
* \retval -1 on error.
*/
double SCPerfGetLocalCounterValue(uint16_t id, SCPerfCounterArray *pca)
{
if (pca == NULL) {
SCLogDebug("pca NULL inside SCPerfUpdateCounterArray");
return -1;
}
if ((id < 1) || (id > pca->size)) {
SCLogDebug("counter doesn't exist");
return -1;
}
/* we check the type of the counter. Whether it's a counter that holds an
* unsigned_int_64 value or double value */
switch (pca->head[id].pc->value->type) {
/* the counter holds an unsigned_int_64 value */
case SC_PERF_TYPE_UINT64:
return pca->head[id].ui64_cnt;
/* the counter holds a double */
case SC_PERF_TYPE_DOUBLE:
return pca->head[id].d_cnt;
default:
/* this can never happen */
return -1;
}
}
/**
* \brief The output interface dispatcher for the counter api
*/

@ -229,6 +229,7 @@ inline void SCPerfCounterSetUI64(uint16_t, SCPerfCounterArray *, uint64_t);
inline void SCPerfCounterSetDouble(uint16_t, SCPerfCounterArray *, double);
int SCPerfUpdateCounterArray(SCPerfCounterArray *, SCPerfContext *, int);
double SCPerfGetLocalCounterValue(uint16_t, SCPerfCounterArray *);
void SCPerfOutputCounters(void);

@ -859,7 +859,9 @@ void DetectEngineIPOnlyThreadDeinit(DetectEngineIPOnlyThreadCtx *io_tctx) {
* \param io_ctx Pointer to the current ip only thread detection engine
* \param p Pointer to the Packet to match against
*/
void IPOnlyMatchPacket(DetectEngineCtx *de_ctx, DetectEngineIPOnlyCtx *io_ctx,
void IPOnlyMatchPacket(DetectEngineCtx *de_ctx,
DetectEngineThreadCtx *det_ctx,
DetectEngineIPOnlyCtx *io_ctx,
DetectEngineIPOnlyThreadCtx *io_tctx, Packet *p)
{
SCRadixNode *srcnode = NULL, *dstnode = NULL;
@ -933,7 +935,7 @@ void IPOnlyMatchPacket(DetectEngineCtx *de_ctx, DetectEngineIPOnlyCtx *io_ctx,
u * 8 + i, s->id, s->msg);
if (!(s->flags & SIG_FLAG_NOALERT)) {
PacketAlertHandle(de_ctx,s,p);
PacketAlertHandle(de_ctx, det_ctx, s, p);
/* set verdict on packet */
p->action |= s->action;

@ -28,7 +28,9 @@ int IPOnlyCIDRItemParseSingle(IPOnlyCIDRItem *dd, char *str);
int IPOnlyCIDRItemSetup(IPOnlyCIDRItem *gh, char *s);
void IPOnlyCIDRListPrint(IPOnlyCIDRItem *);
void IPOnlyMatchPacket(DetectEngineCtx *, DetectEngineIPOnlyCtx *, DetectEngineIPOnlyThreadCtx *, Packet *);
void IPOnlyMatchPacket(DetectEngineCtx *, DetectEngineThreadCtx *,
DetectEngineIPOnlyCtx *, DetectEngineIPOnlyThreadCtx *,
Packet *);
void IPOnlyInit(DetectEngineCtx *, DetectEngineIPOnlyCtx *);
void IPOnlyPrint(DetectEngineCtx *, DetectEngineIPOnlyCtx *);
void IPOnlyDeinit(DetectEngineCtx *, DetectEngineIPOnlyCtx *);

@ -42,20 +42,21 @@
* \param p Packet structure
*
*/
void PacketAlertHandle(DetectEngineCtx *de_ctx, Signature *sig, Packet *p)
void PacketAlertHandle(DetectEngineCtx *de_ctx, DetectEngineThreadCtx *det_ctx,
Signature *s, Packet *p)
{
SCEnter();
/* retrieve the sig match data */
DetectThresholdData *td = SigGetThresholdType(sig,p);
DetectThresholdData *td = SigGetThresholdType(s,p);
SCLogDebug("td %p", td);
/* if have none just alert, otherwise handle thresholding */
if (td == NULL) {
PacketAlertAppend(p, sig->gid, sig->id, sig->rev, sig->prio, sig->msg, sig->class_msg, sig->references);
PacketAlertAppend(det_ctx, s, p);
} else {
PacketAlertThreshold(de_ctx, td, p, sig);
PacketAlertThreshold(de_ctx, det_ctx, td, p, s);
}
SCReturn;
@ -224,7 +225,8 @@ void ThresholdHashAdd(DetectEngineCtx *de_ctx, DetectThresholdEntry *tsh_ptr, Pa
* \param s Signature structure
*
*/
void PacketAlertThreshold(DetectEngineCtx *de_ctx, DetectThresholdData *td, Packet *p, Signature *s)
void PacketAlertThreshold(DetectEngineCtx *de_ctx, DetectEngineThreadCtx *det_ctx,
DetectThresholdData *td, Packet *p, Signature *s)
{
SCEnter();
@ -277,20 +279,20 @@ void PacketAlertThreshold(DetectEngineCtx *de_ctx, DetectThresholdData *td, Pack
if (lookup_tsh != NULL) {
if ((ts.tv_sec - lookup_tsh->tv_sec1) < td->seconds) {
if (lookup_tsh->current_count < td->count) {
PacketAlertAppend(p, s->gid, s->id, s->rev, s->prio, s->msg, s->class_msg, s->references);
PacketAlertAppend(det_ctx, s, p);
}
lookup_tsh->current_count++;
} else {
lookup_tsh->tv_sec1 = ts.tv_sec;
lookup_tsh->current_count = 1;
PacketAlertAppend(p, s->gid, s->id, s->rev, s->prio, s->msg, s->class_msg, s->references);
PacketAlertAppend(det_ctx, s, p);
}
} else {
ste->tv_sec1 = ts.tv_sec;
ste->current_count = 1;
PacketAlertAppend(p, s->gid, s->id, s->rev, s->prio, s->msg, s->class_msg, s->references);
PacketAlertAppend(det_ctx, s, p);
ThresholdHashAdd(de_ctx, ste, p);
ste = NULL;
@ -307,7 +309,7 @@ void PacketAlertThreshold(DetectEngineCtx *de_ctx, DetectThresholdData *td, Pack
lookup_tsh->current_count++;
if (lookup_tsh->current_count >= td->count) {
PacketAlertAppend(p, s->gid, s->id, s->rev, s->prio, s->msg, s->class_msg, s->references);
PacketAlertAppend(det_ctx, s, p);
lookup_tsh->current_count = 0;
}
} else {
@ -319,7 +321,7 @@ void PacketAlertThreshold(DetectEngineCtx *de_ctx, DetectThresholdData *td, Pack
ste->tv_sec1 = ts.tv_sec;
if (td->count == 1) {
PacketAlertAppend(p, s->gid, s->id, s->rev, s->prio, s->msg, s->class_msg, s->references);
PacketAlertAppend(det_ctx, s, p);
ste->current_count = 0;
} else {
ThresholdHashAdd(de_ctx,ste,p);
@ -337,7 +339,7 @@ void PacketAlertThreshold(DetectEngineCtx *de_ctx, DetectThresholdData *td, Pack
if ((ts.tv_sec - lookup_tsh->tv_sec1) < td->seconds) {
lookup_tsh->current_count++;
if (lookup_tsh->current_count == td->count) {
PacketAlertAppend(p, s->gid, s->id, s->rev, s->prio, s->msg, s->class_msg, s->references);
PacketAlertAppend(det_ctx, s, p);
}
} else {
lookup_tsh->tv_sec1 = ts.tv_sec;
@ -348,7 +350,7 @@ void PacketAlertThreshold(DetectEngineCtx *de_ctx, DetectThresholdData *td, Pack
ste->tv_sec1 = ts.tv_sec;
if (td->count == 1) {
PacketAlertAppend(p, s->gid, s->id, s->rev, s->prio, s->msg, s->class_msg, s->references);
PacketAlertAppend(det_ctx, s, p);
ste->current_count = 0;
} else {
ThresholdHashAdd(de_ctx,ste,p);
@ -367,7 +369,7 @@ void PacketAlertThreshold(DetectEngineCtx *de_ctx, DetectThresholdData *td, Pack
if ((ts.tv_sec - lookup_tsh->tv_sec1) < td->seconds) {
lookup_tsh->current_count++;
if (lookup_tsh->current_count >= td->count) {
PacketAlertAppend(p, s->gid, s->id, s->rev, s->prio, s->msg, s->class_msg, s->references);
PacketAlertAppend(det_ctx, s, p);
}
} else {
lookup_tsh->tv_sec1 = ts.tv_sec;
@ -378,7 +380,7 @@ void PacketAlertThreshold(DetectEngineCtx *de_ctx, DetectThresholdData *td, Pack
ste->tv_sec1 = ts.tv_sec;
if (td->count == 1) {
PacketAlertAppend(p, s->gid, s->id, s->rev, s->prio, s->msg, s->class_msg, s->references);
PacketAlertAppend(det_ctx, s, p);
}
ThresholdHashAdd(de_ctx, ste, p);
ste = NULL;

@ -12,9 +12,11 @@
#define THRESHOLD_HASH_SIZE 0xffff
void PacketAlertHandle(DetectEngineCtx *de_ctx, Signature *sig, Packet *p);
void PacketAlertHandle(DetectEngineCtx *de_ctx, DetectEngineThreadCtx *,
Signature *sig, Packet *p);
DetectThresholdData *SigGetThresholdType(Signature *, Packet *);
void PacketAlertThreshold(DetectEngineCtx *,DetectThresholdData *, Packet *, Signature *);
void PacketAlertThreshold(DetectEngineCtx *, DetectEngineThreadCtx *,
DetectThresholdData *, Packet *, Signature *);
void ThresholdFreeFunc(void *data);
char ThresholdCompareFunc(void *data1, uint16_t len1, void *data2,uint16_t len2);
uint32_t ThresholdHashFunc(HashListTable *ht, void *data, uint16_t datalen);

@ -437,6 +437,9 @@ TmEcode DetectEngineThreadCtxInit(ThreadVars *tv, void *initdata, void **data) {
tv->sc_perf_pca = SCPerfGetAllCountersArray(&tv->sc_perf_pctx);
SCPerfAddToClubbedTMTable(tv->name, &tv->sc_perf_pctx);
/* this detection engine context belongs to this thread instance */
det_ctx->tv = tv;
*data = (void *)det_ctx;
#ifdef __SC_CUDA_SUPPORT__

@ -388,27 +388,28 @@ int PacketAlertCheck(Packet *p, uint32_t sid)
return match;
}
int PacketAlertAppend(Packet *p, uint32_t gid, uint32_t sid, uint8_t rev,
uint8_t prio, char *msg, char *class_msg, Reference *references)
int PacketAlertAppend(DetectEngineThreadCtx *det_ctx, Signature *s, Packet *p)
{
if (p->alerts.cnt == PACKET_ALERT_MAX)
return 0;
SCLogDebug("sid %"PRIu32"", sid);
SCLogDebug("sid %"PRIu32"", s->id);
if (gid > 1)
p->alerts.alerts[p->alerts.cnt].gid = gid;
if (s->gid > 1)
p->alerts.alerts[p->alerts.cnt].gid = s->gid;
else
p->alerts.alerts[p->alerts.cnt].gid = 1;
p->alerts.alerts[p->alerts.cnt].sid = sid;
p->alerts.alerts[p->alerts.cnt].rev = rev;
p->alerts.alerts[p->alerts.cnt].prio = prio;
p->alerts.alerts[p->alerts.cnt].msg = msg;
p->alerts.alerts[p->alerts.cnt].class_msg = class_msg;
p->alerts.alerts[p->alerts.cnt].references = references;
p->alerts.alerts[p->alerts.cnt].sid = s->id;
p->alerts.alerts[p->alerts.cnt].rev = s->rev;
p->alerts.alerts[p->alerts.cnt].prio = s->prio;
p->alerts.alerts[p->alerts.cnt].msg = s->msg;
p->alerts.alerts[p->alerts.cnt].class_msg = s->class_msg;
p->alerts.alerts[p->alerts.cnt].references = s->references;
p->alerts.cnt++;
SCPerfCounterIncr(det_ctx->counter_alerts, det_ctx->tv->sc_perf_pca);
return 0;
}
@ -507,7 +508,7 @@ int SigMatchSignatures(ThreadVars *th_v, DetectEngineCtx *de_ctx, DetectEngineTh
(p->flowflags & FLOW_PKT_TOCLIENT && !(p->flowflags & FLOW_PKT_TOCLIENT_IPONLY_SET))) {
SCLogDebug("testing against \"ip-only\" signatures");
IPOnlyMatchPacket(de_ctx, &de_ctx->io_ctx, &det_ctx->io_ctx, p);
IPOnlyMatchPacket(de_ctx, det_ctx, &de_ctx->io_ctx, &det_ctx->io_ctx, p);
/* save in the flow that we scanned this direction... locking is
* done in the FlowSetIPOnlyFlag function. */
if (p->flow != NULL) {
@ -521,7 +522,7 @@ int SigMatchSignatures(ThreadVars *th_v, DetectEngineCtx *de_ctx, DetectEngineTh
if (p->flow->flags & FLOW_ACTION_DROP) p->action |= ACTION_DROP;
} else {
/* Even without flow we should match the packet src/dst */
IPOnlyMatchPacket(de_ctx, &de_ctx->io_ctx, &det_ctx->io_ctx, p);
IPOnlyMatchPacket(de_ctx, det_ctx, &de_ctx->io_ctx, &det_ctx->io_ctx, p);
}
/* we assume we have an uri when we start inspection */
@ -681,7 +682,7 @@ int SigMatchSignatures(ThreadVars *th_v, DetectEngineCtx *de_ctx, DetectEngineTh
fmatch = 1;
if (!(s->flags & SIG_FLAG_NOALERT)) {
PacketAlertHandle(de_ctx,s,p);
PacketAlertHandle(de_ctx, det_ctx, s, p);
/* set verdict on packet */
p->action |= s->action;
}
@ -719,7 +720,7 @@ int SigMatchSignatures(ThreadVars *th_v, DetectEngineCtx *de_ctx, DetectEngineTh
if (!(s->flags & SIG_FLAG_NOALERT)) {
/* only add once */
if (rmatch == 0) {
PacketAlertHandle(de_ctx,s,p);
PacketAlertHandle(de_ctx, det_ctx, s, p);
/* set verdict on packet */
p->action |= s->action;
}
@ -765,7 +766,7 @@ int SigMatchSignatures(ThreadVars *th_v, DetectEngineCtx *de_ctx, DetectEngineTh
if (!(s->flags & SIG_FLAG_NOALERT)) {
/* set flowbit for this match */
PacketAlertHandle(de_ctx,s,p);
PacketAlertHandle(de_ctx, det_ctx, s, p);
/* set verdict on packet */
p->action |= s->action;
@ -8463,6 +8464,62 @@ static int SigTestDepthOffset01Wm (void) {
return SigTestDepthOffset01Real(MPM_WUMANBER);
}
static int SigTestDetectAlertCounter(void)
{
Packet p;
ThreadVars tv;
DetectEngineThreadCtx *det_ctx = NULL;
int result = 0;
memset(&tv, 0, sizeof(tv));
DetectEngineCtx *de_ctx = DetectEngineCtxInit();
if (de_ctx == NULL) {
goto end;
}
de_ctx->mpm_matcher = MPM_B2G;
de_ctx->flags |= DE_QUIET;
de_ctx->sig_list = SigInit(de_ctx, "alert tcp any any -> any any (msg:\"Test counter\"; "
"content:\"boo\"; sid:1;)");
if (de_ctx->sig_list == NULL) {
goto end;
}
SigGroupBuild(de_ctx);
tv.name = "detect_test";
DetectEngineThreadCtxInit(&tv, de_ctx, (void *)&det_ctx);
memset(&p, 0, sizeof(p));
p.src.family = AF_INET;
p.dst.family = AF_INET;
p.payload = (uint8_t *)"boo";
p.payload_len = strlen((char *)p.payload);
p.proto = IPPROTO_TCP;
Detect(&tv, &p, det_ctx, NULL);
result = (SCPerfGetLocalCounterValue(det_ctx->counter_alerts, tv.sc_perf_pca) == 1);
Detect(&tv, &p, det_ctx, NULL);
result &= (SCPerfGetLocalCounterValue(det_ctx->counter_alerts, tv.sc_perf_pca) == 2);
p.payload = (uint8_t *)"roo";
p.payload_len = strlen((char *)p.payload);
Detect(&tv, &p, det_ctx, NULL);
result &= (SCPerfGetLocalCounterValue(det_ctx->counter_alerts, tv.sc_perf_pca) == 2);
p.payload = (uint8_t *)"laboosa";
p.payload_len = strlen((char *)p.payload);
Detect(&tv, &p, det_ctx, NULL);
result &= (SCPerfGetLocalCounterValue(det_ctx->counter_alerts, tv.sc_perf_pca) == 3);
end:
SigGroupCleanup(de_ctx);
SigCleanSignatures(de_ctx);
DetectEngineThreadCtxDeinit(&tv, (void *)det_ctx);
DetectEngineCtxFree(de_ctx);
return result;
}
#endif /* UNITTESTS */
@ -8664,6 +8721,8 @@ void SigRegisterTests(void) {
UtRegisterTest("SigTestDepthOffset01B3g", SigTestDepthOffset01B3g, 1);
UtRegisterTest("SigTestDepthOffset01Wm", SigTestDepthOffset01Wm, 1);
UtRegisterTest("SigTestDetectAlertCounter", SigTestDetectAlertCounter, 1);
#endif /* UNITTESTS */
}

@ -415,6 +415,9 @@ enum {
* Detection engine thread data.
*/
typedef struct DetectionEngineThreadCtx_ {
/* the thread to which this detection engine thread belongs */
ThreadVars *tv;
/* detection engine variables */
/** offset into the payload of the last match by:
@ -663,8 +666,7 @@ int SigGroupBuild(DetectEngineCtx *);
int SigGroupCleanup();
void SigAddressPrepareBidirectionals (DetectEngineCtx *);
int PacketAlertAppend(Packet *, uint32_t, uint32_t, uint8_t, uint8_t, char *,
char *, Reference *);
int PacketAlertAppend(DetectEngineThreadCtx *, Signature *s, Packet *);
int SigLoadSignatures (DetectEngineCtx *, char *);
void SigTableSetup(void);

Loading…
Cancel
Save