diff options
author | Eric Dumazet <eric.dumazet@gmail.com> | 2011-05-18 21:14:23 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2011-05-19 16:21:22 -0400 |
commit | be281e554e2a4cf2478df7a8b8926c89454bccfa (patch) | |
tree | 7e80e5eb0aa76efcdb39a06413ff9e0ae73de35a /include/net/snmp.h | |
parent | 75e308c894c4a5e47c005b8e821ae5f539ad2ef3 (diff) |
ipv6: reduce per device ICMP mib sizes
ipv6 has per device ICMP SNMP counters, taking too much space because
they use percpu storage.
needed size per device is :
(512+4)*sizeof(long)*number_of_possible_cpus*2
On a 32bit kernel, 16 possible cpus, this wastes more than 64kbytes of
memory per ipv6 enabled network device, taken in vmalloc pool.
Since ICMP messages are rare, just use shared counters (atomic_long_t)
Per network space ICMP counters are still using percpu memory, we might
also convert them to shared counters in a future patch.
Signed-off-by: Eric Dumazet <eric.dumazet@gmail.com>
CC: Denys Fedoryshchenko <denys@visp.net.lb>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'include/net/snmp.h')
-rw-r--r-- | include/net/snmp.h | 14 |
1 files changed, 14 insertions, 0 deletions
diff --git a/include/net/snmp.h b/include/net/snmp.h index 27461d6dd46f..479083a78b0c 100644 --- a/include/net/snmp.h +++ b/include/net/snmp.h | |||
@@ -72,14 +72,24 @@ struct icmpmsg_mib { | |||
72 | 72 | ||
73 | /* ICMP6 (IPv6-ICMP) */ | 73 | /* ICMP6 (IPv6-ICMP) */ |
74 | #define ICMP6_MIB_MAX __ICMP6_MIB_MAX | 74 | #define ICMP6_MIB_MAX __ICMP6_MIB_MAX |
75 | /* per network ns counters */ | ||
75 | struct icmpv6_mib { | 76 | struct icmpv6_mib { |
76 | unsigned long mibs[ICMP6_MIB_MAX]; | 77 | unsigned long mibs[ICMP6_MIB_MAX]; |
77 | }; | 78 | }; |
79 | /* per device counters, (shared on all cpus) */ | ||
80 | struct icmpv6_mib_device { | ||
81 | atomic_long_t mibs[ICMP6_MIB_MAX]; | ||
82 | }; | ||
78 | 83 | ||
79 | #define ICMP6MSG_MIB_MAX __ICMP6MSG_MIB_MAX | 84 | #define ICMP6MSG_MIB_MAX __ICMP6MSG_MIB_MAX |
85 | /* per network ns counters */ | ||
80 | struct icmpv6msg_mib { | 86 | struct icmpv6msg_mib { |
81 | unsigned long mibs[ICMP6MSG_MIB_MAX]; | 87 | unsigned long mibs[ICMP6MSG_MIB_MAX]; |
82 | }; | 88 | }; |
89 | /* per device counters, (shared on all cpus) */ | ||
90 | struct icmpv6msg_mib_device { | ||
91 | atomic_long_t mibs[ICMP6MSG_MIB_MAX]; | ||
92 | }; | ||
83 | 93 | ||
84 | 94 | ||
85 | /* TCP */ | 95 | /* TCP */ |
@@ -114,6 +124,8 @@ struct linux_xfrm_mib { | |||
114 | */ | 124 | */ |
115 | #define DEFINE_SNMP_STAT(type, name) \ | 125 | #define DEFINE_SNMP_STAT(type, name) \ |
116 | __typeof__(type) __percpu *name[2] | 126 | __typeof__(type) __percpu *name[2] |
127 | #define DEFINE_SNMP_STAT_ATOMIC(type, name) \ | ||
128 | __typeof__(type) *name | ||
117 | #define DECLARE_SNMP_STAT(type, name) \ | 129 | #define DECLARE_SNMP_STAT(type, name) \ |
118 | extern __typeof__(type) __percpu *name[2] | 130 | extern __typeof__(type) __percpu *name[2] |
119 | 131 | ||
@@ -124,6 +136,8 @@ struct linux_xfrm_mib { | |||
124 | __this_cpu_inc(mib[0]->mibs[field]) | 136 | __this_cpu_inc(mib[0]->mibs[field]) |
125 | #define SNMP_INC_STATS_USER(mib, field) \ | 137 | #define SNMP_INC_STATS_USER(mib, field) \ |
126 | this_cpu_inc(mib[1]->mibs[field]) | 138 | this_cpu_inc(mib[1]->mibs[field]) |
139 | #define SNMP_INC_STATS_ATOMIC_LONG(mib, field) \ | ||
140 | atomic_long_inc(&mib->mibs[field]) | ||
127 | #define SNMP_INC_STATS(mib, field) \ | 141 | #define SNMP_INC_STATS(mib, field) \ |
128 | this_cpu_inc(mib[!in_softirq()]->mibs[field]) | 142 | this_cpu_inc(mib[!in_softirq()]->mibs[field]) |
129 | #define SNMP_DEC_STATS(mib, field) \ | 143 | #define SNMP_DEC_STATS(mib, field) \ |