iproute2/include/libnetlink.h
<<
>>
Prefs
   1/* SPDX-License-Identifier: GPL-2.0 */
   2#ifndef __LIBNETLINK_H__
   3#define __LIBNETLINK_H__ 1
   4
   5#include <stdio.h>
   6#include <string.h>
   7#include <asm/types.h>
   8#include <linux/netlink.h>
   9#include <linux/rtnetlink.h>
  10#include <linux/if_link.h>
  11#include <linux/if_addr.h>
  12#include <linux/neighbour.h>
  13#include <linux/netconf.h>
  14#include <arpa/inet.h>
  15
  16struct rtnl_handle {
  17        int                     fd;
  18        struct sockaddr_nl      local;
  19        struct sockaddr_nl      peer;
  20        __u32                   seq;
  21        __u32                   dump;
  22        int                     proto;
  23        FILE                   *dump_fp;
  24#define RTNL_HANDLE_F_LISTEN_ALL_NSID           0x01
  25#define RTNL_HANDLE_F_SUPPRESS_NLERR            0x02
  26#define RTNL_HANDLE_F_STRICT_CHK                0x04
  27        int                     flags;
  28};
  29
  30struct nlmsg_list {
  31        struct nlmsg_list *next;
  32        struct nlmsghdr   h;
  33};
  34
  35struct nlmsg_chain {
  36        struct nlmsg_list *head;
  37        struct nlmsg_list *tail;
  38};
  39
  40extern int rcvbuf;
  41
  42int rtnl_open(struct rtnl_handle *rth, unsigned int subscriptions)
  43        __attribute__((warn_unused_result));
  44
  45int rtnl_open_byproto(struct rtnl_handle *rth, unsigned int subscriptions,
  46                             int protocol)
  47        __attribute__((warn_unused_result));
  48int rtnl_add_nl_group(struct rtnl_handle *rth, unsigned int group)
  49        __attribute__((warn_unused_result));
  50void rtnl_close(struct rtnl_handle *rth);
  51void rtnl_set_strict_dump(struct rtnl_handle *rth);
  52
  53typedef int (*req_filter_fn_t)(struct nlmsghdr *nlh, int reqlen);
  54
  55int rtnl_addrdump_req(struct rtnl_handle *rth, int family,
  56                      req_filter_fn_t filter_fn)
  57        __attribute__((warn_unused_result));
  58int rtnl_addrlbldump_req(struct rtnl_handle *rth, int family)
  59        __attribute__((warn_unused_result));
  60int rtnl_routedump_req(struct rtnl_handle *rth, int family,
  61                       req_filter_fn_t filter_fn)
  62        __attribute__((warn_unused_result));
  63int rtnl_ruledump_req(struct rtnl_handle *rth, int family)
  64        __attribute__((warn_unused_result));
  65int rtnl_neighdump_req(struct rtnl_handle *rth, int family,
  66                       req_filter_fn_t filter_fn)
  67        __attribute__((warn_unused_result));
  68int rtnl_neightbldump_req(struct rtnl_handle *rth, int family)
  69        __attribute__((warn_unused_result));
  70int rtnl_mdbdump_req(struct rtnl_handle *rth, int family)
  71        __attribute__((warn_unused_result));
  72int rtnl_brvlandump_req(struct rtnl_handle *rth, int family, __u32 dump_flags)
  73        __attribute__((warn_unused_result));
  74int rtnl_netconfdump_req(struct rtnl_handle *rth, int family)
  75        __attribute__((warn_unused_result));
  76
  77int rtnl_linkdump_req(struct rtnl_handle *rth, int fam)
  78        __attribute__((warn_unused_result));
  79int rtnl_linkdump_req_filter(struct rtnl_handle *rth, int fam, __u32 filt_mask)
  80        __attribute__((warn_unused_result));
  81
  82int rtnl_linkdump_req_filter_fn(struct rtnl_handle *rth, int fam,
  83                                req_filter_fn_t fn)
  84        __attribute__((warn_unused_result));
  85int rtnl_fdb_linkdump_req_filter_fn(struct rtnl_handle *rth,
  86                                    req_filter_fn_t filter_fn)
  87        __attribute__((warn_unused_result));
  88int rtnl_nsiddump_req_filter_fn(struct rtnl_handle *rth, int family,
  89                                req_filter_fn_t filter_fn)
  90        __attribute__((warn_unused_result));
  91int rtnl_statsdump_req_filter(struct rtnl_handle *rth, int fam, __u32 filt_mask)
  92        __attribute__((warn_unused_result));
  93int rtnl_dump_request(struct rtnl_handle *rth, int type, void *req,
  94                             int len)
  95        __attribute__((warn_unused_result));
  96int rtnl_dump_request_n(struct rtnl_handle *rth, struct nlmsghdr *n)
  97        __attribute__((warn_unused_result));
  98
  99int rtnl_nexthopdump_req(struct rtnl_handle *rth, int family,
 100                         req_filter_fn_t filter_fn)
 101        __attribute__((warn_unused_result));
 102int rtnl_nexthop_bucket_dump_req(struct rtnl_handle *rth, int family,
 103                                 req_filter_fn_t filter_fn)
 104        __attribute__((warn_unused_result));
 105
 106struct rtnl_ctrl_data {
 107        int     nsid;
 108};
 109
 110typedef int (*rtnl_filter_t)(struct nlmsghdr *n, void *);
 111
 112/**
 113 * rtnl error handler called from
 114 *      rtnl_dump_done()
 115 *      rtnl_dump_error()
 116 *
 117 * Return value is a bitmask of the following values:
 118 * RTNL_LET_NLERR
 119 *      error handled as usual
 120 * RTNL_SUPPRESS_NLMSG_DONE_NLERR
 121 *      error in nlmsg_type == NLMSG_DONE will be suppressed
 122 * RTNL_SUPPRESS_NLMSG_ERROR_NLERR
 123 *      error in nlmsg_type == NLMSG_ERROR will be suppressed
 124 *      and nlmsg will be skipped
 125 * RTNL_SUPPRESS_NLERR - suppress error in both previous cases
 126 */
 127#define RTNL_LET_NLERR                          0x01
 128#define RTNL_SUPPRESS_NLMSG_DONE_NLERR          0x02
 129#define RTNL_SUPPRESS_NLMSG_ERROR_NLERR         0x04
 130#define RTNL_SUPPRESS_NLERR                     0x06
 131typedef int (*rtnl_err_hndlr_t)(struct nlmsghdr *n, void *);
 132
 133typedef int (*rtnl_listen_filter_t)(struct rtnl_ctrl_data *,
 134                                    struct nlmsghdr *n, void *);
 135
 136typedef int (*nl_ext_ack_fn_t)(const char *errmsg, uint32_t off,
 137                               const struct nlmsghdr *inner_nlh);
 138
 139struct rtnl_dump_filter_arg {
 140        rtnl_filter_t filter;
 141        void *arg1;
 142        rtnl_err_hndlr_t errhndlr;
 143        void *arg2;
 144        __u16 nc_flags;
 145};
 146
 147int rtnl_dump_filter_nc(struct rtnl_handle *rth,
 148                        rtnl_filter_t filter,
 149                        void *arg, __u16 nc_flags);
 150#define rtnl_dump_filter(rth, filter, arg) \
 151        rtnl_dump_filter_nc(rth, filter, arg, 0)
 152int rtnl_dump_filter_errhndlr_nc(struct rtnl_handle *rth,
 153                                 rtnl_filter_t filter,
 154                                 void *arg1,
 155                                 rtnl_err_hndlr_t errhndlr,
 156                                 void *arg2,
 157                                 __u16 nc_flags);
 158#define rtnl_dump_filter_errhndlr(rth, filter, farg, errhndlr, earg) \
 159        rtnl_dump_filter_errhndlr_nc(rth, filter, farg, errhndlr, earg, 0)
 160
 161int rtnl_talk(struct rtnl_handle *rtnl, struct nlmsghdr *n,
 162              struct nlmsghdr **answer)
 163        __attribute__((warn_unused_result));
 164int rtnl_talk_iov(struct rtnl_handle *rtnl, struct iovec *iovec, size_t iovlen,
 165                  struct nlmsghdr **answer)
 166        __attribute__((warn_unused_result));
 167int rtnl_talk_suppress_rtnl_errmsg(struct rtnl_handle *rtnl, struct nlmsghdr *n,
 168                                   struct nlmsghdr **answer)
 169        __attribute__((warn_unused_result));
 170int rtnl_send(struct rtnl_handle *rth, const void *buf, int)
 171        __attribute__((warn_unused_result));
 172int rtnl_send_check(struct rtnl_handle *rth, const void *buf, int)
 173        __attribute__((warn_unused_result));
 174int nl_dump_ext_ack(const struct nlmsghdr *nlh, nl_ext_ack_fn_t errfn);
 175int nl_dump_ext_ack_done(const struct nlmsghdr *nlh, int error);
 176
 177int addattr(struct nlmsghdr *n, int maxlen, int type);
 178int addattr8(struct nlmsghdr *n, int maxlen, int type, __u8 data);
 179int addattr16(struct nlmsghdr *n, int maxlen, int type, __u16 data);
 180int addattr32(struct nlmsghdr *n, int maxlen, int type, __u32 data);
 181int addattr64(struct nlmsghdr *n, int maxlen, int type, __u64 data);
 182int addattrstrz(struct nlmsghdr *n, int maxlen, int type, const char *data);
 183
 184int addattr_l(struct nlmsghdr *n, int maxlen, int type,
 185              const void *data, int alen);
 186int addraw_l(struct nlmsghdr *n, int maxlen, const void *data, int len);
 187struct rtattr *addattr_nest(struct nlmsghdr *n, int maxlen, int type);
 188int addattr_nest_end(struct nlmsghdr *n, struct rtattr *nest);
 189struct rtattr *addattr_nest_compat(struct nlmsghdr *n, int maxlen, int type,
 190                                   const void *data, int len);
 191int addattr_nest_compat_end(struct nlmsghdr *n, struct rtattr *nest);
 192int rta_addattr8(struct rtattr *rta, int maxlen, int type, __u8 data);
 193int rta_addattr16(struct rtattr *rta, int maxlen, int type, __u16 data);
 194int rta_addattr32(struct rtattr *rta, int maxlen, int type, __u32 data);
 195int rta_addattr64(struct rtattr *rta, int maxlen, int type, __u64 data);
 196int rta_addattr_l(struct rtattr *rta, int maxlen, int type,
 197                  const void *data, int alen);
 198
 199int parse_rtattr(struct rtattr *tb[], int max, struct rtattr *rta, int len);
 200int parse_rtattr_flags(struct rtattr *tb[], int max, struct rtattr *rta,
 201                              int len, unsigned short flags);
 202struct rtattr *parse_rtattr_one(int type, struct rtattr *rta, int len);
 203int __parse_rtattr_nested_compat(struct rtattr *tb[], int max, struct rtattr *rta, int len);
 204
 205struct rtattr *rta_nest(struct rtattr *rta, int maxlen, int type);
 206int rta_nest_end(struct rtattr *rta, struct rtattr *nest);
 207
 208#define RTA_TAIL(rta) \
 209                ((struct rtattr *) (((void *) (rta)) + \
 210                                    RTA_ALIGN((rta)->rta_len)))
 211
 212#define parse_rtattr_nested(tb, max, rta) \
 213        (parse_rtattr_flags((tb), (max), RTA_DATA(rta), RTA_PAYLOAD(rta), \
 214                            NLA_F_NESTED))
 215
 216#define parse_rtattr_one_nested(type, rta) \
 217        (parse_rtattr_one(type, RTA_DATA(rta), RTA_PAYLOAD(rta)))
 218
 219#define parse_rtattr_nested_compat(tb, max, rta, data, len) \
 220        ({ data = RTA_PAYLOAD(rta) >= len ? RTA_DATA(rta) : NULL;       \
 221                __parse_rtattr_nested_compat(tb, max, rta, len); })
 222
 223static inline __u8 rta_getattr_u8(const struct rtattr *rta)
 224{
 225        return *(__u8 *)RTA_DATA(rta);
 226}
 227static inline __u16 rta_getattr_u16(const struct rtattr *rta)
 228{
 229        return *(__u16 *)RTA_DATA(rta);
 230}
 231static inline __be16 rta_getattr_be16(const struct rtattr *rta)
 232{
 233        return ntohs(rta_getattr_u16(rta));
 234}
 235static inline __u32 rta_getattr_u32(const struct rtattr *rta)
 236{
 237        return *(__u32 *)RTA_DATA(rta);
 238}
 239static inline __be32 rta_getattr_be32(const struct rtattr *rta)
 240{
 241        return ntohl(rta_getattr_u32(rta));
 242}
 243static inline __u64 rta_getattr_u64(const struct rtattr *rta)
 244{
 245        __u64 tmp;
 246
 247        memcpy(&tmp, RTA_DATA(rta), sizeof(__u64));
 248        return tmp;
 249}
 250static inline __s32 rta_getattr_s32(const struct rtattr *rta)
 251{
 252        return *(__s32 *)RTA_DATA(rta);
 253}
 254static inline __s64 rta_getattr_s64(const struct rtattr *rta)
 255{
 256        __s64 tmp;
 257
 258        memcpy(&tmp, RTA_DATA(rta), sizeof(tmp));
 259        return tmp;
 260}
 261static inline const char *rta_getattr_str(const struct rtattr *rta)
 262{
 263        return (const char *)RTA_DATA(rta);
 264}
 265
 266int rtnl_listen_all_nsid(struct rtnl_handle *);
 267int rtnl_listen(struct rtnl_handle *, rtnl_listen_filter_t handler,
 268                void *jarg);
 269int rtnl_from_file(FILE *, rtnl_listen_filter_t handler,
 270                   void *jarg);
 271
 272#define NLMSG_TAIL(nmsg) \
 273        ((struct rtattr *) (((void *) (nmsg)) + NLMSG_ALIGN((nmsg)->nlmsg_len)))
 274
 275#ifndef IFA_RTA
 276#define IFA_RTA(r) \
 277        ((struct rtattr *)(((char *)(r)) + NLMSG_ALIGN(sizeof(struct ifaddrmsg))))
 278#endif
 279#ifndef IFA_PAYLOAD
 280#define IFA_PAYLOAD(n)  NLMSG_PAYLOAD(n, sizeof(struct ifaddrmsg))
 281#endif
 282
 283#ifndef IFLA_RTA
 284#define IFLA_RTA(r) \
 285        ((struct rtattr *)(((char *)(r)) + NLMSG_ALIGN(sizeof(struct ifinfomsg))))
 286#endif
 287#ifndef IFLA_PAYLOAD
 288#define IFLA_PAYLOAD(n) NLMSG_PAYLOAD(n, sizeof(struct ifinfomsg))
 289#endif
 290
 291#ifndef NDA_RTA
 292#define NDA_RTA(r) \
 293        ((struct rtattr *)(((char *)(r)) + NLMSG_ALIGN(sizeof(struct ndmsg))))
 294#endif
 295#ifndef NDA_PAYLOAD
 296#define NDA_PAYLOAD(n)  NLMSG_PAYLOAD(n, sizeof(struct ndmsg))
 297#endif
 298
 299#ifndef NDTA_RTA
 300#define NDTA_RTA(r) \
 301        ((struct rtattr *)(((char *)(r)) + NLMSG_ALIGN(sizeof(struct ndtmsg))))
 302#endif
 303#ifndef NDTA_PAYLOAD
 304#define NDTA_PAYLOAD(n) NLMSG_PAYLOAD(n, sizeof(struct ndtmsg))
 305#endif
 306
 307#ifndef NETNS_RTA
 308#define NETNS_RTA(r) \
 309        ((struct rtattr *)(((char *)(r)) + NLMSG_ALIGN(sizeof(struct rtgenmsg))))
 310#endif
 311#ifndef NETNS_PAYLOAD
 312#define NETNS_PAYLOAD(n)        NLMSG_PAYLOAD(n, sizeof(struct rtgenmsg))
 313#endif
 314
 315#ifndef IFLA_STATS_RTA
 316#define IFLA_STATS_RTA(r) \
 317        ((struct rtattr *)(((char *)(r)) + NLMSG_ALIGN(sizeof(struct if_stats_msg))))
 318#endif
 319
 320#ifndef BRVLAN_RTA
 321#define BRVLAN_RTA(r) \
 322        ((struct rtattr *)(((char *)(r)) + NLMSG_ALIGN(sizeof(struct br_vlan_msg))))
 323#endif
 324
 325/* User defined nlmsg_type which is used mostly for logging netlink
 326 * messages from dump file */
 327#define NLMSG_TSTAMP    15
 328
 329#define rtattr_for_each_nested(attr, nest) \
 330        for ((attr) = (void *)RTA_DATA(nest); \
 331             RTA_OK(attr, RTA_PAYLOAD(nest) - ((char *)(attr) - (char *)RTA_DATA((nest)))); \
 332             (attr) = RTA_TAIL((attr)))
 333
 334void nl_print_policy(const struct rtattr *attr, FILE *fp);
 335
 336#endif /* __LIBNETLINK_H__ */
 337