int inet_frags_init(struct inet_frags *);
void inet_frags_fini(struct inet_frags *);
-static inline int fqdir_init(struct fqdir *fqdir, struct inet_frags *f,
+static inline int fqdir_init(struct fqdir **fqdirp, struct inet_frags *f,
struct net *net)
{
+ struct fqdir *fqdir = kzalloc(sizeof(*fqdir), GFP_KERNEL);
+ int res;
+
+ if (!fqdir)
+ return -ENOMEM;
fqdir->f = f;
fqdir->net = net;
- atomic_long_set(&fqdir->mem, 0);
- return rhashtable_init(&fqdir->rhashtable, &fqdir->f->rhash_params);
+ res = rhashtable_init(&fqdir->rhashtable, &fqdir->f->rhash_params);
+ if (res < 0) {
+ kfree(fqdir);
+ return res;
+ }
+ *fqdirp = fqdir;
+ return 0;
}
+
void fqdir_exit(struct fqdir *fqdir);
void inet_frag_kill(struct inet_frag_queue *q);
struct netns_ieee802154_lowpan {
struct netns_sysctl_lowpan sysctl;
- struct fqdir fqdir;
+ struct fqdir *fqdir;
};
#endif
struct inet_peer_base *peers;
struct sock * __percpu *tcp_sk;
- struct fqdir fqdir;
+ struct fqdir *fqdir;
#ifdef CONFIG_NETFILTER
struct xt_table *iptable_filter;
struct xt_table *iptable_mangle;
struct ipv6_devconf *devconf_all;
struct ipv6_devconf *devconf_dflt;
struct inet_peer_base *peers;
- struct fqdir fqdir;
+ struct fqdir *fqdir;
#ifdef CONFIG_NETFILTER
struct xt_table *ip6table_filter;
struct xt_table *ip6table_mangle;
#if IS_ENABLED(CONFIG_NF_DEFRAG_IPV6)
struct netns_nf_frag {
- struct fqdir fqdir;
+ struct fqdir *fqdir;
};
#endif
key.src = *src;
key.dst = *dst;
- q = inet_frag_find(&ieee802154_lowpan->fqdir, &key);
+ q = inet_frag_find(ieee802154_lowpan->fqdir, &key);
if (!q)
return NULL;
table[0].procname = NULL;
}
- table[0].data = &ieee802154_lowpan->fqdir.high_thresh;
- table[0].extra1 = &ieee802154_lowpan->fqdir.low_thresh;
- table[1].data = &ieee802154_lowpan->fqdir.low_thresh;
- table[1].extra2 = &ieee802154_lowpan->fqdir.high_thresh;
- table[2].data = &ieee802154_lowpan->fqdir.timeout;
+ table[0].data = &ieee802154_lowpan->fqdir->high_thresh;
+ table[0].extra1 = &ieee802154_lowpan->fqdir->low_thresh;
+ table[1].data = &ieee802154_lowpan->fqdir->low_thresh;
+ table[1].extra2 = &ieee802154_lowpan->fqdir->high_thresh;
+ table[2].data = &ieee802154_lowpan->fqdir->timeout;
hdr = register_net_sysctl(net, "net/ieee802154/6lowpan", table);
if (hdr == NULL)
net_ieee802154_lowpan(net);
int res;
- ieee802154_lowpan->fqdir.high_thresh = IPV6_FRAG_HIGH_THRESH;
- ieee802154_lowpan->fqdir.low_thresh = IPV6_FRAG_LOW_THRESH;
- ieee802154_lowpan->fqdir.timeout = IPV6_FRAG_TIMEOUT;
res = fqdir_init(&ieee802154_lowpan->fqdir, &lowpan_frags, net);
if (res < 0)
return res;
+
+ ieee802154_lowpan->fqdir->high_thresh = IPV6_FRAG_HIGH_THRESH;
+ ieee802154_lowpan->fqdir->low_thresh = IPV6_FRAG_LOW_THRESH;
+ ieee802154_lowpan->fqdir->timeout = IPV6_FRAG_TIMEOUT;
+
res = lowpan_frags_ns_sysctl_register(net);
if (res < 0)
- fqdir_exit(&ieee802154_lowpan->fqdir);
+ fqdir_exit(ieee802154_lowpan->fqdir);
return res;
}
net_ieee802154_lowpan(net);
lowpan_frags_ns_sysctl_unregister(net);
- fqdir_exit(&ieee802154_lowpan->fqdir);
+ fqdir_exit(ieee802154_lowpan->fqdir);
}
static struct pernet_operations lowpan_frags_ops = {
fqdir->high_thresh = 0; /* prevent creation of new frags */
rhashtable_free_and_destroy(&fqdir->rhashtable, inet_frags_free_cb, NULL);
+ kfree(fqdir);
}
EXPORT_SYMBOL(fqdir_exit);
};
struct inet_frag_queue *q;
- q = inet_frag_find(&net->ipv4.fqdir, &key);
+ q = inet_frag_find(net->ipv4.fqdir, &key);
if (!q)
return NULL;
goto err_alloc;
}
- table[0].data = &net->ipv4.fqdir.high_thresh;
- table[0].extra1 = &net->ipv4.fqdir.low_thresh;
- table[1].data = &net->ipv4.fqdir.low_thresh;
- table[1].extra2 = &net->ipv4.fqdir.high_thresh;
- table[2].data = &net->ipv4.fqdir.timeout;
- table[3].data = &net->ipv4.fqdir.max_dist;
+ table[0].data = &net->ipv4.fqdir->high_thresh;
+ table[0].extra1 = &net->ipv4.fqdir->low_thresh;
+ table[1].data = &net->ipv4.fqdir->low_thresh;
+ table[1].extra2 = &net->ipv4.fqdir->high_thresh;
+ table[2].data = &net->ipv4.fqdir->timeout;
+ table[3].data = &net->ipv4.fqdir->max_dist;
hdr = register_net_sysctl(net, "net/ipv4", table);
if (!hdr)
{
int res;
+ res = fqdir_init(&net->ipv4.fqdir, &ip4_frags, net);
+ if (res < 0)
+ return res;
/* Fragment cache limits.
*
* The fragment memory accounting code, (tries to) account for
* we will prune down to 3MB, making room for approx 8 big 64K
* fragments 8x128k.
*/
- net->ipv4.fqdir.high_thresh = 4 * 1024 * 1024;
- net->ipv4.fqdir.low_thresh = 3 * 1024 * 1024;
+ net->ipv4.fqdir->high_thresh = 4 * 1024 * 1024;
+ net->ipv4.fqdir->low_thresh = 3 * 1024 * 1024;
/*
* Important NOTE! Fragment queue must be destroyed before MSL expires.
* RFC791 is wrong proposing to prolongate timer each fragment arrival
* by TTL.
*/
- net->ipv4.fqdir.timeout = IP_FRAG_TIME;
+ net->ipv4.fqdir->timeout = IP_FRAG_TIME;
- net->ipv4.fqdir.max_dist = 64;
+ net->ipv4.fqdir->max_dist = 64;
- res = fqdir_init(&net->ipv4.fqdir, &ip4_frags, net);
- if (res < 0)
- return res;
res = ip4_frags_ns_ctl_register(net);
if (res < 0)
- fqdir_exit(&net->ipv4.fqdir);
+ fqdir_exit(net->ipv4.fqdir);
return res;
}
static void __net_exit ipv4_frags_exit_net(struct net *net)
{
ip4_frags_ns_ctl_unregister(net);
- fqdir_exit(&net->ipv4.fqdir);
+ fqdir_exit(net->ipv4.fqdir);
}
static struct pernet_operations ip4_frags_ops = {
seq_printf(seq, "RAW: inuse %d\n",
sock_prot_inuse_get(net, &raw_prot));
seq_printf(seq, "FRAG: inuse %u memory %lu\n",
- atomic_read(&net->ipv4.fqdir.rhashtable.nelems),
- frag_mem_limit(&net->ipv4.fqdir));
+ atomic_read(&net->ipv4.fqdir->rhashtable.nelems),
+ frag_mem_limit(net->ipv4.fqdir));
return 0;
}
goto err_alloc;
}
- table[0].data = &net->nf_frag.fqdir.timeout;
- table[1].data = &net->nf_frag.fqdir.low_thresh;
- table[1].extra2 = &net->nf_frag.fqdir.high_thresh;
- table[2].data = &net->nf_frag.fqdir.high_thresh;
- table[2].extra1 = &net->nf_frag.fqdir.low_thresh;
- table[2].extra2 = &init_net.nf_frag.fqdir.high_thresh;
+ table[0].data = &net->nf_frag.fqdir->timeout;
+ table[1].data = &net->nf_frag.fqdir->low_thresh;
+ table[1].extra2 = &net->nf_frag.fqdir->high_thresh;
+ table[2].data = &net->nf_frag.fqdir->high_thresh;
+ table[2].extra1 = &net->nf_frag.fqdir->low_thresh;
+ table[2].extra2 = &init_net.nf_frag.fqdir->high_thresh;
hdr = register_net_sysctl(net, "net/netfilter", table);
if (hdr == NULL)
};
struct inet_frag_queue *q;
- q = inet_frag_find(&net->nf_frag.fqdir, &key);
+ q = inet_frag_find(net->nf_frag.fqdir, &key);
if (!q)
return NULL;
{
int res;
- net->nf_frag.fqdir.high_thresh = IPV6_FRAG_HIGH_THRESH;
- net->nf_frag.fqdir.low_thresh = IPV6_FRAG_LOW_THRESH;
- net->nf_frag.fqdir.timeout = IPV6_FRAG_TIMEOUT;
-
res = fqdir_init(&net->nf_frag.fqdir, &nf_frags, net);
if (res < 0)
return res;
+
+ net->nf_frag.fqdir->high_thresh = IPV6_FRAG_HIGH_THRESH;
+ net->nf_frag.fqdir->low_thresh = IPV6_FRAG_LOW_THRESH;
+ net->nf_frag.fqdir->timeout = IPV6_FRAG_TIMEOUT;
+
res = nf_ct_frag6_sysctl_register(net);
if (res < 0)
- fqdir_exit(&net->nf_frag.fqdir);
+ fqdir_exit(net->nf_frag.fqdir);
return res;
}
static void nf_ct_net_exit(struct net *net)
{
nf_ct_frags6_sysctl_unregister(net);
- fqdir_exit(&net->nf_frag.fqdir);
+ fqdir_exit(net->nf_frag.fqdir);
}
static struct pernet_operations nf_ct_net_ops = {
seq_printf(seq, "RAW6: inuse %d\n",
sock_prot_inuse_get(net, &rawv6_prot));
seq_printf(seq, "FRAG6: inuse %u memory %lu\n",
- atomic_read(&net->ipv6.fqdir.rhashtable.nelems),
- frag_mem_limit(&net->ipv6.fqdir));
+ atomic_read(&net->ipv6.fqdir->rhashtable.nelems),
+ frag_mem_limit(net->ipv6.fqdir));
return 0;
}
IPV6_ADDR_LINKLOCAL)))
key.iif = 0;
- q = inet_frag_find(&net->ipv6.fqdir, &key);
+ q = inet_frag_find(net->ipv6.fqdir, &key);
if (!q)
return NULL;
goto err_alloc;
}
- table[0].data = &net->ipv6.fqdir.high_thresh;
- table[0].extra1 = &net->ipv6.fqdir.low_thresh;
- table[1].data = &net->ipv6.fqdir.low_thresh;
- table[1].extra2 = &net->ipv6.fqdir.high_thresh;
- table[2].data = &net->ipv6.fqdir.timeout;
+ table[0].data = &net->ipv6.fqdir->high_thresh;
+ table[0].extra1 = &net->ipv6.fqdir->low_thresh;
+ table[1].data = &net->ipv6.fqdir->low_thresh;
+ table[1].extra2 = &net->ipv6.fqdir->high_thresh;
+ table[2].data = &net->ipv6.fqdir->timeout;
hdr = register_net_sysctl(net, "net/ipv6", table);
if (!hdr)
{
int res;
- net->ipv6.fqdir.high_thresh = IPV6_FRAG_HIGH_THRESH;
- net->ipv6.fqdir.low_thresh = IPV6_FRAG_LOW_THRESH;
- net->ipv6.fqdir.timeout = IPV6_FRAG_TIMEOUT;
-
res = fqdir_init(&net->ipv6.fqdir, &ip6_frags, net);
if (res < 0)
return res;
+ net->ipv6.fqdir->high_thresh = IPV6_FRAG_HIGH_THRESH;
+ net->ipv6.fqdir->low_thresh = IPV6_FRAG_LOW_THRESH;
+ net->ipv6.fqdir->timeout = IPV6_FRAG_TIMEOUT;
+
res = ip6_frags_ns_sysctl_register(net);
if (res < 0)
- fqdir_exit(&net->ipv6.fqdir);
+ fqdir_exit(net->ipv6.fqdir);
return res;
}
static void __net_exit ipv6_frags_exit_net(struct net *net)
{
ip6_frags_ns_sysctl_unregister(net);
- fqdir_exit(&net->ipv6.fqdir);
+ fqdir_exit(net->ipv6.fqdir);
}
static struct pernet_operations ip6_frags_ops = {