Package: ulogd Severity: normal Hi,
attached a hackish patch to make a 32bit ulogd work on a 64bit kernel. It also includes printf debugging output. The patch is in no way ment to go into the ulogd package. It is only ment to show the differences between 32bit and 64bit. It also only fixes one instance of unaligned access to the payload. All other instances where payload is used need to be checked and fixed as well. To fix the issue for existing kernels the 32bit ulogd must check wether it runs on a 32bit or 64bit kernel and convert the ulog_packet_msg_t structure accordingly. To fix this for future kernels the kernels ulog_packet_msg_t should be made bitness independent, the /usr/include/linux/netfilter_ipv4/ipt_ULOG.h provided by linux-libc-dev needs to be changed to match and the debian/include should be removed or only used for backward compatibility with old kernels. MfG Goswin PS: I tested the patch on i386/amd64, which should have the same alignment and padding problems as sparc/sparc64. -- System Information: Debian Release: squeeze/sid APT prefers unstable APT policy: (500, 'unstable'), (499, 'unstable') Architecture: amd64 (x86_64) Kernel: Linux 2.6.31.6-xen-2010.02.18 (SMP w/4 CPU cores) Locale: LANG=C, LC_CTYPE=de_DE (charmap=ISO-8859-1) Shell: /bin/sh linked to /bin/bash Versions of packages ulogd depends on: ii debconf [debconf-2.0] 1.5.28 Debian configuration management sy ii libc6 2.10.2-6 Embedded GNU C Library: Shared lib ii lsb-base 3.2-23 Linux Standard Base 3.2 init scrip ulogd recommends no packages. Versions of packages ulogd suggests: pn ulogd-mysql <none> (no description available) pn ulogd-pcap <none> (no description available) pn ulogd-pgsql <none> (no description available) pn ulogd-sqlite3 <none> (no description available)
diff -u ulogd-1.24/debian/changelog ulogd-1.24/debian/changelog --- ulogd-1.24/debian/changelog +++ ulogd-1.24/debian/changelog @@ -1,3 +1,9 @@ +ulogd (1.24-3a0.mrvn.1) unstable; urgency=low + + * Hack to make 32bitulogd work with 64bit kernel. + + -- Goswin von Brederlow <goswin-...@web.de> Tue, 06 Apr 2010 00:16:38 +0000 + ulogd (1.24-3) unstable; urgency=low * Acknowledge NMUs. diff -u ulogd-1.24/debian/patches/ipt_ULOG.patch ulogd-1.24/debian/patches/ipt_ULOG.patch --- ulogd-1.24/debian/patches/ipt_ULOG.patch +++ ulogd-1.24/debian/patches/ipt_ULOG.patch @@ -11,0 +12,11 @@ +--- extensions/Makefile.in.orig 2005-11-25 19:58:26.000000000 +0000 ++++ extensions/Makefile.in 2010-04-06 00:12:47.000000000 +0000 +@@ -4,7 +4,7 @@ + # + include @top_srcdir@/Rules.make + +-cflags+...@top_srcdir@ -...@top_srcdir@/libipulog/include -...@top_srcdir@/include ++cflags+...@top_srcdir@ -...@top_srcdir@/libipulog/include -...@top_srcdir@/include -...@top_srcdir@/debian/include + SH_CFLAGS:=$(CFLAGS) -fPIC + + SHARED_LIBS+=$(foreach T,$(ULOGD_SL),ulogd_$(T).so) diff -u ulogd-1.24/debian/include/linux/netfilter_ipv4/ipt_ULOG.h ulogd-1.24/debian/include/linux/netfilter_ipv4/ipt_ULOG.h --- ulogd-1.24/debian/include/linux/netfilter_ipv4/ipt_ULOG.h +++ ulogd-1.24/debian/include/linux/netfilter_ipv4/ipt_ULOG.h @@ -33,13 +33,14 @@ /* Format of the ULOG packets passed through netlink */ typedef struct ulog_packet_msg { - unsigned long mark; - long timestamp_sec; - long timestamp_usec; + unsigned long long mark; + long long timestamp_sec; + long long timestamp_usec; unsigned int hook; char indev_name[IFNAMSIZ]; char outdev_name[IFNAMSIZ]; - size_t data_len; + char pad[4]; + unsigned long long data_len; char prefix[ULOG_PREFIX_LEN]; unsigned char mac_len; unsigned char mac[ULOG_MAC_LEN]; only in patch2: unchanged: --- ulogd-1.24.orig/ulogd.c +++ ulogd-1.24/ulogd.c @@ -419,6 +419,37 @@ } } +void dump_packet(ulog_packet_msg_t *pkt) { + char *p = (char*)pkt; + int i; + fprintf(stderr, "mark = "); + for(i = 0; i < 8; ++i) { fprintf(stderr, "%02x ", (unsigned char)*p++); } + fprintf(stderr, "\nsec = "); + for(i = 0; i < 8; ++i) { fprintf(stderr, "%02x ", (unsigned char)*p++); } + fprintf(stderr, "\nusec = "); + for(i = 0; i < 8; ++i) { fprintf(stderr, "%02x ", (unsigned char)*p++); } + fprintf(stderr, "\nhook = "); + for(i = 0; i < 4; ++i) { fprintf(stderr, "%02x ", (unsigned char)*p++); } + fprintf(stderr, "\nindev = "); + for(i = 0; i < IFNAMSIZ; ++i) { fprintf(stderr, "%02x ", (unsigned char)*p++); } + fprintf(stderr, "\noutdev = "); + for(i = 0; i < IFNAMSIZ; ++i) { fprintf(stderr, "%02x ", (unsigned char)*p++); } + fprintf(stderr, "\npad = "); + for(i = 0; i < 4; ++i) { fprintf(stderr, "%02x ", (unsigned char)*p++); } + fprintf(stderr, "\ndata_len = (%llu) ", pkt->data_len); + for(i = 0; i < 8; ++i) { fprintf(stderr, "%02x ", (unsigned char)*p++); } + fprintf(stderr, "\nprefix = "); + for(i = 0; i < ULOG_PREFIX_LEN; ++i) { fprintf(stderr, "%02x ", (unsigned char)*p++); } + fprintf(stderr, "\nmac_len = "); + for(i = 0; i < 1; ++i) { fprintf(stderr, "%02x ", (unsigned char)*p++); } + fprintf(stderr, "\nmac = "); + for(i = 0; i < ULOG_MAC_LEN; ++i) { fprintf(stderr, "%02x ", (unsigned char)*p++); } + fprintf(stderr, "\npayload (%p %p) = ", pkt, pkt->payload); + for(i = 0; i < pkt->data_len; ++i) { fprintf(stderr, "%02x ", (unsigned char)*p++); } + fprintf(stderr, "\n"); + fprintf(stderr, "\n"); +} + /* call all registered interpreters and hand the results over to * propagate_results */ static void handle_packet(ulog_packet_msg_t *pkt) @@ -428,7 +459,7 @@ ulog_interpreter_t *ip; unsigned int i,j; - +dump_packet(pkt); /* If there are no interpreters registered yet, * ignore this packet */ if (!ulogd_interh_ids) { @@ -438,6 +469,8 @@ } for (i = 1; i <= ulogd_interh_ids; i++) { +fprintf(stderr, "\nInterpreter %d:\n", i); +dump_packet(pkt); ip = ulogd_interh[i]; /* call interpreter */ if ((ret = ((ip)->interp)(ip, pkt))) { only in patch2: unchanged: --- ulogd-1.24.orig/extensions/ulogd_BASE.c +++ ulogd-1.24/extensions/ulogd_BASE.c @@ -32,6 +32,7 @@ #include <stdio.h> #include <stdlib.h> +#include <string.h> #include <sys/socket.h> #include <netinet/ip.h> #include <netinet/in.h> @@ -199,16 +200,30 @@ }, }; +void dump_packet(ulog_packet_msg_t *pkt); static ulog_iret_t *_interp_iphdr(struct ulog_interpreter *ip, ulog_packet_msg_t *pkt) { ulog_iret_t *ret = ip->result; - struct iphdr *iph = (struct iphdr *) pkt->payload; - + struct iphdr iph_aligned; + struct iphdr *iph = &iph_aligned; + int i; + unsigned char *p, *q; +dump_packet(pkt); +fprintf(stderr, "pkt->payload = %p -> %p\n", pkt, pkt->payload); + memcpy(iph, pkt->payload, sizeof(struct iphdr)); + p = (unsigned char*)pkt->payload; + q = (unsigned char*)iph; +for(i = 0; i < sizeof(struct iphdr); ++i) { + fprintf(stderr, "%2x/%2x ", *p++, *q++); +} +fprintf(stderr, "\n"); ret[0].value.ui32 = ntohl(iph->saddr); ret[0].flags |= ULOGD_RETF_VALID; +fprintf(stderr, "saddr = %x\n", ret[0].value.ui32); ret[1].value.ui32 = ntohl(iph->daddr); ret[1].flags |= ULOGD_RETF_VALID; +fprintf(stderr, "daddr = %x\n", ret[1].value.ui32); ret[2].value.ui8 = iph->protocol; ret[2].flags |= ULOGD_RETF_VALID; ret[3].value.ui8 = iph->tos; @@ -217,6 +232,7 @@ ret[4].flags |= ULOGD_RETF_VALID; ret[5].value.ui16 = ntohs(iph->tot_len); ret[5].flags |= ULOGD_RETF_VALID; +fprintf(stderr, "tot_len = %x\n", ret[0].value.ui16); ret[6].value.ui8 = iph->ihl; ret[6].flags |= ULOGD_RETF_VALID; ret[7].value.ui16 = ntohs(iph->check);