]> git.ipfire.org Git - thirdparty/ulogd2.git/commitdiff
NFLOG: attach struct nf_conntrack
authorKen-ichirou MATSUZAWA <chamas@h4.dion.ne.jp>
Thu, 18 Nov 2021 11:09:19 +0000 (20:09 +0900)
committerPablo Neira Ayuso <pablo@netfilter.org>
Tue, 23 Nov 2021 13:47:50 +0000 (14:47 +0100)
put nf_conntrack in ct outputkey when "attach_conntrack" is specified.
But there is no way to show both nflog "raw" and "ct" now.

Signed-off-by: Ken-ichirou MATSUZAWA <chamas@h4.dion.ne.jp>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
input/packet/Makefile.am
input/packet/ulogd_inppkt_NFLOG.c

index 3aa01112084edae6e6aee8b2e54b4b4678a2e76c..851c6088e10d5efa981c5e886edbfab526a89ceb 100644 (file)
@@ -1,6 +1,6 @@
 include $(top_srcdir)/Make_global.am
 
-AM_CPPFLAGS += ${LIBNETFILTER_LOG_CFLAGS}
+AM_CPPFLAGS += ${LIBNETFILTER_LOG_CFLAGS} ${LIBNETFILTER_CONNTRACK_CFLAGS}
 
 pkglib_LTLIBRARIES = ulogd_inppkt_UNIXSOCK.la
 
@@ -20,5 +20,6 @@ pkglib_LTLIBRARIES += ulogd_inppkt_NFLOG.la
 
 ulogd_inppkt_NFLOG_la_SOURCES = ulogd_inppkt_NFLOG.c
 ulogd_inppkt_NFLOG_la_LDFLAGS = -avoid-version -module
-ulogd_inppkt_NFLOG_la_LIBADD  = $(LIBNETFILTER_LOG_LIBS)
+ulogd_inppkt_NFLOG_la_LIBADD  = $(LIBNETFILTER_LOG_LIBS) \
+                               $(LIBNETFILTER_CONNTRACK_LIBS)
 endif
index 449c0c6d42e25712aa49757fc548ec06a5f01fb3..4fdeb12886ccefa5e6344d18bbf3071fd34f233d 100644 (file)
 #include <ulogd/ulogd.h>
 #include <libnfnetlink/libnfnetlink.h>
 #include <libnetfilter_log/libnetfilter_log.h>
+#ifdef BUILD_NFCT
+#include <libmnl/libmnl.h>
+#include <libnetfilter_conntrack/libnetfilter_conntrack.h>
+#else
+struct nf_conntrack;
+#endif
+
 
 #ifndef NFLOG_GROUP_DEFAULT
 #define NFLOG_GROUP_DEFAULT    0
@@ -148,6 +155,7 @@ enum nflog_keys {
        NFLOG_KEY_RAW_MAC_SADDR,
        NFLOG_KEY_RAW_MAC_ADDRLEN,
        NFLOG_KEY_RAW,
+       NFLOG_KEY_RAW_CT,
 };
 
 static struct ulogd_key output_keys[] = {
@@ -319,11 +327,52 @@ static struct ulogd_key output_keys[] = {
                .flags = ULOGD_RETF_NONE,
                .name = "raw",
        },
+       [NFLOG_KEY_RAW_CT] = {
+               .type = ULOGD_RET_RAW,
+               .flags = ULOGD_RETF_NONE,
+               .name = "ct",
+       },
 };
 
+struct nf_conntrack *build_ct(struct nfgenmsg *nfmsg)
+{
+#ifdef BUILD_NFCT
+       struct nlmsghdr *nlh =
+               (struct nlmsghdr *)((void *)nfmsg - sizeof(*nlh));
+       struct nlattr *attr, *ctattr = NULL;
+       struct nf_conntrack *ct;
+
+       mnl_attr_for_each(attr, nlh, sizeof(struct nfgenmsg)) {
+               if (mnl_attr_get_type(attr) == NFULA_CT) {
+                       ctattr = attr;
+                       break;
+               }
+       }
+       if (!ctattr)
+               return NULL;
+
+       ct = nfct_new();
+       if (!ct) {
+               ulogd_log(ULOGD_ERROR, "failed to allocate nfct\n");
+               return NULL;
+       }
+       if (nfct_payload_parse(mnl_attr_get_payload(ctattr),
+                              mnl_attr_get_payload_len(ctattr),
+                              nfmsg->nfgen_family, ct) < 0) {
+               ulogd_log(ULOGD_ERROR, "failed to parse nfct payload\n");
+               nfct_destroy(ct);
+               return NULL;
+       }
+
+       return ct;
+#else
+       return NULL;
+#endif
+}
+
 static inline int
 interp_packet(struct ulogd_pluginstance *upi, uint8_t pf_family,
-             struct nflog_data *ldata)
+             struct nflog_data *ldata, struct nf_conntrack *ct)
 {
        struct ulogd_key *ret = upi->output.keys;
 
@@ -404,6 +453,9 @@ interp_packet(struct ulogd_pluginstance *upi, uint8_t pf_family,
 
        okey_set_ptr(&ret[NFLOG_KEY_RAW], ldata);
 
+       if (ct != NULL)
+               okey_set_ptr(&ret[NFLOG_KEY_RAW_CT], ct);
+
        ulogd_propagate_results(upi);
        return 0;
 }
@@ -478,16 +530,25 @@ static int msg_cb(struct nflog_g_handle *gh, struct nfgenmsg *nfmsg,
 {
        struct ulogd_pluginstance *upi = data;
        struct ulogd_pluginstance *npi = NULL;
+       void *ct = build_ct(nfmsg);
        int ret = 0;
 
        /* since we support the re-use of one instance in several 
         * different stacks, we duplicate the message to let them know */
        llist_for_each_entry(npi, &upi->plist, plist) {
-               ret = interp_packet(npi, nfmsg->nfgen_family, nfa);
+               ret = interp_packet(npi, nfmsg->nfgen_family, nfa, ct);
                if (ret != 0)
-                       return ret;
+                       goto release_ct;
        }
-       return interp_packet(upi, nfmsg->nfgen_family, nfa);
+       ret = interp_packet(upi, nfmsg->nfgen_family, nfa, ct);
+
+release_ct:
+#ifdef BUILD_NFCT
+       if (ct != NULL)
+               nfct_destroy(ct);
+#endif
+
+       return ret;
 }
 
 static int configure(struct ulogd_pluginstance *upi,