diff options
-rw-r--r-- | include/net/ip_fib.h | 39 | ||||
-rw-r--r-- | net/ipv4/fib_frontend.c | 29 |
2 files changed, 40 insertions, 28 deletions
diff --git a/include/net/ip_fib.h b/include/net/ip_fib.h index 338d3ed10c31..249af662e897 100644 --- a/include/net/ip_fib.h +++ b/include/net/ip_fib.h | |||
@@ -120,16 +120,22 @@ struct fib_result_nl { | |||
120 | int err; | 120 | int err; |
121 | }; | 121 | }; |
122 | 122 | ||
123 | extern struct hlist_head fib_table_hash[]; | ||
124 | |||
123 | #ifdef CONFIG_IP_ROUTE_MULTIPATH | 125 | #ifdef CONFIG_IP_ROUTE_MULTIPATH |
124 | 126 | ||
125 | #define FIB_RES_NH(res) ((res).fi->fib_nh[(res).nh_sel]) | 127 | #define FIB_RES_NH(res) ((res).fi->fib_nh[(res).nh_sel]) |
126 | #define FIB_RES_RESET(res) ((res).nh_sel = 0) | 128 | #define FIB_RES_RESET(res) ((res).nh_sel = 0) |
127 | 129 | ||
130 | #define FIB_TABLE_HASHSZ 2 | ||
131 | |||
128 | #else /* CONFIG_IP_ROUTE_MULTIPATH */ | 132 | #else /* CONFIG_IP_ROUTE_MULTIPATH */ |
129 | 133 | ||
130 | #define FIB_RES_NH(res) ((res).fi->fib_nh[0]) | 134 | #define FIB_RES_NH(res) ((res).fi->fib_nh[0]) |
131 | #define FIB_RES_RESET(res) | 135 | #define FIB_RES_RESET(res) |
132 | 136 | ||
137 | #define FIB_TABLE_HASHSZ 256 | ||
138 | |||
133 | #endif /* CONFIG_IP_ROUTE_MULTIPATH */ | 139 | #endif /* CONFIG_IP_ROUTE_MULTIPATH */ |
134 | 140 | ||
135 | #define FIB_RES_PREFSRC(res) ((res).fi->fib_prefsrc ? : __fib_res_prefsrc(&res)) | 141 | #define FIB_RES_PREFSRC(res) ((res).fi->fib_prefsrc ? : __fib_res_prefsrc(&res)) |
@@ -156,14 +162,17 @@ struct fib_table { | |||
156 | 162 | ||
157 | #ifndef CONFIG_IP_MULTIPLE_TABLES | 163 | #ifndef CONFIG_IP_MULTIPLE_TABLES |
158 | 164 | ||
159 | extern struct fib_table *ip_fib_local_table; | 165 | #define TABLE_LOCAL_INDEX 0 |
160 | extern struct fib_table *ip_fib_main_table; | 166 | #define TABLE_MAIN_INDEX 1 |
161 | 167 | ||
162 | static inline struct fib_table *fib_get_table(u32 id) | 168 | static inline struct fib_table *fib_get_table(u32 id) |
163 | { | 169 | { |
164 | if (id != RT_TABLE_LOCAL) | 170 | struct hlist_head *ptr; |
165 | return ip_fib_main_table; | 171 | |
166 | return ip_fib_local_table; | 172 | ptr = id == RT_TABLE_LOCAL ? |
173 | &fib_table_hash[TABLE_LOCAL_INDEX] : | ||
174 | &fib_table_hash[TABLE_MAIN_INDEX]; | ||
175 | return hlist_entry(ptr->first, struct fib_table, tb_hlist); | ||
167 | } | 176 | } |
168 | 177 | ||
169 | static inline struct fib_table *fib_new_table(u32 id) | 178 | static inline struct fib_table *fib_new_table(u32 id) |
@@ -173,16 +182,24 @@ static inline struct fib_table *fib_new_table(u32 id) | |||
173 | 182 | ||
174 | static inline int fib_lookup(const struct flowi *flp, struct fib_result *res) | 183 | static inline int fib_lookup(const struct flowi *flp, struct fib_result *res) |
175 | { | 184 | { |
176 | if (ip_fib_local_table->tb_lookup(ip_fib_local_table, flp, res) && | 185 | struct fib_table *table; |
177 | ip_fib_main_table->tb_lookup(ip_fib_main_table, flp, res)) | 186 | |
178 | return -ENETUNREACH; | 187 | table = fib_get_table(RT_TABLE_LOCAL); |
179 | return 0; | 188 | if (!table->tb_lookup(table, flp, res)) |
189 | return 0; | ||
190 | |||
191 | table = fib_get_table(RT_TABLE_MAIN); | ||
192 | if (!table->tb_lookup(table, flp, res)) | ||
193 | return 0; | ||
194 | return -ENETUNREACH; | ||
180 | } | 195 | } |
181 | 196 | ||
182 | static inline void fib_select_default(const struct flowi *flp, struct fib_result *res) | 197 | static inline void fib_select_default(const struct flowi *flp, |
198 | struct fib_result *res) | ||
183 | { | 199 | { |
200 | struct fib_table *table = fib_get_table(RT_TABLE_MAIN); | ||
184 | if (FIB_RES_GW(*res) && FIB_RES_NH(*res).nh_scope == RT_SCOPE_LINK) | 201 | if (FIB_RES_GW(*res) && FIB_RES_NH(*res).nh_scope == RT_SCOPE_LINK) |
185 | ip_fib_main_table->tb_select_default(ip_fib_main_table, flp, res); | 202 | table->tb_select_default(table, flp, res); |
186 | } | 203 | } |
187 | 204 | ||
188 | #else /* CONFIG_IP_MULTIPLE_TABLES */ | 205 | #else /* CONFIG_IP_MULTIPLE_TABLES */ |
diff --git a/net/ipv4/fib_frontend.c b/net/ipv4/fib_frontend.c index 0484cae02736..9ff1e6669ef2 100644 --- a/net/ipv4/fib_frontend.c +++ b/net/ipv4/fib_frontend.c | |||
@@ -50,39 +50,34 @@ | |||
50 | #define FFprint(a...) printk(KERN_DEBUG a) | 50 | #define FFprint(a...) printk(KERN_DEBUG a) |
51 | 51 | ||
52 | static struct sock *fibnl; | 52 | static struct sock *fibnl; |
53 | struct hlist_head fib_table_hash[FIB_TABLE_HASHSZ]; | ||
53 | 54 | ||
54 | #ifndef CONFIG_IP_MULTIPLE_TABLES | 55 | #ifndef CONFIG_IP_MULTIPLE_TABLES |
55 | 56 | ||
56 | struct fib_table *ip_fib_local_table; | ||
57 | struct fib_table *ip_fib_main_table; | ||
58 | |||
59 | #define FIB_TABLE_HASHSZ 1 | ||
60 | static struct hlist_head fib_table_hash[FIB_TABLE_HASHSZ]; | ||
61 | |||
62 | static int __net_init fib4_rules_init(struct net *net) | 57 | static int __net_init fib4_rules_init(struct net *net) |
63 | { | 58 | { |
64 | ip_fib_local_table = fib_hash_init(RT_TABLE_LOCAL); | 59 | struct fib_table *local_table, *main_table; |
65 | if (ip_fib_local_table == NULL) | 60 | |
61 | local_table = fib_hash_init(RT_TABLE_LOCAL); | ||
62 | if (local_table == NULL) | ||
66 | return -ENOMEM; | 63 | return -ENOMEM; |
67 | 64 | ||
68 | ip_fib_main_table = fib_hash_init(RT_TABLE_MAIN); | 65 | main_table = fib_hash_init(RT_TABLE_MAIN); |
69 | if (ip_fib_main_table == NULL) | 66 | if (main_table == NULL) |
70 | goto fail; | 67 | goto fail; |
71 | 68 | ||
72 | hlist_add_head_rcu(&ip_fib_local_table->tb_hlist, &fib_table_hash[0]); | 69 | hlist_add_head_rcu(&local_table->tb_hlist, |
73 | hlist_add_head_rcu(&ip_fib_main_table->tb_hlist, &fib_table_hash[0]); | 70 | &fib_table_hash[TABLE_LOCAL_INDEX]); |
71 | hlist_add_head_rcu(&main_table->tb_hlist, | ||
72 | &fib_table_hash[TABLE_MAIN_INDEX]); | ||
74 | return 0; | 73 | return 0; |
75 | 74 | ||
76 | fail: | 75 | fail: |
77 | kfree(ip_fib_local_table); | 76 | kfree(local_table); |
78 | ip_fib_local_table = NULL; | ||
79 | return -ENOMEM; | 77 | return -ENOMEM; |
80 | } | 78 | } |
81 | #else | 79 | #else |
82 | 80 | ||
83 | #define FIB_TABLE_HASHSZ 256 | ||
84 | static struct hlist_head fib_table_hash[FIB_TABLE_HASHSZ]; | ||
85 | |||
86 | struct fib_table *fib_new_table(u32 id) | 81 | struct fib_table *fib_new_table(u32 id) |
87 | { | 82 | { |
88 | struct fib_table *tb; | 83 | struct fib_table *tb; |