*/
static int DetectAddressParse2(const DetectEngineCtx *de_ctx,
DetectAddressHead *gh, DetectAddressHead *ghn,
- char *s, int negate, ResolvedVariablesList *var_list)
+ const char *s, int negate, ResolvedVariablesList *var_list)
{
size_t x = 0;
size_t u = 0;
if (DetectAddressParse2(de_ctx, gh, ghn, temp_rule_var_address,
(negate + n_set) % 2, var_list) < 0) {
SCLogDebug("DetectAddressParse2 hates us");
+ if (temp_rule_var_address != rule_var_address)
+ SCFree(temp_rule_var_address);
goto error;
}
d_set = 0;
return -1;
}
+#include "util-hash-lookup3.h"
+
+typedef struct DetectAddressMap_ {
+ char *string;
+ DetectAddressHead *address;
+} DetectAddressMap;
+
+static uint32_t DetectAddressMapHashFunc(HashListTable *ht, void *data, uint16_t datalen)
+{
+ const DetectAddressMap *map = (DetectAddressMap *)data;
+ uint32_t hash = 0;
+
+ hash = hashlittle_safe(map->string, strlen(map->string), 0);
+ hash %= ht->array_size;
+
+ return hash;
+}
+
+static char DetectAddressMapCompareFunc(void *data1, uint16_t len1, void *data2,
+ uint16_t len2)
+{
+ DetectAddressMap *map1 = (DetectAddressMap *)data1;
+ DetectAddressMap *map2 = (DetectAddressMap *)data2;
+
+
+ int r = (strcmp(map1->string, map2->string) == 0);
+ return r;
+}
+
+static void DetectAddressMapFreeFunc(void *data)
+{
+ DetectAddressMap *map = (DetectAddressMap *)data;
+ if (map != NULL) {
+ DetectAddressHeadFree(map->address);
+ SCFree(map->string);
+ }
+ SCFree(map);
+}
+
+int DetectAddressMapInit(DetectEngineCtx *de_ctx)
+{
+ de_ctx->address_table = HashListTableInit(4096, DetectAddressMapHashFunc,
+ DetectAddressMapCompareFunc,
+ DetectAddressMapFreeFunc);
+ if (de_ctx->address_table == NULL)
+ return -1;
+
+ return 0;
+}
+
+void DetectAddressMapFree(DetectEngineCtx *de_ctx)
+{
+ if (de_ctx->address_table == NULL)
+ return;
+
+ HashListTableFree(de_ctx->address_table);
+ de_ctx->address_table = NULL;
+ return;
+}
+
+int DetectAddressMapAdd(DetectEngineCtx *de_ctx, const char *string,
+ DetectAddressHead *address)
+{
+ DetectAddressMap *map = SCCalloc(1, sizeof(*map));
+ if (map == NULL)
+ return -1;
+
+ map->string = SCStrdup(string);
+ if (map->string == NULL) {
+ SCFree(map);
+ return -1;
+ }
+ map->address = address;
+
+ BUG_ON(HashListTableAdd(de_ctx->address_table, (void *)map, 0) != 0);
+ return 0;
+}
+
+const DetectAddressHead *DetectAddressMapLookup(DetectEngineCtx *de_ctx,
+ const char *string)
+{
+ DetectAddressMap map = { (char *)string, NULL };
+
+ const DetectAddressMap *res = HashListTableLookup(de_ctx->address_table,
+ &map, 0);
+ if (res == NULL)
+ return NULL;
+ else {
+ return (const DetectAddressHead *)res->address;
+ }
+}
+
/**
* \brief Parses an address group sent as a character string and updates the
* DetectAddressHead sent as the argument with the relevant address
* \retval -1 On failure.
*/
int DetectAddressParse(const DetectEngineCtx *de_ctx,
- DetectAddressHead *gh, char *str)
+ DetectAddressHead *gh, const char *str)
{
int r;
DetectAddressHead *ghn = NULL;
return -1;
}
+const DetectAddressHead *DetectParseAddress(DetectEngineCtx *de_ctx,
+ const char *string)
+{
+ const DetectAddressHead *h = DetectAddressMapLookup(de_ctx, string);
+ if (h != NULL) {
+ SCLogDebug("found: %s :: %p", string, h);
+ return h;
+ }
+
+ SCLogDebug("%s not found", string);
+
+ DetectAddressHead *head = DetectAddressHeadInit();
+ if (head == NULL)
+ return NULL;
+
+ if (DetectAddressParse(de_ctx, head, string) == -1)
+ {
+ DetectAddressHeadFree(head);
+ return NULL;
+ }
+
+ DetectAddressMapAdd((DetectEngineCtx *)de_ctx, string, head);
+ return head;
+}
+
/**
* \brief Returns a new instance of DetectAddressHead.
*
void DetectAddressHeadCleanup(DetectAddressHead *);
int DetectAddressParseString(DetectAddress *, char *);
-int DetectAddressParse(const DetectEngineCtx *, DetectAddressHead *, char *);
+int DetectAddressParse(const DetectEngineCtx *, DetectAddressHead *, const char *);
DetectAddress *DetectAddressInit(void);
void DetectAddressFree(DetectAddress *);
void DetectAddressTests(void);
+int DetectAddressMapInit(DetectEngineCtx *de_ctx);
+void DetectAddressMapFree(DetectEngineCtx *de_ctx);
+const DetectAddressHead *DetectParseAddress(DetectEngineCtx *de_ctx,
+ const char *string);
+
#endif /* __DETECT_ADDRESS_H__ */
ThresholdHashInit(de_ctx);
VariableNameInitHash(de_ctx);
DetectParseDupSigHashInit(de_ctx);
+ DetectAddressMapInit(de_ctx);
/* init iprep... ignore errors for now */
(void)SRepInit(de_ctx);
DetectEngineCtxFreeThreadKeywordData(de_ctx);
SRepDestroy(de_ctx);
+ DetectAddressMapFree(de_ctx);
+
/* if we have a config prefix, remove the config from the tree */
if (strlen(de_ctx->config_prefix) > 0) {
/* remove config */
*
* \retval 0 ok, -1 error
*/
-int SigParseAddress(const DetectEngineCtx *de_ctx,
+static int SigParseAddress(DetectEngineCtx *de_ctx,
Signature *s, const char *addrstr, char flag)
{
SCLogDebug("Address Group \"%s\" to be parsed now", addrstr);
if (strcasecmp(addrstr, "any") == 0)
s->flags |= SIG_FLAG_SRC_ANY;
- if (DetectAddressParse(de_ctx, &s->src, (char *)addrstr) < 0)
+ s->src = DetectParseAddress(de_ctx, addrstr);
+ if (s->src == NULL)
goto error;
} else {
if (strcasecmp(addrstr, "any") == 0)
s->flags |= SIG_FLAG_DST_ANY;
- if (DetectAddressParse(de_ctx, &s->dst, (char *)addrstr) < 0)
+ s->dst = DetectParseAddress(de_ctx, addrstr);
+ if (s->dst == NULL)
goto error;
}
* \internal
* \brief split a signature string into a few blocks for further parsing
*/
-static int SigParseBasics(const DetectEngineCtx *de_ctx,
+static int SigParseBasics(DetectEngineCtx *de_ctx,
Signature *s, const char *sigstr, SignatureParser *parser, uint8_t addrs_direction)
{
#define MAX_SUBSTRINGS 30
}
SigMatchFreeArrays(s);
- DetectAddressHeadCleanup(&s->src);
- DetectAddressHeadCleanup(&s->dst);
-
if (s->sp != NULL) {
DetectPortCleanupList(s->sp);
}
/* source addresses */
uint16_t cnt = 0;
uint16_t idx = 0;
- DetectAddress *da = s->src.ipv4_head;
+ DetectAddress *da = s->src->ipv4_head;
for ( ; da != NULL; da = da->next) {
cnt++;
}
exit(EXIT_FAILURE);
}
- for (da = s->src.ipv4_head; da != NULL; da = da->next) {
+ for (da = s->src->ipv4_head; da != NULL; da = da->next) {
s->addr_src_match4[idx].ip = ntohl(da->ip.addr_data32[0]);
s->addr_src_match4[idx].ip2 = ntohl(da->ip2.addr_data32[0]);
idx++;
/* destination addresses */
cnt = 0;
idx = 0;
- da = s->dst.ipv4_head;
+ da = s->dst->ipv4_head;
for ( ; da != NULL; da = da->next) {
cnt++;
}
exit(EXIT_FAILURE);
}
- for (da = s->dst.ipv4_head; da != NULL; da = da->next) {
+ for (da = s->dst->ipv4_head; da != NULL; da = da->next) {
s->addr_dst_match4[idx].ip = ntohl(da->ip.addr_data32[0]);
s->addr_dst_match4[idx].ip2 = ntohl(da->ip2.addr_data32[0]);
idx++;
/* source addresses IPv6 */
cnt = 0;
idx = 0;
- da = s->src.ipv6_head;
+ da = s->src->ipv6_head;
for ( ; da != NULL; da = da->next) {
cnt++;
}
exit(EXIT_FAILURE);
}
- for (da = s->src.ipv6_head; da != NULL; da = da->next) {
+ for (da = s->src->ipv6_head; da != NULL; da = da->next) {
s->addr_src_match6[idx].ip[0] = ntohl(da->ip.addr_data32[0]);
s->addr_src_match6[idx].ip[1] = ntohl(da->ip.addr_data32[1]);
s->addr_src_match6[idx].ip[2] = ntohl(da->ip.addr_data32[2]);
/* destination addresses IPv6 */
cnt = 0;
idx = 0;
- da = s->dst.ipv6_head;
+ da = s->dst->ipv6_head;
for ( ; da != NULL; da = da->next) {
cnt++;
}
exit(EXIT_FAILURE);
}
- for (da = s->dst.ipv6_head; da != NULL; da = da->next) {
+ for (da = s->dst->ipv6_head; da != NULL; da = da->next) {
s->addr_dst_match6[idx].ip[0] = ntohl(da->ip.addr_data32[0]);
s->addr_dst_match6[idx].ip[1] = ntohl(da->ip.addr_data32[1]);
s->addr_dst_match6[idx].ip[2] = ntohl(da->ip.addr_data32[2]);
DetectReference *references;
/** address settings for this signature */
- DetectAddressHead src, dst;
+ const DetectAddressHead *src, *dst;
/* used at init to determine max dsize */
SigMatch *dsize_sm;
DetectPort *tcp_whitelist;
DetectPort *udp_whitelist;
+ /** table for storing the string representation with the parsers result */
+ HashListTable *address_table;
+
} DetectEngineCtx;
/* Engine groups profiles (low, medium, high, custom) */
}
// Checks if a variable is already in a resolve list and if it's not, adds it.
-int AddVariableToResolveList(ResolvedVariablesList *list, char *var)
+int AddVariableToResolveList(ResolvedVariablesList *list, const char *var)
{
ResolvedVariable *p_item;
void GenericVarAppend(GenericVar **, GenericVar *);
void GenericVarRemove(GenericVar **, GenericVar *);
-int AddVariableToResolveList(ResolvedVariablesList *list, char *var);
+int AddVariableToResolveList(ResolvedVariablesList *list, const char *var);
void CleanVariableResolveList(ResolvedVariablesList *var_list);
#endif /* __UTIL_VAR_H__ */