From 80a5aad70e93d44c59cd5de4c57ca550152426f7 Mon Sep 17 00:00:00 2001 From: Mark Huang Date: Mon, 10 Jan 2005 18:38:07 +0000 Subject: [PATCH] patch-o-matic-ng-20050103 conntrack-acct --- net/ipv4/netfilter/ip_conntrack_amanda.c | 2 +- net/ipv4/netfilter/ip_conntrack_core.c | 26 ++++++++++++++++--- .../netfilter/ip_conntrack_proto_generic.c | 4 +-- net/ipv4/netfilter/ip_conntrack_proto_icmp.c | 2 +- net/ipv4/netfilter/ip_conntrack_proto_tcp.c | 2 +- net/ipv4/netfilter/ip_conntrack_proto_udp.c | 7 ++--- net/ipv4/netfilter/ip_conntrack_standalone.c | 17 +++++++++++- 7 files changed, 47 insertions(+), 13 deletions(-) diff --git a/net/ipv4/netfilter/ip_conntrack_amanda.c b/net/ipv4/netfilter/ip_conntrack_amanda.c index 4e8f4d83b..40ed4474d 100644 --- a/net/ipv4/netfilter/ip_conntrack_amanda.c +++ b/net/ipv4/netfilter/ip_conntrack_amanda.c @@ -58,7 +58,7 @@ static int help(struct sk_buff *skb, /* increase the UDP timeout of the master connection as replies from * Amanda clients to the server can be quite delayed */ - ip_ct_refresh(ct, master_timeout * HZ); + ip_ct_refresh_acct(ct, ctinfo, NULL, master_timeout * HZ); /* No data? */ dataoff = skb->nh.iph->ihl*4 + sizeof(struct udphdr); diff --git a/net/ipv4/netfilter/ip_conntrack_core.c b/net/ipv4/netfilter/ip_conntrack_core.c index 05fbb43cc..e3de532f7 100644 --- a/net/ipv4/netfilter/ip_conntrack_core.c +++ b/net/ipv4/netfilter/ip_conntrack_core.c @@ -1166,21 +1166,39 @@ void ip_conntrack_helper_unregister(struct ip_conntrack_helper *me) synchronize_net(); } -/* Refresh conntrack for this many jiffies. */ -void ip_ct_refresh(struct ip_conntrack *ct, unsigned long extra_jiffies) +static inline void ct_add_counters(struct ip_conntrack *ct, + enum ip_conntrack_info ctinfo, + const struct sk_buff *skb) +{ +#ifdef CONFIG_IP_NF_CT_ACCT + if (skb) { + ct->counters[CTINFO2DIR(ctinfo)].packets++; + ct->counters[CTINFO2DIR(ctinfo)].bytes += + ntohs(skb->nh.iph->tot_len); + } +#endif +} + +/* Refresh conntrack for this many jiffies and do accounting (if skb != NULL) */ +void ip_ct_refresh_acct(struct ip_conntrack *ct, + enum ip_conntrack_info ctinfo, + const struct sk_buff *skb, + unsigned long extra_jiffies) { IP_NF_ASSERT(ct->timeout.data == (unsigned long)ct); /* If not in hash table, timer will not be active yet */ - if (!is_confirmed(ct)) + if (!is_confirmed(ct)) { ct->timeout.expires = extra_jiffies; - else { + ct_add_counters(ct, ctinfo, skb); + } else { WRITE_LOCK(&ip_conntrack_lock); /* Need del_timer for race avoidance (may already be dying). */ if (del_timer(&ct->timeout)) { ct->timeout.expires = jiffies + extra_jiffies; add_timer(&ct->timeout); } + ct_add_counters(ct, ctinfo, skb); WRITE_UNLOCK(&ip_conntrack_lock); } } diff --git a/net/ipv4/netfilter/ip_conntrack_proto_generic.c b/net/ipv4/netfilter/ip_conntrack_proto_generic.c index 0df558a58..6a7db7754 100644 --- a/net/ipv4/netfilter/ip_conntrack_proto_generic.c +++ b/net/ipv4/netfilter/ip_conntrack_proto_generic.c @@ -50,9 +50,9 @@ static unsigned int generic_print_conntrack(char *buffer, /* Returns verdict for packet, or -1 for invalid. */ static int packet(struct ip_conntrack *conntrack, const struct sk_buff *skb, - enum ip_conntrack_info conntrackinfo) + enum ip_conntrack_info ctinfo) { - ip_ct_refresh(conntrack, ip_ct_generic_timeout); + ip_ct_refresh_acct(conntrack, ctinfo, skb, ip_ct_generic_timeout); return NF_ACCEPT; } diff --git a/net/ipv4/netfilter/ip_conntrack_proto_icmp.c b/net/ipv4/netfilter/ip_conntrack_proto_icmp.c index 47114840f..e854193eb 100644 --- a/net/ipv4/netfilter/ip_conntrack_proto_icmp.c +++ b/net/ipv4/netfilter/ip_conntrack_proto_icmp.c @@ -94,7 +94,7 @@ static int icmp_packet(struct ip_conntrack *ct, ct->timeout.function((unsigned long)ct); } else { atomic_inc(&ct->proto.icmp.count); - ip_ct_refresh(ct, ip_ct_icmp_timeout); + ip_ct_refresh_acct(ct, ctinfo, skb, ip_ct_icmp_timeout); } return NF_ACCEPT; diff --git a/net/ipv4/netfilter/ip_conntrack_proto_tcp.c b/net/ipv4/netfilter/ip_conntrack_proto_tcp.c index 463cafa66..73fe0401d 100644 --- a/net/ipv4/netfilter/ip_conntrack_proto_tcp.c +++ b/net/ipv4/netfilter/ip_conntrack_proto_tcp.c @@ -225,7 +225,7 @@ static int tcp_packet(struct ip_conntrack *conntrack, set_bit(IPS_ASSURED_BIT, &conntrack->status); out: WRITE_UNLOCK(&tcp_lock); - ip_ct_refresh(conntrack, *tcp_timeouts[newconntrack]); + ip_ct_refresh_acct(conntrack, ctinfo, skb, *tcp_timeouts[newconntrack]); return NF_ACCEPT; } diff --git a/net/ipv4/netfilter/ip_conntrack_proto_udp.c b/net/ipv4/netfilter/ip_conntrack_proto_udp.c index a63c32d18..a69e14b5c 100644 --- a/net/ipv4/netfilter/ip_conntrack_proto_udp.c +++ b/net/ipv4/netfilter/ip_conntrack_proto_udp.c @@ -60,16 +60,17 @@ static unsigned int udp_print_conntrack(char *buffer, /* Returns verdict for packet, and may modify conntracktype */ static int udp_packet(struct ip_conntrack *conntrack, const struct sk_buff *skb, - enum ip_conntrack_info conntrackinfo) + enum ip_conntrack_info ctinfo) { /* If we've seen traffic both ways, this is some kind of UDP stream. Extend timeout. */ if (test_bit(IPS_SEEN_REPLY_BIT, &conntrack->status)) { - ip_ct_refresh(conntrack, ip_ct_udp_timeout_stream); + ip_ct_refresh_acct(conntrack, ctinfo, skb, + ip_ct_udp_timeout_stream); /* Also, more likely to be important, and not a probe */ set_bit(IPS_ASSURED_BIT, &conntrack->status); } else - ip_ct_refresh(conntrack, ip_ct_udp_timeout); + ip_ct_refresh_acct(conntrack, ctinfo, skb, ip_ct_udp_timeout); return NF_ACCEPT; } diff --git a/net/ipv4/netfilter/ip_conntrack_standalone.c b/net/ipv4/netfilter/ip_conntrack_standalone.c index fd688f4fe..76c827dcb 100644 --- a/net/ipv4/netfilter/ip_conntrack_standalone.c +++ b/net/ipv4/netfilter/ip_conntrack_standalone.c @@ -83,6 +83,17 @@ print_expect(char *buffer, const struct ip_conntrack_expect *expect) return len; } +#ifdef CONFIG_IP_NF_CT_ACCT +static unsigned int +print_counters(char *buffer, struct ip_conntrack_counter *counter) +{ + return sprintf(buffer, "packets=%llu bytes=%llu ", + counter->packets, counter->bytes); +} +#else +#define print_counters(x, y) 0 +#endif + static unsigned int print_conntrack(char *buffer, struct ip_conntrack *conntrack) { @@ -103,12 +114,16 @@ print_conntrack(char *buffer, struct ip_conntrack *conntrack) &conntrack->tuplehash[IP_CT_DIR_ORIGINAL].tuple, proto); len += sprintf(buffer + len, "xid=%d ", conntrack->xid[IP_CT_DIR_ORIGINAL]); + len += print_counters(buffer + len, + &conntrack->counters[IP_CT_DIR_ORIGINAL]); if (!(test_bit(IPS_SEEN_REPLY_BIT, &conntrack->status))) len += sprintf(buffer + len, "[UNREPLIED] "); len += print_tuple(buffer + len, &conntrack->tuplehash[IP_CT_DIR_REPLY].tuple, proto); len += sprintf(buffer + len, "xid=%d ", conntrack->xid[IP_CT_DIR_REPLY]); + len += print_counters(buffer + len, + &conntrack->counters[IP_CT_DIR_REPLY]); if (test_bit(IPS_ASSURED_BIT, &conntrack->status)) len += sprintf(buffer + len, "[ASSURED] "); len += sprintf(buffer + len, "use=%u ", @@ -640,7 +655,7 @@ EXPORT_SYMBOL(need_ip_conntrack); EXPORT_SYMBOL(ip_conntrack_helper_register); EXPORT_SYMBOL(ip_conntrack_helper_unregister); EXPORT_SYMBOL(ip_ct_selective_cleanup); -EXPORT_SYMBOL(ip_ct_refresh); +EXPORT_SYMBOL(ip_ct_refresh_acct); EXPORT_SYMBOL(ip_ct_find_proto); EXPORT_SYMBOL(__ip_ct_find_proto); EXPORT_SYMBOL(ip_ct_find_helper); -- 2.47.0