aboutsummaryrefslogtreecommitdiffstats
path: root/net
diff options
context:
space:
mode:
Diffstat (limited to 'net')
-rw-r--r--net/xfrm/xfrm_policy.c173
-rw-r--r--net/xfrm/xfrm_state.c170
2 files changed, 170 insertions, 173 deletions
diff --git a/net/xfrm/xfrm_policy.c b/net/xfrm/xfrm_policy.c
index af27c193697c..ca24c90d3796 100644
--- a/net/xfrm/xfrm_policy.c
+++ b/net/xfrm/xfrm_policy.c
@@ -49,8 +49,6 @@ static DEFINE_SPINLOCK(xfrm_policy_gc_lock);
49 49
50static struct xfrm_policy_afinfo *xfrm_policy_get_afinfo(unsigned short family); 50static struct xfrm_policy_afinfo *xfrm_policy_get_afinfo(unsigned short family);
51static void xfrm_policy_put_afinfo(struct xfrm_policy_afinfo *afinfo); 51static void xfrm_policy_put_afinfo(struct xfrm_policy_afinfo *afinfo);
52static struct xfrm_policy_afinfo *xfrm_policy_lock_afinfo(unsigned int family);
53static void xfrm_policy_unlock_afinfo(struct xfrm_policy_afinfo *afinfo);
54 52
55static inline int 53static inline int
56__xfrm4_selector_match(struct xfrm_selector *sel, struct flowi *fl) 54__xfrm4_selector_match(struct xfrm_selector *sel, struct flowi *fl)
@@ -86,72 +84,6 @@ int xfrm_selector_match(struct xfrm_selector *sel, struct flowi *fl,
86 return 0; 84 return 0;
87} 85}
88 86
89int xfrm_register_type(struct xfrm_type *type, unsigned short family)
90{
91 struct xfrm_policy_afinfo *afinfo = xfrm_policy_lock_afinfo(family);
92 struct xfrm_type **typemap;
93 int err = 0;
94
95 if (unlikely(afinfo == NULL))
96 return -EAFNOSUPPORT;
97 typemap = afinfo->type_map;
98
99 if (likely(typemap[type->proto] == NULL))
100 typemap[type->proto] = type;
101 else
102 err = -EEXIST;
103 xfrm_policy_unlock_afinfo(afinfo);
104 return err;
105}
106EXPORT_SYMBOL(xfrm_register_type);
107
108int xfrm_unregister_type(struct xfrm_type *type, unsigned short family)
109{
110 struct xfrm_policy_afinfo *afinfo = xfrm_policy_lock_afinfo(family);
111 struct xfrm_type **typemap;
112 int err = 0;
113
114 if (unlikely(afinfo == NULL))
115 return -EAFNOSUPPORT;
116 typemap = afinfo->type_map;
117
118 if (unlikely(typemap[type->proto] != type))
119 err = -ENOENT;
120 else
121 typemap[type->proto] = NULL;
122 xfrm_policy_unlock_afinfo(afinfo);
123 return err;
124}
125EXPORT_SYMBOL(xfrm_unregister_type);
126
127struct xfrm_type *xfrm_get_type(u8 proto, unsigned short family)
128{
129 struct xfrm_policy_afinfo *afinfo;
130 struct xfrm_type **typemap;
131 struct xfrm_type *type;
132 int modload_attempted = 0;
133
134retry:
135 afinfo = xfrm_policy_get_afinfo(family);
136 if (unlikely(afinfo == NULL))
137 return NULL;
138 typemap = afinfo->type_map;
139
140 type = typemap[proto];
141 if (unlikely(type && !try_module_get(type->owner)))
142 type = NULL;
143 if (!type && !modload_attempted) {
144 xfrm_policy_put_afinfo(afinfo);
145 request_module("xfrm-type-%d-%d",
146 (int) family, (int) proto);
147 modload_attempted = 1;
148 goto retry;
149 }
150
151 xfrm_policy_put_afinfo(afinfo);
152 return type;
153}
154
155int xfrm_dst_lookup(struct xfrm_dst **dst, struct flowi *fl, 87int xfrm_dst_lookup(struct xfrm_dst **dst, struct flowi *fl,
156 unsigned short family) 88 unsigned short family)
157{ 89{
@@ -170,94 +102,6 @@ int xfrm_dst_lookup(struct xfrm_dst **dst, struct flowi *fl,
170} 102}
171EXPORT_SYMBOL(xfrm_dst_lookup); 103EXPORT_SYMBOL(xfrm_dst_lookup);
172 104
173void xfrm_put_type(struct xfrm_type *type)
174{
175 module_put(type->owner);
176}
177
178int xfrm_register_mode(struct xfrm_mode *mode, int family)
179{
180 struct xfrm_policy_afinfo *afinfo;
181 struct xfrm_mode **modemap;
182 int err;
183
184 if (unlikely(mode->encap >= XFRM_MODE_MAX))
185 return -EINVAL;
186
187 afinfo = xfrm_policy_lock_afinfo(family);
188 if (unlikely(afinfo == NULL))
189 return -EAFNOSUPPORT;
190
191 err = -EEXIST;
192 modemap = afinfo->mode_map;
193 if (likely(modemap[mode->encap] == NULL)) {
194 modemap[mode->encap] = mode;
195 err = 0;
196 }
197
198 xfrm_policy_unlock_afinfo(afinfo);
199 return err;
200}
201EXPORT_SYMBOL(xfrm_register_mode);
202
203int xfrm_unregister_mode(struct xfrm_mode *mode, int family)
204{
205 struct xfrm_policy_afinfo *afinfo;
206 struct xfrm_mode **modemap;
207 int err;
208
209 if (unlikely(mode->encap >= XFRM_MODE_MAX))
210 return -EINVAL;
211
212 afinfo = xfrm_policy_lock_afinfo(family);
213 if (unlikely(afinfo == NULL))
214 return -EAFNOSUPPORT;
215
216 err = -ENOENT;
217 modemap = afinfo->mode_map;
218 if (likely(modemap[mode->encap] == mode)) {
219 modemap[mode->encap] = NULL;
220 err = 0;
221 }
222
223 xfrm_policy_unlock_afinfo(afinfo);
224 return err;
225}
226EXPORT_SYMBOL(xfrm_unregister_mode);
227
228struct xfrm_mode *xfrm_get_mode(unsigned int encap, int family)
229{
230 struct xfrm_policy_afinfo *afinfo;
231 struct xfrm_mode *mode;
232 int modload_attempted = 0;
233
234 if (unlikely(encap >= XFRM_MODE_MAX))
235 return NULL;
236
237retry:
238 afinfo = xfrm_policy_get_afinfo(family);
239 if (unlikely(afinfo == NULL))
240 return NULL;
241
242 mode = afinfo->mode_map[encap];
243 if (unlikely(mode && !try_module_get(mode->owner)))
244 mode = NULL;
245 if (!mode && !modload_attempted) {
246 xfrm_policy_put_afinfo(afinfo);
247 request_module("xfrm-mode-%d-%d", family, encap);
248 modload_attempted = 1;
249 goto retry;
250 }
251
252 xfrm_policy_put_afinfo(afinfo);
253 return mode;
254}
255
256void xfrm_put_mode(struct xfrm_mode *mode)
257{
258 module_put(mode->owner);
259}
260
261static inline unsigned long make_jiffies(long secs) 105static inline unsigned long make_jiffies(long secs)
262{ 106{
263 if (secs >= (MAX_SCHEDULE_TIMEOUT-1)/HZ) 107 if (secs >= (MAX_SCHEDULE_TIMEOUT-1)/HZ)
@@ -2213,23 +2057,6 @@ static void xfrm_policy_put_afinfo(struct xfrm_policy_afinfo *afinfo)
2213 read_unlock(&xfrm_policy_afinfo_lock); 2057 read_unlock(&xfrm_policy_afinfo_lock);
2214} 2058}
2215 2059
2216static struct xfrm_policy_afinfo *xfrm_policy_lock_afinfo(unsigned int family)
2217{
2218 struct xfrm_policy_afinfo *afinfo;
2219 if (unlikely(family >= NPROTO))
2220 return NULL;
2221 write_lock_bh(&xfrm_policy_afinfo_lock);
2222 afinfo = xfrm_policy_afinfo[family];
2223 if (unlikely(!afinfo))
2224 write_unlock_bh(&xfrm_policy_afinfo_lock);
2225 return afinfo;
2226}
2227
2228static void xfrm_policy_unlock_afinfo(struct xfrm_policy_afinfo *afinfo)
2229{
2230 write_unlock_bh(&xfrm_policy_afinfo_lock);
2231}
2232
2233static int xfrm_dev_event(struct notifier_block *this, unsigned long event, void *ptr) 2060static int xfrm_dev_event(struct notifier_block *this, unsigned long event, void *ptr)
2234{ 2061{
2235 struct net_device *dev = ptr; 2062 struct net_device *dev = ptr;
diff --git a/net/xfrm/xfrm_state.c b/net/xfrm/xfrm_state.c
index 344f0a6abec5..dc438f2b9442 100644
--- a/net/xfrm/xfrm_state.c
+++ b/net/xfrm/xfrm_state.c
@@ -187,6 +187,176 @@ int __xfrm_state_delete(struct xfrm_state *x);
187int km_query(struct xfrm_state *x, struct xfrm_tmpl *t, struct xfrm_policy *pol); 187int km_query(struct xfrm_state *x, struct xfrm_tmpl *t, struct xfrm_policy *pol);
188void km_state_expired(struct xfrm_state *x, int hard, u32 pid); 188void km_state_expired(struct xfrm_state *x, int hard, u32 pid);
189 189
190static struct xfrm_state_afinfo *xfrm_state_lock_afinfo(unsigned int family)
191{
192 struct xfrm_state_afinfo *afinfo;
193 if (unlikely(family >= NPROTO))
194 return NULL;
195 write_lock_bh(&xfrm_state_afinfo_lock);
196 afinfo = xfrm_state_afinfo[family];
197 if (unlikely(!afinfo))
198 write_unlock_bh(&xfrm_state_afinfo_lock);
199 return afinfo;
200}
201
202static void xfrm_state_unlock_afinfo(struct xfrm_state_afinfo *afinfo)
203{
204 write_unlock_bh(&xfrm_state_afinfo_lock);
205}
206
207int xfrm_register_type(struct xfrm_type *type, unsigned short family)
208{
209 struct xfrm_state_afinfo *afinfo = xfrm_state_lock_afinfo(family);
210 struct xfrm_type **typemap;
211 int err = 0;
212
213 if (unlikely(afinfo == NULL))
214 return -EAFNOSUPPORT;
215 typemap = afinfo->type_map;
216
217 if (likely(typemap[type->proto] == NULL))
218 typemap[type->proto] = type;
219 else
220 err = -EEXIST;
221 xfrm_state_unlock_afinfo(afinfo);
222 return err;
223}
224EXPORT_SYMBOL(xfrm_register_type);
225
226int xfrm_unregister_type(struct xfrm_type *type, unsigned short family)
227{
228 struct xfrm_state_afinfo *afinfo = xfrm_state_lock_afinfo(family);
229 struct xfrm_type **typemap;
230 int err = 0;
231
232 if (unlikely(afinfo == NULL))
233 return -EAFNOSUPPORT;
234 typemap = afinfo->type_map;
235
236 if (unlikely(typemap[type->proto] != type))
237 err = -ENOENT;
238 else
239 typemap[type->proto] = NULL;
240 xfrm_state_unlock_afinfo(afinfo);
241 return err;
242}
243EXPORT_SYMBOL(xfrm_unregister_type);
244
245static struct xfrm_type *xfrm_get_type(u8 proto, unsigned short family)
246{
247 struct xfrm_state_afinfo *afinfo;
248 struct xfrm_type **typemap;
249 struct xfrm_type *type;
250 int modload_attempted = 0;
251
252retry:
253 afinfo = xfrm_state_get_afinfo(family);
254 if (unlikely(afinfo == NULL))
255 return NULL;
256 typemap = afinfo->type_map;
257
258 type = typemap[proto];
259 if (unlikely(type && !try_module_get(type->owner)))
260 type = NULL;
261 if (!type && !modload_attempted) {
262 xfrm_state_put_afinfo(afinfo);
263 request_module("xfrm-type-%d-%d", family, proto);
264 modload_attempted = 1;
265 goto retry;
266 }
267
268 xfrm_state_put_afinfo(afinfo);
269 return type;
270}
271
272static void xfrm_put_type(struct xfrm_type *type)
273{
274 module_put(type->owner);
275}
276
277int xfrm_register_mode(struct xfrm_mode *mode, int family)
278{
279 struct xfrm_state_afinfo *afinfo;
280 struct xfrm_mode **modemap;
281 int err;
282
283 if (unlikely(mode->encap >= XFRM_MODE_MAX))
284 return -EINVAL;
285
286 afinfo = xfrm_state_lock_afinfo(family);
287 if (unlikely(afinfo == NULL))
288 return -EAFNOSUPPORT;
289
290 err = -EEXIST;
291 modemap = afinfo->mode_map;
292 if (likely(modemap[mode->encap] == NULL)) {
293 modemap[mode->encap] = mode;
294 err = 0;
295 }
296
297 xfrm_state_unlock_afinfo(afinfo);
298 return err;
299}
300EXPORT_SYMBOL(xfrm_register_mode);
301
302int xfrm_unregister_mode(struct xfrm_mode *mode, int family)
303{
304 struct xfrm_state_afinfo *afinfo;
305 struct xfrm_mode **modemap;
306 int err;
307
308 if (unlikely(mode->encap >= XFRM_MODE_MAX))
309 return -EINVAL;
310
311 afinfo = xfrm_state_lock_afinfo(family);
312 if (unlikely(afinfo == NULL))
313 return -EAFNOSUPPORT;
314
315 err = -ENOENT;
316 modemap = afinfo->mode_map;
317 if (likely(modemap[mode->encap] == mode)) {
318 modemap[mode->encap] = NULL;
319 err = 0;
320 }
321
322 xfrm_state_unlock_afinfo(afinfo);
323 return err;
324}
325EXPORT_SYMBOL(xfrm_unregister_mode);
326
327static struct xfrm_mode *xfrm_get_mode(unsigned int encap, int family)
328{
329 struct xfrm_state_afinfo *afinfo;
330 struct xfrm_mode *mode;
331 int modload_attempted = 0;
332
333 if (unlikely(encap >= XFRM_MODE_MAX))
334 return NULL;
335
336retry:
337 afinfo = xfrm_state_get_afinfo(family);
338 if (unlikely(afinfo == NULL))
339 return NULL;
340
341 mode = afinfo->mode_map[encap];
342 if (unlikely(mode && !try_module_get(mode->owner)))
343 mode = NULL;
344 if (!mode && !modload_attempted) {
345 xfrm_state_put_afinfo(afinfo);
346 request_module("xfrm-mode-%d-%d", family, encap);
347 modload_attempted = 1;
348 goto retry;
349 }
350
351 xfrm_state_put_afinfo(afinfo);
352 return mode;
353}
354
355static void xfrm_put_mode(struct xfrm_mode *mode)
356{
357 module_put(mode->owner);
358}
359
190static void xfrm_state_gc_destroy(struct xfrm_state *x) 360static void xfrm_state_gc_destroy(struct xfrm_state *x)
191{ 361{
192 del_timer_sync(&x->timer); 362 del_timer_sync(&x->timer);