]> Git Repo - linux.git/blame - include/linux/mroute_base.h
ipmr, ip6mr: Unite vif seq functions
[linux.git] / include / linux / mroute_base.h
CommitLineData
6853f21f
YM
1#ifndef __LINUX_MROUTE_BASE_H
2#define __LINUX_MROUTE_BASE_H
3
4#include <linux/netdevice.h>
b70432f7 5#include <linux/rhashtable.h>
c8d61968 6#include <linux/spinlock.h>
b70432f7
YM
7#include <net/net_namespace.h>
8#include <net/sock.h>
6853f21f
YM
9
10/**
11 * struct vif_device - interface representor for multicast routing
12 * @dev: network device being used
13 * @bytes_in: statistic; bytes ingressing
14 * @bytes_out: statistic; bytes egresing
15 * @pkt_in: statistic; packets ingressing
16 * @pkt_out: statistic; packets egressing
17 * @rate_limit: Traffic shaping (NI)
18 * @threshold: TTL threshold
19 * @flags: Control flags
20 * @link: Physical interface index
21 * @dev_parent_id: device parent id
22 * @local: Local address
23 * @remote: Remote address for tunnels
24 */
25struct vif_device {
26 struct net_device *dev;
27 unsigned long bytes_in, bytes_out;
28 unsigned long pkt_in, pkt_out;
29 unsigned long rate_limit;
30 unsigned char threshold;
31 unsigned short flags;
32 int link;
33
34 /* Currently only used by ipmr */
35 struct netdev_phys_item_id dev_parent_id;
36 __be32 local, remote;
37};
38
b70432f7
YM
39#ifndef MAXVIFS
40/* This one is nasty; value is defined in uapi using different symbols for
41 * mroute and morute6 but both map into same 32.
42 */
43#define MAXVIFS 32
44#endif
45
46#define VIF_EXISTS(_mrt, _idx) (!!((_mrt)->vif_table[_idx].dev))
47
494fff56
YM
48/**
49 * struct mr_mfc - common multicast routing entries
50 * @mnode: rhashtable list
51 * @mfc_parent: source interface (iif)
52 * @mfc_flags: entry flags
53 * @expires: unresolved entry expire time
54 * @unresolved: unresolved cached skbs
55 * @last_assert: time of last assert
56 * @minvif: minimum VIF id
57 * @maxvif: maximum VIF id
58 * @bytes: bytes that have passed for this entry
59 * @pkt: packets that have passed for this entry
60 * @wrong_if: number of wrong source interface hits
61 * @lastuse: time of last use of the group (traffic or update)
62 * @ttls: OIF TTL threshold array
63 * @refcount: reference count for this entry
64 * @list: global entry list
65 * @rcu: used for entry destruction
66 */
67struct mr_mfc {
68 struct rhlist_head mnode;
69 unsigned short mfc_parent;
70 int mfc_flags;
71
72 union {
73 struct {
74 unsigned long expires;
75 struct sk_buff_head unresolved;
76 } unres;
77 struct {
78 unsigned long last_assert;
79 int minvif;
80 int maxvif;
81 unsigned long bytes;
82 unsigned long pkt;
83 unsigned long wrong_if;
84 unsigned long lastuse;
85 unsigned char ttls[MAXVIFS];
86 refcount_t refcount;
87 } res;
88 } mfc_un;
89 struct list_head list;
90 struct rcu_head rcu;
91};
92
845c9a7a
YM
93struct mr_table;
94
95/**
96 * struct mr_table_ops - callbacks and info for protocol-specific ops
97 * @rht_params: parameters for accessing the MFC hash
98 * @cmparg_any: a hash key to be used for matching on (*,*) routes
99 */
100struct mr_table_ops {
101 const struct rhashtable_params *rht_params;
102 void *cmparg_any;
103};
104
b70432f7
YM
105/**
106 * struct mr_table - a multicast routing table
107 * @list: entry within a list of multicast routing tables
108 * @net: net where this table belongs
845c9a7a 109 * @ops: protocol specific operations
b70432f7
YM
110 * @id: identifier of the table
111 * @mroute_sk: socket associated with the table
112 * @ipmr_expire_timer: timer for handling unresolved routes
113 * @mfc_unres_queue: list of unresolved MFC entries
114 * @vif_table: array containing all possible vifs
115 * @mfc_hash: Hash table of all resolved routes for easy lookup
116 * @mfc_cache_list: list of resovled routes for possible traversal
117 * @maxvif: Identifier of highest value vif currently in use
118 * @cache_resolve_queue_len: current size of unresolved queue
119 * @mroute_do_assert: Whether to inform userspace on wrong ingress
120 * @mroute_do_pim: Whether to receive IGMP PIMv1
121 * @mroute_reg_vif_num: PIM-device vif index
122 */
123struct mr_table {
124 struct list_head list;
125 possible_net_t net;
845c9a7a 126 struct mr_table_ops ops;
b70432f7
YM
127 u32 id;
128 struct sock __rcu *mroute_sk;
129 struct timer_list ipmr_expire_timer;
130 struct list_head mfc_unres_queue;
131 struct vif_device vif_table[MAXVIFS];
132 struct rhltable mfc_hash;
133 struct list_head mfc_cache_list;
134 int maxvif;
135 atomic_t cache_resolve_queue_len;
136 bool mroute_do_assert;
137 bool mroute_do_pim;
138 int mroute_reg_vif_num;
139};
140
6853f21f
YM
141#ifdef CONFIG_IP_MROUTE_COMMON
142void vif_device_init(struct vif_device *v,
143 struct net_device *dev,
144 unsigned long rate_limit,
145 unsigned char threshold,
146 unsigned short flags,
147 unsigned short get_iflink_mask);
0bbbf0e7
YM
148
149struct mr_table *
150mr_table_alloc(struct net *net, u32 id,
845c9a7a 151 struct mr_table_ops *ops,
0bbbf0e7
YM
152 void (*expire_func)(struct timer_list *t),
153 void (*table_set)(struct mr_table *mrt,
154 struct net *net));
845c9a7a
YM
155
156/* These actually return 'struct mr_mfc *', but to avoid need for explicit
157 * castings they simply return void.
158 */
159void *mr_mfc_find_parent(struct mr_table *mrt,
160 void *hasharg, int parent);
161void *mr_mfc_find_any_parent(struct mr_table *mrt, int vifi);
162void *mr_mfc_find_any(struct mr_table *mrt, int vifi, void *hasharg);
163
6853f21f
YM
164#else
165static inline void vif_device_init(struct vif_device *v,
166 struct net_device *dev,
167 unsigned long rate_limit,
168 unsigned char threshold,
169 unsigned short flags,
170 unsigned short get_iflink_mask)
171{
172}
0bbbf0e7 173
845c9a7a 174static inline void *
0bbbf0e7 175mr_table_alloc(struct net *net, u32 id,
845c9a7a 176 struct mr_table_ops *ops,
0bbbf0e7
YM
177 void (*expire_func)(struct timer_list *t),
178 void (*table_set)(struct mr_table *mrt,
179 struct net *net))
180{
181 return NULL;
182}
845c9a7a
YM
183
184static inline void *mr_mfc_find_parent(struct mr_table *mrt,
185 void *hasharg, int parent)
186{
187 return NULL;
188}
189
190static inline void *mr_mfc_find_any_parent(struct mr_table *mrt,
191 int vifi)
192{
193 return NULL;
194}
195
196static inline struct mr_mfc *mr_mfc_find_any(struct mr_table *mrt,
197 int vifi, void *hasharg)
198{
199 return NULL;
200}
6853f21f 201#endif
845c9a7a
YM
202
203static inline void *mr_mfc_find(struct mr_table *mrt, void *hasharg)
204{
205 return mr_mfc_find_parent(mrt, hasharg, -1);
206}
c8d61968
YM
207
208#ifdef CONFIG_PROC_FS
3feda6b4
YM
209struct mr_vif_iter {
210 struct seq_net_private p;
211 struct mr_table *mrt;
212 int ct;
213};
214
c8d61968
YM
215struct mr_mfc_iter {
216 struct seq_net_private p;
217 struct mr_table *mrt;
218 struct list_head *cache;
219
220 /* Lock protecting the mr_table's unresolved queue */
221 spinlock_t *lock;
222};
223
224#ifdef CONFIG_IP_MROUTE_COMMON
3feda6b4
YM
225void *mr_vif_seq_idx(struct net *net, struct mr_vif_iter *iter, loff_t pos);
226void *mr_vif_seq_next(struct seq_file *seq, void *v, loff_t *pos);
227
228static inline void *mr_vif_seq_start(struct seq_file *seq, loff_t *pos)
229{
230 return *pos ? mr_vif_seq_idx(seq_file_net(seq),
231 seq->private, *pos - 1)
232 : SEQ_START_TOKEN;
233}
234
c8d61968
YM
235/* These actually return 'struct mr_mfc *', but to avoid need for explicit
236 * castings they simply return void.
237 */
238void *mr_mfc_seq_idx(struct net *net,
239 struct mr_mfc_iter *it, loff_t pos);
240void *mr_mfc_seq_next(struct seq_file *seq, void *v,
241 loff_t *pos);
242
243static inline void *mr_mfc_seq_start(struct seq_file *seq, loff_t *pos,
244 struct mr_table *mrt, spinlock_t *lock)
245{
246 struct mr_mfc_iter *it = seq->private;
247
248 it->mrt = mrt;
249 it->cache = NULL;
250 it->lock = lock;
251
252 return *pos ? mr_mfc_seq_idx(seq_file_net(seq),
253 seq->private, *pos - 1)
254 : SEQ_START_TOKEN;
255}
256
257static inline void mr_mfc_seq_stop(struct seq_file *seq, void *v)
258{
259 struct mr_mfc_iter *it = seq->private;
260 struct mr_table *mrt = it->mrt;
261
262 if (it->cache == &mrt->mfc_unres_queue)
263 spin_unlock_bh(it->lock);
264 else if (it->cache == &mrt->mfc_cache_list)
265 rcu_read_unlock();
266}
267#else
3feda6b4
YM
268static inline void *mr_vif_seq_idx(struct net *net, struct mr_vif_iter *iter,
269 loff_t pos)
270{
271 return NULL;
272}
273
274static inline void *mr_vif_seq_next(struct seq_file *seq,
275 void *v, loff_t *pos)
276{
277 return NULL;
278}
279
280static inline void *mr_vif_seq_start(struct seq_file *seq, loff_t *pos)
281{
282 return NULL;
283}
284
c8d61968
YM
285static inline void *mr_mfc_seq_idx(struct net *net,
286 struct mr_mfc_iter *it, loff_t pos)
287{
288 return NULL;
289}
290
291static inline void *mr_mfc_seq_next(struct seq_file *seq, void *v,
292 loff_t *pos)
293{
294 return NULL;
295}
296
297static inline void *mr_mfc_seq_start(struct seq_file *seq, loff_t *pos,
298 struct mr_table *mrt, spinlock_t *lock)
299{
300 return NULL;
301}
302
303static inline void mr_mfc_seq_stop(struct seq_file *seq, void *v)
304{
305}
306#endif
307#endif
6853f21f 308#endif
This page took 0.069188 seconds and 4 git commands to generate.