GNU Linux-libre 4.19.245-gnu1
[releases.git] / include / linux / netfilter / ipset / ip_set_counter.h
1 #ifndef _IP_SET_COUNTER_H
2 #define _IP_SET_COUNTER_H
3
4 /* Copyright (C) 2015 Jozsef Kadlecsik <kadlec@blackhole.kfki.hu>
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License version 2 as
8  * published by the Free Software Foundation.
9  */
10
11 #ifdef __KERNEL__
12
13 static inline void
14 ip_set_add_bytes(u64 bytes, struct ip_set_counter *counter)
15 {
16         atomic64_add((long long)bytes, &(counter)->bytes);
17 }
18
19 static inline void
20 ip_set_add_packets(u64 packets, struct ip_set_counter *counter)
21 {
22         atomic64_add((long long)packets, &(counter)->packets);
23 }
24
25 static inline u64
26 ip_set_get_bytes(const struct ip_set_counter *counter)
27 {
28         return (u64)atomic64_read(&(counter)->bytes);
29 }
30
31 static inline u64
32 ip_set_get_packets(const struct ip_set_counter *counter)
33 {
34         return (u64)atomic64_read(&(counter)->packets);
35 }
36
37 static inline bool
38 ip_set_match_counter(u64 counter, u64 match, u8 op)
39 {
40         switch (op) {
41         case IPSET_COUNTER_NONE:
42                 return true;
43         case IPSET_COUNTER_EQ:
44                 return counter == match;
45         case IPSET_COUNTER_NE:
46                 return counter != match;
47         case IPSET_COUNTER_LT:
48                 return counter < match;
49         case IPSET_COUNTER_GT:
50                 return counter > match;
51         }
52         return false;
53 }
54
55 static inline void
56 ip_set_update_counter(struct ip_set_counter *counter,
57                       const struct ip_set_ext *ext, u32 flags)
58 {
59         if (ext->packets != ULLONG_MAX &&
60             !(flags & IPSET_FLAG_SKIP_COUNTER_UPDATE)) {
61                 ip_set_add_bytes(ext->bytes, counter);
62                 ip_set_add_packets(ext->packets, counter);
63         }
64 }
65
66 static inline bool
67 ip_set_put_counter(struct sk_buff *skb, const struct ip_set_counter *counter)
68 {
69         return nla_put_net64(skb, IPSET_ATTR_BYTES,
70                              cpu_to_be64(ip_set_get_bytes(counter)),
71                              IPSET_ATTR_PAD) ||
72                nla_put_net64(skb, IPSET_ATTR_PACKETS,
73                              cpu_to_be64(ip_set_get_packets(counter)),
74                              IPSET_ATTR_PAD);
75 }
76
77 static inline void
78 ip_set_init_counter(struct ip_set_counter *counter,
79                     const struct ip_set_ext *ext)
80 {
81         if (ext->bytes != ULLONG_MAX)
82                 atomic64_set(&(counter)->bytes, (long long)(ext->bytes));
83         if (ext->packets != ULLONG_MAX)
84                 atomic64_set(&(counter)->packets, (long long)(ext->packets));
85 }
86
87 #endif /* __KERNEL__ */
88 #endif /* _IP_SET_COUNTER_H */