.. | .. |
---|
34 | 34 | #define NETLINK_CREDS(skb) (&NETLINK_CB((skb)).creds) |
---|
35 | 35 | |
---|
36 | 36 | |
---|
37 | | -extern void netlink_table_grab(void); |
---|
38 | | -extern void netlink_table_ungrab(void); |
---|
| 37 | +void netlink_table_grab(void); |
---|
| 38 | +void netlink_table_ungrab(void); |
---|
39 | 39 | |
---|
40 | 40 | #define NL_CFG_F_NONROOT_RECV (1 << 0) |
---|
41 | 41 | #define NL_CFG_F_NONROOT_SEND (1 << 1) |
---|
.. | .. |
---|
51 | 51 | bool (*compare)(struct net *net, struct sock *sk); |
---|
52 | 52 | }; |
---|
53 | 53 | |
---|
54 | | -extern struct sock *__netlink_kernel_create(struct net *net, int unit, |
---|
| 54 | +struct sock *__netlink_kernel_create(struct net *net, int unit, |
---|
55 | 55 | struct module *module, |
---|
56 | 56 | struct netlink_kernel_cfg *cfg); |
---|
57 | 57 | static inline struct sock * |
---|
.. | .. |
---|
68 | 68 | * @_msg: message string to report - don't access directly, use |
---|
69 | 69 | * %NL_SET_ERR_MSG |
---|
70 | 70 | * @bad_attr: attribute with error |
---|
| 71 | + * @policy: policy for a bad attribute |
---|
71 | 72 | * @cookie: cookie data to return to userspace (for success) |
---|
72 | 73 | * @cookie_len: actual cookie data length |
---|
73 | 74 | */ |
---|
74 | 75 | struct netlink_ext_ack { |
---|
75 | 76 | const char *_msg; |
---|
76 | 77 | const struct nlattr *bad_attr; |
---|
| 78 | + const struct nla_policy *policy; |
---|
77 | 79 | u8 cookie[NETLINK_MAX_COOKIE_LEN]; |
---|
78 | 80 | u8 cookie_len; |
---|
79 | 81 | }; |
---|
.. | .. |
---|
95 | 97 | #define NL_SET_ERR_MSG_MOD(extack, msg) \ |
---|
96 | 98 | NL_SET_ERR_MSG((extack), KBUILD_MODNAME ": " msg) |
---|
97 | 99 | |
---|
98 | | -#define NL_SET_BAD_ATTR(extack, attr) do { \ |
---|
99 | | - if ((extack)) \ |
---|
| 100 | +#define NL_SET_BAD_ATTR_POLICY(extack, attr, pol) do { \ |
---|
| 101 | + if ((extack)) { \ |
---|
100 | 102 | (extack)->bad_attr = (attr); \ |
---|
101 | | -} while (0) |
---|
102 | | - |
---|
103 | | -#define NL_SET_ERR_MSG_ATTR(extack, attr, msg) do { \ |
---|
104 | | - static const char __msg[] = msg; \ |
---|
105 | | - struct netlink_ext_ack *__extack = (extack); \ |
---|
106 | | - \ |
---|
107 | | - if (__extack) { \ |
---|
108 | | - __extack->_msg = __msg; \ |
---|
109 | | - __extack->bad_attr = (attr); \ |
---|
| 103 | + (extack)->policy = (pol); \ |
---|
110 | 104 | } \ |
---|
111 | 105 | } while (0) |
---|
112 | 106 | |
---|
113 | | -extern void netlink_kernel_release(struct sock *sk); |
---|
114 | | -extern int __netlink_change_ngroups(struct sock *sk, unsigned int groups); |
---|
115 | | -extern int netlink_change_ngroups(struct sock *sk, unsigned int groups); |
---|
116 | | -extern void __netlink_clear_multicast_users(struct sock *sk, unsigned int group); |
---|
117 | | -extern void netlink_ack(struct sk_buff *in_skb, struct nlmsghdr *nlh, int err, |
---|
118 | | - const struct netlink_ext_ack *extack); |
---|
119 | | -extern int netlink_has_listeners(struct sock *sk, unsigned int group); |
---|
| 107 | +#define NL_SET_BAD_ATTR(extack, attr) NL_SET_BAD_ATTR_POLICY(extack, attr, NULL) |
---|
120 | 108 | |
---|
121 | | -extern int netlink_unicast(struct sock *ssk, struct sk_buff *skb, __u32 portid, int nonblock); |
---|
122 | | -extern int netlink_broadcast(struct sock *ssk, struct sk_buff *skb, __u32 portid, |
---|
123 | | - __u32 group, gfp_t allocation); |
---|
124 | | -extern int netlink_broadcast_filtered(struct sock *ssk, struct sk_buff *skb, |
---|
125 | | - __u32 portid, __u32 group, gfp_t allocation, |
---|
126 | | - int (*filter)(struct sock *dsk, struct sk_buff *skb, void *data), |
---|
127 | | - void *filter_data); |
---|
128 | | -extern int netlink_set_err(struct sock *ssk, __u32 portid, __u32 group, int code); |
---|
129 | | -extern int netlink_register_notifier(struct notifier_block *nb); |
---|
130 | | -extern int netlink_unregister_notifier(struct notifier_block *nb); |
---|
| 109 | +#define NL_SET_ERR_MSG_ATTR_POL(extack, attr, pol, msg) do { \ |
---|
| 110 | + static const char __msg[] = msg; \ |
---|
| 111 | + struct netlink_ext_ack *__extack = (extack); \ |
---|
| 112 | + \ |
---|
| 113 | + if (__extack) { \ |
---|
| 114 | + __extack->_msg = __msg; \ |
---|
| 115 | + __extack->bad_attr = (attr); \ |
---|
| 116 | + __extack->policy = (pol); \ |
---|
| 117 | + } \ |
---|
| 118 | +} while (0) |
---|
| 119 | + |
---|
| 120 | +#define NL_SET_ERR_MSG_ATTR(extack, attr, msg) \ |
---|
| 121 | + NL_SET_ERR_MSG_ATTR_POL(extack, attr, NULL, msg) |
---|
| 122 | + |
---|
| 123 | +static inline void nl_set_extack_cookie_u64(struct netlink_ext_ack *extack, |
---|
| 124 | + u64 cookie) |
---|
| 125 | +{ |
---|
| 126 | + u64 __cookie = cookie; |
---|
| 127 | + |
---|
| 128 | + if (!extack) |
---|
| 129 | + return; |
---|
| 130 | + memcpy(extack->cookie, &__cookie, sizeof(__cookie)); |
---|
| 131 | + extack->cookie_len = sizeof(__cookie); |
---|
| 132 | +} |
---|
| 133 | + |
---|
| 134 | +static inline void nl_set_extack_cookie_u32(struct netlink_ext_ack *extack, |
---|
| 135 | + u32 cookie) |
---|
| 136 | +{ |
---|
| 137 | + u32 __cookie = cookie; |
---|
| 138 | + |
---|
| 139 | + if (!extack) |
---|
| 140 | + return; |
---|
| 141 | + memcpy(extack->cookie, &__cookie, sizeof(__cookie)); |
---|
| 142 | + extack->cookie_len = sizeof(__cookie); |
---|
| 143 | +} |
---|
| 144 | + |
---|
| 145 | +void netlink_kernel_release(struct sock *sk); |
---|
| 146 | +int __netlink_change_ngroups(struct sock *sk, unsigned int groups); |
---|
| 147 | +int netlink_change_ngroups(struct sock *sk, unsigned int groups); |
---|
| 148 | +void __netlink_clear_multicast_users(struct sock *sk, unsigned int group); |
---|
| 149 | +void netlink_ack(struct sk_buff *in_skb, struct nlmsghdr *nlh, int err, |
---|
| 150 | + const struct netlink_ext_ack *extack); |
---|
| 151 | +int netlink_has_listeners(struct sock *sk, unsigned int group); |
---|
| 152 | +bool netlink_strict_get_check(struct sk_buff *skb); |
---|
| 153 | + |
---|
| 154 | +int netlink_unicast(struct sock *ssk, struct sk_buff *skb, __u32 portid, int nonblock); |
---|
| 155 | +int netlink_broadcast(struct sock *ssk, struct sk_buff *skb, __u32 portid, |
---|
| 156 | + __u32 group, gfp_t allocation); |
---|
| 157 | +int netlink_broadcast_filtered(struct sock *ssk, struct sk_buff *skb, |
---|
| 158 | + __u32 portid, __u32 group, gfp_t allocation, |
---|
| 159 | + int (*filter)(struct sock *dsk, struct sk_buff *skb, void *data), |
---|
| 160 | + void *filter_data); |
---|
| 161 | +int netlink_set_err(struct sock *ssk, __u32 portid, __u32 group, int code); |
---|
| 162 | +int netlink_register_notifier(struct notifier_block *nb); |
---|
| 163 | +int netlink_unregister_notifier(struct notifier_block *nb); |
---|
131 | 164 | |
---|
132 | 165 | /* finegrained unicast helpers: */ |
---|
133 | 166 | struct sock *netlink_getsockbyfilp(struct file *filp); |
---|
.. | .. |
---|
176 | 209 | void *data; |
---|
177 | 210 | /* the module that dump function belong to */ |
---|
178 | 211 | struct module *module; |
---|
| 212 | + struct netlink_ext_ack *extack; |
---|
179 | 213 | u16 family; |
---|
180 | | - u16 min_dump_alloc; |
---|
| 214 | + u16 answer_flags; |
---|
| 215 | + u32 min_dump_alloc; |
---|
181 | 216 | unsigned int prev_seq, seq; |
---|
182 | | - long args[6]; |
---|
| 217 | + bool strict_check; |
---|
| 218 | + union { |
---|
| 219 | + u8 ctx[48]; |
---|
| 220 | + |
---|
| 221 | + /* args is deprecated. Cast a struct over ctx instead |
---|
| 222 | + * for proper type safety. |
---|
| 223 | + */ |
---|
| 224 | + long args[6]; |
---|
| 225 | + }; |
---|
183 | 226 | }; |
---|
184 | 227 | |
---|
185 | 228 | struct netlink_notify { |
---|
.. | .. |
---|
197 | 240 | int (*done)(struct netlink_callback *); |
---|
198 | 241 | void *data; |
---|
199 | 242 | struct module *module; |
---|
200 | | - u16 min_dump_alloc; |
---|
| 243 | + u32 min_dump_alloc; |
---|
201 | 244 | }; |
---|
202 | 245 | |
---|
203 | | -extern int __netlink_dump_start(struct sock *ssk, struct sk_buff *skb, |
---|
| 246 | +int __netlink_dump_start(struct sock *ssk, struct sk_buff *skb, |
---|
204 | 247 | const struct nlmsghdr *nlh, |
---|
205 | 248 | struct netlink_dump_control *control); |
---|
206 | 249 | static inline int netlink_dump_start(struct sock *ssk, struct sk_buff *skb, |
---|
.. | .. |
---|
219 | 262 | struct list_head list; |
---|
220 | 263 | }; |
---|
221 | 264 | |
---|
222 | | -extern int netlink_add_tap(struct netlink_tap *nt); |
---|
223 | | -extern int netlink_remove_tap(struct netlink_tap *nt); |
---|
| 265 | +int netlink_add_tap(struct netlink_tap *nt); |
---|
| 266 | +int netlink_remove_tap(struct netlink_tap *nt); |
---|
224 | 267 | |
---|
225 | 268 | bool __netlink_ns_capable(const struct netlink_skb_parms *nsp, |
---|
226 | 269 | struct user_namespace *ns, int cap); |
---|