Back to home page

OSCL-LXR

 
 

    


0001 /* SPDX-License-Identifier: GPL-2.0 */
0002 #ifndef __NET_GENERIC_NETLINK_H
0003 #define __NET_GENERIC_NETLINK_H
0004 
0005 #include <linux/genetlink.h>
0006 #include <net/netlink.h>
0007 #include <net/net_namespace.h>
0008 
0009 #define GENLMSG_DEFAULT_SIZE (NLMSG_DEFAULT_SIZE - GENL_HDRLEN)
0010 
0011 /**
0012  * struct genl_multicast_group - generic netlink multicast group
0013  * @name: name of the multicast group, names are per-family
0014  * @flags: GENL_* flags (%GENL_ADMIN_PERM or %GENL_UNS_ADMIN_PERM)
0015  */
0016 struct genl_multicast_group {
0017     char            name[GENL_NAMSIZ];
0018     u8          flags;
0019 };
0020 
0021 struct genl_ops;
0022 struct genl_info;
0023 
0024 /**
0025  * struct genl_family - generic netlink family
0026  * @id: protocol family identifier (private)
0027  * @hdrsize: length of user specific header in bytes
0028  * @name: name of family
0029  * @version: protocol version
0030  * @maxattr: maximum number of attributes supported
0031  * @policy: netlink policy
0032  * @netnsok: set to true if the family can handle network
0033  *  namespaces and should be presented in all of them
0034  * @parallel_ops: operations can be called in parallel and aren't
0035  *  synchronized by the core genetlink code
0036  * @pre_doit: called before an operation's doit callback, it may
0037  *  do additional, common, filtering and return an error
0038  * @post_doit: called after an operation's doit callback, it may
0039  *  undo operations done by pre_doit, for example release locks
0040  * @mcgrps: multicast groups used by this family
0041  * @n_mcgrps: number of multicast groups
0042  * @mcgrp_offset: starting number of multicast group IDs in this family
0043  *  (private)
0044  * @ops: the operations supported by this family
0045  * @n_ops: number of operations supported by this family
0046  * @small_ops: the small-struct operations supported by this family
0047  * @n_small_ops: number of small-struct operations supported by this family
0048  */
0049 struct genl_family {
0050     int         id;     /* private */
0051     unsigned int        hdrsize;
0052     char            name[GENL_NAMSIZ];
0053     unsigned int        version;
0054     unsigned int        maxattr;
0055     unsigned int        mcgrp_offset;   /* private */
0056     u8          netnsok:1;
0057     u8          parallel_ops:1;
0058     u8          n_ops;
0059     u8          n_small_ops;
0060     u8          n_mcgrps;
0061     const struct nla_policy *policy;
0062     int         (*pre_doit)(const struct genl_ops *ops,
0063                         struct sk_buff *skb,
0064                         struct genl_info *info);
0065     void            (*post_doit)(const struct genl_ops *ops,
0066                          struct sk_buff *skb,
0067                          struct genl_info *info);
0068     const struct genl_ops * ops;
0069     const struct genl_small_ops *small_ops;
0070     const struct genl_multicast_group *mcgrps;
0071     struct module       *module;
0072 };
0073 
0074 /**
0075  * struct genl_info - receiving information
0076  * @snd_seq: sending sequence number
0077  * @snd_portid: netlink portid of sender
0078  * @nlhdr: netlink message header
0079  * @genlhdr: generic netlink message header
0080  * @userhdr: user specific header
0081  * @attrs: netlink attributes
0082  * @_net: network namespace
0083  * @user_ptr: user pointers
0084  * @extack: extended ACK report struct
0085  */
0086 struct genl_info {
0087     u32         snd_seq;
0088     u32         snd_portid;
0089     struct nlmsghdr *   nlhdr;
0090     struct genlmsghdr * genlhdr;
0091     void *          userhdr;
0092     struct nlattr **    attrs;
0093     possible_net_t      _net;
0094     void *          user_ptr[2];
0095     struct netlink_ext_ack *extack;
0096 };
0097 
0098 static inline struct net *genl_info_net(struct genl_info *info)
0099 {
0100     return read_pnet(&info->_net);
0101 }
0102 
0103 static inline void genl_info_net_set(struct genl_info *info, struct net *net)
0104 {
0105     write_pnet(&info->_net, net);
0106 }
0107 
0108 #define GENL_SET_ERR_MSG(info, msg) NL_SET_ERR_MSG((info)->extack, msg)
0109 
0110 enum genl_validate_flags {
0111     GENL_DONT_VALIDATE_STRICT       = BIT(0),
0112     GENL_DONT_VALIDATE_DUMP         = BIT(1),
0113     GENL_DONT_VALIDATE_DUMP_STRICT      = BIT(2),
0114 };
0115 
0116 /**
0117  * struct genl_small_ops - generic netlink operations (small version)
0118  * @cmd: command identifier
0119  * @internal_flags: flags used by the family
0120  * @flags: GENL_* flags (%GENL_ADMIN_PERM or %GENL_UNS_ADMIN_PERM)
0121  * @validate: validation flags from enum genl_validate_flags
0122  * @doit: standard command callback
0123  * @dumpit: callback for dumpers
0124  *
0125  * This is a cut-down version of struct genl_ops for users who don't need
0126  * most of the ancillary infra and want to save space.
0127  */
0128 struct genl_small_ops {
0129     int (*doit)(struct sk_buff *skb, struct genl_info *info);
0130     int (*dumpit)(struct sk_buff *skb, struct netlink_callback *cb);
0131     u8  cmd;
0132     u8  internal_flags;
0133     u8  flags;
0134     u8  validate;
0135 };
0136 
0137 /**
0138  * struct genl_ops - generic netlink operations
0139  * @cmd: command identifier
0140  * @internal_flags: flags used by the family
0141  * @flags: GENL_* flags (%GENL_ADMIN_PERM or %GENL_UNS_ADMIN_PERM)
0142  * @maxattr: maximum number of attributes supported
0143  * @policy: netlink policy (takes precedence over family policy)
0144  * @validate: validation flags from enum genl_validate_flags
0145  * @doit: standard command callback
0146  * @start: start callback for dumps
0147  * @dumpit: callback for dumpers
0148  * @done: completion callback for dumps
0149  */
0150 struct genl_ops {
0151     int            (*doit)(struct sk_buff *skb,
0152                        struct genl_info *info);
0153     int            (*start)(struct netlink_callback *cb);
0154     int            (*dumpit)(struct sk_buff *skb,
0155                      struct netlink_callback *cb);
0156     int            (*done)(struct netlink_callback *cb);
0157     const struct nla_policy *policy;
0158     unsigned int        maxattr;
0159     u8          cmd;
0160     u8          internal_flags;
0161     u8          flags;
0162     u8          validate;
0163 };
0164 
0165 /**
0166  * struct genl_info - info that is available during dumpit op call
0167  * @family: generic netlink family - for internal genl code usage
0168  * @ops: generic netlink ops - for internal genl code usage
0169  * @attrs: netlink attributes
0170  */
0171 struct genl_dumpit_info {
0172     const struct genl_family *family;
0173     struct genl_ops op;
0174     struct nlattr **attrs;
0175 };
0176 
0177 static inline const struct genl_dumpit_info *
0178 genl_dumpit_info(struct netlink_callback *cb)
0179 {
0180     return cb->data;
0181 }
0182 
0183 int genl_register_family(struct genl_family *family);
0184 int genl_unregister_family(const struct genl_family *family);
0185 void genl_notify(const struct genl_family *family, struct sk_buff *skb,
0186          struct genl_info *info, u32 group, gfp_t flags);
0187 
0188 void *genlmsg_put(struct sk_buff *skb, u32 portid, u32 seq,
0189           const struct genl_family *family, int flags, u8 cmd);
0190 
0191 /**
0192  * genlmsg_nlhdr - Obtain netlink header from user specified header
0193  * @user_hdr: user header as returned from genlmsg_put()
0194  *
0195  * Returns pointer to netlink header.
0196  */
0197 static inline struct nlmsghdr *genlmsg_nlhdr(void *user_hdr)
0198 {
0199     return (struct nlmsghdr *)((char *)user_hdr -
0200                    GENL_HDRLEN -
0201                    NLMSG_HDRLEN);
0202 }
0203 
0204 /**
0205  * genlmsg_parse_deprecated - parse attributes of a genetlink message
0206  * @nlh: netlink message header
0207  * @family: genetlink message family
0208  * @tb: destination array with maxtype+1 elements
0209  * @maxtype: maximum attribute type to be expected
0210  * @policy: validation policy
0211  * @extack: extended ACK report struct
0212  */
0213 static inline int genlmsg_parse_deprecated(const struct nlmsghdr *nlh,
0214                        const struct genl_family *family,
0215                        struct nlattr *tb[], int maxtype,
0216                        const struct nla_policy *policy,
0217                        struct netlink_ext_ack *extack)
0218 {
0219     return __nlmsg_parse(nlh, family->hdrsize + GENL_HDRLEN, tb, maxtype,
0220                  policy, NL_VALIDATE_LIBERAL, extack);
0221 }
0222 
0223 /**
0224  * genlmsg_parse - parse attributes of a genetlink message
0225  * @nlh: netlink message header
0226  * @family: genetlink message family
0227  * @tb: destination array with maxtype+1 elements
0228  * @maxtype: maximum attribute type to be expected
0229  * @policy: validation policy
0230  * @extack: extended ACK report struct
0231  */
0232 static inline int genlmsg_parse(const struct nlmsghdr *nlh,
0233                 const struct genl_family *family,
0234                 struct nlattr *tb[], int maxtype,
0235                 const struct nla_policy *policy,
0236                 struct netlink_ext_ack *extack)
0237 {
0238     return __nlmsg_parse(nlh, family->hdrsize + GENL_HDRLEN, tb, maxtype,
0239                  policy, NL_VALIDATE_STRICT, extack);
0240 }
0241 
0242 /**
0243  * genl_dump_check_consistent - check if sequence is consistent and advertise if not
0244  * @cb: netlink callback structure that stores the sequence number
0245  * @user_hdr: user header as returned from genlmsg_put()
0246  *
0247  * Cf. nl_dump_check_consistent(), this just provides a wrapper to make it
0248  * simpler to use with generic netlink.
0249  */
0250 static inline void genl_dump_check_consistent(struct netlink_callback *cb,
0251                           void *user_hdr)
0252 {
0253     nl_dump_check_consistent(cb, genlmsg_nlhdr(user_hdr));
0254 }
0255 
0256 /**
0257  * genlmsg_put_reply - Add generic netlink header to a reply message
0258  * @skb: socket buffer holding the message
0259  * @info: receiver info
0260  * @family: generic netlink family
0261  * @flags: netlink message flags
0262  * @cmd: generic netlink command
0263  *
0264  * Returns pointer to user specific header
0265  */
0266 static inline void *genlmsg_put_reply(struct sk_buff *skb,
0267                       struct genl_info *info,
0268                       const struct genl_family *family,
0269                       int flags, u8 cmd)
0270 {
0271     return genlmsg_put(skb, info->snd_portid, info->snd_seq, family,
0272                flags, cmd);
0273 }
0274 
0275 /**
0276  * genlmsg_end - Finalize a generic netlink message
0277  * @skb: socket buffer the message is stored in
0278  * @hdr: user specific header
0279  */
0280 static inline void genlmsg_end(struct sk_buff *skb, void *hdr)
0281 {
0282     nlmsg_end(skb, hdr - GENL_HDRLEN - NLMSG_HDRLEN);
0283 }
0284 
0285 /**
0286  * genlmsg_cancel - Cancel construction of a generic netlink message
0287  * @skb: socket buffer the message is stored in
0288  * @hdr: generic netlink message header
0289  */
0290 static inline void genlmsg_cancel(struct sk_buff *skb, void *hdr)
0291 {
0292     if (hdr)
0293         nlmsg_cancel(skb, hdr - GENL_HDRLEN - NLMSG_HDRLEN);
0294 }
0295 
0296 /**
0297  * genlmsg_multicast_netns - multicast a netlink message to a specific netns
0298  * @family: the generic netlink family
0299  * @net: the net namespace
0300  * @skb: netlink message as socket buffer
0301  * @portid: own netlink portid to avoid sending to yourself
0302  * @group: offset of multicast group in groups array
0303  * @flags: allocation flags
0304  */
0305 static inline int genlmsg_multicast_netns(const struct genl_family *family,
0306                       struct net *net, struct sk_buff *skb,
0307                       u32 portid, unsigned int group, gfp_t flags)
0308 {
0309     if (WARN_ON_ONCE(group >= family->n_mcgrps))
0310         return -EINVAL;
0311     group = family->mcgrp_offset + group;
0312     return nlmsg_multicast(net->genl_sock, skb, portid, group, flags);
0313 }
0314 
0315 /**
0316  * genlmsg_multicast - multicast a netlink message to the default netns
0317  * @family: the generic netlink family
0318  * @skb: netlink message as socket buffer
0319  * @portid: own netlink portid to avoid sending to yourself
0320  * @group: offset of multicast group in groups array
0321  * @flags: allocation flags
0322  */
0323 static inline int genlmsg_multicast(const struct genl_family *family,
0324                     struct sk_buff *skb, u32 portid,
0325                     unsigned int group, gfp_t flags)
0326 {
0327     return genlmsg_multicast_netns(family, &init_net, skb,
0328                        portid, group, flags);
0329 }
0330 
0331 /**
0332  * genlmsg_multicast_allns - multicast a netlink message to all net namespaces
0333  * @family: the generic netlink family
0334  * @skb: netlink message as socket buffer
0335  * @portid: own netlink portid to avoid sending to yourself
0336  * @group: offset of multicast group in groups array
0337  * @flags: allocation flags
0338  *
0339  * This function must hold the RTNL or rcu_read_lock().
0340  */
0341 int genlmsg_multicast_allns(const struct genl_family *family,
0342                 struct sk_buff *skb, u32 portid,
0343                 unsigned int group, gfp_t flags);
0344 
0345 /**
0346  * genlmsg_unicast - unicast a netlink message
0347  * @skb: netlink message as socket buffer
0348  * @portid: netlink portid of the destination socket
0349  */
0350 static inline int genlmsg_unicast(struct net *net, struct sk_buff *skb, u32 portid)
0351 {
0352     return nlmsg_unicast(net->genl_sock, skb, portid);
0353 }
0354 
0355 /**
0356  * genlmsg_reply - reply to a request
0357  * @skb: netlink message to be sent back
0358  * @info: receiver information
0359  */
0360 static inline int genlmsg_reply(struct sk_buff *skb, struct genl_info *info)
0361 {
0362     return genlmsg_unicast(genl_info_net(info), skb, info->snd_portid);
0363 }
0364 
0365 /**
0366  * gennlmsg_data - head of message payload
0367  * @gnlh: genetlink message header
0368  */
0369 static inline void *genlmsg_data(const struct genlmsghdr *gnlh)
0370 {
0371     return ((unsigned char *) gnlh + GENL_HDRLEN);
0372 }
0373 
0374 /**
0375  * genlmsg_len - length of message payload
0376  * @gnlh: genetlink message header
0377  */
0378 static inline int genlmsg_len(const struct genlmsghdr *gnlh)
0379 {
0380     struct nlmsghdr *nlh = (struct nlmsghdr *)((unsigned char *)gnlh -
0381                             NLMSG_HDRLEN);
0382     return (nlh->nlmsg_len - GENL_HDRLEN - NLMSG_HDRLEN);
0383 }
0384 
0385 /**
0386  * genlmsg_msg_size - length of genetlink message not including padding
0387  * @payload: length of message payload
0388  */
0389 static inline int genlmsg_msg_size(int payload)
0390 {
0391     return GENL_HDRLEN + payload;
0392 }
0393 
0394 /**
0395  * genlmsg_total_size - length of genetlink message including padding
0396  * @payload: length of message payload
0397  */
0398 static inline int genlmsg_total_size(int payload)
0399 {
0400     return NLMSG_ALIGN(genlmsg_msg_size(payload));
0401 }
0402 
0403 /**
0404  * genlmsg_new - Allocate a new generic netlink message
0405  * @payload: size of the message payload
0406  * @flags: the type of memory to allocate.
0407  */
0408 static inline struct sk_buff *genlmsg_new(size_t payload, gfp_t flags)
0409 {
0410     return nlmsg_new(genlmsg_total_size(payload), flags);
0411 }
0412 
0413 /**
0414  * genl_set_err - report error to genetlink broadcast listeners
0415  * @family: the generic netlink family
0416  * @net: the network namespace to report the error to
0417  * @portid: the PORTID of a process that we want to skip (if any)
0418  * @group: the broadcast group that will notice the error
0419  *  (this is the offset of the multicast group in the groups array)
0420  * @code: error code, must be negative (as usual in kernelspace)
0421  *
0422  * This function returns the number of broadcast listeners that have set the
0423  * NETLINK_RECV_NO_ENOBUFS socket option.
0424  */
0425 static inline int genl_set_err(const struct genl_family *family,
0426                    struct net *net, u32 portid,
0427                    u32 group, int code)
0428 {
0429     if (WARN_ON_ONCE(group >= family->n_mcgrps))
0430         return -EINVAL;
0431     group = family->mcgrp_offset + group;
0432     return netlink_set_err(net->genl_sock, portid, group, code);
0433 }
0434 
0435 static inline int genl_has_listeners(const struct genl_family *family,
0436                      struct net *net, unsigned int group)
0437 {
0438     if (WARN_ON_ONCE(group >= family->n_mcgrps))
0439         return -EINVAL;
0440     group = family->mcgrp_offset + group;
0441     return netlink_has_listeners(net->genl_sock, group);
0442 }
0443 #endif  /* __NET_GENERIC_NETLINK_H */