18c2ecf20Sopenharmony_ci/* SPDX-License-Identifier: GPL-2.0 */ 28c2ecf20Sopenharmony_ci/* 38c2ecf20Sopenharmony_ci * Operations on the network namespace 48c2ecf20Sopenharmony_ci */ 58c2ecf20Sopenharmony_ci#ifndef __NET_NET_NAMESPACE_H 68c2ecf20Sopenharmony_ci#define __NET_NET_NAMESPACE_H 78c2ecf20Sopenharmony_ci 88c2ecf20Sopenharmony_ci#include <linux/atomic.h> 98c2ecf20Sopenharmony_ci#include <linux/refcount.h> 108c2ecf20Sopenharmony_ci#include <linux/workqueue.h> 118c2ecf20Sopenharmony_ci#include <linux/list.h> 128c2ecf20Sopenharmony_ci#include <linux/sysctl.h> 138c2ecf20Sopenharmony_ci#include <linux/uidgid.h> 148c2ecf20Sopenharmony_ci 158c2ecf20Sopenharmony_ci#include <net/flow.h> 168c2ecf20Sopenharmony_ci#include <net/netns/core.h> 178c2ecf20Sopenharmony_ci#include <net/netns/mib.h> 188c2ecf20Sopenharmony_ci#include <net/netns/unix.h> 198c2ecf20Sopenharmony_ci#include <net/netns/packet.h> 208c2ecf20Sopenharmony_ci#include <net/netns/ipv4.h> 218c2ecf20Sopenharmony_ci#include <net/netns/ipv6.h> 228c2ecf20Sopenharmony_ci#include <net/netns/nexthop.h> 238c2ecf20Sopenharmony_ci#include <net/netns/ieee802154_6lowpan.h> 248c2ecf20Sopenharmony_ci#include <net/netns/sctp.h> 258c2ecf20Sopenharmony_ci#include <net/netns/dccp.h> 268c2ecf20Sopenharmony_ci#include <net/netns/netfilter.h> 278c2ecf20Sopenharmony_ci#include <net/netns/x_tables.h> 288c2ecf20Sopenharmony_ci#if defined(CONFIG_NF_CONNTRACK) || defined(CONFIG_NF_CONNTRACK_MODULE) 298c2ecf20Sopenharmony_ci#include <net/netns/conntrack.h> 308c2ecf20Sopenharmony_ci#endif 318c2ecf20Sopenharmony_ci#include <net/netns/nftables.h> 328c2ecf20Sopenharmony_ci#include <net/netns/xfrm.h> 338c2ecf20Sopenharmony_ci#include <net/netns/mpls.h> 348c2ecf20Sopenharmony_ci#include <net/netns/can.h> 358c2ecf20Sopenharmony_ci#include <net/netns/xdp.h> 368c2ecf20Sopenharmony_ci#include <net/netns/bpf.h> 378c2ecf20Sopenharmony_ci#include <linux/ns_common.h> 388c2ecf20Sopenharmony_ci#include <linux/idr.h> 398c2ecf20Sopenharmony_ci#include <linux/skbuff.h> 408c2ecf20Sopenharmony_ci#include <linux/notifier.h> 418c2ecf20Sopenharmony_ci#ifdef CONFIG_NEWIP 428c2ecf20Sopenharmony_ci#include <net/netns/nip.h> 438c2ecf20Sopenharmony_ci#endif 448c2ecf20Sopenharmony_ci 458c2ecf20Sopenharmony_cistruct user_namespace; 468c2ecf20Sopenharmony_cistruct proc_dir_entry; 478c2ecf20Sopenharmony_cistruct net_device; 488c2ecf20Sopenharmony_cistruct sock; 498c2ecf20Sopenharmony_cistruct ctl_table_header; 508c2ecf20Sopenharmony_cistruct net_generic; 518c2ecf20Sopenharmony_cistruct uevent_sock; 528c2ecf20Sopenharmony_cistruct netns_ipvs; 538c2ecf20Sopenharmony_cistruct bpf_prog; 548c2ecf20Sopenharmony_ci 558c2ecf20Sopenharmony_ci 568c2ecf20Sopenharmony_ci#define NETDEV_HASHBITS 8 578c2ecf20Sopenharmony_ci#define NETDEV_HASHENTRIES (1 << NETDEV_HASHBITS) 588c2ecf20Sopenharmony_ci 598c2ecf20Sopenharmony_cistruct net { 608c2ecf20Sopenharmony_ci /* First cache line can be often dirtied. 618c2ecf20Sopenharmony_ci * Do not place here read-mostly fields. 628c2ecf20Sopenharmony_ci */ 638c2ecf20Sopenharmony_ci refcount_t passive; /* To decide when the network 648c2ecf20Sopenharmony_ci * namespace should be freed. 658c2ecf20Sopenharmony_ci */ 668c2ecf20Sopenharmony_ci refcount_t count; /* To decided when the network 678c2ecf20Sopenharmony_ci * namespace should be shut down. 688c2ecf20Sopenharmony_ci */ 698c2ecf20Sopenharmony_ci spinlock_t rules_mod_lock; 708c2ecf20Sopenharmony_ci 718c2ecf20Sopenharmony_ci unsigned int dev_unreg_count; 728c2ecf20Sopenharmony_ci 738c2ecf20Sopenharmony_ci unsigned int dev_base_seq; /* protected by rtnl_mutex */ 748c2ecf20Sopenharmony_ci int ifindex; 758c2ecf20Sopenharmony_ci 768c2ecf20Sopenharmony_ci spinlock_t nsid_lock; 778c2ecf20Sopenharmony_ci atomic_t fnhe_genid; 788c2ecf20Sopenharmony_ci 798c2ecf20Sopenharmony_ci struct list_head list; /* list of network namespaces */ 808c2ecf20Sopenharmony_ci struct list_head exit_list; /* To linked to call pernet exit 818c2ecf20Sopenharmony_ci * methods on dead net ( 828c2ecf20Sopenharmony_ci * pernet_ops_rwsem read locked), 838c2ecf20Sopenharmony_ci * or to unregister pernet ops 848c2ecf20Sopenharmony_ci * (pernet_ops_rwsem write locked). 858c2ecf20Sopenharmony_ci */ 868c2ecf20Sopenharmony_ci struct llist_node cleanup_list; /* namespaces on death row */ 878c2ecf20Sopenharmony_ci 888c2ecf20Sopenharmony_ci#ifdef CONFIG_KEYS 898c2ecf20Sopenharmony_ci struct key_tag *key_domain; /* Key domain of operation tag */ 908c2ecf20Sopenharmony_ci#endif 918c2ecf20Sopenharmony_ci struct user_namespace *user_ns; /* Owning user namespace */ 928c2ecf20Sopenharmony_ci struct ucounts *ucounts; 938c2ecf20Sopenharmony_ci struct idr netns_ids; 948c2ecf20Sopenharmony_ci 958c2ecf20Sopenharmony_ci struct ns_common ns; 968c2ecf20Sopenharmony_ci 978c2ecf20Sopenharmony_ci struct list_head dev_base_head; 988c2ecf20Sopenharmony_ci struct proc_dir_entry *proc_net; 998c2ecf20Sopenharmony_ci struct proc_dir_entry *proc_net_stat; 1008c2ecf20Sopenharmony_ci 1018c2ecf20Sopenharmony_ci#ifdef CONFIG_SYSCTL 1028c2ecf20Sopenharmony_ci struct ctl_table_set sysctls; 1038c2ecf20Sopenharmony_ci#endif 1048c2ecf20Sopenharmony_ci 1058c2ecf20Sopenharmony_ci struct sock *rtnl; /* rtnetlink socket */ 1068c2ecf20Sopenharmony_ci struct sock *genl_sock; 1078c2ecf20Sopenharmony_ci 1088c2ecf20Sopenharmony_ci struct uevent_sock *uevent_sock; /* uevent socket */ 1098c2ecf20Sopenharmony_ci 1108c2ecf20Sopenharmony_ci struct hlist_head *dev_name_head; 1118c2ecf20Sopenharmony_ci struct hlist_head *dev_index_head; 1128c2ecf20Sopenharmony_ci struct raw_notifier_head netdev_chain; 1138c2ecf20Sopenharmony_ci 1148c2ecf20Sopenharmony_ci /* Note that @hash_mix can be read millions times per second, 1158c2ecf20Sopenharmony_ci * it is critical that it is on a read_mostly cache line. 1168c2ecf20Sopenharmony_ci */ 1178c2ecf20Sopenharmony_ci u32 hash_mix; 1188c2ecf20Sopenharmony_ci 1198c2ecf20Sopenharmony_ci struct net_device *loopback_dev; /* The loopback */ 1208c2ecf20Sopenharmony_ci 1218c2ecf20Sopenharmony_ci /* core fib_rules */ 1228c2ecf20Sopenharmony_ci struct list_head rules_ops; 1238c2ecf20Sopenharmony_ci 1248c2ecf20Sopenharmony_ci struct netns_core core; 1258c2ecf20Sopenharmony_ci struct netns_mib mib; 1268c2ecf20Sopenharmony_ci struct netns_packet packet; 1278c2ecf20Sopenharmony_ci struct netns_unix unx; 1288c2ecf20Sopenharmony_ci struct netns_nexthop nexthop; 1298c2ecf20Sopenharmony_ci struct netns_ipv4 ipv4; 1308c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_IPV6) 1318c2ecf20Sopenharmony_ci struct netns_ipv6 ipv6; 1328c2ecf20Sopenharmony_ci#endif 1338c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_NEWIP) 1348c2ecf20Sopenharmony_ci struct netns_newip newip; /* NIP */ 1358c2ecf20Sopenharmony_ci#endif 1368c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_IEEE802154_6LOWPAN) 1378c2ecf20Sopenharmony_ci struct netns_ieee802154_lowpan ieee802154_lowpan; 1388c2ecf20Sopenharmony_ci#endif 1398c2ecf20Sopenharmony_ci#if defined(CONFIG_IP_SCTP) || defined(CONFIG_IP_SCTP_MODULE) 1408c2ecf20Sopenharmony_ci struct netns_sctp sctp; 1418c2ecf20Sopenharmony_ci#endif 1428c2ecf20Sopenharmony_ci#if defined(CONFIG_IP_DCCP) || defined(CONFIG_IP_DCCP_MODULE) 1438c2ecf20Sopenharmony_ci struct netns_dccp dccp; 1448c2ecf20Sopenharmony_ci#endif 1458c2ecf20Sopenharmony_ci#ifdef CONFIG_NETFILTER 1468c2ecf20Sopenharmony_ci struct netns_nf nf; 1478c2ecf20Sopenharmony_ci struct netns_xt xt; 1488c2ecf20Sopenharmony_ci#if defined(CONFIG_NF_CONNTRACK) || defined(CONFIG_NF_CONNTRACK_MODULE) 1498c2ecf20Sopenharmony_ci struct netns_ct ct; 1508c2ecf20Sopenharmony_ci#endif 1518c2ecf20Sopenharmony_ci#if defined(CONFIG_NF_TABLES) || defined(CONFIG_NF_TABLES_MODULE) 1528c2ecf20Sopenharmony_ci struct netns_nftables nft; 1538c2ecf20Sopenharmony_ci#endif 1548c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_NF_DEFRAG_IPV6) 1558c2ecf20Sopenharmony_ci struct netns_nf_frag nf_frag; 1568c2ecf20Sopenharmony_ci struct ctl_table_header *nf_frag_frags_hdr; 1578c2ecf20Sopenharmony_ci#endif 1588c2ecf20Sopenharmony_ci struct sock *nfnl; 1598c2ecf20Sopenharmony_ci struct sock *nfnl_stash; 1608c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_NETFILTER_NETLINK_ACCT) 1618c2ecf20Sopenharmony_ci struct list_head nfnl_acct_list; 1628c2ecf20Sopenharmony_ci#endif 1638c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_NF_CT_NETLINK_TIMEOUT) 1648c2ecf20Sopenharmony_ci struct list_head nfct_timeout_list; 1658c2ecf20Sopenharmony_ci#endif 1668c2ecf20Sopenharmony_ci#endif 1678c2ecf20Sopenharmony_ci#ifdef CONFIG_WEXT_CORE 1688c2ecf20Sopenharmony_ci struct sk_buff_head wext_nlevents; 1698c2ecf20Sopenharmony_ci#endif 1708c2ecf20Sopenharmony_ci struct net_generic __rcu *gen; 1718c2ecf20Sopenharmony_ci 1728c2ecf20Sopenharmony_ci /* Used to store attached BPF programs */ 1738c2ecf20Sopenharmony_ci struct netns_bpf bpf; 1748c2ecf20Sopenharmony_ci 1758c2ecf20Sopenharmony_ci /* Note : following structs are cache line aligned */ 1768c2ecf20Sopenharmony_ci#ifdef CONFIG_XFRM 1778c2ecf20Sopenharmony_ci struct netns_xfrm xfrm; 1788c2ecf20Sopenharmony_ci#endif 1798c2ecf20Sopenharmony_ci 1808c2ecf20Sopenharmony_ci atomic64_t net_cookie; /* written once */ 1818c2ecf20Sopenharmony_ci 1828c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_IP_VS) 1838c2ecf20Sopenharmony_ci struct netns_ipvs *ipvs; 1848c2ecf20Sopenharmony_ci#endif 1858c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_MPLS) 1868c2ecf20Sopenharmony_ci struct netns_mpls mpls; 1878c2ecf20Sopenharmony_ci#endif 1888c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_CAN) 1898c2ecf20Sopenharmony_ci struct netns_can can; 1908c2ecf20Sopenharmony_ci#endif 1918c2ecf20Sopenharmony_ci#ifdef CONFIG_XDP_SOCKETS 1928c2ecf20Sopenharmony_ci struct netns_xdp xdp; 1938c2ecf20Sopenharmony_ci#endif 1948c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_CRYPTO_USER) 1958c2ecf20Sopenharmony_ci struct sock *crypto_nlsk; 1968c2ecf20Sopenharmony_ci#endif 1978c2ecf20Sopenharmony_ci struct sock *diag_nlsk; 1988c2ecf20Sopenharmony_ci} __randomize_layout; 1998c2ecf20Sopenharmony_ci 2008c2ecf20Sopenharmony_ci#include <linux/seq_file_net.h> 2018c2ecf20Sopenharmony_ci 2028c2ecf20Sopenharmony_ci/* Init's network namespace */ 2038c2ecf20Sopenharmony_ciextern struct net init_net; 2048c2ecf20Sopenharmony_ci 2058c2ecf20Sopenharmony_ci#ifdef CONFIG_NET_NS 2068c2ecf20Sopenharmony_cistruct net *copy_net_ns(unsigned long flags, struct user_namespace *user_ns, 2078c2ecf20Sopenharmony_ci struct net *old_net); 2088c2ecf20Sopenharmony_ci 2098c2ecf20Sopenharmony_civoid net_ns_get_ownership(const struct net *net, kuid_t *uid, kgid_t *gid); 2108c2ecf20Sopenharmony_ci 2118c2ecf20Sopenharmony_civoid net_ns_barrier(void); 2128c2ecf20Sopenharmony_ci 2138c2ecf20Sopenharmony_cistruct ns_common *get_net_ns(struct ns_common *ns); 2148c2ecf20Sopenharmony_ci#else /* CONFIG_NET_NS */ 2158c2ecf20Sopenharmony_ci#include <linux/sched.h> 2168c2ecf20Sopenharmony_ci#include <linux/nsproxy.h> 2178c2ecf20Sopenharmony_cistatic inline struct net *copy_net_ns(unsigned long flags, 2188c2ecf20Sopenharmony_ci struct user_namespace *user_ns, struct net *old_net) 2198c2ecf20Sopenharmony_ci{ 2208c2ecf20Sopenharmony_ci if (flags & CLONE_NEWNET) 2218c2ecf20Sopenharmony_ci return ERR_PTR(-EINVAL); 2228c2ecf20Sopenharmony_ci return old_net; 2238c2ecf20Sopenharmony_ci} 2248c2ecf20Sopenharmony_ci 2258c2ecf20Sopenharmony_cistatic inline void net_ns_get_ownership(const struct net *net, 2268c2ecf20Sopenharmony_ci kuid_t *uid, kgid_t *gid) 2278c2ecf20Sopenharmony_ci{ 2288c2ecf20Sopenharmony_ci *uid = GLOBAL_ROOT_UID; 2298c2ecf20Sopenharmony_ci *gid = GLOBAL_ROOT_GID; 2308c2ecf20Sopenharmony_ci} 2318c2ecf20Sopenharmony_ci 2328c2ecf20Sopenharmony_cistatic inline void net_ns_barrier(void) {} 2338c2ecf20Sopenharmony_ci 2348c2ecf20Sopenharmony_cistatic inline struct ns_common *get_net_ns(struct ns_common *ns) 2358c2ecf20Sopenharmony_ci{ 2368c2ecf20Sopenharmony_ci return ERR_PTR(-EINVAL); 2378c2ecf20Sopenharmony_ci} 2388c2ecf20Sopenharmony_ci#endif /* CONFIG_NET_NS */ 2398c2ecf20Sopenharmony_ci 2408c2ecf20Sopenharmony_ci 2418c2ecf20Sopenharmony_ciextern struct list_head net_namespace_list; 2428c2ecf20Sopenharmony_ci 2438c2ecf20Sopenharmony_cistruct net *get_net_ns_by_pid(pid_t pid); 2448c2ecf20Sopenharmony_cistruct net *get_net_ns_by_fd(int fd); 2458c2ecf20Sopenharmony_ci 2468c2ecf20Sopenharmony_ciu64 __net_gen_cookie(struct net *net); 2478c2ecf20Sopenharmony_ci 2488c2ecf20Sopenharmony_ci#ifdef CONFIG_SYSCTL 2498c2ecf20Sopenharmony_civoid ipx_register_sysctl(void); 2508c2ecf20Sopenharmony_civoid ipx_unregister_sysctl(void); 2518c2ecf20Sopenharmony_ci#else 2528c2ecf20Sopenharmony_ci#define ipx_register_sysctl() 2538c2ecf20Sopenharmony_ci#define ipx_unregister_sysctl() 2548c2ecf20Sopenharmony_ci#endif 2558c2ecf20Sopenharmony_ci 2568c2ecf20Sopenharmony_ci#ifdef CONFIG_NET_NS 2578c2ecf20Sopenharmony_civoid __put_net(struct net *net); 2588c2ecf20Sopenharmony_ci 2598c2ecf20Sopenharmony_cistatic inline struct net *get_net(struct net *net) 2608c2ecf20Sopenharmony_ci{ 2618c2ecf20Sopenharmony_ci refcount_inc(&net->count); 2628c2ecf20Sopenharmony_ci return net; 2638c2ecf20Sopenharmony_ci} 2648c2ecf20Sopenharmony_ci 2658c2ecf20Sopenharmony_cistatic inline struct net *maybe_get_net(struct net *net) 2668c2ecf20Sopenharmony_ci{ 2678c2ecf20Sopenharmony_ci /* Used when we know struct net exists but we 2688c2ecf20Sopenharmony_ci * aren't guaranteed a previous reference count 2698c2ecf20Sopenharmony_ci * exists. If the reference count is zero this 2708c2ecf20Sopenharmony_ci * function fails and returns NULL. 2718c2ecf20Sopenharmony_ci */ 2728c2ecf20Sopenharmony_ci if (!refcount_inc_not_zero(&net->count)) 2738c2ecf20Sopenharmony_ci net = NULL; 2748c2ecf20Sopenharmony_ci return net; 2758c2ecf20Sopenharmony_ci} 2768c2ecf20Sopenharmony_ci 2778c2ecf20Sopenharmony_cistatic inline void put_net(struct net *net) 2788c2ecf20Sopenharmony_ci{ 2798c2ecf20Sopenharmony_ci if (refcount_dec_and_test(&net->count)) 2808c2ecf20Sopenharmony_ci __put_net(net); 2818c2ecf20Sopenharmony_ci} 2828c2ecf20Sopenharmony_ci 2838c2ecf20Sopenharmony_cistatic inline 2848c2ecf20Sopenharmony_ciint net_eq(const struct net *net1, const struct net *net2) 2858c2ecf20Sopenharmony_ci{ 2868c2ecf20Sopenharmony_ci return net1 == net2; 2878c2ecf20Sopenharmony_ci} 2888c2ecf20Sopenharmony_ci 2898c2ecf20Sopenharmony_cistatic inline int check_net(const struct net *net) 2908c2ecf20Sopenharmony_ci{ 2918c2ecf20Sopenharmony_ci return refcount_read(&net->count) != 0; 2928c2ecf20Sopenharmony_ci} 2938c2ecf20Sopenharmony_ci 2948c2ecf20Sopenharmony_civoid net_drop_ns(void *); 2958c2ecf20Sopenharmony_ci 2968c2ecf20Sopenharmony_ci#else 2978c2ecf20Sopenharmony_ci 2988c2ecf20Sopenharmony_cistatic inline struct net *get_net(struct net *net) 2998c2ecf20Sopenharmony_ci{ 3008c2ecf20Sopenharmony_ci return net; 3018c2ecf20Sopenharmony_ci} 3028c2ecf20Sopenharmony_ci 3038c2ecf20Sopenharmony_cistatic inline void put_net(struct net *net) 3048c2ecf20Sopenharmony_ci{ 3058c2ecf20Sopenharmony_ci} 3068c2ecf20Sopenharmony_ci 3078c2ecf20Sopenharmony_cistatic inline struct net *maybe_get_net(struct net *net) 3088c2ecf20Sopenharmony_ci{ 3098c2ecf20Sopenharmony_ci return net; 3108c2ecf20Sopenharmony_ci} 3118c2ecf20Sopenharmony_ci 3128c2ecf20Sopenharmony_cistatic inline 3138c2ecf20Sopenharmony_ciint net_eq(const struct net *net1, const struct net *net2) 3148c2ecf20Sopenharmony_ci{ 3158c2ecf20Sopenharmony_ci return 1; 3168c2ecf20Sopenharmony_ci} 3178c2ecf20Sopenharmony_ci 3188c2ecf20Sopenharmony_cistatic inline int check_net(const struct net *net) 3198c2ecf20Sopenharmony_ci{ 3208c2ecf20Sopenharmony_ci return 1; 3218c2ecf20Sopenharmony_ci} 3228c2ecf20Sopenharmony_ci 3238c2ecf20Sopenharmony_ci#define net_drop_ns NULL 3248c2ecf20Sopenharmony_ci#endif 3258c2ecf20Sopenharmony_ci 3268c2ecf20Sopenharmony_ci 3278c2ecf20Sopenharmony_citypedef struct { 3288c2ecf20Sopenharmony_ci#ifdef CONFIG_NET_NS 3298c2ecf20Sopenharmony_ci struct net *net; 3308c2ecf20Sopenharmony_ci#endif 3318c2ecf20Sopenharmony_ci} possible_net_t; 3328c2ecf20Sopenharmony_ci 3338c2ecf20Sopenharmony_cistatic inline void write_pnet(possible_net_t *pnet, struct net *net) 3348c2ecf20Sopenharmony_ci{ 3358c2ecf20Sopenharmony_ci#ifdef CONFIG_NET_NS 3368c2ecf20Sopenharmony_ci pnet->net = net; 3378c2ecf20Sopenharmony_ci#endif 3388c2ecf20Sopenharmony_ci} 3398c2ecf20Sopenharmony_ci 3408c2ecf20Sopenharmony_cistatic inline struct net *read_pnet(const possible_net_t *pnet) 3418c2ecf20Sopenharmony_ci{ 3428c2ecf20Sopenharmony_ci#ifdef CONFIG_NET_NS 3438c2ecf20Sopenharmony_ci return pnet->net; 3448c2ecf20Sopenharmony_ci#else 3458c2ecf20Sopenharmony_ci return &init_net; 3468c2ecf20Sopenharmony_ci#endif 3478c2ecf20Sopenharmony_ci} 3488c2ecf20Sopenharmony_ci 3498c2ecf20Sopenharmony_ci/* Protected by net_rwsem */ 3508c2ecf20Sopenharmony_ci#define for_each_net(VAR) \ 3518c2ecf20Sopenharmony_ci list_for_each_entry(VAR, &net_namespace_list, list) 3528c2ecf20Sopenharmony_ci#define for_each_net_continue_reverse(VAR) \ 3538c2ecf20Sopenharmony_ci list_for_each_entry_continue_reverse(VAR, &net_namespace_list, list) 3548c2ecf20Sopenharmony_ci#define for_each_net_rcu(VAR) \ 3558c2ecf20Sopenharmony_ci list_for_each_entry_rcu(VAR, &net_namespace_list, list) 3568c2ecf20Sopenharmony_ci 3578c2ecf20Sopenharmony_ci#ifdef CONFIG_NET_NS 3588c2ecf20Sopenharmony_ci#define __net_init 3598c2ecf20Sopenharmony_ci#define __net_exit 3608c2ecf20Sopenharmony_ci#define __net_initdata 3618c2ecf20Sopenharmony_ci#define __net_initconst 3628c2ecf20Sopenharmony_ci#else 3638c2ecf20Sopenharmony_ci#define __net_init __init 3648c2ecf20Sopenharmony_ci#define __net_exit __ref 3658c2ecf20Sopenharmony_ci#define __net_initdata __initdata 3668c2ecf20Sopenharmony_ci#define __net_initconst __initconst 3678c2ecf20Sopenharmony_ci#endif 3688c2ecf20Sopenharmony_ci 3698c2ecf20Sopenharmony_ciint peernet2id_alloc(struct net *net, struct net *peer, gfp_t gfp); 3708c2ecf20Sopenharmony_ciint peernet2id(const struct net *net, struct net *peer); 3718c2ecf20Sopenharmony_cibool peernet_has_id(const struct net *net, struct net *peer); 3728c2ecf20Sopenharmony_cistruct net *get_net_ns_by_id(const struct net *net, int id); 3738c2ecf20Sopenharmony_ci 3748c2ecf20Sopenharmony_cistruct pernet_operations { 3758c2ecf20Sopenharmony_ci struct list_head list; 3768c2ecf20Sopenharmony_ci /* 3778c2ecf20Sopenharmony_ci * Below methods are called without any exclusive locks. 3788c2ecf20Sopenharmony_ci * More than one net may be constructed and destructed 3798c2ecf20Sopenharmony_ci * in parallel on several cpus. Every pernet_operations 3808c2ecf20Sopenharmony_ci * have to keep in mind all other pernet_operations and 3818c2ecf20Sopenharmony_ci * to introduce a locking, if they share common resources. 3828c2ecf20Sopenharmony_ci * 3838c2ecf20Sopenharmony_ci * The only time they are called with exclusive lock is 3848c2ecf20Sopenharmony_ci * from register_pernet_subsys(), unregister_pernet_subsys() 3858c2ecf20Sopenharmony_ci * register_pernet_device() and unregister_pernet_device(). 3868c2ecf20Sopenharmony_ci * 3878c2ecf20Sopenharmony_ci * Exit methods using blocking RCU primitives, such as 3888c2ecf20Sopenharmony_ci * synchronize_rcu(), should be implemented via exit_batch. 3898c2ecf20Sopenharmony_ci * Then, destruction of a group of net requires single 3908c2ecf20Sopenharmony_ci * synchronize_rcu() related to these pernet_operations, 3918c2ecf20Sopenharmony_ci * instead of separate synchronize_rcu() for every net. 3928c2ecf20Sopenharmony_ci * Please, avoid synchronize_rcu() at all, where it's possible. 3938c2ecf20Sopenharmony_ci * 3948c2ecf20Sopenharmony_ci * Note that a combination of pre_exit() and exit() can 3958c2ecf20Sopenharmony_ci * be used, since a synchronize_rcu() is guaranteed between 3968c2ecf20Sopenharmony_ci * the calls. 3978c2ecf20Sopenharmony_ci */ 3988c2ecf20Sopenharmony_ci int (*init)(struct net *net); 3998c2ecf20Sopenharmony_ci void (*pre_exit)(struct net *net); 4008c2ecf20Sopenharmony_ci void (*exit)(struct net *net); 4018c2ecf20Sopenharmony_ci void (*exit_batch)(struct list_head *net_exit_list); 4028c2ecf20Sopenharmony_ci unsigned int *id; 4038c2ecf20Sopenharmony_ci size_t size; 4048c2ecf20Sopenharmony_ci}; 4058c2ecf20Sopenharmony_ci 4068c2ecf20Sopenharmony_ci/* 4078c2ecf20Sopenharmony_ci * Use these carefully. If you implement a network device and it 4088c2ecf20Sopenharmony_ci * needs per network namespace operations use device pernet operations, 4098c2ecf20Sopenharmony_ci * otherwise use pernet subsys operations. 4108c2ecf20Sopenharmony_ci * 4118c2ecf20Sopenharmony_ci * Network interfaces need to be removed from a dying netns _before_ 4128c2ecf20Sopenharmony_ci * subsys notifiers can be called, as most of the network code cleanup 4138c2ecf20Sopenharmony_ci * (which is done from subsys notifiers) runs with the assumption that 4148c2ecf20Sopenharmony_ci * dev_remove_pack has been called so no new packets will arrive during 4158c2ecf20Sopenharmony_ci * and after the cleanup functions have been called. dev_remove_pack 4168c2ecf20Sopenharmony_ci * is not per namespace so instead the guarantee of no more packets 4178c2ecf20Sopenharmony_ci * arriving in a network namespace is provided by ensuring that all 4188c2ecf20Sopenharmony_ci * network devices and all sockets have left the network namespace 4198c2ecf20Sopenharmony_ci * before the cleanup methods are called. 4208c2ecf20Sopenharmony_ci * 4218c2ecf20Sopenharmony_ci * For the longest time the ipv4 icmp code was registered as a pernet 4228c2ecf20Sopenharmony_ci * device which caused kernel oops, and panics during network 4238c2ecf20Sopenharmony_ci * namespace cleanup. So please don't get this wrong. 4248c2ecf20Sopenharmony_ci */ 4258c2ecf20Sopenharmony_ciint register_pernet_subsys(struct pernet_operations *); 4268c2ecf20Sopenharmony_civoid unregister_pernet_subsys(struct pernet_operations *); 4278c2ecf20Sopenharmony_ciint register_pernet_device(struct pernet_operations *); 4288c2ecf20Sopenharmony_civoid unregister_pernet_device(struct pernet_operations *); 4298c2ecf20Sopenharmony_ci 4308c2ecf20Sopenharmony_cistruct ctl_table; 4318c2ecf20Sopenharmony_cistruct ctl_table_header; 4328c2ecf20Sopenharmony_ci 4338c2ecf20Sopenharmony_ci#ifdef CONFIG_SYSCTL 4348c2ecf20Sopenharmony_ciint net_sysctl_init(void); 4358c2ecf20Sopenharmony_cistruct ctl_table_header *register_net_sysctl(struct net *net, const char *path, 4368c2ecf20Sopenharmony_ci struct ctl_table *table); 4378c2ecf20Sopenharmony_civoid unregister_net_sysctl_table(struct ctl_table_header *header); 4388c2ecf20Sopenharmony_ci#else 4398c2ecf20Sopenharmony_cistatic inline int net_sysctl_init(void) { return 0; } 4408c2ecf20Sopenharmony_cistatic inline struct ctl_table_header *register_net_sysctl(struct net *net, 4418c2ecf20Sopenharmony_ci const char *path, struct ctl_table *table) 4428c2ecf20Sopenharmony_ci{ 4438c2ecf20Sopenharmony_ci return NULL; 4448c2ecf20Sopenharmony_ci} 4458c2ecf20Sopenharmony_cistatic inline void unregister_net_sysctl_table(struct ctl_table_header *header) 4468c2ecf20Sopenharmony_ci{ 4478c2ecf20Sopenharmony_ci} 4488c2ecf20Sopenharmony_ci#endif 4498c2ecf20Sopenharmony_ci 4508c2ecf20Sopenharmony_cistatic inline int rt_genid_ipv4(const struct net *net) 4518c2ecf20Sopenharmony_ci{ 4528c2ecf20Sopenharmony_ci return atomic_read(&net->ipv4.rt_genid); 4538c2ecf20Sopenharmony_ci} 4548c2ecf20Sopenharmony_ci 4558c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_IPV6) 4568c2ecf20Sopenharmony_cistatic inline int rt_genid_ipv6(const struct net *net) 4578c2ecf20Sopenharmony_ci{ 4588c2ecf20Sopenharmony_ci return atomic_read(&net->ipv6.fib6_sernum); 4598c2ecf20Sopenharmony_ci} 4608c2ecf20Sopenharmony_ci#endif 4618c2ecf20Sopenharmony_ci 4628c2ecf20Sopenharmony_cistatic inline void rt_genid_bump_ipv4(struct net *net) 4638c2ecf20Sopenharmony_ci{ 4648c2ecf20Sopenharmony_ci atomic_inc(&net->ipv4.rt_genid); 4658c2ecf20Sopenharmony_ci} 4668c2ecf20Sopenharmony_ci 4678c2ecf20Sopenharmony_ciextern void (*__fib6_flush_trees)(struct net *net); 4688c2ecf20Sopenharmony_cistatic inline void rt_genid_bump_ipv6(struct net *net) 4698c2ecf20Sopenharmony_ci{ 4708c2ecf20Sopenharmony_ci if (__fib6_flush_trees) 4718c2ecf20Sopenharmony_ci __fib6_flush_trees(net); 4728c2ecf20Sopenharmony_ci} 4738c2ecf20Sopenharmony_ci 4748c2ecf20Sopenharmony_ci#if IS_ENABLED(CONFIG_IEEE802154_6LOWPAN) 4758c2ecf20Sopenharmony_cistatic inline struct netns_ieee802154_lowpan * 4768c2ecf20Sopenharmony_cinet_ieee802154_lowpan(struct net *net) 4778c2ecf20Sopenharmony_ci{ 4788c2ecf20Sopenharmony_ci return &net->ieee802154_lowpan; 4798c2ecf20Sopenharmony_ci} 4808c2ecf20Sopenharmony_ci#endif 4818c2ecf20Sopenharmony_ci 4828c2ecf20Sopenharmony_ci/* For callers who don't really care about whether it's IPv4 or IPv6 */ 4838c2ecf20Sopenharmony_cistatic inline void rt_genid_bump_all(struct net *net) 4848c2ecf20Sopenharmony_ci{ 4858c2ecf20Sopenharmony_ci rt_genid_bump_ipv4(net); 4868c2ecf20Sopenharmony_ci rt_genid_bump_ipv6(net); 4878c2ecf20Sopenharmony_ci} 4888c2ecf20Sopenharmony_ci 4898c2ecf20Sopenharmony_cistatic inline int fnhe_genid(const struct net *net) 4908c2ecf20Sopenharmony_ci{ 4918c2ecf20Sopenharmony_ci return atomic_read(&net->fnhe_genid); 4928c2ecf20Sopenharmony_ci} 4938c2ecf20Sopenharmony_ci 4948c2ecf20Sopenharmony_cistatic inline void fnhe_genid_bump(struct net *net) 4958c2ecf20Sopenharmony_ci{ 4968c2ecf20Sopenharmony_ci atomic_inc(&net->fnhe_genid); 4978c2ecf20Sopenharmony_ci} 4988c2ecf20Sopenharmony_ci 4998c2ecf20Sopenharmony_ci#endif /* __NET_NET_NAMESPACE_H */ 500