/** \brief initialize the configuration * \warning Not thread safe */ void DefragInitConfig(char quiet) { SCLogDebug("initializing defrag engine..."); memset(&defrag_config, 0, sizeof(defrag_config)); //SC_ATOMIC_INIT(flow_flags); SC_ATOMIC_INIT(defragtracker_counter); SC_ATOMIC_INIT(defrag_memuse); SC_ATOMIC_INIT(defragtracker_prune_idx); DefragTrackerQueueInit(&defragtracker_spare_q); /* set defaults */ defrag_config.hash_rand = (uint32_t)RandomGet(); defrag_config.hash_size = DEFRAG_DEFAULT_HASHSIZE; defrag_config.memcap = DEFRAG_DEFAULT_MEMCAP; defrag_config.prealloc = DEFRAG_DEFAULT_PREALLOC; /* Check if we have memcap and hash_size defined at config */ const char *conf_val; uint32_t configval = 0; /** set config values for memcap, prealloc and hash_size */ if ((ConfGet("defrag.memcap", &conf_val)) == 1) { if (ParseSizeStringU64(conf_val, &defrag_config.memcap) < 0) { SCLogError(SC_ERR_SIZE_PARSE, "Error parsing defrag.memcap " "from conf file - %s. Killing engine", conf_val); exit(EXIT_FAILURE); } } if ((ConfGet("defrag.hash-size", &conf_val)) == 1) { if (ByteExtractStringUint32(&configval, 10, strlen(conf_val), conf_val) > 0) { defrag_config.hash_size = configval; } else { WarnInvalidConfEntry("defrag.hash-size", "%"PRIu32, defrag_config.hash_size); } } if ((ConfGet("defrag.trackers", &conf_val)) == 1) { if (ByteExtractStringUint32(&configval, 10, strlen(conf_val), conf_val) > 0) { defrag_config.prealloc = configval; } else { WarnInvalidConfEntry("defrag.trackers", "%"PRIu32, defrag_config.prealloc); } } SCLogDebug("DefragTracker config from suricata.yaml: memcap: %"PRIu64", hash-size: " "%"PRIu32", prealloc: %"PRIu32, defrag_config.memcap, defrag_config.hash_size, defrag_config.prealloc); /* alloc hash memory */ uint64_t hash_size = defrag_config.hash_size * sizeof(DefragTrackerHashRow); if (!(DEFRAG_CHECK_MEMCAP(hash_size))) { SCLogError(SC_ERR_DEFRAG_INIT, "allocating defrag hash failed: " "max defrag memcap is smaller than projected hash size. " "Memcap: %"PRIu64", Hash table size %"PRIu64". Calculate " "total hash size by multiplying \"defrag.hash-size\" with %"PRIuMAX", " "which is the hash bucket size.", defrag_config.memcap, hash_size, (uintmax_t)sizeof(DefragTrackerHashRow)); exit(EXIT_FAILURE); } defragtracker_hash = SCCalloc(defrag_config.hash_size, sizeof(DefragTrackerHashRow)); if (unlikely(defragtracker_hash == NULL)) { SCLogError(SC_ERR_FATAL, "Fatal error encountered in DefragTrackerInitConfig. Exiting..."); exit(EXIT_FAILURE); } memset(defragtracker_hash, 0, defrag_config.hash_size * sizeof(DefragTrackerHashRow)); uint32_t i = 0; for (i = 0; i < defrag_config.hash_size; i++) { DRLOCK_INIT(&defragtracker_hash[i]); } (void) SC_ATOMIC_ADD(defrag_memuse, (defrag_config.hash_size * sizeof(DefragTrackerHashRow))); if (quiet == FALSE) { SCLogConfig("allocated %"PRIu64" bytes of memory for the defrag hash... " "%" PRIu32 " buckets of size %" PRIuMAX "", SC_ATOMIC_GET(defrag_memuse), defrag_config.hash_size, (uintmax_t)sizeof(DefragTrackerHashRow)); } if ((ConfGet("defrag.prealloc", &conf_val)) == 1) { if (ConfValIsTrue(conf_val)) { /* pre allocate defrag trackers */ for (i = 0; i < defrag_config.prealloc; i++) { if (!(DEFRAG_CHECK_MEMCAP(sizeof(DefragTracker)))) { SCLogError(SC_ERR_DEFRAG_INIT, "preallocating defrag trackers failed: " "max defrag memcap reached. Memcap %"PRIu64", " "Memuse %"PRIu64".", defrag_config.memcap, ((uint64_t)SC_ATOMIC_GET(defrag_memuse) + (uint64_t)sizeof(DefragTracker))); exit(EXIT_FAILURE); } DefragTracker *h = DefragTrackerAlloc(); if (h == NULL) { SCLogError(SC_ERR_DEFRAG_INIT, "preallocating defrag failed: %s", strerror(errno)); exit(EXIT_FAILURE); } DefragTrackerEnqueue(&defragtracker_spare_q,h); } if (quiet == FALSE) { SCLogConfig("preallocated %" PRIu32 " defrag trackers of size %" PRIuMAX "", defragtracker_spare_q.len, (uintmax_t)sizeof(DefragTracker)); } } } if (quiet == FALSE) { SCLogConfig("defrag memory usage: %"PRIu64" bytes, maximum: %"PRIu64, SC_ATOMIC_GET(defrag_memuse), defrag_config.memcap); } return; }
/** \brief initialize the configuration * \warning Not thread safe */ void IPPairInitConfig(char quiet) { SCLogDebug("initializing ippair engine..."); if (IPPairStorageSize() > 0) g_ippair_size = sizeof(IPPair) + IPPairStorageSize(); memset(&ippair_config, 0, sizeof(ippair_config)); //SC_ATOMIC_INIT(flow_flags); SC_ATOMIC_INIT(ippair_counter); SC_ATOMIC_INIT(ippair_memuse); SC_ATOMIC_INIT(ippair_prune_idx); SC_ATOMIC_INIT(ippair_config.memcap); IPPairQueueInit(&ippair_spare_q); /* set defaults */ ippair_config.hash_rand = (uint32_t)RandomGet(); ippair_config.hash_size = IPPAIR_DEFAULT_HASHSIZE; ippair_config.prealloc = IPPAIR_DEFAULT_PREALLOC; SC_ATOMIC_SET(ippair_config.memcap, IPPAIR_DEFAULT_MEMCAP); /* Check if we have memcap and hash_size defined at config */ const char *conf_val; uint32_t configval = 0; /** set config values for memcap, prealloc and hash_size */ uint64_t ippair_memcap; if ((ConfGet("ippair.memcap", &conf_val)) == 1) { if (ParseSizeStringU64(conf_val, &ippair_memcap) < 0) { SCLogError(SC_ERR_SIZE_PARSE, "Error parsing ippair.memcap " "from conf file - %s. Killing engine", conf_val); exit(EXIT_FAILURE); } else { SC_ATOMIC_SET(ippair_config.memcap, ippair_memcap); } } if ((ConfGet("ippair.hash-size", &conf_val)) == 1) { if (ByteExtractStringUint32(&configval, 10, strlen(conf_val), conf_val) > 0) { ippair_config.hash_size = configval; } } if ((ConfGet("ippair.prealloc", &conf_val)) == 1) { if (ByteExtractStringUint32(&configval, 10, strlen(conf_val), conf_val) > 0) { ippair_config.prealloc = configval; } else { WarnInvalidConfEntry("ippair.prealloc", "%"PRIu32, ippair_config.prealloc); } } SCLogDebug("IPPair config from suricata.yaml: memcap: %"PRIu64", hash-size: " "%"PRIu32", prealloc: %"PRIu32, SC_ATOMIC_GET(ippair_config.memcap), ippair_config.hash_size, ippair_config.prealloc); /* alloc hash memory */ uint64_t hash_size = ippair_config.hash_size * sizeof(IPPairHashRow); if (!(IPPAIR_CHECK_MEMCAP(hash_size))) { SCLogError(SC_ERR_IPPAIR_INIT, "allocating ippair hash failed: " "max ippair memcap is smaller than projected hash size. " "Memcap: %"PRIu64", Hash table size %"PRIu64". Calculate " "total hash size by multiplying \"ippair.hash-size\" with %"PRIuMAX", " "which is the hash bucket size.", SC_ATOMIC_GET(ippair_config.memcap), hash_size, (uintmax_t)sizeof(IPPairHashRow)); exit(EXIT_FAILURE); } ippair_hash = SCMallocAligned(ippair_config.hash_size * sizeof(IPPairHashRow), CLS); if (unlikely(ippair_hash == NULL)) { SCLogError(SC_ERR_FATAL, "Fatal error encountered in IPPairInitConfig. Exiting..."); exit(EXIT_FAILURE); } memset(ippair_hash, 0, ippair_config.hash_size * sizeof(IPPairHashRow)); uint32_t i = 0; for (i = 0; i < ippair_config.hash_size; i++) { HRLOCK_INIT(&ippair_hash[i]); } (void) SC_ATOMIC_ADD(ippair_memuse, (ippair_config.hash_size * sizeof(IPPairHashRow))); if (quiet == FALSE) { SCLogConfig("allocated %"PRIu64" bytes of memory for the ippair hash... " "%" PRIu32 " buckets of size %" PRIuMAX "", SC_ATOMIC_GET(ippair_memuse), ippair_config.hash_size, (uintmax_t)sizeof(IPPairHashRow)); } /* pre allocate ippairs */ for (i = 0; i < ippair_config.prealloc; i++) { if (!(IPPAIR_CHECK_MEMCAP(g_ippair_size))) { SCLogError(SC_ERR_IPPAIR_INIT, "preallocating ippairs failed: " "max ippair memcap reached. Memcap %"PRIu64", " "Memuse %"PRIu64".", SC_ATOMIC_GET(ippair_config.memcap), ((uint64_t)SC_ATOMIC_GET(ippair_memuse) + g_ippair_size)); exit(EXIT_FAILURE); } IPPair *h = IPPairAlloc(); if (h == NULL) { SCLogError(SC_ERR_IPPAIR_INIT, "preallocating ippair failed: %s", strerror(errno)); exit(EXIT_FAILURE); } IPPairEnqueue(&ippair_spare_q,h); } if (quiet == FALSE) { SCLogConfig("preallocated %" PRIu32 " ippairs of size %" PRIu16 "", ippair_spare_q.len, g_ippair_size); SCLogConfig("ippair memory usage: %"PRIu64" bytes, maximum: %"PRIu64, SC_ATOMIC_GET(ippair_memuse), SC_ATOMIC_GET(ippair_config.memcap)); } return; }