Date: Tue, 25 Nov 2008 20:42:39 +0700 From: Eugene Grosbein <eugen@kuzbass.ru> To: net@freebsd.org Cc: ipfw@freebsd.org Subject: m_tag_find() overhead Message-ID: <20081125134239.GA17138@svzserv.kemerovo.su>
next in thread | raw e-mail | index | archive | help
Hi! I wonder if one more call to m_tag_find() for every outgoing packet would be expensive. For many years conventional way to implement PBR was: use 'ipfw fwd'. Currently 'ipfw add fwd ... in' marks a packet with PACKET_TAG_IPFORWARD. Such forwarding changes packet's outgoing interface generally but none in the kernel reflect this in packet's metadata and packets are passed by ip_output() to PFIL hooks with wrong outgoing interface name ( details and How-To-Repeat may be found here: http://www.freebsd.org/cgi/query-pr.cgi?pr=kern/129036 ) I've patched src/sys/netinet/ip_output.c to fix this problem by extra check for PACKET_TAG_IPFORWARD and update of route if necessary. This adds a call to m_tag_find() for every outgoing packet if packet filtering is enabled and kernel has options IPFIREWALL_FORWARD. Please review. It works for my test lab but I'm not sure if that's correct: should a call to rtalloc_ign() be accomplished with some resource freeing call? And what's the meaning of RTF_CLONING second argument of rtalloc_ign? --- ip_output.c.orig 2008-11-25 14:21:26.000000000 +0700 +++ ip_output.c 2008-11-25 18:29:32.000000000 +0700 @@ -195,6 +195,20 @@ ro->ro_rt = (struct rtentry *)0; } #ifdef IPFIREWALL_FORWARD + /* + * Check if packet has changed next-hop in ip_input() + * If so, update route so pfil hooks get it right + */ + if ((inet_pfil_hook.ph_busy_count != -1) && + (fwd_tag = m_tag_find(m, PACKET_TAG_IPFORWARD, NULL))) { + bzero(&iproute, sizeof(iproute)); + ro = &iproute; + bcopy((fwd_tag+1), &ro->ro_dst, sizeof(struct sockaddr_in)); + m_tag_delete(m, fwd_tag); + rtalloc_ign(ro, RTF_CLONING); + dst = (struct sockaddr_in *)&ro->ro_dst; + } + if (ro->ro_rt == NULL && fwd_tag == NULL) { #else if (ro->ro_rt == NULL) { Eugene Grosbein
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?20081125134239.GA17138>