* [PATCH V2] bgmac: fix "cmdcfg" calls for promisc and loopback modes
From: Rafał Miłecki @ 2013-02-07 15:40 UTC (permalink / raw)
To: netdev, David S. Miller; +Cc: Nathan Hintz, Rafał Miłecki
In-Reply-To: <1360232591-25789-1-git-send-email-zajec5@gmail.com>
The last (bool) parameter in bgmac_cmdcfg_maskset says if the write
should be made, even if value didn't change. Currently driver doesn't
match the specs about (not) forcing some changes. This makes it follow
them.
Reported-by: Nathan Hintz <nlhintz@hotmail.com>
Signed-off-by: Rafał Miłecki <zajec5@gmail.com>
---
V2: commit message
---
drivers/net/ethernet/broadcom/bgmac.c | 8 ++++----
1 file changed, 4 insertions(+), 4 deletions(-)
diff --git a/drivers/net/ethernet/broadcom/bgmac.c b/drivers/net/ethernet/broadcom/bgmac.c
index f90d1dc..8cf5e39 100644
--- a/drivers/net/ethernet/broadcom/bgmac.c
+++ b/drivers/net/ethernet/broadcom/bgmac.c
@@ -776,9 +776,9 @@ static void bgmac_set_rx_mode(struct net_device *net_dev)
struct bgmac *bgmac = netdev_priv(net_dev);
if (net_dev->flags & IFF_PROMISC)
- bgmac_cmdcfg_maskset(bgmac, ~0, BGMAC_CMDCFG_PROM, false);
+ bgmac_cmdcfg_maskset(bgmac, ~0, BGMAC_CMDCFG_PROM, true);
else
- bgmac_cmdcfg_maskset(bgmac, ~BGMAC_CMDCFG_PROM, 0, false);
+ bgmac_cmdcfg_maskset(bgmac, ~BGMAC_CMDCFG_PROM, 0, true);
}
#if 0 /* We don't use that regs yet */
@@ -1039,9 +1039,9 @@ static void bgmac_chip_init(struct bgmac *bgmac, bool full_init)
bgmac_write_mac_address(bgmac, bgmac->net_dev->dev_addr);
if (bgmac->loopback)
- bgmac_cmdcfg_maskset(bgmac, ~0, BGMAC_CMDCFG_ML, true);
+ bgmac_cmdcfg_maskset(bgmac, ~0, BGMAC_CMDCFG_ML, false);
else
- bgmac_cmdcfg_maskset(bgmac, ~BGMAC_CMDCFG_ML, 0, true);
+ bgmac_cmdcfg_maskset(bgmac, ~BGMAC_CMDCFG_ML, 0, false);
bgmac_write(bgmac, BGMAC_RXMAX_LENGTH, 32 + ETHER_MAX_LEN);
--
1.7.10.4
^ permalink raw reply related
* Re: [IPv6] interface-local multicast escapes the local node
From: YOSHIFUJI Hideaki @ 2013-02-07 15:41 UTC (permalink / raw)
To: Erik Hugne; +Cc: netdev, YOSHIFUJI Hideaki
In-Reply-To: <20130207072857.GA27969@eerihug-hybrid.ki.sw.ericsson.se>
Erik Hugne wrote:
> On Thu, Feb 07, 2013 at 02:00:10AM +0100, Hannes Frederic Sowa wrote:
>> RFC4541 3. IPv6 Considerations:
>>
>> MLD messages are also not sent regarding groups with addresses in the
>> range FF00::/15 (which encompasses both the reserved FF00::/16 and
>> node-local FF01::/16 IPv6 address spaces). These addresses should
>> never appear in packets on the link.
>>
>> It gives a strong indication that we should drop these packets. What do you
>> think?
>
> That was my understanding aswell. I asked for some clarifications on the ietf list:
> <quote>
> > The key is that the packets should be dropped without generating
> > any errors or traffic.
> Yep, you are right - I assumed that implicitly, but
> I should have mentioned that explicitly :-)
> </quote>
> http://www.ietf.org/mail-archive/web/ipv6/current/msg17126.html
Please file errata on RFC4291. Thanks.
--yoshfuji
^ permalink raw reply
* Re: [PATCH net 1/2] net: sctp: sctp_auth_make_key_vector: fix undefined ref-count behaviour
From: Vlad Yasevich @ 2013-02-07 15:45 UTC (permalink / raw)
To: Daniel Borkmann; +Cc: davem, netdev, linux-sctp
In-Reply-To: <5113C745.10103@redhat.com>
On 02/07/2013 10:24 AM, Daniel Borkmann wrote:
> On 02/07/2013 04:04 PM, Vlad Yasevich wrote:
>> On 02/07/2013 05:55 AM, Daniel Borkmann wrote:
>>> In sctp_auth_make_key_vector(), a sctp_auth_bytes structure is being
>>> allocated, but without setting its object reference count, thus it's
>>> initialized with a random value from the memory, which can lead to
>>> i) premature free's of this object when being put (with possible
>>> subsequent kernel panics), or ii) memory leaks when refcount has a
>>> high value.
>>>
>>> Fix this by using the appropriate sctp_auth_create_key() allocator,
>>> which performs sanity checks, sets length and the refcount, as similar
>>> done in sctp_auth_asoc_set_secret() and others. This bug seems to be
>>> present since 2007 (1f485649f529: Implement SCTP-AUTH internals).
>>
>> Not strictly a bug. The vectors are temporary and directly freed by
>> the caller. They are only used by sctp_auth_asoc_create_secret()
>> which builds the association secret key. The vectors are destroyed at
>> the end of that function using kfree() thus noone really cares about
>> the refcount on them and there are no leaks.
>>
>> If you are going to convert to using sctp_auth_create_key() then you
>> need to convert the callers to user to use sctp_auth_key_put().
>> Otherwise you are leaking object counts.
>
> Thanks for your feedback!
>
> If Dave is okay with this, then:
>
> - [PATCH net 2/2] net: sctp: sctp_auth_key_put: use kzfree instead of
> kfree
> - [PATCH net-next] net: sctp: sctp_auth_make_key_vector: remove
> duplicate ntohs calls
>
> can be applied as is. (If necessary, I could send the first one
> _unchanged_ as a
> single patch again, since it was part of a patchset. However, it will apply
> cleanly as we have it right here.)
>
That's fine. Those 2 patches are ok.
> Then, to avoid any future confusion and to stay consistent, I'll convert
> this
> to sctp_auth_create_key() API as well and make use of the
> sctp_auth_key_put()
> in a later possible patch *after* those two have been applied.
Fine by me.
-vlad
>
>>> Signed-off-by: Daniel Borkmann <dborkman@redhat.com>
>>> ---
>>> net/sctp/auth.c | 4 +---
>>> 1 file changed, 1 insertion(+), 3 deletions(-)
>>>
>>> diff --git a/net/sctp/auth.c b/net/sctp/auth.c
>>> index 159b9bc..55f1b06 100644
>>> --- a/net/sctp/auth.c
>>> +++ b/net/sctp/auth.c
>>> @@ -205,12 +205,10 @@ static struct sctp_auth_bytes
>>> *sctp_auth_make_key_vector(
>>> if (chunks)
>>> len += ntohs(chunks->param_hdr.length);
>>>
>>> - new = kmalloc(sizeof(struct sctp_auth_bytes) + len, gfp);
>>> + new = sctp_auth_create_key(len, gfp);
>>> if (!new)
>>> return NULL;
>>>
>>> - new->len = len;
>>> -
>>> memcpy(new->data, random, ntohs(random->param_hdr.length));
>>> offset += ntohs(random->param_hdr.length);
>>>
>>>
>>
^ permalink raw reply
* Re: [PATCH] netpoll: cleanup sparse warnings
From: Eric Dumazet @ 2013-02-07 15:52 UTC (permalink / raw)
To: Neil Horman; +Cc: netdev, fengguang.wu, David Miller
In-Reply-To: <1360248961-30721-1-git-send-email-nhorman@tuxdriver.com>
On Thu, 2013-02-07 at 09:56 -0500, Neil Horman wrote:
> With my recent commit I introduced two sparse warnings. Looking closer there
> were a few more in the same file, so I fixed them all up. Basic rcu pointer
> dereferencing suff
> - npinfo = np->dev->npinfo;
> + /* rtnl_dereference would be preferable here but
> + * rcu_cleanup_netpoll path can put us in here safely without
> + * holding the rtnl, so plain rcu_dereference it is
> + */
> + npinfo = rcu_dereference(np->dev->npinfo);
> if (!npinfo)
> return;
>
Are you sure it wont trigger a LOCKDEP complain (CONFIG_PROVE_RCU=y) ?
^ permalink raw reply
* Re: [PATCH v4 3/3] tg3: add support for Ethernet core in bcm4785
From: Michael Chan @ 2013-02-07 16:07 UTC (permalink / raw)
To: Hauke Mehrtens; +Cc: davem, mcarlson, nsujir, netdev, m
In-Reply-To: <1360251459-32384-4-git-send-email-hauke@hauke-m.de>
On Thu, 2013-02-07 at 16:37 +0100, Hauke Mehrtens wrote:
> The BCM4785 or sometimes named BMC4705 is a Broadcom SoC which a
> Gigabit 5750 Ethernet core. The core is connected via PCI with the rest
> of the SoC, but it uses some extension.
>
> This core does not use a firmware or an eeprom.
>
> Some devices only have a switch which supports 100MBit/s, this
> currently does not work with this driver.
>
> This patch was original written by Michael Buesch <m@bues.ch> and is in
> OpenWrt for some years now.
>
> This was tested on a Linksys WRT610N V1 and older versions of this patch
> were tested by other people on different devices.
>
> Signed-off-by: Hauke Mehrtens <hauke@hauke-m.de>
Looks good.
Acked-by: Michael Chan <mchan@broadcom.com>
^ permalink raw reply
* Re: [PATCH v4 2/3] tg3: make it possible to provide phy_id in ioctl
From: Michael Chan @ 2013-02-07 16:10 UTC (permalink / raw)
To: Hauke Mehrtens; +Cc: davem, mcarlson, nsujir, netdev, m
In-Reply-To: <1360251459-32384-3-git-send-email-hauke@hauke-m.de>
On Thu, 2013-02-07 at 16:37 +0100, Hauke Mehrtens wrote:
> In OpenWrt we currently use a switch driver which uses the ioctls to
> configure the switch in the phy. We have to provide the phy_id to do
> so, but without this patch this is not possible.
>
> Signed-off-by: Hauke Mehrtens <hauke@hauke-m.de>
Looks good.
Acked-by: Michael Chan <mchan@broadcom.com>
^ permalink raw reply
* Re: inaccurate packet scheduling
From: Jiri Pirko @ 2013-02-07 16:13 UTC (permalink / raw)
To: Eric Dumazet; +Cc: edumazet, netdev, kuznet, jhs
In-Reply-To: <20130130121447.GB1604@minipsycho.orion>
Wed, Jan 30, 2013 at 01:14:47PM CET, jiri@resnulli.us wrote:
>Tue, Jan 29, 2013 at 05:13:03PM CET, eric.dumazet@gmail.com wrote:
>>On Tue, 2013-01-29 at 13:23 +0100, Jiri Pirko wrote:
>>
>>> part of the commit message says:
>>> <quote>
>>> The bits per second on the wire is still 5200Mb/s with new HTB
>>> because qdisc accounts for packet length using skb->len, which
>>> is smaller than total bytes on the wire if GSO is used. But
>>> that is for another patch regardless of how time is accounted.
>>> </quote>
>>> I believe that is a similar problem like ours. But looks like this
>>> "another patch" never got in.
>>>
>>
>>Hmm, I thought I addressed this in
>>
>>commit 1def9238d4aa2146924994aa4b7dc861f03b9362
>>Author: Eric Dumazet <edumazet@google.com>
>>Date: Thu Jan 10 12:36:42 2013 +0000
>>
>> net_sched: more precise pkt_len computation
>>
>> One long standing problem with TSO/GSO/GRO packets is that skb->len
>> doesn't represent a precise amount of bytes on wire.
>>
>> Headers are only accounted for the first segment.
>> For TCP, thats typically 66 bytes per 1448 bytes segment missing,
>> an error of 4.5 % for normal MSS value.
>>
>> As consequences :
>>
>> 1) TBF/CBQ/HTB/NETEM/... can send more bytes than the assigned limits.
>> 2) Device stats are slightly under estimated as well.
>>
>> Fix this by taking account of headers in qdisc_skb_cb(skb)->pkt_len
>> computation.
>>
>> Packet schedulers should use qdisc pkt_len instead of skb->len for their
>> bandwidth limitations, and TSO enabled devices drivers could use pkt_len
>> if their statistics are not hardware assisted, and if they don't scratch
>> skb->cb[] first word.
>>
>> Both egress and ingress paths work, thanks to commit fda55eca5a
>> (net: introduce skb_transport_header_was_set()) : If GRO built
>> a GSO packet, it also set the transport header for us.
>>
>
>
>I tried kernel with this patch in. I also ported
>56b765b79e9a78dc7d3f8850ba5e5567205a3ecd to tbf. I'm getting always the
>similar numbers with iperf. There must be something else needed :/
Any other ideas?
>
>Thanks
>
>Jiri
^ permalink raw reply
* Re: [PATCH 0/2] fix kernel crash with macvtap on top of LRO
From: Ben Hutchings @ 2013-02-07 16:20 UTC (permalink / raw)
To: Eric Dumazet
Cc: Michael S. Tsirkin, Greenstein, John Fastabend, e1000-devel,
Jesse Brandeburg, Jacob Keller, Don, Tushar, Sony Chacko,
Jitendra Kalsaria, netdev, Bruce Allan, linux-kernel,
David S. Miller, John Ronciak, Eilon, linux-driver
In-Reply-To: <1360207111.28557.47.camel@edumazet-glaptop>
On Wed, 2013-02-06 at 19:18 -0800, Eric Dumazet wrote:
> On Wed, 2013-02-06 at 23:34 +0000, Ben Hutchings wrote:
>
> > If we want to allow forwarding from LRO then net/ipv4/inet_lro.c also
> > needs to set gso_type.
>
> Then, what is dev_disable_lro() purpose ?
The purpose was to disable LRO when forwarding because they weren't
compatible.
If the consensus now is that the modifications made by LRO+TSO are
acceptable in a bridge/router, then we should get rid of
dev_disable_lro() and set both gso_size & gso_type on all LRO receive
paths.
If the consensus is still that we must preserve packets exactly (aside
from the usual modifications by IP routers) then LRO should be disabled
on all devices for which forwarding is enabled. (Also, we really ought
to keep a count of the number of forwarders and use that in
netdev_fix_features(), rather than doing a one-time disable.)
Ben.
--
Ben Hutchings, Staff Engineer, Solarflare
Not speaking for my employer; that's the marketing department's job.
They asked us to note that Solarflare product names are trademarked.
------------------------------------------------------------------------------
Free Next-Gen Firewall Hardware Offer
Buy your Sophos next-gen firewall before the end March 2013
and get the hardware for free! Learn more.
http://p.sf.net/sfu/sophos-d2d-feb
_______________________________________________
E1000-devel mailing list
E1000-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/e1000-devel
To learn more about Intel® Ethernet, visit http://communities.intel.com/community/wired
^ permalink raw reply
* Re: inaccurate packet scheduling
From: Eric Dumazet @ 2013-02-07 16:39 UTC (permalink / raw)
To: Jiri Pirko; +Cc: edumazet, netdev, kuznet, jhs
In-Reply-To: <20130207161327.GA1619@minipsycho.brq.redhat.com>
On Thu, 2013-02-07 at 17:13 +0100, Jiri Pirko wrote:
> >I tried kernel with this patch in. I also ported
> >56b765b79e9a78dc7d3f8850ba5e5567205a3ecd to tbf. I'm getting always the
> >similar numbers with iperf. There must be something else needed :/
>
> Any other ideas?
You didn't post any patch, how can I comment on them ?
^ permalink raw reply
* Re: [PATCH] qmi_wwan, cdc-ether: add ADU960S
From: Dan Williams @ 2013-02-07 16:53 UTC (permalink / raw)
To: Bjørn Mork; +Cc: linux-usb, netdev
In-Reply-To: <874nhp6x1o.fsf@nemi.mork.no>
On Wed, 2013-02-06 at 20:51 +0100, Bjørn Mork wrote:
> Dan Williams <dcbw@redhat.com> writes:
>
> > It advertises a standard CDC-ETHER interface, which actually should be
> > driven by qmi_wwan.
> >
> > Signed-off-by: Dan Williams <dcbw@redhat.com>
> > ---
> > diff --git a/drivers/net/usb/cdc_ether.c b/drivers/net/usb/cdc_ether.c
> > index 3f3d12d..cc6d0c1 100644
> > --- a/drivers/net/usb/cdc_ether.c
> > +++ b/drivers/net/usb/cdc_ether.c
> > @@ -615,6 +615,13 @@ static const struct usb_device_id products [] = {
> > .driver_info = 0,
> > },
> >
> > +/* AnyDATA ADU960S - handled by qmi_wwan */
> > +{
> > + USB_DEVICE_AND_INTERFACE_INFO(0x16d5, 0x650a, USB_CLASS_COMM,
> > + USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE),
> > + .driver_info = 0,
> > +},
> > +
> > /*
> > * WHITELIST!!!
> > *
> > diff --git a/drivers/net/usb/qmi_wwan.c b/drivers/net/usb/qmi_wwan.c
> > index 6a1ca50..2b5ea32 100644
> > --- a/drivers/net/usb/qmi_wwan.c
> > +++ b/drivers/net/usb/qmi_wwan.c
> > @@ -459,6 +459,7 @@ static const struct usb_device_id products[] = {
> > {QMI_FIXED_INTF(0x1199, 0x68a2, 19)}, /* Sierra Wireless MC7710 in QMI mode */
> > {QMI_FIXED_INTF(0x1199, 0x901c, 8)}, /* Sierra Wireless EM7700 */
> > {QMI_FIXED_INTF(0x1bbb, 0x011e, 4)}, /* Telekom Speedstick LTE II (Alcatel One Touch L100V LTE) */
> > + {QMI_FIXED_INTF(0x16d5, 0x650a, 8)}, /* AnyDATA ADU960S */
> >
> > /* 4. Gobi 1000 devices */
> > {QMI_GOBI1K_DEVICE(0x05c6, 0x9212)}, /* Acer Gobi Modem Device */
>
>
> Just thinking....
>
> Maybe we should use USB_DEVICE_AND_INTERFACE_INFO() in qmi_wwan as well
> for these devices? The only reason we match on interface number for
> most devices in that driver is because those devices use ff/ff/ff for
> multiple different functions. When the function is uniquely identified
> using class/subclass/protocol as here, then I believe it makes more
> sense to use those values. And it creates a symmetry between the
> cdc_ether and the qmi_wwan entries, making the connection between them
> clearer.
Ok, I'll resubmit with DEVICE_AND_INTERFACE_INFO in qmi_wwan.
Dan
> Not to mention that such symmetry prevents us from ending up with no
> driver supporting the device if some firmware upgrade happened to change
> the interface number..
>
>
> Bjørn
> --
> To unsubscribe from this list: send the line "unsubscribe linux-usb" in
> the body of a message to majordomo@vger.kernel.org
> More majordomo info at http://vger.kernel.org/majordomo-info.html
^ permalink raw reply
* Re: [PATCHv2-net-3.8 0/3] fix kernel crash with macvtap on top of LRO
From: Ben Hutchings @ 2013-02-07 17:05 UTC (permalink / raw)
To: Michael S. Tsirkin, David S. Miller
Cc: Eilon Greenstein, John Fastabend, e1000-devel, Jesse Brandeburg,
Jacob, Keller, Tushar, Sony Chacko, Jitendra Kalsaria, Carolyn,
Jeff, netdev, Bruce Allan, linux-kernel, John Ronciak,
linux-driver, Peter
In-Reply-To: <cover.1360236441.git.mst@redhat.com>
On Thu, 2013-02-07 at 15:12 +0200, Michael S. Tsirkin wrote:
> At the moment, macvtap crashes are observed if macvtap is attached
> to an interface with LRO enabled.
> The crash in question is BUG() in macvtap_skb_to_vnet_hdr.
> This happens because several drivers set gso_size but not gso_type
> in incoming skbs.
> This didn't use to be the case: with intel cards on 3.2 and older
> kernels, with qlogic - on 3.4 and older kernels, so it's a regression if
> not a recent one.
> The following patches fix this for qlogic, broadcom and intel drivers.
>
> I tested that the patch fixes the crash for ixgbe but
> don't have qlogic/broadcom hardware to test.
> I also only tested TCPv4.
>
> Please review, and consider for 3.8.
>
> Changes from v1:
> - added missing htons as suggested by Eric
> - backported the relevant bits from
> cbf1de72324a8105ddcc3d9ce9acbc613faea17e for bnx2x
I still don't think macvtap should behave inconsistently with forwarding
and the bridge device. We need a consensus as to whether transformation
by LRO is allowable before making changes one way or the other. If
we're going to allow it then inet_lro also needs this fix.
Ben.
--
Ben Hutchings, Staff Engineer, Solarflare
Not speaking for my employer; that's the marketing department's job.
They asked us to note that Solarflare product names are trademarked.
------------------------------------------------------------------------------
Free Next-Gen Firewall Hardware Offer
Buy your Sophos next-gen firewall before the end March 2013
and get the hardware for free! Learn more.
http://p.sf.net/sfu/sophos-d2d-feb
_______________________________________________
E1000-devel mailing list
E1000-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/e1000-devel
To learn more about Intel® Ethernet, visit http://communities.intel.com/community/wired
^ permalink raw reply
* Re: [PATCH 2/2 v2] sierra_net: fix issues with SYNC/RESTART messages and interrupt pipe setup
From: Dan Williams @ 2013-02-07 17:06 UTC (permalink / raw)
To: Bjørn Mork
Cc: Oliver Neukum, Elina Pasheva, netdev, linux-usb, Rory Filer,
Phil Sutter
In-Reply-To: <87ip655eqw.fsf@nemi.mork.no>
On Wed, 2013-02-06 at 22:11 +0100, Bjørn Mork wrote:
> Dan Williams <dcbw@redhat.com> writes:
>
> > As part of the initialization sequence, the driver sends a SYNC message
> > via the control pipe to the firmware, which appears to request a
> > firmware restart. The firmware responds with an indication via the
> > interrupt pipe set up by usbnet. If the driver does not receive a
> > RESTART indication within a certain amount of time, it will periodically
> > send additional SYNC messages until it receives the RESTART indication.
> >
> > Unfortunately, the interrupt URB is only submitted while the netdev
> > is open, which is usually not the case during initialization, and thus
> > the firmware's RESTART indication is lost. So the driver continues
> > sending SYNC messages, and eventually the firmware crashes when it
> > receives too many. This leads to a wedged netdev.
> >
> > To ensure the firmware's RESTART indications can be received by the
> > driver, request that usbnet keep the interrupt URB active via
> > FLAG_INTR_ALWAYS.
> >
> > Second, move the code that sends the SYNC message out of the
> > bind() hook and after usbnet_probe() to ensure the interrupt URB
> > is set up before trying to use it.
>
> Given this description I am wondering if you couldn't just move the
> whole SYNC thing to a new reset() hook, using some private flag to make
> sure it only runs once? Does it really need to start at probe time?
It doesn't need to run exactly at probe, but it appears to need to be
the first thing the driver does when communicating with the firmware to
ensure clear state and whatnot. Possibly like the QMI SYNC message that
clears all the client IDs and resets the internal stack. (the driver
also sends a "shutdown" message to the firmware when unbinding).
So I do think that somewhere around probe() is the best time to do this,
because it's best to initialize the device when the driver binds to it
and react to errors as soon as possible, rather than trying to set
everything up on open/IFF_UP and then fail right before you want to
actually use the device. Late-fail is quite unhelpful for applications.
I don't really care if it happens in probe() or somewhere else right
after the driver is bound to the device, but it should be part of the
initialization process.
Dan
^ permalink raw reply
* Re: [PATCHv2-net-3.8 2/3] qlcnic: set gso_type
From: Jitendra Kalsaria @ 2013-02-07 17:08 UTC (permalink / raw)
To: Michael S. Tsirkin, netdev
Cc: Eilon Greenstein, Jeff Kirsher, Jesse Brandeburg, Bruce Allan,
Carolyn Wyborny, Don Skidmore, Greg Rose, Peter P Waskiewicz Jr,
Alex Duyck, John Ronciak, Tushar Dave, Sony Chacko,
Dept-Eng Linux Driver, John Fastabend, David Miller, Jacob Keller,
linux-kernel, e1000-devel@lists.sourceforge.net,
bhutchings@solarflare.com, "eric.dumazet@gma
In-Reply-To: <50a60e1293901965901edb46ae49e52da1d469d5.1360236441.git.mst@redhat.com>
On 2/7/13 5:13 AM, "Michael S. Tsirkin" <mst@redhat.com> wrote:
>qlcnic set gso_size but not gso type. This leads to crashes
>in macvtap.
>
>Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
>---
> drivers/net/ethernet/qlogic/qlcnic/qlcnic_io.c | 7 ++++++-
> 1 file changed, 6 insertions(+), 1 deletion(-)
>
>diff --git a/drivers/net/ethernet/qlogic/qlcnic/qlcnic_io.c
>b/drivers/net/ethernet/qlogic/qlcnic/qlcnic_io.c
>index 6f82812..09aa310 100644
>--- a/drivers/net/ethernet/qlogic/qlcnic/qlcnic_io.c
>+++ b/drivers/net/ethernet/qlogic/qlcnic/qlcnic_io.c
>@@ -986,8 +986,13 @@ qlcnic_process_lro(struct qlcnic_adapter *adapter,
> th->seq = htonl(seq_number);
> length = skb->len;
>
>- if (adapter->flags & QLCNIC_FW_LRO_MSS_CAP)
>+ if (adapter->flags & QLCNIC_FW_LRO_MSS_CAP) {
> skb_shinfo(skb)->gso_size = qlcnic_get_lro_sts_mss(sts_data1);
>+ if (skb->protocol == htons(ETH_P_IPV6))
>+ skb_shinfo(skb)->gso_type = SKB_GSO_TCPV6;
>+ else
>+ skb_shinfo(skb)->gso_type = SKB_GSO_TCPV4;
>+ }
>
> if (vid != 0xffff)
> __vlan_hwaccel_put_tag(skb, vid);
>--
>MST
Thanks!
Acked-by: Jitendra Kalsaria <jitendra.kalsaria@qlogic.com>
^ permalink raw reply
* Re: inaccurate packet scheduling
From: Jiri Pirko @ 2013-02-07 17:39 UTC (permalink / raw)
To: Eric Dumazet; +Cc: edumazet, netdev, kuznet, jhs
In-Reply-To: <1360255175.28557.55.camel@edumazet-glaptop>
Thu, Feb 07, 2013 at 05:39:35PM CET, eric.dumazet@gmail.com wrote:
>On Thu, 2013-02-07 at 17:13 +0100, Jiri Pirko wrote:
>
>> >I tried kernel with this patch in. I also ported
>> >56b765b79e9a78dc7d3f8850ba5e5567205a3ecd to tbf. I'm getting always the
>> >similar numbers with iperf. There must be something else needed :/
>>
>> Any other ideas?
>
>You didn't post any patch, how can I comment on them ?
Okay, sorry, here it is. But as I said, it did not help.
Subject: [patch net-next RFC] tbf: improved accuracy at high rates
Current TBF uses rate table computed by the "tc" userspace program,
which has the following issue:
The rate table has 256 entries to map packet lengths to
token (time units). With TSO sized packets, the 256 entry granularity
leads to loss/gain of rate, making the token bucket inaccurate.
Thus, instead of relying on rate table, this patch explicitly computes
the time and accounts for packet transmission times with nanosecond
granularity.
This is a followup to 56b765b79e9a78dc7d3f8850ba5e5567205a3ecd
Signed-off-by: Jiri Pirko <jiri@resnulli.us>
---
net/sched/sch_tbf.c | 97 +++++++++++++++++++++++++++++++++++++++--------------
1 file changed, 71 insertions(+), 26 deletions(-)
diff --git a/net/sched/sch_tbf.c b/net/sched/sch_tbf.c
index 4b056c15..fdec80b 100644
--- a/net/sched/sch_tbf.c
+++ b/net/sched/sch_tbf.c
@@ -97,25 +97,68 @@
changed the limit is not effective anymore.
*/
+struct tbf_rate_cfg {
+ u64 rate_bps;
+ u32 mult;
+ u32 shift;
+};
+
struct tbf_sched_data {
/* Parameters */
u32 limit; /* Maximal length of backlog: bytes */
u32 buffer; /* Token bucket depth/rate: MUST BE >= MTU/B */
u32 mtu;
u32 max_size;
- struct qdisc_rate_table *R_tab;
- struct qdisc_rate_table *P_tab;
+ struct tbf_rate_cfg rate;
+ struct tbf_rate_cfg peek;
+ bool peek_present;
/* Variables */
- long tokens; /* Current number of B tokens */
- long ptokens; /* Current number of P tokens */
+ s64 tokens; /* Current number of B tokens */
+ s64 ptokens; /* Current number of P tokens */
psched_time_t t_c; /* Time check-point */
struct Qdisc *qdisc; /* Inner qdisc, default - bfifo queue */
struct qdisc_watchdog watchdog; /* Watchdog timer */
};
-#define L2T(q, L) qdisc_l2t((q)->R_tab, L)
-#define L2T_P(q, L) qdisc_l2t((q)->P_tab, L)
+static u64 l2t_ns(struct tbf_rate_cfg *r, unsigned int len)
+{
+ return ((u64)len * r->mult) >> r->shift;
+}
+
+static void htb_precompute_ratedata(struct tbf_rate_cfg *r)
+{
+ u64 factor;
+ u64 mult;
+ int shift;
+
+ r->shift = 0;
+ r->mult = 1;
+ /*
+ * Calibrate mult, shift so that token counting is accurate
+ * for smallest packet size (64 bytes). Token (time in ns) is
+ * computed as (bytes * 8) * NSEC_PER_SEC / rate_bps. It will
+ * work as long as the smallest packet transfer time can be
+ * accurately represented in nanosec.
+ */
+ if (r->rate_bps > 0) {
+ /*
+ * Higher shift gives better accuracy. Find the largest
+ * shift such that mult fits in 32 bits.
+ */
+ for (shift = 0; shift < 16; shift++) {
+ r->shift = shift;
+ factor = 8LLU * NSEC_PER_SEC * (1 << r->shift);
+ mult = div64_u64(factor, r->rate_bps);
+ if (mult > UINT_MAX)
+ break;
+ }
+
+ r->shift = shift - 1;
+ factor = 8LLU * NSEC_PER_SEC * (1 << r->shift);
+ r->mult = div64_u64(factor, r->rate_bps);
+ }
+}
static int tbf_enqueue(struct sk_buff *skb, struct Qdisc *sch)
{
@@ -157,23 +200,23 @@ static struct sk_buff *tbf_dequeue(struct Qdisc *sch)
if (skb) {
psched_time_t now;
- long toks;
- long ptoks = 0;
+ s64 toks;
+ s64 ptoks = 0;
unsigned int len = qdisc_pkt_len(skb);
- now = psched_get_time();
- toks = psched_tdiff_bounded(now, q->t_c, q->buffer);
+ now = ktime_to_ns(ktime_get());
+ toks = min_t(s64, now - q->t_c, q->buffer);
- if (q->P_tab) {
+ if (q->peek_present) {
ptoks = toks + q->ptokens;
if (ptoks > (long)q->mtu)
ptoks = q->mtu;
- ptoks -= L2T_P(q, len);
+ ptoks -= (s64) l2t_ns(&q->peek, len);
}
toks += q->tokens;
if (toks > (long)q->buffer)
toks = q->buffer;
- toks -= L2T(q, len);
+ toks -= (s64) l2t_ns(&q->rate, len);
if ((toks|ptoks) >= 0) {
skb = qdisc_dequeue_peeked(q->qdisc);
@@ -214,7 +257,7 @@ static void tbf_reset(struct Qdisc *sch)
qdisc_reset(q->qdisc);
sch->q.qlen = 0;
- q->t_c = psched_get_time();
+ q->t_c = ktime_to_ns(ktime_get());
q->tokens = q->buffer;
q->ptokens = q->mtu;
qdisc_watchdog_cancel(&q->watchdog);
@@ -299,8 +342,16 @@ static int tbf_change(struct Qdisc *sch, struct nlattr *opt)
q->tokens = q->buffer;
q->ptokens = q->mtu;
- swap(q->R_tab, rtab);
- swap(q->P_tab, ptab);
+ q->rate.rate_bps = (u64) rtab->rate.rate << 3;
+ if (ptab) {
+ q->peek.rate_bps = (u64) ptab->rate.rate << 3;
+ q->peek_present = true;
+ } else {
+ q->peek_present = false;
+ }
+
+ htb_precompute_ratedata(&q->rate);
+ htb_precompute_ratedata(&q->peek);
sch_tree_unlock(sch);
err = 0;
@@ -319,7 +370,7 @@ static int tbf_init(struct Qdisc *sch, struct nlattr *opt)
if (opt == NULL)
return -EINVAL;
- q->t_c = psched_get_time();
+ q->t_c = ktime_to_ns(ktime_get());
qdisc_watchdog_init(&q->watchdog, sch);
q->qdisc = &noop_qdisc;
@@ -331,12 +382,6 @@ static void tbf_destroy(struct Qdisc *sch)
struct tbf_sched_data *q = qdisc_priv(sch);
qdisc_watchdog_cancel(&q->watchdog);
-
- if (q->P_tab)
- qdisc_put_rtab(q->P_tab);
- if (q->R_tab)
- qdisc_put_rtab(q->R_tab);
-
qdisc_destroy(q->qdisc);
}
@@ -352,9 +397,9 @@ static int tbf_dump(struct Qdisc *sch, struct sk_buff *skb)
goto nla_put_failure;
opt.limit = q->limit;
- opt.rate = q->R_tab->rate;
- if (q->P_tab)
- opt.peakrate = q->P_tab->rate;
+ opt.rate.rate = q->rate.rate_bps >> 3;
+ if (q->peek_present)
+ opt.peakrate.rate = q->peek.rate_bps >> 3;
else
memset(&opt.peakrate, 0, sizeof(opt.peakrate));
opt.mtu = q->mtu;
--
1.8.1.2
^ permalink raw reply related
* Re: inaccurate packet scheduling
From: Eric Dumazet @ 2013-02-07 17:47 UTC (permalink / raw)
To: Jiri Pirko; +Cc: edumazet, netdev, kuznet, jhs
In-Reply-To: <20130207173909.GA1651@minipsycho.orion>
On Thu, 2013-02-07 at 18:39 +0100, Jiri Pirko wrote:
> Thu, Feb 07, 2013 at 05:39:35PM CET, eric.dumazet@gmail.com wrote:
> >On Thu, 2013-02-07 at 17:13 +0100, Jiri Pirko wrote:
> >
> >> >I tried kernel with this patch in. I also ported
> >> >56b765b79e9a78dc7d3f8850ba5e5567205a3ecd to tbf. I'm getting always the
> >> >similar numbers with iperf. There must be something else needed :/
> >>
> >> Any other ideas?
> >
> >You didn't post any patch, how can I comment on them ?
>
> Okay, sorry, here it is. But as I said, it did not help.
>
> Subject: [patch net-next RFC] tbf: improved accuracy at high rates
>
> Current TBF uses rate table computed by the "tc" userspace program,
> which has the following issue:
>
> The rate table has 256 entries to map packet lengths to
> token (time units). With TSO sized packets, the 256 entry granularity
> leads to loss/gain of rate, making the token bucket inaccurate.
>
> Thus, instead of relying on rate table, this patch explicitly computes
> the time and accounts for packet transmission times with nanosecond
> granularity.
>
> This is a followup to 56b765b79e9a78dc7d3f8850ba5e5567205a3ecd
>
> Signed-off-by: Jiri Pirko <jiri@resnulli.us>
> ---
This patch doesnt change q->max_size
So you hit this :
if (qdisc_pkt_len(skb) > q->max_size)
return qdisc_reshape_fail(skb, sch);
I thought this point was already mentioned in my previous mails.
^ permalink raw reply
* [PATCH] tcp: sysctl to disable TCP simultaneous connect
From: Kees Cook @ 2013-02-07 17:52 UTC (permalink / raw)
To: linux-kernel
Cc: Rob Landley, David S. Miller, Alexey Kuznetsov, James Morris,
Hideaki YOSHIFUJI, Patrick McHardy, Eric Dumazet, Neil Horman,
Yuchung Cheng, Shan Wei, linux-doc, netdev, Willy Tarreau
This is based on Willy Tarreau's patch from 2008[1]. The goal is to
close a corner-case of TCP that isn't used and poses a small DoS risk.
For systems that do not want to take any risk at all, this is a desirable
configuration knob.
It is possible for two clients to connect with crossed SYNs without
checking sequence numbers. As such, it might be possible to guess a source
port number to block a system from making connections to well-known
ports and IP addresses (e.g. auto-update checks) without requiring a
MiTM position.
The feature can now be disabled via sysctl:
$ echo 0 > /proc/sys/net/ipv4/tcp_simult_connect
$ echo ohai | nc -w 1 -p 50000 localhost 50000 -v -v -v
nc: connect to localhost port 50000 (tcp) timed out: Operation now in progress
nc: connect to localhost port 50000 (tcp) timed out: Operation now in progress
$ echo 1 > /proc/sys/net/ipv4/tcp_simult_connect
$ echo ohai | nc -w 1 -p 50000 localhost 50000 -v -v -v
Connection to localhost 50000 port [tcp/*] succeeded!
ohai
[1] http://thread.gmane.org/gmane.linux.network/107971
Cc: Willy Tarreau <w@1wt.eu>
Signed-off-by: Kees Cook <keescook@chromium.org>
---
Documentation/networking/ip-sysctl.txt | 17 +++++++++++++++++
include/net/tcp.h | 1 +
net/ipv4/sysctl_net_ipv4.c | 9 +++++++++
net/ipv4/tcp_input.c | 3 ++-
4 files changed, 29 insertions(+), 1 deletion(-)
diff --git a/Documentation/networking/ip-sysctl.txt b/Documentation/networking/ip-sysctl.txt
index dbca661..2e5bd51 100644
--- a/Documentation/networking/ip-sysctl.txt
+++ b/Documentation/networking/ip-sysctl.txt
@@ -431,6 +431,23 @@ tcp_rmem - vector of 3 INTEGERs: min, default, max
tcp_sack - BOOLEAN
Enable select acknowledgments (SACKS).
+tcp_simult_connect - BOOLEAN
+ Enables TCP simultaneous connect feature conforming to RFC793.
+ Strict implementation of RFC793 (TCP) requires support for a
+ feature called "simultaneous connect", which allows two clients to
+ connect to each other without anyone entering a listening state.
+ While almost never used, and supported by few OSes, Linux supports
+ this feature.
+
+ However, it introduces a weakness in the protocol which makes it
+ very easy for an attacker to prevent a client from connecting to
+ a known server. The attacker only has to guess the source port
+ to shut down the client connection during its establishment. The
+ impact is limited, but it may be used to prevent an antivirus
+ or IPS from fetching updates and not detecting an attack, or to
+ prevent an SSL gateway or browser from fetching a CRL.
+ Default: TRUE
+
tcp_slow_start_after_idle - BOOLEAN
If set, provide RFC2861 behavior and time out the congestion
window after an idle period. An idle period is defined at
diff --git a/include/net/tcp.h b/include/net/tcp.h
index aed42c7..ecd55d0 100644
--- a/include/net/tcp.h
+++ b/include/net/tcp.h
@@ -292,6 +292,7 @@ extern int sysctl_tcp_thin_dupack;
extern int sysctl_tcp_early_retrans;
extern int sysctl_tcp_limit_output_bytes;
extern int sysctl_tcp_challenge_ack_limit;
+extern int sysctl_tcp_simult_connect;
extern atomic_long_t tcp_memory_allocated;
extern struct percpu_counter tcp_sockets_allocated;
diff --git a/net/ipv4/sysctl_net_ipv4.c b/net/ipv4/sysctl_net_ipv4.c
index d84400b..01e475f 100644
--- a/net/ipv4/sysctl_net_ipv4.c
+++ b/net/ipv4/sysctl_net_ipv4.c
@@ -774,6 +774,15 @@ static struct ctl_table ipv4_table[] = {
.extra2 = &two,
},
{
+ .procname = "tcp_simult_connect",
+ .data = &sysctl_tcp_simult_connect,
+ .maxlen = sizeof(int),
+ .mode = 0644,
+ .proc_handler = proc_dointvec_minmax,
+ .extra1 = &zero,
+ .extra2 = &two,
+ },
+ {
.procname = "udp_mem",
.data = &sysctl_udp_mem,
.maxlen = sizeof(sysctl_udp_mem),
diff --git a/net/ipv4/tcp_input.c b/net/ipv4/tcp_input.c
index 18f97ca..c71f8bb 100644
--- a/net/ipv4/tcp_input.c
+++ b/net/ipv4/tcp_input.c
@@ -102,6 +102,7 @@ int sysctl_tcp_thin_dupack __read_mostly;
int sysctl_tcp_moderate_rcvbuf __read_mostly = 1;
int sysctl_tcp_abc __read_mostly;
int sysctl_tcp_early_retrans __read_mostly = 2;
+int sysctl_tcp_simult_connect __read_mostly = 1;
#define FLAG_DATA 0x01 /* Incoming frame contained data. */
#define FLAG_WIN_UPDATE 0x02 /* Incoming ACK was a window update. */
@@ -5846,7 +5847,7 @@ discard:
tcp_paws_reject(&tp->rx_opt, 0))
goto discard_and_undo;
- if (th->syn) {
+ if (th->syn && sysctl_tcp_simult_connect) {
/* We see SYN without ACK. It is attempt of
* simultaneous connect with crossed SYNs.
* Particularly, it can be connect to self.
--
1.7.9.5
--
Kees Cook
Chrome OS Security
^ permalink raw reply related
* Re: [GIT PULL nf] IPVS fixes #2
From: Pablo Neira Ayuso @ 2013-02-07 18:12 UTC (permalink / raw)
To: Simon Horman
Cc: lvs-devel, netdev, netfilter-devel, Wensong Zhang,
Julian Anastasov, Daniel Borkmann
In-Reply-To: <1360113878-31051-1-git-send-email-horms@verge.net.au>
On Wed, Feb 06, 2013 at 10:24:37AM +0900, Simon Horman wrote:
> Hi Pablo,
>
> Another fix. This one seems suitable for stable all the way back to
> 2.6.34. I suspect this change may not apply cleanly all the way back there.
> Please let me know if I should prepare some backports.
>
> ----------------------------------------------------------------
> The following changes since commit b425df4cdd953a400d814b4474c9d3ec04481858:
>
> ipvs: freeing uninitialized pointer on error (2013-01-28 10:14:37 +0900)
>
> are available in the git repository at:
>
> git://git.kernel.org/pub/scm/linux/kernel/git/horms/ipvs.git tags/ipvs-fixes2-for-v3.8
Pulled, thanks Simon.
^ permalink raw reply
* Re: [PATCH 0/2] fix kernel crash with macvtap on top of LRO
From: David Miller @ 2013-02-07 18:14 UTC (permalink / raw)
To: bhutchings
Cc: mst, e1000-devel, netdev, jitendra.kalsaria, bruce.w.allan,
jesse.brandeburg, eilong, john.r.fastabend, john.ronciak,
sony.chacko, linux-driver, linux-kernel, jacob.e.keller
In-Reply-To: <1360254046.3605.8.camel@bwh-desktop.uk.solarflarecom.com>
From: Ben Hutchings <bhutchings@solarflare.com>
Date: Thu, 7 Feb 2013 16:20:46 +0000
> If the consensus is still that we must preserve packets exactly (aside
> from the usual modifications by IP routers) then LRO should be disabled
> on all devices for which forwarding is enabled.
I believe this is still undoubtedly the consensus.
------------------------------------------------------------------------------
Free Next-Gen Firewall Hardware Offer
Buy your Sophos next-gen firewall before the end March 2013
and get the hardware for free! Learn more.
http://p.sf.net/sfu/sophos-d2d-feb
_______________________________________________
E1000-devel mailing list
E1000-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/e1000-devel
To learn more about Intel® Ethernet, visit http://communities.intel.com/community/wired
^ permalink raw reply
* Re: [PATCH] tcp: sysctl to disable TCP simultaneous connect
From: David Miller @ 2013-02-07 18:15 UTC (permalink / raw)
To: keescook
Cc: linux-kernel, rob, kuznet, jmorris, yoshfuji, kaber, edumazet,
nhorman, ycheng, davidshan, linux-doc, netdev, w
In-Reply-To: <20130207175240.GA12520@www.outflux.net>
Sorry I'm not applying this.
^ permalink raw reply
* Re: [PATCH iproute-3.8 0/6] ip netns bug fixes and enhancements
From: Vijay Subramanian @ 2013-02-07 18:17 UTC (permalink / raw)
To: Eric W. Biederman
Cc: Stephen Hemminger, netdev, Serge E. Hallyn, Ben Hutchings
In-Reply-To: <87obfw5wmj.fsf@xmission.com>
>
> On my system those defines are coming out of sys/mount.h and date back
> to 2.6.5 or so. You should have them available on your system.
>
> What weird system are you on that doesn't export those?
The broken machine is not weird at all, just running a standard
version of Ubuntu (a little older though).
Ubuntu 10.04.1 LTS (lucid).
On this machine, I have the following version of libc6. Version:
2.11.1-0ubuntu7.10
The defines are not present in sys/mount.h but are in linux/fs.h. When
I include linux/fs.h, ipnetns.c compiles fine (but causes other
problems).
As Stephen said, it is probably the version of glibc that is causing this.
I verified this by trying to compile iproute2 on a newer version of
Ubuntu (Ubuntu 12.04.1 LTS, precise) which has glibc version
2.15-0ubuntu10.3. Everything compiles fine here. The defines are
present in both linux/fs.h and x86_64-linux-gnu/sys/mount.h
I found the libc6 version by running 'aptitude show libc6'. Let me
know if you need any other info.
>
> I don't have a clue on where to start at a practical level. It wouldn't
> be hard to provide some #ifndef compat glue but I can't imagine why that
> would be needed.
>
> Eric
I didn't realize it was a libc versioning error. Sorry if this was noise.
Thanks,
Vijay
^ permalink raw reply
* Re: [PATCH 01/10] netfilter: make /proc/net/netfilter pernet
From: Pablo Neira Ayuso @ 2013-02-07 18:33 UTC (permalink / raw)
To: Gao feng; +Cc: netfilter-devel, containers, ebiederm, netdev, lve
In-Reply-To: <1360223390-15589-1-git-send-email-gaofeng@cn.fujitsu.com>
Hi Gao,
Thanks again for improving netns support for netfilter. Comments
below:
On Thu, Feb 07, 2013 at 03:49:41PM +0800, Gao feng wrote:
> Now,only init net has directroy /proc/net/netfilter,
> this patch make this proc dentry pernet.
>
> Signed-off-by: Gao feng <gaofeng@cn.fujitsu.com>
> ---
> include/net/netns/x_tables.h | 3 +++
> net/netfilter/core.c | 40 ++++++++++++++++++++++++++++++++++------
> 2 files changed, 37 insertions(+), 6 deletions(-)
>
> diff --git a/include/net/netns/x_tables.h b/include/net/netns/x_tables.h
> index c24060e..aa6a545 100644
> --- a/include/net/netns/x_tables.h
> +++ b/include/net/netns/x_tables.h
> @@ -9,6 +9,9 @@ struct ebt_table;
> struct netns_xt {
> struct list_head tables[NFPROTO_NUMPROTO];
> bool notrack_deprecated_warning;
> +#if defined CONFIG_PROC_FS
> + struct proc_dir_entry *proc_netfilter;
> +#endif
This doesn't belong here to x_tables, it should be place in
include/net/net_namespace.h.
> #if defined(CONFIG_BRIDGE_NF_EBTABLES) || \
> defined(CONFIG_BRIDGE_NF_EBTABLES_MODULE)
> struct ebt_table *broute_table;
> diff --git a/net/netfilter/core.c b/net/netfilter/core.c
> index a9c488b..2038673 100644
> --- a/net/netfilter/core.c
> +++ b/net/netfilter/core.c
> @@ -281,6 +281,35 @@ struct proc_dir_entry *proc_net_netfilter;
> EXPORT_SYMBOL(proc_net_netfilter);
> #endif
>
> +static int __net_init netfilter_net_init(struct net *net)
> +{
> +#ifdef CONFIG_PROC_FS
> + net->xt.proc_netfilter = proc_net_mkdir(net,
> + "netfilter",
> + net->proc_net);
> + if (net_eq(net, &init_net)) {
> + if (!net->xt.proc_netfilter)
> + panic("cannot create netfilter proc entry");
> + else
> + proc_net_netfilter = net->xt.proc_netfilter;
> + } else if (!net->xt.proc_netfilter) {
> + pr_err("cannot create netfilter proc entry");
> + return -EINVAL;
> + }
> +#endif
> + return 0;
> +}
> +
> +static void __net_exit netfilter_net_exit(struct net *net)
> +{
> + remove_proc_entry("netfilter", net->proc_net);
> +}
> +
> +static struct pernet_operations netfilter_net_ops = {
> + .init = netfilter_net_init,
> + .exit = netfilter_net_exit,
> +};
> +
> void __init netfilter_init(void)
> {
> int i, h;
> @@ -289,12 +318,11 @@ void __init netfilter_init(void)
> INIT_LIST_HEAD(&nf_hooks[i][h]);
> }
>
> -#ifdef CONFIG_PROC_FS
> - proc_net_netfilter = proc_mkdir("netfilter", init_net.proc_net);
> - if (!proc_net_netfilter)
> - panic("cannot create netfilter proc entry");
> -#endif
> + if (register_pernet_subsys(&netfilter_net_ops) < 0)
> + return;
>
> - if (netfilter_log_init() < 0)
> + if (netfilter_log_init() < 0) {
> + unregister_pernet_subsys(&netfilter_net_ops);
> panic("cannot initialize nf_log");
> + }
> }
> --
> 1.7.11.7
>
^ permalink raw reply
* Re: [PATCH] netpoll: cleanup sparse warnings
From: Neil Horman @ 2013-02-07 18:37 UTC (permalink / raw)
To: Eric Dumazet; +Cc: netdev, fengguang.wu, David Miller
In-Reply-To: <1360252376.28557.52.camel@edumazet-glaptop>
On Thu, Feb 07, 2013 at 07:52:56AM -0800, Eric Dumazet wrote:
> On Thu, 2013-02-07 at 09:56 -0500, Neil Horman wrote:
> > With my recent commit I introduced two sparse warnings. Looking closer there
> > were a few more in the same file, so I fixed them all up. Basic rcu pointer
> > dereferencing suff
>
> > - npinfo = np->dev->npinfo;
> > + /* rtnl_dereference would be preferable here but
> > + * rcu_cleanup_netpoll path can put us in here safely without
> > + * holding the rtnl, so plain rcu_dereference it is
> > + */
> > + npinfo = rcu_dereference(np->dev->npinfo);
> > if (!npinfo)
> > return;
> >
>
> Are you sure it wont trigger a LOCKDEP complain (CONFIG_PROVE_RCU=y) ?
>
Hm, looking at it, you're probably right. We're not holding the rcu_read_lock,
and I'd forgotten that rcu_dereference implicitly checks that rcu_read_lock is
held. I guess, since the only paths that we get here on are in a bh rcu
quiescence point or with the rtnl held we should probably make this:
rcu_dereference_protected(np->dev->npinfo, rtnl_locked() || in_interrupt());
Although, thinking about this further somewhat begs the question as to how we
prevent one context from calling __netpoll_cleanup in a path holding rtnl, while
in parallel calling __netpoll_cleanup from the rcu callback. That might not be
a huge deal as __netpoll_cleanup uses spinlocks to do list modification, and an
atomic_dec_and_test to gate the free, but it still seems ugly.
What do you think?
>
>
^ permalink raw reply
* Re: [PATCH 02/10] netfilter: nf_log: prepar net namespace support for nf_log
From: Pablo Neira Ayuso @ 2013-02-07 18:39 UTC (permalink / raw)
To: Gao feng
Cc: netdev-u79uwXL29TY76Z2rM5mHXA,
containers-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA,
netfilter-devel-u79uwXL29TY76Z2rM5mHXA,
ebiederm-aS9lmoZGLiVWk0Htik3J/w, lve-ke3WRBg/xIg
In-Reply-To: <1360223390-15589-2-git-send-email-gaofeng-BthXqXjhjHXQFUHtdCDX3A@public.gmane.org>
On Thu, Feb 07, 2013 at 03:49:42PM +0800, Gao feng wrote:
> This patch adds netns support for nf_log,contains
> three major changes.
>
> 1,nf_log_register is split to two functions:
> nf_log_register and nf_log_set.
> The new nf_log_register is used only for register nf_logger,
> nf_log_set is used for setting pernet nf_loggers.
>
> Because the moudules that use the nf_log_register should be
> changed to use these new functions, and in order not to
> change the behavior. only allow to set the nf_loggers of
> init net.
>
> 2,Add net as a parameter of nf_log_bind_pf,only allow init net
> to bind the nflogger to the proto family.
>
> 3,Some l4proto such as tcp,udp... use nf_log_packet to log
> the invalid packets, we need pass proper netns to the
> nf_log_packet. Since other netns except init net has
> no nflogger binding to the proto, we only allow nf_log_packet
> handle the log request which comes from init net.
>
> Signed-off-by: Gao feng <gaofeng-BthXqXjhjHXQFUHtdCDX3A@public.gmane.org>
> ---
> include/net/netfilter/nf_log.h | 14 +-
> include/net/netns/conntrack.h | 3 +
> net/bridge/netfilter/ebt_log.c | 5 +-
> net/bridge/netfilter/ebt_nflog.c | 5 +-
> net/ipv4/netfilter/ip_tables.c | 5 +-
> net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c | 6 +-
> net/ipv4/netfilter/nf_conntrack_proto_icmp.c | 10 +-
> net/ipv6/netfilter/ip6_tables.c | 5 +-
> net/ipv6/netfilter/nf_conntrack_l3proto_ipv6.c | 5 +-
> net/ipv6/netfilter/nf_conntrack_proto_icmpv6.c | 9 +-
> net/netfilter/nf_conntrack_proto_dccp.c | 9 +-
> net/netfilter/nf_conntrack_proto_tcp.c | 18 +-
> net/netfilter/nf_conntrack_proto_udp.c | 6 +-
> net/netfilter/nf_conntrack_proto_udplite.c | 8 +-
> net/netfilter/nf_log.c | 241 ++++++++++++++++++-------
> net/netfilter/nfnetlink_log.c | 5 +-
> net/netfilter/xt_osf.c | 8 +-
> 17 files changed, 249 insertions(+), 113 deletions(-)
>
> diff --git a/include/net/netfilter/nf_log.h b/include/net/netfilter/nf_log.h
> index e991bd0..518eb01 100644
> --- a/include/net/netfilter/nf_log.h
> +++ b/include/net/netfilter/nf_log.h
> @@ -49,12 +49,18 @@ struct nf_logger {
> int nf_log_register(u_int8_t pf, struct nf_logger *logger);
> void nf_log_unregister(struct nf_logger *logger);
>
> -int nf_log_bind_pf(u_int8_t pf, const struct nf_logger *logger);
> -void nf_log_unbind_pf(u_int8_t pf);
> +void nf_log_set(struct net *net, u_int8_t pf,
> + struct nf_logger *logger);
> +void nf_log_unset(struct net *net, struct nf_logger *logger);
> +
> +int nf_log_bind_pf(struct net *net, u_int8_t pf,
> + const struct nf_logger *logger);
> +void nf_log_unbind_pf(struct net *net, u_int8_t pf);
>
> /* Calls the registered backend logging function */
> -__printf(7, 8)
> -void nf_log_packet(u_int8_t pf,
> +__printf(8, 9)
> +void nf_log_packet(struct net *net,
> + u_int8_t pf,
> unsigned int hooknum,
> const struct sk_buff *skb,
> const struct net_device *in,
> diff --git a/include/net/netns/conntrack.h b/include/net/netns/conntrack.h
> index c9c0c53..6358d5f 100644
> --- a/include/net/netns/conntrack.h
> +++ b/include/net/netns/conntrack.h
> @@ -8,6 +8,7 @@
>
> struct ctl_table_header;
> struct nf_conntrack_ecache;
> +struct nf_logger;
>
> struct nf_proto_net {
> #ifdef CONFIG_SYSCTL
> @@ -73,6 +74,7 @@ struct netns_ct {
> struct hlist_nulls_head dying;
> struct hlist_nulls_head tmpl;
> struct ip_conntrack_stat __percpu *stat;
> + const struct nf_logger __rcu *nf_loggers[NFPROTO_NUMPROTO];
This doesn't belong to conntrack. Probably a new file
include/net/netns/netfilter.h file for core netfilter features would
be a good idea.
> struct nf_ct_event_notifier __rcu *nf_conntrack_event_cb;
> struct nf_exp_event_notifier __rcu *nf_expect_event_cb;
> int sysctl_events;
> @@ -98,6 +100,7 @@ struct netns_ct {
> struct ctl_table_header *tstamp_sysctl_header;
> struct ctl_table_header *event_sysctl_header;
> struct ctl_table_header *helper_sysctl_header;
> + struct ctl_table_header *nf_log_dir_header;
> #endif
> char *slabname;
> };
> diff --git a/net/bridge/netfilter/ebt_log.c b/net/bridge/netfilter/ebt_log.c
> index 92de5e5..1d397ac 100644
> --- a/net/bridge/netfilter/ebt_log.c
> +++ b/net/bridge/netfilter/ebt_log.c
> @@ -176,14 +176,15 @@ ebt_log_tg(struct sk_buff *skb, const struct xt_action_param *par)
> {
> const struct ebt_log_info *info = par->targinfo;
> struct nf_loginfo li;
> + struct net *net = dev_net(par->in ? par->in : par->out);
>
> li.type = NF_LOG_TYPE_LOG;
> li.u.log.level = info->loglevel;
> li.u.log.logflags = info->bitmask;
>
> if (info->bitmask & EBT_LOG_NFLOG)
> - nf_log_packet(NFPROTO_BRIDGE, par->hooknum, skb, par->in,
> - par->out, &li, "%s", info->prefix);
> + nf_log_packet(net, NFPROTO_BRIDGE, par->hooknum, skb,
> + par->in, par->out, &li, "%s", info->prefix);
> else
> ebt_log_packet(NFPROTO_BRIDGE, par->hooknum, skb, par->in,
> par->out, &li, info->prefix);
> diff --git a/net/bridge/netfilter/ebt_nflog.c b/net/bridge/netfilter/ebt_nflog.c
> index 5be68bb..101b6e4 100644
> --- a/net/bridge/netfilter/ebt_nflog.c
> +++ b/net/bridge/netfilter/ebt_nflog.c
> @@ -24,14 +24,15 @@ ebt_nflog_tg(struct sk_buff *skb, const struct xt_action_param *par)
> {
> const struct ebt_nflog_info *info = par->targinfo;
> struct nf_loginfo li;
> + struct net *net = dev_net(par->in ? par->in : par->out);
>
> li.type = NF_LOG_TYPE_ULOG;
> li.u.ulog.copy_len = info->len;
> li.u.ulog.group = info->group;
> li.u.ulog.qthreshold = info->threshold;
>
> - nf_log_packet(PF_BRIDGE, par->hooknum, skb, par->in, par->out,
> - &li, "%s", info->prefix);
> + nf_log_packet(net, PF_BRIDGE, par->hooknum, skb,
> + par->in, par->out, &li, "%s", info->prefix);
> return EBT_CONTINUE;
> }
>
> diff --git a/net/ipv4/netfilter/ip_tables.c b/net/ipv4/netfilter/ip_tables.c
> index 17c5e06..3b5e0e2 100644
> --- a/net/ipv4/netfilter/ip_tables.c
> +++ b/net/ipv4/netfilter/ip_tables.c
> @@ -259,6 +259,7 @@ static void trace_packet(const struct sk_buff *skb,
> const char *hookname, *chainname, *comment;
> const struct ipt_entry *iter;
> unsigned int rulenum = 0;
> + struct net *net = dev_net(in ? in : out);
>
> table_base = private->entries[smp_processor_id()];
> root = get_entry(table_base, private->hook_entry[hook]);
> @@ -271,8 +272,8 @@ static void trace_packet(const struct sk_buff *skb,
> &chainname, &comment, &rulenum) != 0)
> break;
>
> - nf_log_packet(AF_INET, hook, skb, in, out, &trace_loginfo,
> - "TRACE: %s:%s:%s:%u ",
> + nf_log_packet(net, AF_INET, hook, skb, in, out,
> + &trace_loginfo, "TRACE: %s:%s:%s:%u ",
> tablename, chainname, comment, rulenum);
> }
> #endif
> diff --git a/net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c b/net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c
> index 48990ad..640215c 100644
> --- a/net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c
> +++ b/net/ipv4/netfilter/nf_conntrack_l3proto_ipv4.c
> @@ -101,6 +101,7 @@ static unsigned int ipv4_helper(unsigned int hooknum,
> const struct nf_conn_help *help;
> const struct nf_conntrack_helper *helper;
> unsigned int ret;
> + struct net *net = dev_net(in ? in : out);
>
> /* This is where we call the helper: as the packet goes out. */
> ct = nf_ct_get(skb, &ctinfo);
> @@ -119,8 +120,9 @@ static unsigned int ipv4_helper(unsigned int hooknum,
> ret = helper->help(skb, skb_network_offset(skb) + ip_hdrlen(skb),
> ct, ctinfo);
> if (ret != NF_ACCEPT && (ret & NF_VERDICT_MASK) != NF_QUEUE) {
> - nf_log_packet(NFPROTO_IPV4, hooknum, skb, in, out, NULL,
> - "nf_ct_%s: dropping packet", helper->name);
> + nf_log_packet(net, NFPROTO_IPV4, hooknum, skb, in,
> + out, NULL, "nf_ct_%s: dropping packet",
> + helper->name);
> }
> return ret;
> }
> diff --git a/net/ipv4/netfilter/nf_conntrack_proto_icmp.c b/net/ipv4/netfilter/nf_conntrack_proto_icmp.c
> index 5241d99..4275a63 100644
> --- a/net/ipv4/netfilter/nf_conntrack_proto_icmp.c
> +++ b/net/ipv4/netfilter/nf_conntrack_proto_icmp.c
> @@ -187,8 +187,8 @@ icmp_error(struct net *net, struct nf_conn *tmpl,
> icmph = skb_header_pointer(skb, ip_hdrlen(skb), sizeof(_ih), &_ih);
> if (icmph == NULL) {
> if (LOG_INVALID(net, IPPROTO_ICMP))
> - nf_log_packet(PF_INET, 0, skb, NULL, NULL, NULL,
> - "nf_ct_icmp: short packet ");
> + nf_log_packet(net, PF_INET, 0, skb, NULL, NULL,
> + NULL, "nf_ct_icmp: short packet ");
> return -NF_ACCEPT;
> }
>
> @@ -196,8 +196,8 @@ icmp_error(struct net *net, struct nf_conn *tmpl,
> if (net->ct.sysctl_checksum && hooknum == NF_INET_PRE_ROUTING &&
> nf_ip_checksum(skb, hooknum, dataoff, 0)) {
> if (LOG_INVALID(net, IPPROTO_ICMP))
> - nf_log_packet(PF_INET, 0, skb, NULL, NULL, NULL,
> - "nf_ct_icmp: bad HW ICMP checksum ");
> + nf_log_packet(net, PF_INET, 0, skb, NULL, NULL,
> + NULL, "nf_ct_icmp: bad HW ICMP checksum ");
> return -NF_ACCEPT;
> }
>
> @@ -209,7 +209,7 @@ icmp_error(struct net *net, struct nf_conn *tmpl,
> */
> if (icmph->type > NR_ICMP_TYPES) {
> if (LOG_INVALID(net, IPPROTO_ICMP))
> - nf_log_packet(PF_INET, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, PF_INET, 0, skb, NULL, NULL, NULL,
> "nf_ct_icmp: invalid ICMP type ");
> return -NF_ACCEPT;
> }
> diff --git a/net/ipv6/netfilter/ip6_tables.c b/net/ipv6/netfilter/ip6_tables.c
> index 125a90d..71b3631 100644
> --- a/net/ipv6/netfilter/ip6_tables.c
> +++ b/net/ipv6/netfilter/ip6_tables.c
> @@ -283,6 +283,7 @@ static void trace_packet(const struct sk_buff *skb,
> const struct ip6t_entry *root;
> const char *hookname, *chainname, *comment;
> const struct ip6t_entry *iter;
> + struct net *net = dev_net(in ? in : out);
> unsigned int rulenum = 0;
>
> table_base = private->entries[smp_processor_id()];
> @@ -296,8 +297,8 @@ static void trace_packet(const struct sk_buff *skb,
> &chainname, &comment, &rulenum) != 0)
> break;
>
> - nf_log_packet(AF_INET6, hook, skb, in, out, &trace_loginfo,
> - "TRACE: %s:%s:%s:%u ",
> + nf_log_packet(net, AF_INET6, hook, skb, in, out,
> + &trace_loginfo, "TRACE: %s:%s:%s:%u ",
> tablename, chainname, comment, rulenum);
> }
> #endif
> diff --git a/net/ipv6/netfilter/nf_conntrack_l3proto_ipv6.c b/net/ipv6/netfilter/nf_conntrack_l3proto_ipv6.c
> index 8a45bb2..375a75b 100644
> --- a/net/ipv6/netfilter/nf_conntrack_l3proto_ipv6.c
> +++ b/net/ipv6/netfilter/nf_conntrack_l3proto_ipv6.c
> @@ -104,6 +104,7 @@ static unsigned int ipv6_helper(unsigned int hooknum,
> const struct nf_conn_help *help;
> const struct nf_conntrack_helper *helper;
> enum ip_conntrack_info ctinfo;
> + struct net *net = dev_net(in ? in : out);
> unsigned int ret;
> __be16 frag_off;
> int protoff;
> @@ -132,8 +133,8 @@ static unsigned int ipv6_helper(unsigned int hooknum,
>
> ret = helper->help(skb, protoff, ct, ctinfo);
> if (ret != NF_ACCEPT && (ret & NF_VERDICT_MASK) != NF_QUEUE) {
> - nf_log_packet(NFPROTO_IPV6, hooknum, skb, in, out, NULL,
> - "nf_ct_%s: dropping packet", helper->name);
> + nf_log_packet(net, NFPROTO_IPV6, hooknum, skb, in, out,
> + NULL, "nf_ct_%s: dropping packet", helper->name);
> }
> return ret;
> }
> diff --git a/net/ipv6/netfilter/nf_conntrack_proto_icmpv6.c b/net/ipv6/netfilter/nf_conntrack_proto_icmpv6.c
> index 24df3dd..4b6c9e0 100644
> --- a/net/ipv6/netfilter/nf_conntrack_proto_icmpv6.c
> +++ b/net/ipv6/netfilter/nf_conntrack_proto_icmpv6.c
> @@ -131,7 +131,8 @@ static bool icmpv6_new(struct nf_conn *ct, const struct sk_buff *skb,
> type + 128);
> nf_ct_dump_tuple_ipv6(&ct->tuplehash[0].tuple);
> if (LOG_INVALID(nf_ct_net(ct), IPPROTO_ICMPV6))
> - nf_log_packet(PF_INET6, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(nf_ct_net(ct), PF_INET6, 0, skb, NULL,
> + NULL, NULL,
> "nf_ct_icmpv6: invalid new with type %d ",
> type + 128);
> return false;
> @@ -203,15 +204,15 @@ icmpv6_error(struct net *net, struct nf_conn *tmpl,
> icmp6h = skb_header_pointer(skb, dataoff, sizeof(_ih), &_ih);
> if (icmp6h == NULL) {
> if (LOG_INVALID(net, IPPROTO_ICMPV6))
> - nf_log_packet(PF_INET6, 0, skb, NULL, NULL, NULL,
> - "nf_ct_icmpv6: short packet ");
> + nf_log_packet(net, PF_INET6, 0, skb, NULL, NULL, NULL,
> + "nf_ct_icmpv6: short packet ");
> return -NF_ACCEPT;
> }
>
> if (net->ct.sysctl_checksum && hooknum == NF_INET_PRE_ROUTING &&
> nf_ip6_checksum(skb, hooknum, dataoff, IPPROTO_ICMPV6)) {
> if (LOG_INVALID(net, IPPROTO_ICMPV6))
> - nf_log_packet(PF_INET6, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, PF_INET6, 0, skb, NULL, NULL, NULL,
> "nf_ct_icmpv6: ICMPv6 checksum failed ");
> return -NF_ACCEPT;
> }
> diff --git a/net/netfilter/nf_conntrack_proto_dccp.c b/net/netfilter/nf_conntrack_proto_dccp.c
> index 432f957..ef7201a 100644
> --- a/net/netfilter/nf_conntrack_proto_dccp.c
> +++ b/net/netfilter/nf_conntrack_proto_dccp.c
> @@ -456,7 +456,8 @@ static bool dccp_new(struct nf_conn *ct, const struct sk_buff *skb,
>
> out_invalid:
> if (LOG_INVALID(net, IPPROTO_DCCP))
> - nf_log_packet(nf_ct_l3num(ct), 0, skb, NULL, NULL, NULL, msg);
> + nf_log_packet(net, nf_ct_l3num(ct), 0, skb, NULL,
> + NULL, NULL, msg);
> return false;
> }
>
> @@ -542,13 +543,13 @@ static int dccp_packet(struct nf_conn *ct, const struct sk_buff *skb,
>
> spin_unlock_bh(&ct->lock);
> if (LOG_INVALID(net, IPPROTO_DCCP))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL,
> "nf_ct_dccp: invalid packet ignored ");
> return NF_ACCEPT;
> case CT_DCCP_INVALID:
> spin_unlock_bh(&ct->lock);
> if (LOG_INVALID(net, IPPROTO_DCCP))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL,
> "nf_ct_dccp: invalid state transition ");
> return -NF_ACCEPT;
> }
> @@ -613,7 +614,7 @@ static int dccp_error(struct net *net, struct nf_conn *tmpl,
>
> out_invalid:
> if (LOG_INVALID(net, IPPROTO_DCCP))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL, msg);
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL, msg);
> return -NF_ACCEPT;
> }
>
> diff --git a/net/netfilter/nf_conntrack_proto_tcp.c b/net/netfilter/nf_conntrack_proto_tcp.c
> index 83876e9..f021a20 100644
> --- a/net/netfilter/nf_conntrack_proto_tcp.c
> +++ b/net/netfilter/nf_conntrack_proto_tcp.c
> @@ -720,7 +720,7 @@ static bool tcp_in_window(const struct nf_conn *ct,
> tn->tcp_be_liberal)
> res = true;
> if (!res && LOG_INVALID(net, IPPROTO_TCP))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL,
> "nf_ct_tcp: %s ",
> before(seq, sender->td_maxend + 1) ?
> after(end, sender->td_end - receiver->td_maxwin - 1) ?
> @@ -772,7 +772,7 @@ static int tcp_error(struct net *net, struct nf_conn *tmpl,
> th = skb_header_pointer(skb, dataoff, sizeof(_tcph), &_tcph);
> if (th == NULL) {
> if (LOG_INVALID(net, IPPROTO_TCP))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL,
> "nf_ct_tcp: short packet ");
> return -NF_ACCEPT;
> }
> @@ -780,7 +780,7 @@ static int tcp_error(struct net *net, struct nf_conn *tmpl,
> /* Not whole TCP header or malformed packet */
> if (th->doff*4 < sizeof(struct tcphdr) || tcplen < th->doff*4) {
> if (LOG_INVALID(net, IPPROTO_TCP))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL,
> "nf_ct_tcp: truncated/malformed packet ");
> return -NF_ACCEPT;
> }
> @@ -793,7 +793,7 @@ static int tcp_error(struct net *net, struct nf_conn *tmpl,
> if (net->ct.sysctl_checksum && hooknum == NF_INET_PRE_ROUTING &&
> nf_checksum(skb, hooknum, dataoff, IPPROTO_TCP, pf)) {
> if (LOG_INVALID(net, IPPROTO_TCP))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL,
> "nf_ct_tcp: bad TCP checksum ");
> return -NF_ACCEPT;
> }
> @@ -802,7 +802,7 @@ static int tcp_error(struct net *net, struct nf_conn *tmpl,
> tcpflags = (tcp_flag_byte(th) & ~(TCPHDR_ECE|TCPHDR_CWR|TCPHDR_PSH));
> if (!tcp_valid_flags[tcpflags]) {
> if (LOG_INVALID(net, IPPROTO_TCP))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL,
> "nf_ct_tcp: invalid TCP flag combination ");
> return -NF_ACCEPT;
> }
> @@ -949,7 +949,7 @@ static int tcp_packet(struct nf_conn *ct,
> }
> spin_unlock_bh(&ct->lock);
> if (LOG_INVALID(net, IPPROTO_TCP))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL,
> "nf_ct_tcp: invalid packet ignored in "
> "state %s ", tcp_conntrack_names[old_state]);
> return NF_ACCEPT;
> @@ -959,7 +959,7 @@ static int tcp_packet(struct nf_conn *ct,
> dir, get_conntrack_index(th), old_state);
> spin_unlock_bh(&ct->lock);
> if (LOG_INVALID(net, IPPROTO_TCP))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL,
> "nf_ct_tcp: invalid state ");
> return -NF_ACCEPT;
> case TCP_CONNTRACK_CLOSE:
> @@ -969,8 +969,8 @@ static int tcp_packet(struct nf_conn *ct,
> /* Invalid RST */
> spin_unlock_bh(&ct->lock);
> if (LOG_INVALID(net, IPPROTO_TCP))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> - "nf_ct_tcp: invalid RST ");
> + nf_log_packet(net, pf, 0, skb, NULL, NULL,
> + NULL, "nf_ct_tcp: invalid RST ");
> return -NF_ACCEPT;
> }
> if (index == TCP_RST_SET
> diff --git a/net/netfilter/nf_conntrack_proto_udp.c b/net/netfilter/nf_conntrack_proto_udp.c
> index 59623cc..fee4322 100644
> --- a/net/netfilter/nf_conntrack_proto_udp.c
> +++ b/net/netfilter/nf_conntrack_proto_udp.c
> @@ -119,7 +119,7 @@ static int udp_error(struct net *net, struct nf_conn *tmpl, struct sk_buff *skb,
> hdr = skb_header_pointer(skb, dataoff, sizeof(_hdr), &_hdr);
> if (hdr == NULL) {
> if (LOG_INVALID(net, IPPROTO_UDP))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL,
> "nf_ct_udp: short packet ");
> return -NF_ACCEPT;
> }
> @@ -127,7 +127,7 @@ static int udp_error(struct net *net, struct nf_conn *tmpl, struct sk_buff *skb,
> /* Truncated/malformed packets */
> if (ntohs(hdr->len) > udplen || ntohs(hdr->len) < sizeof(*hdr)) {
> if (LOG_INVALID(net, IPPROTO_UDP))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL,
> "nf_ct_udp: truncated/malformed packet ");
> return -NF_ACCEPT;
> }
> @@ -143,7 +143,7 @@ static int udp_error(struct net *net, struct nf_conn *tmpl, struct sk_buff *skb,
> if (net->ct.sysctl_checksum && hooknum == NF_INET_PRE_ROUTING &&
> nf_checksum(skb, hooknum, dataoff, IPPROTO_UDP, pf)) {
> if (LOG_INVALID(net, IPPROTO_UDP))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL,
> "nf_ct_udp: bad UDP checksum ");
> return -NF_ACCEPT;
> }
> diff --git a/net/netfilter/nf_conntrack_proto_udplite.c b/net/netfilter/nf_conntrack_proto_udplite.c
> index 1574895..c29d359 100644
> --- a/net/netfilter/nf_conntrack_proto_udplite.c
> +++ b/net/netfilter/nf_conntrack_proto_udplite.c
> @@ -131,7 +131,7 @@ static int udplite_error(struct net *net, struct nf_conn *tmpl,
> hdr = skb_header_pointer(skb, dataoff, sizeof(_hdr), &_hdr);
> if (hdr == NULL) {
> if (LOG_INVALID(net, IPPROTO_UDPLITE))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL,
> "nf_ct_udplite: short packet ");
> return -NF_ACCEPT;
> }
> @@ -141,7 +141,7 @@ static int udplite_error(struct net *net, struct nf_conn *tmpl,
> cscov = udplen;
> else if (cscov < sizeof(*hdr) || cscov > udplen) {
> if (LOG_INVALID(net, IPPROTO_UDPLITE))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL,
> "nf_ct_udplite: invalid checksum coverage ");
> return -NF_ACCEPT;
> }
> @@ -149,7 +149,7 @@ static int udplite_error(struct net *net, struct nf_conn *tmpl,
> /* UDPLITE mandates checksums */
> if (!hdr->check) {
> if (LOG_INVALID(net, IPPROTO_UDPLITE))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL,
> "nf_ct_udplite: checksum missing ");
> return -NF_ACCEPT;
> }
> @@ -159,7 +159,7 @@ static int udplite_error(struct net *net, struct nf_conn *tmpl,
> nf_checksum_partial(skb, hooknum, dataoff, cscov, IPPROTO_UDP,
> pf)) {
> if (LOG_INVALID(net, IPPROTO_UDPLITE))
> - nf_log_packet(pf, 0, skb, NULL, NULL, NULL,
> + nf_log_packet(net, pf, 0, skb, NULL, NULL, NULL,
> "nf_ct_udplite: bad UDPLite checksum ");
> return -NF_ACCEPT;
> }
> diff --git a/net/netfilter/nf_log.c b/net/netfilter/nf_log.c
> index 9e31269..b1e5126 100644
> --- a/net/netfilter/nf_log.c
> +++ b/net/netfilter/nf_log.c
> @@ -16,7 +16,6 @@
> #define NF_LOG_PREFIXLEN 128
> #define NFLOGGER_NAME_LEN 64
>
> -static const struct nf_logger __rcu *nf_loggers[NFPROTO_NUMPROTO] __read_mostly;
> static struct list_head nf_loggers_l[NFPROTO_NUMPROTO] __read_mostly;
> static DEFINE_MUTEX(nf_log_mutex);
>
> @@ -32,13 +31,50 @@ static struct nf_logger *__find_logger(int pf, const char *str_logger)
> return NULL;
> }
>
> +void nf_log_set(struct net *net, u_int8_t pf, struct nf_logger *logger)
> +{
> + if (!net_eq(net, &init_net))
> + return;
> +
> + if (pf != NFPROTO_UNSPEC) {
> + const struct nf_logger *llog;
> + mutex_lock(&nf_log_mutex);
> + llog = rcu_dereference_protected(net->ct.nf_loggers[pf],
> + lockdep_is_held(&nf_log_mutex));
> + if (llog == NULL)
> + rcu_assign_pointer(net->ct.nf_loggers[pf], logger);
> +
> + mutex_unlock(&nf_log_mutex);
> + }
> +}
> +EXPORT_SYMBOL(nf_log_set);
> +
> +void nf_log_unset(struct net *net, struct nf_logger *logger)
> +{
> + int i;
> + const struct nf_logger *c_logger;
> +
> + if (!net_eq(net, &init_net))
> + return;
> +
> + mutex_lock(&nf_log_mutex);
> + for (i = 0; i < NFPROTO_NUMPROTO; i++) {
> + c_logger = rcu_dereference_protected(net->ct.nf_loggers[i],
> + lockdep_is_held(&nf_log_mutex));
> + if (c_logger == logger)
> + RCU_INIT_POINTER(net->ct.nf_loggers[i], NULL);
> + }
> + mutex_unlock(&nf_log_mutex);
> + synchronize_rcu();
> +}
> +EXPORT_SYMBOL(nf_log_unset);
> +
> /* return EEXIST if the same logger is registered, 0 on success. */
> int nf_log_register(u_int8_t pf, struct nf_logger *logger)
> {
> - const struct nf_logger *llog;
> int i;
>
> - if (pf >= ARRAY_SIZE(nf_loggers))
> + if (pf >= ARRAY_SIZE(init_net.ct.nf_loggers))
> return -EINVAL;
>
> for (i = 0; i < ARRAY_SIZE(logger->list); i++)
> @@ -46,69 +82,69 @@ int nf_log_register(u_int8_t pf, struct nf_logger *logger)
>
> mutex_lock(&nf_log_mutex);
>
> - if (pf == NFPROTO_UNSPEC) {
> + if (pf == NFPROTO_UNSPEC)
> for (i = NFPROTO_UNSPEC; i < NFPROTO_NUMPROTO; i++)
> list_add_tail(&(logger->list[i]), &(nf_loggers_l[i]));
> - } else {
> + else
> /* register at end of list to honor first register win */
> list_add_tail(&logger->list[pf], &nf_loggers_l[pf]);
> - llog = rcu_dereference_protected(nf_loggers[pf],
> - lockdep_is_held(&nf_log_mutex));
> - if (llog == NULL)
> - rcu_assign_pointer(nf_loggers[pf], logger);
> - }
>
> mutex_unlock(&nf_log_mutex);
>
> + nf_log_set(&init_net, pf, logger);
> return 0;
> }
> EXPORT_SYMBOL(nf_log_register);
>
> void nf_log_unregister(struct nf_logger *logger)
> {
> - const struct nf_logger *c_logger;
> int i;
>
> mutex_lock(&nf_log_mutex);
> - for (i = 0; i < ARRAY_SIZE(nf_loggers); i++) {
> - c_logger = rcu_dereference_protected(nf_loggers[i],
> - lockdep_is_held(&nf_log_mutex));
> - if (c_logger == logger)
> - RCU_INIT_POINTER(nf_loggers[i], NULL);
> + for (i = 0; i < NFPROTO_NUMPROTO; i++)
> list_del(&logger->list[i]);
> - }
> - mutex_unlock(&nf_log_mutex);
>
> - synchronize_rcu();
> + mutex_unlock(&nf_log_mutex);
> + nf_log_unset(&init_net, logger);
> }
> EXPORT_SYMBOL(nf_log_unregister);
>
> -int nf_log_bind_pf(u_int8_t pf, const struct nf_logger *logger)
> +int nf_log_bind_pf(struct net *net, u_int8_t pf,
> + const struct nf_logger *logger)
> {
> - if (pf >= ARRAY_SIZE(nf_loggers))
> + if (!net_eq(net, &init_net))
> + return 0;
> +
> + if (pf >= ARRAY_SIZE(net->ct.nf_loggers))
> return -EINVAL;
> +
> mutex_lock(&nf_log_mutex);
> if (__find_logger(pf, logger->name) == NULL) {
> mutex_unlock(&nf_log_mutex);
> return -ENOENT;
> }
> - rcu_assign_pointer(nf_loggers[pf], logger);
> + rcu_assign_pointer(net->ct.nf_loggers[pf], logger);
> mutex_unlock(&nf_log_mutex);
> return 0;
> }
> EXPORT_SYMBOL(nf_log_bind_pf);
>
> -void nf_log_unbind_pf(u_int8_t pf)
> +void nf_log_unbind_pf(struct net *net, u_int8_t pf)
> {
> - if (pf >= ARRAY_SIZE(nf_loggers))
> + if (!net_eq(net, &init_net))
> + return;
> +
> + if (pf >= ARRAY_SIZE(net->ct.nf_loggers))
> return;
> +
> mutex_lock(&nf_log_mutex);
> - RCU_INIT_POINTER(nf_loggers[pf], NULL);
> + RCU_INIT_POINTER(net->ct.nf_loggers[pf], NULL);
> mutex_unlock(&nf_log_mutex);
> }
> EXPORT_SYMBOL(nf_log_unbind_pf);
>
> -void nf_log_packet(u_int8_t pf,
> +void nf_log_packet(struct net *net,
> + u_int8_t pf,
> unsigned int hooknum,
> const struct sk_buff *skb,
> const struct net_device *in,
> @@ -120,8 +156,11 @@ void nf_log_packet(u_int8_t pf,
> char prefix[NF_LOG_PREFIXLEN];
> const struct nf_logger *logger;
>
> + if (!net_eq(net, &init_net))
> + return;
> +
> rcu_read_lock();
> - logger = rcu_dereference(nf_loggers[pf]);
> + logger = rcu_dereference(net->ct.nf_loggers[pf]);
> if (logger) {
> va_start(args, fmt);
> vsnprintf(prefix, sizeof(prefix), fmt, args);
> @@ -133,11 +172,13 @@ void nf_log_packet(u_int8_t pf,
> EXPORT_SYMBOL(nf_log_packet);
>
> #ifdef CONFIG_PROC_FS
> -static void *seq_start(struct seq_file *seq, loff_t *pos)
> +static void *seq_start(struct seq_file *s, loff_t *pos)
> {
> + struct net *net = seq_file_net(s);
> +
> mutex_lock(&nf_log_mutex);
>
> - if (*pos >= ARRAY_SIZE(nf_loggers))
> + if (*pos >= ARRAY_SIZE(net->ct.nf_loggers))
> return NULL;
>
> return pos;
> @@ -145,9 +186,10 @@ static void *seq_start(struct seq_file *seq, loff_t *pos)
>
> static void *seq_next(struct seq_file *s, void *v, loff_t *pos)
> {
> - (*pos)++;
> + struct net *net = seq_file_net(s);
>
> - if (*pos >= ARRAY_SIZE(nf_loggers))
> + (*pos)++;
> + if (*pos >= ARRAY_SIZE(net->ct.nf_loggers))
> return NULL;
>
> return pos;
> @@ -163,9 +205,10 @@ static int seq_show(struct seq_file *s, void *v)
> loff_t *pos = v;
> const struct nf_logger *logger;
> struct nf_logger *t;
> + struct net *net = seq_file_net(s);
> int ret;
>
> - logger = rcu_dereference_protected(nf_loggers[*pos],
> + logger = rcu_dereference_protected(net->ct.nf_loggers[*pos],
> lockdep_is_held(&nf_log_mutex));
>
> if (!logger)
> @@ -199,7 +242,8 @@ static const struct seq_operations nflog_seq_ops = {
>
> static int nflog_open(struct inode *inode, struct file *file)
> {
> - return seq_open(file, &nflog_seq_ops);
> + return seq_open_net(inode, file, &nflog_seq_ops,
> + sizeof(struct seq_net_private));
> }
>
> static const struct file_operations nflog_file_ops = {
> @@ -207,7 +251,7 @@ static const struct file_operations nflog_file_ops = {
> .open = nflog_open,
> .read = seq_read,
> .llseek = seq_lseek,
> - .release = seq_release,
> + .release = seq_release_net,
> };
>
>
> @@ -216,7 +260,6 @@ static const struct file_operations nflog_file_ops = {
> #ifdef CONFIG_SYSCTL
> static char nf_log_sysctl_fnames[NFPROTO_NUMPROTO-NFPROTO_UNSPEC][3];
> static struct ctl_table nf_log_sysctl_table[NFPROTO_NUMPROTO+1];
> -static struct ctl_table_header *nf_log_dir_header;
>
> static int nf_log_proc_dostring(ctl_table *table, int write,
> void __user *buffer, size_t *lenp, loff_t *ppos)
> @@ -226,15 +269,19 @@ static int nf_log_proc_dostring(ctl_table *table, int write,
> size_t size = *lenp;
> int r = 0;
> int tindex = (unsigned long)table->extra1;
> + struct net *net = current->nsproxy->net_ns;
>
> if (write) {
> + if (!net_eq(net, &init_net))
> + return -EPERM;
> +
> if (size > sizeof(buf))
> size = sizeof(buf);
> if (copy_from_user(buf, buffer, size))
> return -EFAULT;
>
> if (!strcmp(buf, "NONE")) {
> - nf_log_unbind_pf(tindex);
> + nf_log_unbind_pf(net, tindex);
> return 0;
> }
> mutex_lock(&nf_log_mutex);
> @@ -243,11 +290,11 @@ static int nf_log_proc_dostring(ctl_table *table, int write,
> mutex_unlock(&nf_log_mutex);
> return -ENOENT;
> }
> - rcu_assign_pointer(nf_loggers[tindex], logger);
> + rcu_assign_pointer(net->ct.nf_loggers[tindex], logger);
> mutex_unlock(&nf_log_mutex);
> } else {
> mutex_lock(&nf_log_mutex);
> - logger = rcu_dereference_protected(nf_loggers[tindex],
> + logger = rcu_dereference_protected(net->ct.nf_loggers[tindex],
> lockdep_is_held(&nf_log_mutex));
> if (!logger)
> table->data = "NONE";
> @@ -260,49 +307,117 @@ static int nf_log_proc_dostring(ctl_table *table, int write,
> return r;
> }
>
> -static __init int netfilter_log_sysctl_init(void)
> +static int netfilter_log_sysctl_init(struct net *net)
> {
> - int i;
> + unsigned int i;
> + struct ctl_table *table;
>
> - for (i = NFPROTO_UNSPEC; i < NFPROTO_NUMPROTO; i++) {
> - snprintf(nf_log_sysctl_fnames[i-NFPROTO_UNSPEC], 3, "%d", i);
> - nf_log_sysctl_table[i].procname =
> - nf_log_sysctl_fnames[i-NFPROTO_UNSPEC];
> - nf_log_sysctl_table[i].data = NULL;
> - nf_log_sysctl_table[i].maxlen =
> - NFLOGGER_NAME_LEN * sizeof(char);
> - nf_log_sysctl_table[i].mode = 0644;
> - nf_log_sysctl_table[i].proc_handler = nf_log_proc_dostring;
> - nf_log_sysctl_table[i].extra1 = (void *)(unsigned long) i;
> + table = nf_log_sysctl_table;
> + if (!net_eq(net, &init_net)) {
> + table = kmemdup(nf_log_sysctl_table,
> + sizeof(nf_log_sysctl_table),
> + GFP_KERNEL);
> + if (!table)
> + goto err_alloc;
> +
> + for (i = NFPROTO_UNSPEC; i < NFPROTO_NUMPROTO; i++)
> + table[i].data = NULL;
> + } else {
> + for (i = NFPROTO_UNSPEC; i < NFPROTO_NUMPROTO; i++) {
> + snprintf(nf_log_sysctl_fnames[i-NFPROTO_UNSPEC],
> + 3, "%d", i);
> + nf_log_sysctl_table[i].procname =
> + nf_log_sysctl_fnames[i-NFPROTO_UNSPEC];
> + nf_log_sysctl_table[i].data = NULL;
> + nf_log_sysctl_table[i].maxlen =
> + NFLOGGER_NAME_LEN * sizeof(char);
> + nf_log_sysctl_table[i].mode = 0644;
> + nf_log_sysctl_table[i].proc_handler =
> + nf_log_proc_dostring;
> + nf_log_sysctl_table[i].extra1 =
> + (void *)(unsigned long) i;
> + }
> }
>
> - nf_log_dir_header = register_net_sysctl(&init_net, "net/netfilter/nf_log",
> - nf_log_sysctl_table);
> - if (!nf_log_dir_header)
> - return -ENOMEM;
> + net->ct.nf_log_dir_header = register_net_sysctl(net,
> + "net/netfilter/nf_log",
> + table);
> + if (!net->ct.nf_log_dir_header)
> + goto err_reg;
>
> return 0;
> +
> +err_reg:
> + if (!net_eq(net, &init_net))
> + kfree(net);
> +err_alloc:
> + return -ENOMEM;
> +}
> +
> +static void netfilter_log_sysctl_exit(struct net *net)
> +{
> + struct ctl_table *table;
> +
> + table = net->ct.nf_log_dir_header->ctl_table_arg;
> + unregister_net_sysctl_table(net->ct.nf_log_dir_header);
> + if (!net_eq(net, &init_net))
> + kfree(table);
> }
> #else
> -static __init int netfilter_log_sysctl_init(void)
> +static int netfilter_log_sysctl_init(struct net *net)
> {
> return 0;
> }
> +
> +static void netfilter_log_sysctl_exit(struct net *net)
> +{
> +}
> #endif /* CONFIG_SYSCTL */
>
> -int __init netfilter_log_init(void)
> +static int __net_init nf_log_net_init(struct net *net)
> {
> - int i, r;
> + int ret = -ENOMEM;
> #ifdef CONFIG_PROC_FS
> if (!proc_create("nf_log", S_IRUGO,
> - proc_net_netfilter, &nflog_file_ops))
> - return -1;
> + net->xt.proc_netfilter, &nflog_file_ops))
> + goto out_proc;
> #endif
> + ret = netfilter_log_sysctl_init(net);
> + if (ret < 0)
> + goto out_sysctl;
> +
> + return 0;
> +out_sysctl:
> +#ifdef CONFIG_PROC_FS
> + /*
> + * For init net, Errors will trigger panic,
> + * unroll on error is unnecessary.
> + */
> + if (!net_eq(net, &init_net))
> + remove_proc_entry("nf_log", net->xt.proc_netfilter);
> +out_proc:
> +#endif
> + return ret;
> +}
> +
> +static void __net_exit nf_log_net_exit(struct net *net)
> +{
> + netfilter_log_sysctl_exit(net);
> + remove_proc_entry("nf_log", net->xt.proc_netfilter);
> +}
>
> - /* Errors will trigger panic, unroll on error is unnecessary. */
> - r = netfilter_log_sysctl_init();
> - if (r < 0)
> - return r;
> +static struct pernet_operations nf_log_net_ops = {
> + .init = nf_log_net_init,
> + .exit = nf_log_net_exit,
> +};
> +
> +int __init netfilter_log_init(void)
> +{
> + int i, ret;
> +
> + ret = register_pernet_subsys(&nf_log_net_ops);
> + if (ret < 0)
> + return ret;
>
> for (i = NFPROTO_UNSPEC; i < NFPROTO_NUMPROTO; i++)
> INIT_LIST_HEAD(&(nf_loggers_l[i]));
> diff --git a/net/netfilter/nfnetlink_log.c b/net/netfilter/nfnetlink_log.c
> index 92fd8ec..8f35467 100644
> --- a/net/netfilter/nfnetlink_log.c
> +++ b/net/netfilter/nfnetlink_log.c
> @@ -768,6 +768,7 @@ nfulnl_recv_config(struct sock *ctnl, struct sk_buff *skb,
> u_int16_t group_num = ntohs(nfmsg->res_id);
> struct nfulnl_instance *inst;
> struct nfulnl_msg_config_cmd *cmd = NULL;
> + struct net *net = sock_net(ctnl);
> int ret = 0;
>
> if (nfula[NFULA_CFG_CMD]) {
> @@ -777,9 +778,9 @@ nfulnl_recv_config(struct sock *ctnl, struct sk_buff *skb,
> /* Commands without queue context */
> switch (cmd->command) {
> case NFULNL_CFG_CMD_PF_BIND:
> - return nf_log_bind_pf(pf, &nfulnl_logger);
> + return nf_log_bind_pf(net, pf, &nfulnl_logger);
> case NFULNL_CFG_CMD_PF_UNBIND:
> - nf_log_unbind_pf(pf);
> + nf_log_unbind_pf(net, pf);
> return 0;
> }
> }
> diff --git a/net/netfilter/xt_osf.c b/net/netfilter/xt_osf.c
> index a5e673d..b6c61cd 100644
> --- a/net/netfilter/xt_osf.c
> +++ b/net/netfilter/xt_osf.c
> @@ -201,6 +201,7 @@ xt_osf_match_packet(const struct sk_buff *skb, struct xt_action_param *p)
> unsigned char opts[MAX_IPOPTLEN];
> const struct xt_osf_finger *kf;
> const struct xt_osf_user_finger *f;
> + struct net *net = dev_net(p->in ? p->in : p->out);
>
> if (!info)
> return false;
> @@ -325,8 +326,8 @@ xt_osf_match_packet(const struct sk_buff *skb, struct xt_action_param *p)
> fcount++;
>
> if (info->flags & XT_OSF_LOG)
> - nf_log_packet(p->family, p->hooknum, skb,
> - p->in, p->out, NULL,
> + nf_log_packet(net, p->family, p->hooknum,
> + skb, p->in, p->out, NULL,
> "%s [%s:%s] : %pI4:%d -> %pI4:%d hops=%d\n",
> f->genre, f->version, f->subtype,
> &ip->saddr, ntohs(tcp->source),
> @@ -341,7 +342,8 @@ xt_osf_match_packet(const struct sk_buff *skb, struct xt_action_param *p)
> rcu_read_unlock();
>
> if (!fcount && (info->flags & XT_OSF_LOG))
> - nf_log_packet(p->family, p->hooknum, skb, p->in, p->out, NULL,
> + nf_log_packet(net, p->family, p->hooknum, skb, p->in,
> + p->out, NULL,
> "Remote OS is not known: %pI4:%u -> %pI4:%u\n",
> &ip->saddr, ntohs(tcp->source),
> &ip->daddr, ntohs(tcp->dest));
> --
> 1.7.11.7
>
^ permalink raw reply
* Re: [PATCH] tcp: sysctl to disable TCP simultaneous connect
From: Stephen Hemminger @ 2013-02-07 18:39 UTC (permalink / raw)
To: Kees Cook
Cc: linux-kernel, Rob Landley, David S. Miller, Alexey Kuznetsov,
James Morris, Hideaki YOSHIFUJI, Patrick McHardy, Eric Dumazet,
Neil Horman, Yuchung Cheng, Shan Wei, linux-doc, netdev,
Willy Tarreau
In-Reply-To: <20130207175240.GA12520@www.outflux.net>
On Thu, 7 Feb 2013 09:52:40 -0800
Kees Cook <keescook@chromium.org> wrote:
> This is based on Willy Tarreau's patch from 2008[1]. The goal is to
> close a corner-case of TCP that isn't used and poses a small DoS risk.
> For systems that do not want to take any risk at all, this is a desirable
> configuration knob.
>
> It is possible for two clients to connect with crossed SYNs without
> checking sequence numbers. As such, it might be possible to guess a source
> port number to block a system from making connections to well-known
> ports and IP addresses (e.g. auto-update checks) without requiring a
> MiTM position.
>
This patch probably also breaks TCP STUNT that is used by some applications for NAT
traversal.
^ permalink raw reply
* Re: IP_FREEBIND and binding to in-use addr:ports
From: Andy Grover @ 2013-02-07 18:42 UTC (permalink / raw)
To: target-devel; +Cc: netdev
In-Reply-To: <5112F998.8050605@redhat.com>
On 02/06/2013 04:47 PM, Andy Grover wrote:
> OK, this is weird:
>
> https://bugzilla.redhat.com/show_bug.cgi?id=908368
>
> It appears you can listen on the same address:port if you do it from a
> different iscsi target, or even a different tpg (so there are no
> configfs name collisions). I believe this is because we are setting
> IP_FREEBIND sockopt, so we can configure listening on iscsi portals (aka
> ip:port) before the IP is assigned.
>
> from ip(7):
> IP_FREEBIND (since Linux 2.4)
> If enabled, this boolean option allows binding to an IP address that is
> nonlocal or does not (yet) exist. This permits listening on a socket,
> without requiring the underlying network interface or the specified
> dynamic IP address to be up at the time that the application is trying
> to bind to it. This option is the per-socket equivalent of the
> ip_nonlocal_bind /proc interface described below.
>
> This doesn't say anything about if the address:port is already in use.
> Dave/netdev, should the network stack be returning an error when
> attempting to bind to an address:port already in use even if IP_FREEBIND
> is set, or should the caller be checking for this before trying to
> kernel_bind()?
>
> Or is something else the issue?
Looks like IP_FREEBIND doesn't make a difference. More shortly. -- Andy
^ permalink raw reply
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox