Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit a051a8f7 authored by Harald Welte's avatar Harald Welte Committed by David S. Miller
Browse files

[NETFILTER]: Use only 32bit counters for CONNTRACK_ACCT



Initially we used 64bit counters for conntrack-based accounting, since we
had no event mechanism to tell userspace that our counters are about to
overflow.  With nfnetlink_conntrack, we now have such a event mechanism and
thus can save 16bytes per connection.

Signed-off-by: default avatarHarald Welte <laforge@netfilter.org>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent d4875b04
Loading
Loading
Loading
Loading
+4 −2
Original line number Diff line number Diff line
@@ -84,8 +84,10 @@ enum ctattr_protoinfo_tcp {

enum ctattr_counters {
	CTA_COUNTERS_UNSPEC,
	CTA_COUNTERS_PACKETS,
	CTA_COUNTERS_BYTES,
	CTA_COUNTERS_PACKETS,		/* old 64bit counters */
	CTA_COUNTERS_BYTES,		/* old 64bit counters */
	CTA_COUNTERS32_PACKETS,
	CTA_COUNTERS32_BYTES,
	__CTA_COUNTERS_MAX
};
#define CTA_COUNTERS_MAX (__CTA_COUNTERS_MAX - 1)
+6 −2
Original line number Diff line number Diff line
@@ -117,6 +117,10 @@ enum ip_conntrack_events
	/* NAT info */
	IPCT_NATINFO_BIT = 10,
	IPCT_NATINFO = (1 << IPCT_NATINFO_BIT),

	/* Counter highest bit has been set */
	IPCT_COUNTER_FILLING_BIT = 11,
	IPCT_COUNTER_FILLING = (1 << IPCT_COUNTER_FILLING_BIT),
};

enum ip_conntrack_expect_events {
@@ -192,8 +196,8 @@ do { \

struct ip_conntrack_counter
{
	u_int64_t packets;
	u_int64_t bytes;
	u_int32_t packets;
	u_int32_t bytes;
};

struct ip_conntrack_helper;
+8 −5
Original line number Diff line number Diff line
@@ -1119,7 +1119,7 @@ void __ip_ct_refresh_acct(struct ip_conntrack *ct,
			unsigned long extra_jiffies,
			int do_acct)
{
	int do_event = 0;
	int event = 0;

	IP_NF_ASSERT(ct->timeout.data == (unsigned long)ct);
	IP_NF_ASSERT(skb);
@@ -1129,13 +1129,13 @@ void __ip_ct_refresh_acct(struct ip_conntrack *ct,
	/* If not in hash table, timer will not be active yet */
	if (!is_confirmed(ct)) {
		ct->timeout.expires = extra_jiffies;
		do_event = 1;
		event = IPCT_REFRESH;
	} else {
		/* 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);
			do_event = 1;
			event = IPCT_REFRESH;
		}
	}

@@ -1144,14 +1144,17 @@ void __ip_ct_refresh_acct(struct ip_conntrack *ct,
		ct->counters[CTINFO2DIR(ctinfo)].packets++;
		ct->counters[CTINFO2DIR(ctinfo)].bytes += 
						ntohs(skb->nh.iph->tot_len);
		if ((ct->counters[CTINFO2DIR(ctinfo)].packets & 0x80000000)
		    || (ct->counters[CTINFO2DIR(ctinfo)].bytes & 0x80000000))
			event |= IPCT_COUNTER_FILLING;
	}
#endif

	write_unlock_bh(&ip_conntrack_lock);

	/* must be unlocked when calling event cache */
	if (do_event)
		ip_conntrack_event_cache(IPCT_REFRESH, skb);
	if (event)
		ip_conntrack_event_cache(event, skb);
}

#if defined(CONFIG_IP_NF_CONNTRACK_NETLINK) || \
+4 −4
Original line number Diff line number Diff line
@@ -177,11 +177,11 @@ ctnetlink_dump_counters(struct sk_buff *skb, const struct ip_conntrack *ct,
	struct nfattr *nest_count = NFA_NEST(skb, type);
	u_int64_t tmp;

	tmp = cpu_to_be64(ct->counters[dir].packets);
	NFA_PUT(skb, CTA_COUNTERS_PACKETS, sizeof(u_int64_t), &tmp);
	tmp = htonl(ct->counters[dir].packets);
	NFA_PUT(skb, CTA_COUNTERS32_PACKETS, sizeof(u_int32_t), &tmp);

	tmp = cpu_to_be64(ct->counters[dir].bytes);
	NFA_PUT(skb, CTA_COUNTERS_BYTES, sizeof(u_int64_t), &tmp);
	tmp = htonl(ct->counters[dir].bytes);
	NFA_PUT(skb, CTA_COUNTERS32_BYTES, sizeof(u_int32_t), &tmp);

	NFA_NEST_END(skb, nest_count);