libmnl
1.0.3
|
00001 #ifndef _LIBMNL_H_ 00002 #define _LIBMNL_H_ 00003 00004 #ifdef __cplusplus 00005 # include <cstdio> 00006 # include <cstdint> 00007 #else 00008 # include <stdbool.h> /* not in C++ */ 00009 # include <stdio.h> 00010 # include <stdint.h> 00011 #endif 00012 #include <unistd.h> 00013 #include <sys/socket.h> /* for sa_family_t */ 00014 #include <linux/netlink.h> 00015 00016 #ifdef __cplusplus 00017 extern "C" { 00018 #endif 00019 00020 /* 00021 * Netlink socket API 00022 */ 00023 00024 #define MNL_SOCKET_AUTOPID 0 00025 #define MNL_SOCKET_BUFFER_SIZE (getpagesize() < 8192L ? getpagesize() : 8192L) 00026 00027 struct mnl_socket; 00028 00029 extern struct mnl_socket *mnl_socket_open(int type); 00030 extern int mnl_socket_bind(struct mnl_socket *nl, unsigned int groups, pid_t pid); 00031 extern int mnl_socket_close(struct mnl_socket *nl); 00032 extern int mnl_socket_get_fd(const struct mnl_socket *nl); 00033 extern unsigned int mnl_socket_get_portid(const struct mnl_socket *nl); 00034 extern ssize_t mnl_socket_sendto(const struct mnl_socket *nl, const void *req, size_t siz); 00035 extern ssize_t mnl_socket_recvfrom(const struct mnl_socket *nl, void *buf, size_t siz); 00036 extern int mnl_socket_setsockopt(const struct mnl_socket *nl, int type, void *buf, socklen_t len); 00037 extern int mnl_socket_getsockopt(const struct mnl_socket *nl, int type, void *buf, socklen_t *len); 00038 00039 /* 00040 * Netlink message API 00041 */ 00042 00043 #define MNL_ALIGNTO 4 00044 #define MNL_ALIGN(len) (((len)+MNL_ALIGNTO-1) & ~(MNL_ALIGNTO-1)) 00045 #define MNL_NLMSG_HDRLEN MNL_ALIGN(sizeof(struct nlmsghdr)) 00046 00047 extern size_t mnl_nlmsg_size(size_t len); 00048 extern size_t mnl_nlmsg_get_payload_len(const struct nlmsghdr *nlh); 00049 00050 /* Netlink message header builder */ 00051 extern struct nlmsghdr *mnl_nlmsg_put_header(void *buf); 00052 extern void *mnl_nlmsg_put_extra_header(struct nlmsghdr *nlh, size_t size); 00053 00054 /* Netlink message iterators */ 00055 extern bool mnl_nlmsg_ok(const struct nlmsghdr *nlh, int len); 00056 extern struct nlmsghdr *mnl_nlmsg_next(const struct nlmsghdr *nlh, int *len); 00057 00058 /* Netlink sequence tracking */ 00059 extern bool mnl_nlmsg_seq_ok(const struct nlmsghdr *nlh, unsigned int seq); 00060 00061 /* Netlink portID checking */ 00062 extern bool mnl_nlmsg_portid_ok(const struct nlmsghdr *nlh, unsigned int portid); 00063 00064 /* Netlink message getters */ 00065 extern void *mnl_nlmsg_get_payload(const struct nlmsghdr *nlh); 00066 extern void *mnl_nlmsg_get_payload_offset(const struct nlmsghdr *nlh, size_t offset); 00067 extern void *mnl_nlmsg_get_payload_tail(const struct nlmsghdr *nlh); 00068 00069 /* Netlink message printer */ 00070 extern void mnl_nlmsg_fprintf(FILE *fd, const void *data, size_t datalen, size_t extra_header_size); 00071 00072 /* Message batch helpers */ 00073 struct mnl_nlmsg_batch; 00074 extern struct mnl_nlmsg_batch *mnl_nlmsg_batch_start(void *buf, size_t bufsiz); 00075 extern bool mnl_nlmsg_batch_next(struct mnl_nlmsg_batch *b); 00076 extern void mnl_nlmsg_batch_stop(struct mnl_nlmsg_batch *b); 00077 extern size_t mnl_nlmsg_batch_size(struct mnl_nlmsg_batch *b); 00078 extern void mnl_nlmsg_batch_reset(struct mnl_nlmsg_batch *b); 00079 extern void *mnl_nlmsg_batch_head(struct mnl_nlmsg_batch *b); 00080 extern void *mnl_nlmsg_batch_current(struct mnl_nlmsg_batch *b); 00081 extern bool mnl_nlmsg_batch_is_empty(struct mnl_nlmsg_batch *b); 00082 00083 /* 00084 * Netlink attributes API 00085 */ 00086 #define MNL_ATTR_HDRLEN MNL_ALIGN(sizeof(struct nlattr)) 00087 00088 /* TLV attribute getters */ 00089 extern uint16_t mnl_attr_get_type(const struct nlattr *attr); 00090 extern uint16_t mnl_attr_get_len(const struct nlattr *attr); 00091 extern uint16_t mnl_attr_get_payload_len(const struct nlattr *attr); 00092 extern void *mnl_attr_get_payload(const struct nlattr *attr); 00093 extern uint8_t mnl_attr_get_u8(const struct nlattr *attr); 00094 extern uint16_t mnl_attr_get_u16(const struct nlattr *attr); 00095 extern uint32_t mnl_attr_get_u32(const struct nlattr *attr); 00096 extern uint64_t mnl_attr_get_u64(const struct nlattr *attr); 00097 extern const char *mnl_attr_get_str(const struct nlattr *attr); 00098 00099 /* TLV attribute putters */ 00100 extern void mnl_attr_put(struct nlmsghdr *nlh, uint16_t type, size_t len, const void *data); 00101 extern void mnl_attr_put_u8(struct nlmsghdr *nlh, uint16_t type, uint8_t data); 00102 extern void mnl_attr_put_u16(struct nlmsghdr *nlh, uint16_t type, uint16_t data); 00103 extern void mnl_attr_put_u32(struct nlmsghdr *nlh, uint16_t type, uint32_t data); 00104 extern void mnl_attr_put_u64(struct nlmsghdr *nlh, uint16_t type, uint64_t data); 00105 extern void mnl_attr_put_str(struct nlmsghdr *nlh, uint16_t type, const char *data); 00106 extern void mnl_attr_put_strz(struct nlmsghdr *nlh, uint16_t type, const char *data); 00107 00108 /* TLV attribute putters with buffer boundary checkings */ 00109 extern bool mnl_attr_put_check(struct nlmsghdr *nlh, size_t buflen, uint16_t type, size_t len, const void *data); 00110 extern bool mnl_attr_put_u8_check(struct nlmsghdr *nlh, size_t buflen, uint16_t type, uint8_t data); 00111 extern bool mnl_attr_put_u16_check(struct nlmsghdr *nlh, size_t buflen, uint16_t type, uint16_t data); 00112 extern bool mnl_attr_put_u32_check(struct nlmsghdr *nlh, size_t buflen, uint16_t type, uint32_t data); 00113 extern bool mnl_attr_put_u64_check(struct nlmsghdr *nlh, size_t buflen, uint16_t type, uint64_t data); 00114 extern bool mnl_attr_put_str_check(struct nlmsghdr *nlh, size_t buflen, uint16_t type, const char *data); 00115 extern bool mnl_attr_put_strz_check(struct nlmsghdr *nlh, size_t buflen, uint16_t type, const char *data); 00116 00117 /* TLV attribute nesting */ 00118 extern struct nlattr *mnl_attr_nest_start(struct nlmsghdr *nlh, uint16_t type); 00119 extern struct nlattr *mnl_attr_nest_start_check(struct nlmsghdr *nlh, size_t buflen, uint16_t type); 00120 extern void mnl_attr_nest_end(struct nlmsghdr *nlh, struct nlattr *start); 00121 extern void mnl_attr_nest_cancel(struct nlmsghdr *nlh, struct nlattr *start); 00122 00123 /* TLV validation */ 00124 extern int mnl_attr_type_valid(const struct nlattr *attr, uint16_t maxtype); 00125 00126 enum mnl_attr_data_type { 00127 MNL_TYPE_UNSPEC, 00128 MNL_TYPE_U8, 00129 MNL_TYPE_U16, 00130 MNL_TYPE_U32, 00131 MNL_TYPE_U64, 00132 MNL_TYPE_STRING, 00133 MNL_TYPE_FLAG, 00134 MNL_TYPE_MSECS, 00135 MNL_TYPE_NESTED, 00136 MNL_TYPE_NESTED_COMPAT, 00137 MNL_TYPE_NUL_STRING, 00138 MNL_TYPE_BINARY, 00139 MNL_TYPE_MAX, 00140 }; 00141 00142 extern int mnl_attr_validate(const struct nlattr *attr, enum mnl_attr_data_type type); 00143 extern int mnl_attr_validate2(const struct nlattr *attr, enum mnl_attr_data_type type, size_t len); 00144 00145 /* TLV iterators */ 00146 extern bool mnl_attr_ok(const struct nlattr *attr, int len); 00147 extern struct nlattr *mnl_attr_next(const struct nlattr *attr); 00148 00149 #define mnl_attr_for_each(attr, nlh, offset) \ 00150 for ((attr) = mnl_nlmsg_get_payload_offset((nlh), (offset)); \ 00151 mnl_attr_ok((attr), (char *)mnl_nlmsg_get_payload_tail(nlh) - (char *)(attr)); \ 00152 (attr) = mnl_attr_next(attr)) 00153 00154 #define mnl_attr_for_each_nested(attr, nest) \ 00155 for ((attr) = mnl_attr_get_payload(nest); \ 00156 mnl_attr_ok((attr), (char *)mnl_attr_get_payload(nest) + mnl_attr_get_payload_len(nest) - (char *)(attr)); \ 00157 (attr) = mnl_attr_next(attr)) 00158 00159 #define mnl_attr_for_each_payload(payload, payload_size) \ 00160 for ((attr) = (payload); \ 00161 mnl_attr_ok((attr), (char *)(payload) + payload_size - (char *)(attr)); \ 00162 (attr) = mnl_attr_next(attr)) 00163 00164 /* TLV callback-based attribute parsers */ 00165 typedef int (*mnl_attr_cb_t)(const struct nlattr *attr, void *data); 00166 00167 extern int mnl_attr_parse(const struct nlmsghdr *nlh, unsigned int offset, mnl_attr_cb_t cb, void *data); 00168 extern int mnl_attr_parse_nested(const struct nlattr *attr, mnl_attr_cb_t cb, void *data); 00169 extern int mnl_attr_parse_payload(const void *payload, size_t payload_len, mnl_attr_cb_t cb, void *data); 00170 00171 /* 00172 * callback API 00173 */ 00174 #define MNL_CB_ERROR -1 00175 #define MNL_CB_STOP 0 00176 #define MNL_CB_OK 1 00177 00178 typedef int (*mnl_cb_t)(const struct nlmsghdr *nlh, void *data); 00179 00180 extern int mnl_cb_run(const void *buf, size_t numbytes, unsigned int seq, 00181 unsigned int portid, mnl_cb_t cb_data, void *data); 00182 00183 extern int mnl_cb_run2(const void *buf, size_t numbytes, unsigned int seq, 00184 unsigned int portid, mnl_cb_t cb_data, void *data, 00185 mnl_cb_t *cb_ctl_array, unsigned int cb_ctl_array_len); 00186 00187 /* 00188 * other declarations 00189 */ 00190 00191 #ifndef SOL_NETLINK 00192 #define SOL_NETLINK 270 00193 #endif 00194 00195 #ifndef MNL_ARRAY_SIZE 00196 #define MNL_ARRAY_SIZE(a) (sizeof(a)/sizeof((a)[0])) 00197 #endif 00198 00199 #ifdef __cplusplus 00200 } /* extern "C" */ 00201 #endif 00202 00203 #endif