6 #include <sys/socket.h>
7 #include <netinet/in.h>
8 #include <libnfnetlink/libnfnetlink.h>
9 #include <libnetfilter_log/libnetfilter_log.h>
10 #include <libnetfilter_log/libipulog.h>
13 #define PAYLOAD_SIZE 0xffff
20 struct nlmsghdr *last_nlh;
24 struct sockaddr_nl local;
25 struct sockaddr_nl peer;
27 struct ulog_packet_msg upmsg;
30 static const struct ipulog_errmap_t
36 { IPULOG_ERR_NONE,
"No error" },
37 { IPULOG_ERR_IMPL,
"Not implemented yet" },
38 { IPULOG_ERR_HANDLE,
"Unable to create netlink handle" },
39 { IPULOG_ERR_SOCKET,
"Unable to create netlink socket" },
40 { IPULOG_ERR_BIND,
"Unable to bind netlink socket" },
41 { IPULOG_ERR_RECVBUF,
"Receive buffer size invalid" },
42 { IPULOG_ERR_RECV,
"Error during netlink receive" },
43 { IPULOG_ERR_NLEOF,
"Received EOF on netlink socket" },
44 { IPULOG_ERR_TRUNC,
"Receive message truncated" },
45 { IPULOG_ERR_INVGR,
"Invalid group specified" },
46 { IPULOG_ERR_INVNL,
"Invalid netlink message" },
50 static unsigned int gmask2group(
unsigned int gmask)
54 for (bit =
sizeof(gmask)*4 -1; bit >= 0; bit--) {
55 if (gmask & (1 << bit))
65 int ipulog_errno = IPULOG_ERR_NONE;
67 const char *ipulog_strerror(
int errcode)
69 if (errcode < 0 || errcode > IPULOG_MAXERR)
70 errcode = IPULOG_ERR_IMPL;
71 return ipulog_errmap[errcode].message;
75 uint32_t ipulog_group2gmask(uint32_t group)
77 if (group < 1 || group > 32)
79 ipulog_errno = IPULOG_ERR_INVGR;
82 return (1 << (group - 1));
91 unsigned int group = gmask2group(gmask);
93 h = malloc(
sizeof(*h)+PAYLOAD_SIZE);
95 ipulog_errno = IPULOG_ERR_HANDLE;
98 memset(h, 0,
sizeof(*h));
105 if (rv < 0 && rv != -EEXIST)
115 ipulog_errno = IPULOG_ERR_HANDLE;
127 ulog_packet_msg_t *ipulog_get_packet(
struct ipulog_handle *h,
128 const unsigned char *buf,
131 struct nlmsghdr *nlh;
132 struct nfattr *tb[NFULA_MAX];
133 struct nfulnl_msg_packet_hdr *hdr;
137 nlh = nfnl_get_msg_first(nflog_nfnlh(h->nfulh), buf, len);
139 next_msg: printf(
"next\n");
140 nlh = nfnl_get_msg_next(nflog_nfnlh(h->nfulh), buf, len);
147 nfnl_parse_attr(tb, NFULA_MAX, NFM_NFA(NLMSG_DATA(nlh)),
150 if (!tb[NFULA_PACKET_HDR-1])
154 hdr = NFA_DATA(tb[NFULA_PACKET_HDR-1]);
155 h->upmsg.hook = hdr->hook;
157 if (tb[NFULA_MARK-1])
158 h->upmsg.mark = ntohl(*(uint32_t *)NFA_DATA(tb[NFULA_MARK-1]));
162 if (tb[NFULA_TIMESTAMP]) {
164 h->upmsg.timestamp_sec = h->upmsg.timestamp_usec = 0;
166 h->upmsg.timestamp_sec = h->upmsg.timestamp_usec = 0;
168 if (tb[NFULA_IFINDEX_INDEV-1]) {
170 h->upmsg.indev_name[0] =
'\0';
172 h->upmsg.indev_name[0] =
'\0';
174 if (tb[NFULA_IFINDEX_OUTDEV-1]) {
176 h->upmsg.outdev_name[0] =
'\0';
178 h->upmsg.outdev_name[0] =
'\0';
180 if (tb[NFULA_HWADDR-1]) {
181 struct nfulnl_msg_packet_hw *phw = NFA_DATA(tb[NFULA_HWADDR-1]);
182 h->upmsg.mac_len = ntohs(phw->hw_addrlen);
183 memcpy(h->upmsg.mac, phw->hw_addr, 8);
185 h->upmsg.mac_len = 0;
187 if (tb[NFULA_PREFIX-1]) {
188 int plen = NFA_PAYLOAD(tb[NFULA_PREFIX-1]);
189 if (ULOG_PREFIX_LEN < plen)
190 plen = ULOG_PREFIX_LEN;
191 memcpy(h->upmsg.prefix, NFA_DATA(tb[NFULA_PREFIX-1]), plen);
192 h->upmsg.prefix[ULOG_PREFIX_LEN-1] =
'\0';
195 if (tb[NFULA_PAYLOAD-1]) {
196 memcpy(h->upmsg.payload, NFA_DATA(tb[NFULA_PAYLOAD-1]),
197 NFA_PAYLOAD(tb[NFULA_PAYLOAD-1]));
198 h->upmsg.data_len = NFA_PAYLOAD(tb[NFULA_PAYLOAD-1]);
200 h->upmsg.data_len = 0;
205 ssize_t ipulog_read(
struct ipulog_handle *h,
unsigned char *buf,
206 size_t len,
int timeout)
210 return nfnl_recv(nflog_nfnlh(h->nfulh), buf, len);
214 void ipulog_perror(
const char *s)
219 fputs(
"ERROR", stderr);
221 fprintf(stderr,
": %s", ipulog_strerror(ipulog_errno));
223 fprintf(stderr,
": %s", strerror(errno));
struct nflog_handle * nflog_open(void)
struct nflog_g_handle * nflog_bind_group(struct nflog_handle *h, uint16_t num)
int nflog_bind_pf(struct nflog_handle *h, uint16_t pf)
int nflog_unbind_group(struct nflog_g_handle *gh)
int nflog_close(struct nflog_handle *h)