summaryrefslogtreecommitdiffstats
path: root/src/freebsd_ipfw.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/freebsd_ipfw.c')
-rw-r--r--src/freebsd_ipfw.c370
1 files changed, 0 insertions, 370 deletions
diff --git a/src/freebsd_ipfw.c b/src/freebsd_ipfw.c
deleted file mode 100644
index 81264b3f3..000000000
--- a/src/freebsd_ipfw.c
+++ /dev/null
@@ -1,370 +0,0 @@
-#include "common.h"
-
-#include <netinet/ip_fw.h>
-
-#define FREE_MEM_THRESHOLD 10000 // number of unused chunks that trigger memory freeing
-
-#define COMMON_IPFW_ERROR() error("DISABLED: ipfw.packets chart"); \
- error("DISABLED: ipfw.bytes chart"); \
- error("DISABLED: ipfw.dyn_active chart"); \
- error("DISABLED: ipfw.dyn_expired chart"); \
- error("DISABLED: ipfw.mem chart");
-
-// --------------------------------------------------------------------------------------------------------------------
-// ipfw
-
-int do_ipfw(int update_every, usec_t dt) {
- (void)dt;
-#if __FreeBSD__ >= 11
-
- static int do_static = -1, do_dynamic = -1, do_mem = -1;
-
- if (unlikely(do_static == -1)) {
- do_static = config_get_boolean("plugin:freebsd:ipfw", "counters for static rules", 1);
- do_dynamic = config_get_boolean("plugin:freebsd:ipfw", "number of dynamic rules", 1);
- do_mem = config_get_boolean("plugin:freebsd:ipfw", "allocated memory", 1);
- }
-
- // variables for getting ipfw configuration
-
- int error;
- static int ipfw_socket = -1;
- static ipfw_cfg_lheader *cfg = NULL;
- ip_fw3_opheader *op3 = NULL;
- static socklen_t *optlen = NULL, cfg_size = 0;
-
- // variables for static rules handling
-
- ipfw_obj_ctlv *ctlv = NULL;
- ipfw_obj_tlv *rbase = NULL;
- int rcnt = 0;
-
- int n, seen;
- struct ip_fw_rule *rule;
- struct ip_fw_bcounter *cntr;
- int c = 0;
-
- char rule_num_str[12];
-
- // variables for dynamic rules handling
-
- caddr_t dynbase = NULL;
- size_t dynsz = 0;
- size_t readsz = sizeof(*cfg);;
- int ttype = 0;
- ipfw_obj_tlv *tlv;
- ipfw_dyn_rule *dyn_rule;
- uint16_t rulenum, prev_rulenum = IPFW_DEFAULT_RULE;
- unsigned srn, static_rules_num = 0;
- static size_t dyn_rules_num_size = 0;
-
- static struct dyn_rule_num {
- uint16_t rule_num;
- uint32_t active_rules;
- uint32_t expired_rules;
- } *dyn_rules_num = NULL;
-
- uint32_t *dyn_rules_counter;
-
- if (likely(do_static | do_dynamic | do_mem)) {
-
- // initialize the smallest ipfw_cfg_lheader possible
-
- if (unlikely((optlen == NULL) || (cfg == NULL))) {
- optlen = reallocz(optlen, sizeof(socklen_t));
- *optlen = cfg_size = 32;
- cfg = reallocz(cfg, *optlen);
- }
-
- // get socket descriptor and initialize ipfw_cfg_lheader structure
-
- if (unlikely(ipfw_socket == -1))
- ipfw_socket = socket(AF_INET, SOCK_RAW, IPPROTO_RAW);
- if (unlikely(ipfw_socket == -1)) {
- error("FREEBSD: can't get socket for ipfw configuration");
- error("FREEBSD: run netdata as root to get access to ipfw data");
- COMMON_IPFW_ERROR();
- return 1;
- }
-
- bzero(cfg, 32);
- cfg->flags = IPFW_CFG_GET_STATIC | IPFW_CFG_GET_COUNTERS | IPFW_CFG_GET_STATES;
- op3 = &cfg->opheader;
- op3->opcode = IP_FW_XGET;
-
- // get ifpw configuration size than get configuration
-
- *optlen = cfg_size;
- error = getsockopt(ipfw_socket, IPPROTO_IP, IP_FW3, op3, optlen);
- if (error)
- if (errno != ENOMEM) {
- error("FREEBSD: ipfw socket reading error");
- COMMON_IPFW_ERROR();
- return 1;
- }
- if ((cfg->size > cfg_size) || ((cfg_size - cfg->size) > sizeof(struct dyn_rule_num) * FREE_MEM_THRESHOLD)) {
- *optlen = cfg_size = cfg->size;
- cfg = reallocz(cfg, *optlen);
- bzero(cfg, 32);
- cfg->flags = IPFW_CFG_GET_STATIC | IPFW_CFG_GET_COUNTERS | IPFW_CFG_GET_STATES;
- op3 = &cfg->opheader;
- op3->opcode = IP_FW_XGET;
- error = getsockopt(ipfw_socket, IPPROTO_IP, IP_FW3, op3, optlen);
- if (error) {
- error("FREEBSD: ipfw socket reading error");
- COMMON_IPFW_ERROR();
- return 1;
- }
- }
-
- // go through static rules configuration structures
-
- ctlv = (ipfw_obj_ctlv *) (cfg + 1);
-
- if (cfg->flags & IPFW_CFG_GET_STATIC) {
- /* We've requested static rules */
- if (ctlv->head.type == IPFW_TLV_TBLNAME_LIST) {
- readsz += ctlv->head.length;
- ctlv = (ipfw_obj_ctlv *) ((caddr_t) ctlv +
- ctlv->head.length);
- }
-
- if (ctlv->head.type == IPFW_TLV_RULE_LIST) {
- rbase = (ipfw_obj_tlv *) (ctlv + 1);
- rcnt = ctlv->count;
- readsz += ctlv->head.length;
- ctlv = (ipfw_obj_ctlv *) ((caddr_t) ctlv + ctlv->head.length);
- }
- }
-
- if ((cfg->flags & IPFW_CFG_GET_STATES) && (readsz != *optlen)) {
- /* We may have some dynamic states */
- dynsz = *optlen - readsz;
- /* Skip empty header */
- if (dynsz != sizeof(ipfw_obj_ctlv))
- dynbase = (caddr_t) ctlv;
- else
- dynsz = 0;
- }
-
- // --------------------------------------------------------------------
-
- if (likely(do_mem)) {
- static RRDSET *st_mem = NULL;
- static RRDDIM *rd_dyn_mem = NULL;
- static RRDDIM *rd_stat_mem = NULL;
-
- if (unlikely(!st_mem)) {
- st_mem = rrdset_create_localhost("ipfw",
- "mem",
- NULL,
- "memory allocated",
- NULL,
- "Memory allocated by rules",
- "bytes",
- "freebsd",
- "ipfw",
- 3005,
- update_every,
- RRDSET_TYPE_STACKED
- );
- rrdset_flag_set(st_mem, RRDSET_FLAG_DETAIL);
-
- rd_dyn_mem = rrddim_add(st_mem, "dynamic", NULL, 1, 1, RRD_ALGORITHM_ABSOLUTE);
- rd_stat_mem = rrddim_add(st_mem, "static", NULL, 1, 1, RRD_ALGORITHM_ABSOLUTE);
- } else
- rrdset_next(st_mem);
-
- rrddim_set_by_pointer(st_mem, rd_dyn_mem, dynsz);
- rrddim_set_by_pointer(st_mem, rd_stat_mem, *optlen - dynsz);
- rrdset_done(st_mem);
- }
-
- // --------------------------------------------------------------------
-
- static RRDSET *st_packets = NULL, *st_bytes = NULL;
- RRDDIM *rd_packets = NULL, *rd_bytes = NULL;
-
- if (likely(do_static || do_dynamic)) {
- if (likely(do_static)) {
- if (unlikely(!st_packets))
- st_packets = rrdset_create_localhost("ipfw",
- "packets",
- NULL,
- "static rules",
- NULL,
- "Packets",
- "packets/s",
- "freebsd",
- "ipfw",
- 3001,
- update_every,
- RRDSET_TYPE_STACKED
- );
- else
- rrdset_next(st_packets);
-
- if (unlikely(!st_bytes))
- st_bytes = rrdset_create_localhost("ipfw",
- "bytes",
- NULL,
- "static rules",
- NULL,
- "Bytes",
- "bytes/s",
- "freebsd",
- "ipfw",
- 3002,
- update_every,
- RRDSET_TYPE_STACKED
- );
- else
- rrdset_next(st_bytes);
- }
-
- for (n = seen = 0; n < rcnt; n++, rbase = (ipfw_obj_tlv *) ((caddr_t) rbase + rbase->length)) {
- cntr = (struct ip_fw_bcounter *) (rbase + 1);
- rule = (struct ip_fw_rule *) ((caddr_t) cntr + cntr->size);
- if (rule->rulenum != prev_rulenum)
- static_rules_num++;
- if (rule->rulenum > IPFW_DEFAULT_RULE)
- break;
-
- if (likely(do_static)) {
- sprintf(rule_num_str, "%d_%d", rule->rulenum, rule->id);
-
- rd_packets = rrddim_find(st_packets, rule_num_str);
- if (unlikely(!rd_packets))
- rd_packets = rrddim_add(st_packets, rule_num_str, NULL, 1, 1, RRD_ALGORITHM_INCREMENTAL);
- rrddim_set_by_pointer(st_packets, rd_packets, cntr->pcnt);
-
- rd_bytes = rrddim_find(st_bytes, rule_num_str);
- if (unlikely(!rd_bytes))
- rd_bytes = rrddim_add(st_bytes, rule_num_str, NULL, 1, 1, RRD_ALGORITHM_INCREMENTAL);
- rrddim_set_by_pointer(st_bytes, rd_bytes, cntr->bcnt);
- }
-
- c += rbase->length;
- seen++;
- }
-
- if (likely(do_static)) {
- rrdset_done(st_packets);
- rrdset_done(st_bytes);
- }
- }
-
- // --------------------------------------------------------------------
-
- // go through dynamic rules configuration structures
-
- if (likely(do_dynamic && (dynsz > 0))) {
- if ((dyn_rules_num_size < sizeof(struct dyn_rule_num) * static_rules_num) ||
- ((dyn_rules_num_size - sizeof(struct dyn_rule_num) * static_rules_num) >
- sizeof(struct dyn_rule_num) * FREE_MEM_THRESHOLD)) {
- dyn_rules_num_size = sizeof(struct dyn_rule_num) * static_rules_num;
- dyn_rules_num = reallocz(dyn_rules_num, dyn_rules_num_size);
- }
- bzero(dyn_rules_num, sizeof(struct dyn_rule_num) * static_rules_num);
- dyn_rules_num->rule_num = IPFW_DEFAULT_RULE;
-
- if (dynsz > 0 && ctlv->head.type == IPFW_TLV_DYNSTATE_LIST) {
- dynbase += sizeof(*ctlv);
- dynsz -= sizeof(*ctlv);
- ttype = IPFW_TLV_DYN_ENT;
- }
-
- while (dynsz > 0) {
- tlv = (ipfw_obj_tlv *) dynbase;
- if (tlv->type != ttype)
- break;
-
- dyn_rule = (ipfw_dyn_rule *) (tlv + 1);
- bcopy(&dyn_rule->rule, &rulenum, sizeof(rulenum));
-
- for (srn = 0; srn < (static_rules_num - 1); srn++) {
- if (dyn_rule->expire > 0)
- dyn_rules_counter = &dyn_rules_num[srn].active_rules;
- else
- dyn_rules_counter = &dyn_rules_num[srn].expired_rules;
- if (dyn_rules_num[srn].rule_num == rulenum) {
- (*dyn_rules_counter)++;
- break;
- }
- if (dyn_rules_num[srn].rule_num == IPFW_DEFAULT_RULE) {
- dyn_rules_num[srn].rule_num = rulenum;
- dyn_rules_num[srn + 1].rule_num = IPFW_DEFAULT_RULE;
- (*dyn_rules_counter)++;
- break;
- }
- }
-
- dynsz -= tlv->length;
- dynbase += tlv->length;
- }
-
- // --------------------------------------------------------------------
-
- static RRDSET *st_active = NULL, *st_expired = NULL;
- RRDDIM *rd_active = NULL, *rd_expired = NULL;
-
- if (unlikely(!st_active))
- st_active = rrdset_create_localhost("ipfw",
- "active",
- NULL,
- "dynamic_rules",
- NULL,
- "Active rules",
- "rules",
- "freebsd",
- "ipfw",
- 3003,
- update_every,
- RRDSET_TYPE_STACKED
- );
- else
- rrdset_next(st_active);
-
- if (unlikely(!st_expired))
- st_expired = rrdset_create_localhost("ipfw",
- "expired",
- NULL,
- "dynamic_rules",
- NULL,
- "Expired rules",
- "rules",
- "freebsd",
- "ipfw",
- 3004,
- update_every,
- RRDSET_TYPE_STACKED
- );
- else
- rrdset_next(st_expired);
-
- for (srn = 0; (srn < (static_rules_num - 1)) && (dyn_rules_num[srn].rule_num != IPFW_DEFAULT_RULE); srn++) {
- sprintf(rule_num_str, "%d", dyn_rules_num[srn].rule_num);
-
- rd_active = rrddim_find(st_active, rule_num_str);
- if (unlikely(!rd_active))
- rd_active = rrddim_add(st_active, rule_num_str, NULL, 1, 1, RRD_ALGORITHM_ABSOLUTE);
- rrddim_set_by_pointer(st_active, rd_active, dyn_rules_num[srn].active_rules);
-
- rd_expired = rrddim_find(st_expired, rule_num_str);
- if (unlikely(!rd_expired))
- rd_expired = rrddim_add(st_expired, rule_num_str, NULL, 1, 1, RRD_ALGORITHM_ABSOLUTE);
- rrddim_set_by_pointer(st_expired, rd_expired, dyn_rules_num[srn].expired_rules);
- }
-
- rrdset_done(st_active);
- rrdset_done(st_expired);
- }
- }
-
- return 0;
-#else
- error("FREEBSD: ipfw charts supported for FreeBSD 11.0 and newer releases only");
- COMMON_IPFW_ERROR();
- return 1;
-#endif
-}