Skip to content

Commit 9c262d7

Browse files
author
Herton R. Krzesinski
committed
Merge: icmp: Add counters for rate limits
MR: https://gitlab.com/redhat/centos-stream/src/kernel/centos-stream-9/-/merge_requests/2044 Bugzilla: https://bugzilla.redhat.com/show_bug.cgi?id=2155801 Upstream Status: https://git.kernel.org/pub/scm/linux/kernel/git/netdev/net-next.git commit d094113 Author: Jamie Bainbridge <jamie.bainbridge@gmail.com> Date: Wed Jan 25 11:16:52 2023 +1100 icmp: Add counters for rate limits There are multiple ICMP rate limiting mechanisms: * Global limits: net.ipv4.icmp_msgs_burst/icmp_msgs_per_sec * v4 per-host limits: net.ipv4.icmp_ratelimit/ratemask * v6 per-host limits: net.ipv6.icmp_ratelimit/ratemask However, when ICMP output is limited, there is no way to tell which limit has been hit or even if the limits are responsible for the lack of ICMP output. Add counters for each of the cases above. As we are within local_bh_disable(), use the __INC stats variant. Example output: IcmpOutRateLimitGlobal 134 0.0 IcmpOutRateLimitHost 770 0.0 Icmp6OutRateLimitHost 84 0.0 Signed-off-by: Jamie Bainbridge <jamie.bainbridge@gmail.com> Suggested-by: Abhishek Rawal <rawal.abhishek92@gmail.com> Link: https://lore.kernel.org/r/273b32241e6b7fdc5c609e6f5ebc68caf3994342.1674605770.git.jamie.bainbridge@gmail.com Signed-off-by: Paolo Abeni <pabeni@redhat.com> Signed-off-by: Jamie Bainbridge <jbainbri@redhat.com> Approved-by: Paolo Abeni <pabeni@redhat.com> Approved-by: Hangbin Liu <haliu@redhat.com> Signed-off-by: Herton R. Krzesinski <herton@redhat.com>
2 parents c478484 + b615d9f commit 9c262d7

File tree

5 files changed

+16
-3
lines changed

5 files changed

+16
-3
lines changed

include/uapi/linux/snmp.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -95,6 +95,8 @@ enum
9595
ICMP_MIB_OUTADDRMASKS, /* OutAddrMasks */
9696
ICMP_MIB_OUTADDRMASKREPS, /* OutAddrMaskReps */
9797
ICMP_MIB_CSUMERRORS, /* InCsumErrors */
98+
ICMP_MIB_RATELIMITGLOBAL, /* OutRateLimitGlobal */
99+
ICMP_MIB_RATELIMITHOST, /* OutRateLimitHost */
98100
__ICMP_MIB_MAX
99101
};
100102

@@ -112,6 +114,7 @@ enum
112114
ICMP6_MIB_OUTMSGS, /* OutMsgs */
113115
ICMP6_MIB_OUTERRORS, /* OutErrors */
114116
ICMP6_MIB_CSUMERRORS, /* InCsumErrors */
117+
ICMP6_MIB_RATELIMITHOST, /* OutRateLimitHost */
115118
__ICMP6_MIB_MAX
116119
};
117120

net/ipv4/icmp.c

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -296,6 +296,7 @@ static bool icmpv4_global_allow(struct net *net, int type, int code)
296296
if (icmp_global_allow())
297297
return true;
298298

299+
__ICMP_INC_STATS(net, ICMP_MIB_RATELIMITGLOBAL);
299300
return false;
300301
}
301302

@@ -325,6 +326,8 @@ static bool icmpv4_xrlim_allow(struct net *net, struct rtable *rt,
325326
if (peer)
326327
inet_putpeer(peer);
327328
out:
329+
if (!rc)
330+
__ICMP_INC_STATS(net, ICMP_MIB_RATELIMITHOST);
328331
return rc;
329332
}
330333

net/ipv4/proc.c

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -352,7 +352,7 @@ static void icmp_put(struct seq_file *seq)
352352
seq_puts(seq, "\nIcmp: InMsgs InErrors InCsumErrors");
353353
for (i = 0; icmpmibmap[i].name; i++)
354354
seq_printf(seq, " In%s", icmpmibmap[i].name);
355-
seq_puts(seq, " OutMsgs OutErrors");
355+
seq_puts(seq, " OutMsgs OutErrors OutRateLimitGlobal OutRateLimitHost");
356356
for (i = 0; icmpmibmap[i].name; i++)
357357
seq_printf(seq, " Out%s", icmpmibmap[i].name);
358358
seq_printf(seq, "\nIcmp: %lu %lu %lu",
@@ -362,9 +362,11 @@ static void icmp_put(struct seq_file *seq)
362362
for (i = 0; icmpmibmap[i].name; i++)
363363
seq_printf(seq, " %lu",
364364
atomic_long_read(ptr + icmpmibmap[i].index));
365-
seq_printf(seq, " %lu %lu",
365+
seq_printf(seq, " %lu %lu %lu %lu",
366366
snmp_fold_field(net->mib.icmp_statistics, ICMP_MIB_OUTMSGS),
367-
snmp_fold_field(net->mib.icmp_statistics, ICMP_MIB_OUTERRORS));
367+
snmp_fold_field(net->mib.icmp_statistics, ICMP_MIB_OUTERRORS),
368+
snmp_fold_field(net->mib.icmp_statistics, ICMP_MIB_RATELIMITGLOBAL),
369+
snmp_fold_field(net->mib.icmp_statistics, ICMP_MIB_RATELIMITHOST));
368370
for (i = 0; icmpmibmap[i].name; i++)
369371
seq_printf(seq, " %lu",
370372
atomic_long_read(ptr + (icmpmibmap[i].index | 0x100)));

net/ipv6/icmp.c

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -190,6 +190,7 @@ static bool icmpv6_global_allow(struct net *net, int type)
190190
if (icmp_global_allow())
191191
return true;
192192

193+
__ICMP_INC_STATS(net, ICMP_MIB_RATELIMITGLOBAL);
193194
return false;
194195
}
195196

@@ -231,6 +232,9 @@ static bool icmpv6_xrlim_allow(struct sock *sk, u8 type,
231232
if (peer)
232233
inet_putpeer(peer);
233234
}
235+
if (!res)
236+
__ICMP6_INC_STATS(net, ip6_dst_idev(dst),
237+
ICMP6_MIB_RATELIMITHOST);
234238
dst_release(dst);
235239
return res;
236240
}

net/ipv6/proc.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -94,6 +94,7 @@ static const struct snmp_mib snmp6_icmp6_list[] = {
9494
SNMP_MIB_ITEM("Icmp6OutMsgs", ICMP6_MIB_OUTMSGS),
9595
SNMP_MIB_ITEM("Icmp6OutErrors", ICMP6_MIB_OUTERRORS),
9696
SNMP_MIB_ITEM("Icmp6InCsumErrors", ICMP6_MIB_CSUMERRORS),
97+
SNMP_MIB_ITEM("Icmp6OutRateLimitHost", ICMP6_MIB_RATELIMITHOST),
9798
SNMP_MIB_SENTINEL
9899
};
99100

0 commit comments

Comments
 (0)