xref: /linux/net/netfilter/ipset/pfxlen.c (revision 58e16d792a6a8c6b750f637a4649967fcac853dc)
1 // SPDX-License-Identifier: GPL-2.0-only
2 #include <linux/export.h>
3 #include <linux/netfilter/ipset/pfxlen.h>
4 
5 /* Prefixlen maps for fast conversions, by Jan Engelhardt. */
6 
7 #ifdef E
8 #undef E
9 #endif
10 
11 #define PREFIXES_MAP						\
12 	E(0x00000000, 0x00000000, 0x00000000, 0x00000000),	\
13 	E(0x80000000, 0x00000000, 0x00000000, 0x00000000),	\
14 	E(0xC0000000, 0x00000000, 0x00000000, 0x00000000),	\
15 	E(0xE0000000, 0x00000000, 0x00000000, 0x00000000),	\
16 	E(0xF0000000, 0x00000000, 0x00000000, 0x00000000),	\
17 	E(0xF8000000, 0x00000000, 0x00000000, 0x00000000),	\
18 	E(0xFC000000, 0x00000000, 0x00000000, 0x00000000),	\
19 	E(0xFE000000, 0x00000000, 0x00000000, 0x00000000),	\
20 	E(0xFF000000, 0x00000000, 0x00000000, 0x00000000),	\
21 	E(0xFF800000, 0x00000000, 0x00000000, 0x00000000),	\
22 	E(0xFFC00000, 0x00000000, 0x00000000, 0x00000000),	\
23 	E(0xFFE00000, 0x00000000, 0x00000000, 0x00000000),	\
24 	E(0xFFF00000, 0x00000000, 0x00000000, 0x00000000),	\
25 	E(0xFFF80000, 0x00000000, 0x00000000, 0x00000000),	\
26 	E(0xFFFC0000, 0x00000000, 0x00000000, 0x00000000),	\
27 	E(0xFFFE0000, 0x00000000, 0x00000000, 0x00000000),	\
28 	E(0xFFFF0000, 0x00000000, 0x00000000, 0x00000000),	\
29 	E(0xFFFF8000, 0x00000000, 0x00000000, 0x00000000),	\
30 	E(0xFFFFC000, 0x00000000, 0x00000000, 0x00000000),	\
31 	E(0xFFFFE000, 0x00000000, 0x00000000, 0x00000000),	\
32 	E(0xFFFFF000, 0x00000000, 0x00000000, 0x00000000),	\
33 	E(0xFFFFF800, 0x00000000, 0x00000000, 0x00000000),	\
34 	E(0xFFFFFC00, 0x00000000, 0x00000000, 0x00000000),	\
35 	E(0xFFFFFE00, 0x00000000, 0x00000000, 0x00000000),	\
36 	E(0xFFFFFF00, 0x00000000, 0x00000000, 0x00000000),	\
37 	E(0xFFFFFF80, 0x00000000, 0x00000000, 0x00000000),	\
38 	E(0xFFFFFFC0, 0x00000000, 0x00000000, 0x00000000),	\
39 	E(0xFFFFFFE0, 0x00000000, 0x00000000, 0x00000000),	\
40 	E(0xFFFFFFF0, 0x00000000, 0x00000000, 0x00000000),	\
41 	E(0xFFFFFFF8, 0x00000000, 0x00000000, 0x00000000),	\
42 	E(0xFFFFFFFC, 0x00000000, 0x00000000, 0x00000000),	\
43 	E(0xFFFFFFFE, 0x00000000, 0x00000000, 0x00000000),	\
44 	E(0xFFFFFFFF, 0x00000000, 0x00000000, 0x00000000),	\
45 	E(0xFFFFFFFF, 0x80000000, 0x00000000, 0x00000000),	\
46 	E(0xFFFFFFFF, 0xC0000000, 0x00000000, 0x00000000),	\
47 	E(0xFFFFFFFF, 0xE0000000, 0x00000000, 0x00000000),	\
48 	E(0xFFFFFFFF, 0xF0000000, 0x00000000, 0x00000000),	\
49 	E(0xFFFFFFFF, 0xF8000000, 0x00000000, 0x00000000),	\
50 	E(0xFFFFFFFF, 0xFC000000, 0x00000000, 0x00000000),	\
51 	E(0xFFFFFFFF, 0xFE000000, 0x00000000, 0x00000000),	\
52 	E(0xFFFFFFFF, 0xFF000000, 0x00000000, 0x00000000),	\
53 	E(0xFFFFFFFF, 0xFF800000, 0x00000000, 0x00000000),	\
54 	E(0xFFFFFFFF, 0xFFC00000, 0x00000000, 0x00000000),	\
55 	E(0xFFFFFFFF, 0xFFE00000, 0x00000000, 0x00000000),	\
56 	E(0xFFFFFFFF, 0xFFF00000, 0x00000000, 0x00000000),	\
57 	E(0xFFFFFFFF, 0xFFF80000, 0x00000000, 0x00000000),	\
58 	E(0xFFFFFFFF, 0xFFFC0000, 0x00000000, 0x00000000),	\
59 	E(0xFFFFFFFF, 0xFFFE0000, 0x00000000, 0x00000000),	\
60 	E(0xFFFFFFFF, 0xFFFF0000, 0x00000000, 0x00000000),	\
61 	E(0xFFFFFFFF, 0xFFFF8000, 0x00000000, 0x00000000),	\
62 	E(0xFFFFFFFF, 0xFFFFC000, 0x00000000, 0x00000000),	\
63 	E(0xFFFFFFFF, 0xFFFFE000, 0x00000000, 0x00000000),	\
64 	E(0xFFFFFFFF, 0xFFFFF000, 0x00000000, 0x00000000),	\
65 	E(0xFFFFFFFF, 0xFFFFF800, 0x00000000, 0x00000000),	\
66 	E(0xFFFFFFFF, 0xFFFFFC00, 0x00000000, 0x00000000),	\
67 	E(0xFFFFFFFF, 0xFFFFFE00, 0x00000000, 0x00000000),	\
68 	E(0xFFFFFFFF, 0xFFFFFF00, 0x00000000, 0x00000000),	\
69 	E(0xFFFFFFFF, 0xFFFFFF80, 0x00000000, 0x00000000),	\
70 	E(0xFFFFFFFF, 0xFFFFFFC0, 0x00000000, 0x00000000),	\
71 	E(0xFFFFFFFF, 0xFFFFFFE0, 0x00000000, 0x00000000),	\
72 	E(0xFFFFFFFF, 0xFFFFFFF0, 0x00000000, 0x00000000),	\
73 	E(0xFFFFFFFF, 0xFFFFFFF8, 0x00000000, 0x00000000),	\
74 	E(0xFFFFFFFF, 0xFFFFFFFC, 0x00000000, 0x00000000),	\
75 	E(0xFFFFFFFF, 0xFFFFFFFE, 0x00000000, 0x00000000),	\
76 	E(0xFFFFFFFF, 0xFFFFFFFF, 0x00000000, 0x00000000),	\
77 	E(0xFFFFFFFF, 0xFFFFFFFF, 0x80000000, 0x00000000),	\
78 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xC0000000, 0x00000000),	\
79 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xE0000000, 0x00000000),	\
80 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xF0000000, 0x00000000),	\
81 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xF8000000, 0x00000000),	\
82 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFC000000, 0x00000000),	\
83 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFE000000, 0x00000000),	\
84 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFF000000, 0x00000000),	\
85 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFF800000, 0x00000000),	\
86 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFC00000, 0x00000000),	\
87 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFE00000, 0x00000000),	\
88 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFF00000, 0x00000000),	\
89 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFF80000, 0x00000000),	\
90 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFC0000, 0x00000000),	\
91 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFE0000, 0x00000000),	\
92 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFF0000, 0x00000000),	\
93 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFF8000, 0x00000000),	\
94 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFC000, 0x00000000),	\
95 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFE000, 0x00000000),	\
96 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFF000, 0x00000000),	\
97 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFF800, 0x00000000),	\
98 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFC00, 0x00000000),	\
99 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFE00, 0x00000000),	\
100 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFF00, 0x00000000),	\
101 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFF80, 0x00000000),	\
102 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFC0, 0x00000000),	\
103 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFE0, 0x00000000),	\
104 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFF0, 0x00000000),	\
105 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFF8, 0x00000000),	\
106 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFC, 0x00000000),	\
107 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFE, 0x00000000),	\
108 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0x00000000),	\
109 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0x80000000),	\
110 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xC0000000),	\
111 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xE0000000),	\
112 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xF0000000),	\
113 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xF8000000),	\
114 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFC000000),	\
115 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFE000000),	\
116 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFF000000),	\
117 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFF800000),	\
118 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFC00000),	\
119 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFE00000),	\
120 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFF00000),	\
121 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFF80000),	\
122 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFC0000),	\
123 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFE0000),	\
124 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFF0000),	\
125 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFF8000),	\
126 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFC000),	\
127 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFE000),	\
128 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFF000),	\
129 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFF800),	\
130 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFC00),	\
131 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFE00),	\
132 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFF00),	\
133 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFF80),	\
134 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFC0),	\
135 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFE0),	\
136 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFF0),	\
137 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFF8),	\
138 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFC),	\
139 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFE),	\
140 	E(0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF),
141 
142 #define E(a, b, c, d) \
143 	{.ip6 = { \
144 		htonl(a), htonl(b), \
145 		htonl(c), htonl(d), \
146 	} }
147 
148 /* This table works for both IPv4 and IPv6;
149  * just use prefixlen_netmask_map[prefixlength].ip.
150  */
151 const union nf_inet_addr ip_set_netmask_map[] = {
152 	PREFIXES_MAP
153 };
154 EXPORT_SYMBOL_GPL(ip_set_netmask_map);
155 
156 #undef  E
157 #define E(a, b, c, d)					\
158 	{.ip6 = { (__force __be32)a, (__force __be32)b,	\
159 		  (__force __be32)c, (__force __be32)d,	\
160 	} }
161 
162 /* This table works for both IPv4 and IPv6;
163  * just use prefixlen_hostmask_map[prefixlength].ip.
164  */
165 const union nf_inet_addr ip_set_hostmask_map[] = {
166 	PREFIXES_MAP
167 };
168 EXPORT_SYMBOL_GPL(ip_set_hostmask_map);
169 
170 /* Find the largest network which matches the range from left, in host order. */
171 u32
ip_set_range_to_cidr(u32 from,u32 to,u8 * cidr)172 ip_set_range_to_cidr(u32 from, u32 to, u8 *cidr)
173 {
174 	u32 last;
175 	u8 i;
176 
177 	for (i = 1; i < 32; i++) {
178 		if ((from & ip_set_hostmask(i)) != from)
179 			continue;
180 		last = from | ~ip_set_hostmask(i);
181 		if (!after(last, to)) {
182 			*cidr = i;
183 			return last;
184 		}
185 	}
186 	*cidr = 32;
187 	return from;
188 }
189 EXPORT_SYMBOL_GPL(ip_set_range_to_cidr);
190