Netdev List
 help / color / mirror / Atom feed
* Re: [PATCH] net: fec: Add support for multiple phys on mdiobus
From: Wolfgang Grandegger @ 2013-01-21 11:07 UTC (permalink / raw)
  To: Sascha Hauer; +Cc: netdev, linux-arm-kernel, shawn.guo, davem
In-Reply-To: <20130121100701.GX1906@pengutronix.de>

On 01/21/2013 11:07 AM, Sascha Hauer wrote:
> On Mon, Jan 21, 2013 at 09:56:24AM +0100, Wolfgang Grandegger wrote:
>> On 01/21/2013 09:37 AM, Sascha Hauer wrote:
>>> There may be multiple phys on an mdio bus. This series adds support
>>> for this to the fec driver. I recently had a board which has a switch
>>> connected to the fec's mdio bus, so I had to pick the correct phy.
>>
>> Pick one PHY from a switch port? Well, does a PHY-less (or fixed-link)
>> configuration for a switch not make more sense?
> 
> Yes, you're probably right.
> 
>> Various ARM Ethernet
>> contoller drivers do not support it. I recently needed a hack for an
>> AT91 board.
> 
> I wonder how we want to proceed. Should there be a devicetree property
> 'fixed-link' like done for fs_enet (and not recommended for new code,
> stated in the comment above of_phy_connect_fixed_link)?

Also the gianfar and ucc_geth drivers use this interface (via fixed
link phy). I tried to use it for the AT91 macb driver but stopped
quickly because the usage was not straight forward (too much code)...
even if the idea of using a fake fixed-link phy is not bad.

> Currently I have a property 'phy' in the fec binding which has a phandle
> to a phy provided by the fec's mdio bus, but this could equally well

But than the cable must be connected to the associated switch port.

> point to a fixed dummy phy:
> 
> 	phy = &fixed-phy;

The link speed, full/half duplex and maybe some mroe parameter should
be configurable via device tree.

> Currently there seems to be no common convention for the devicetree how
> to handle such situations, or am I missing something?

That's also may impression. There seem to be a few more related hacks:

$ find . -name '*.c'| xargs grep -i "phy-less" 
./ethernet/amd/au1000_eth.c:			netdev_info(dev, "using PHY-less setup\n");
./ethernet/amd/au1000_eth.c:	} else { /* PHY-less op, assume full-duplex */
./ethernet/ibm/emac/core.c:	/* PHY-less configuration.
./ethernet/ibm/emac/core.c:		/* PHY-less configuration.

I would prefer to handle the "fixed-link" property of the ethernet dt
node directly in the driver with a generic helper function.

Wolfgang.

^ permalink raw reply

* Re: [PATCH] iwlegacy: don't return zero on failure paths in il4965_pci_probe()
From: Stanislaw Gruszka @ 2013-01-21 10:41 UTC (permalink / raw)
  To: Alexey Khoroshilov
  Cc: John W. Linville, linux-wireless, netdev, linux-kernel, ilw,
	ldv-project
In-Reply-To: <1358600194-20371-1-git-send-email-khoroshilov@ispras.ru>

On Sat, Jan 19, 2013 at 04:56:34PM +0400, Alexey Khoroshilov wrote:
> If hardware is not ready, il4965_pci_probe() breaks off initialization,
> deallocates all resources, but returns zero.
> The patch adds -EIO as return value in this case.
> 
> Found by Linux Driver Verification project (linuxtesting.org).
> 
> Signed-off-by: Alexey Khoroshilov <khoroshilov@ispras.ru>

ACK

^ permalink raw reply

* [Patch net-next] net: move rx and tx hash functions to net/core/flow_dissector.c
From: Cong Wang @ 2013-01-21 10:39 UTC (permalink / raw)
  To: netdev; +Cc: David S. Miller, Eric Dumazet, Ben Hutchings, Cong Wang

From: Cong Wang <xiyou.wangcong@gmail.com>

__skb_tx_hash() and __skb_get_rxhash() are all for calculating hash
value based by some fields in skb, mostly used for selecting queues
by device drivers.

Meanwhile, net/core/dev.c is bloating.

Cc: "David S. Miller" <davem@davemloft.net>
Cc: Eric Dumazet <edumazet@google.com>
Cc: Ben Hutchings <bhutchings@solarflare.com>
Signed-off-by: Cong Wang <xiyou.wangcong@gmail.com>

---
 net/core/dev.c            |  175 ---------------------------------------------
 net/core/flow_dissector.c |  173 ++++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 173 insertions(+), 175 deletions(-)

diff --git a/net/core/dev.c b/net/core/dev.c
index b6d2b32..c69cd87 100644
--- a/net/core/dev.c
+++ b/net/core/dev.c
@@ -134,7 +134,6 @@
 #include <linux/cpu_rmap.h>
 #include <linux/net_tstamp.h>
 #include <linux/static_key.h>
-#include <net/flow_keys.h>
 
 #include "net-sysfs.h"
 
@@ -2636,136 +2635,6 @@ out:
 	return rc;
 }
 
-static u32 hashrnd __read_mostly;
-
-/*
- * Returns a Tx hash based on the given packet descriptor a Tx queues' number
- * to be used as a distribution range.
- */
-u16 __skb_tx_hash(const struct net_device *dev, const struct sk_buff *skb,
-		  unsigned int num_tx_queues)
-{
-	u32 hash;
-	u16 qoffset = 0;
-	u16 qcount = num_tx_queues;
-
-	if (skb_rx_queue_recorded(skb)) {
-		hash = skb_get_rx_queue(skb);
-		while (unlikely(hash >= num_tx_queues))
-			hash -= num_tx_queues;
-		return hash;
-	}
-
-	if (dev->num_tc) {
-		u8 tc = netdev_get_prio_tc_map(dev, skb->priority);
-		qoffset = dev->tc_to_txq[tc].offset;
-		qcount = dev->tc_to_txq[tc].count;
-	}
-
-	if (skb->sk && skb->sk->sk_hash)
-		hash = skb->sk->sk_hash;
-	else
-		hash = (__force u16) skb->protocol;
-	hash = jhash_1word(hash, hashrnd);
-
-	return (u16) (((u64) hash * qcount) >> 32) + qoffset;
-}
-EXPORT_SYMBOL(__skb_tx_hash);
-
-static inline u16 dev_cap_txqueue(struct net_device *dev, u16 queue_index)
-{
-	if (unlikely(queue_index >= dev->real_num_tx_queues)) {
-		net_warn_ratelimited("%s selects TX queue %d, but real number of TX queues is %d\n",
-				     dev->name, queue_index,
-				     dev->real_num_tx_queues);
-		return 0;
-	}
-	return queue_index;
-}
-
-static inline int get_xps_queue(struct net_device *dev, struct sk_buff *skb)
-{
-#ifdef CONFIG_XPS
-	struct xps_dev_maps *dev_maps;
-	struct xps_map *map;
-	int queue_index = -1;
-
-	rcu_read_lock();
-	dev_maps = rcu_dereference(dev->xps_maps);
-	if (dev_maps) {
-		map = rcu_dereference(
-		    dev_maps->cpu_map[raw_smp_processor_id()]);
-		if (map) {
-			if (map->len == 1)
-				queue_index = map->queues[0];
-			else {
-				u32 hash;
-				if (skb->sk && skb->sk->sk_hash)
-					hash = skb->sk->sk_hash;
-				else
-					hash = (__force u16) skb->protocol ^
-					    skb->rxhash;
-				hash = jhash_1word(hash, hashrnd);
-				queue_index = map->queues[
-				    ((u64)hash * map->len) >> 32];
-			}
-			if (unlikely(queue_index >= dev->real_num_tx_queues))
-				queue_index = -1;
-		}
-	}
-	rcu_read_unlock();
-
-	return queue_index;
-#else
-	return -1;
-#endif
-}
-
-u16 __netdev_pick_tx(struct net_device *dev, struct sk_buff *skb)
-{
-	struct sock *sk = skb->sk;
-	int queue_index = sk_tx_queue_get(sk);
-
-	if (queue_index < 0 || skb->ooo_okay ||
-	    queue_index >= dev->real_num_tx_queues) {
-		int new_index = get_xps_queue(dev, skb);
-		if (new_index < 0)
-			new_index = skb_tx_hash(dev, skb);
-
-		if (queue_index != new_index && sk) {
-			struct dst_entry *dst =
-				    rcu_dereference_check(sk->sk_dst_cache, 1);
-
-			if (dst && skb_dst(skb) == dst)
-				sk_tx_queue_set(sk, queue_index);
-
-		}
-
-		queue_index = new_index;
-	}
-
-	return queue_index;
-}
-EXPORT_SYMBOL(__netdev_pick_tx);
-
-struct netdev_queue *netdev_pick_tx(struct net_device *dev,
-				    struct sk_buff *skb)
-{
-	int queue_index = 0;
-
-	if (dev->real_num_tx_queues != 1) {
-		const struct net_device_ops *ops = dev->netdev_ops;
-		if (ops->ndo_select_queue)
-			queue_index = ops->ndo_select_queue(dev, skb);
-		else
-			queue_index = __netdev_pick_tx(dev, skb);
-		queue_index = dev_cap_txqueue(dev, queue_index);
-	}
-
-	skb_set_queue_mapping(skb, queue_index);
-	return netdev_get_tx_queue(dev, queue_index);
-}
-
 static void qdisc_pkt_len_init(struct sk_buff *skb)
 {
 	const struct skb_shared_info *shinfo = skb_shinfo(skb);
@@ -3015,41 +2884,6 @@ static inline void ____napi_schedule(struct softnet_data *sd,
 	__raise_softirq_irqoff(NET_RX_SOFTIRQ);
 }
 
-/*
- * __skb_get_rxhash: calculate a flow hash based on src/dst addresses
- * and src/dst port numbers.  Sets rxhash in skb to non-zero hash value
- * on success, zero indicates no valid hash.  Also, sets l4_rxhash in skb
- * if hash is a canonical 4-tuple hash over transport ports.
- */
-void __skb_get_rxhash(struct sk_buff *skb)
-{
-	struct flow_keys keys;
-	u32 hash;
-
-	if (!skb_flow_dissect(skb, &keys))
-		return;
-
-	if (keys.ports)
-		skb->l4_rxhash = 1;
-
-	/* get a consistent hash (same value on both flow directions) */
-	if (((__force u32)keys.dst < (__force u32)keys.src) ||
-	    (((__force u32)keys.dst == (__force u32)keys.src) &&
-	     ((__force u16)keys.port16[1] < (__force u16)keys.port16[0]))) {
-		swap(keys.dst, keys.src);
-		swap(keys.port16[0], keys.port16[1]);
-	}
-
-	hash = jhash_3words((__force u32)keys.dst,
-			    (__force u32)keys.src,
-			    (__force u32)keys.ports, hashrnd);
-	if (!hash)
-		hash = 1;
-
-	skb->rxhash = hash;
-}
-EXPORT_SYMBOL(__skb_get_rxhash);
-
 #ifdef CONFIG_RPS
 
 /* One global table that all flow-based protocols share. */
@@ -7308,12 +7142,3 @@ out:
 }
 
 subsys_initcall(net_dev_init);
-
-static int __init initialize_hashrnd(void)
-{
-	get_random_bytes(&hashrnd, sizeof(hashrnd));
-	return 0;
-}
-
-late_initcall_sync(initialize_hashrnd);
-
diff --git a/net/core/flow_dissector.c b/net/core/flow_dissector.c
index 466820b..9d4c720 100644
--- a/net/core/flow_dissector.c
+++ b/net/core/flow_dissector.c
@@ -143,3 +143,176 @@ ipv6:
 	return true;
 }
 EXPORT_SYMBOL(skb_flow_dissect);
+
+static u32 hashrnd __read_mostly;
+
+/*
+ * __skb_get_rxhash: calculate a flow hash based on src/dst addresses
+ * and src/dst port numbers.  Sets rxhash in skb to non-zero hash value
+ * on success, zero indicates no valid hash.  Also, sets l4_rxhash in skb
+ * if hash is a canonical 4-tuple hash over transport ports.
+ */
+void __skb_get_rxhash(struct sk_buff *skb)
+{
+	struct flow_keys keys;
+	u32 hash;
+
+	if (!skb_flow_dissect(skb, &keys))
+		return;
+
+	if (keys.ports)
+		skb->l4_rxhash = 1;
+
+	/* get a consistent hash (same value on both flow directions) */
+	if (((__force u32)keys.dst < (__force u32)keys.src) ||
+	    (((__force u32)keys.dst == (__force u32)keys.src) &&
+	     ((__force u16)keys.port16[1] < (__force u16)keys.port16[0]))) {
+		swap(keys.dst, keys.src);
+		swap(keys.port16[0], keys.port16[1]);
+	}
+
+	hash = jhash_3words((__force u32)keys.dst,
+			    (__force u32)keys.src,
+			    (__force u32)keys.ports, hashrnd);
+	if (!hash)
+		hash = 1;
+
+	skb->rxhash = hash;
+}
+EXPORT_SYMBOL(__skb_get_rxhash);
+
+/*
+ * Returns a Tx hash based on the given packet descriptor a Tx queues' number
+ * to be used as a distribution range.
+ */
+u16 __skb_tx_hash(const struct net_device *dev, const struct sk_buff *skb,
+		  unsigned int num_tx_queues)
+{
+	u32 hash;
+	u16 qoffset = 0;
+	u16 qcount = num_tx_queues;
+
+	if (skb_rx_queue_recorded(skb)) {
+		hash = skb_get_rx_queue(skb);
+		while (unlikely(hash >= num_tx_queues))
+			hash -= num_tx_queues;
+		return hash;
+	}
+
+	if (dev->num_tc) {
+		u8 tc = netdev_get_prio_tc_map(dev, skb->priority);
+		qoffset = dev->tc_to_txq[tc].offset;
+		qcount = dev->tc_to_txq[tc].count;
+	}
+
+	if (skb->sk && skb->sk->sk_hash)
+		hash = skb->sk->sk_hash;
+	else
+		hash = (__force u16) skb->protocol;
+	hash = jhash_1word(hash, hashrnd);
+
+	return (u16) (((u64) hash * qcount) >> 32) + qoffset;
+}
+EXPORT_SYMBOL(__skb_tx_hash);
+
+static inline u16 dev_cap_txqueue(struct net_device *dev, u16 queue_index)
+{
+	if (unlikely(queue_index >= dev->real_num_tx_queues)) {
+		net_warn_ratelimited("%s selects TX queue %d, but real number of TX queues is %d\n",
+				     dev->name, queue_index,
+				     dev->real_num_tx_queues);
+		return 0;
+	}
+	return queue_index;
+}
+
+static inline int get_xps_queue(struct net_device *dev, struct sk_buff *skb)
+{
+#ifdef CONFIG_XPS
+	struct xps_dev_maps *dev_maps;
+	struct xps_map *map;
+	int queue_index = -1;
+
+	rcu_read_lock();
+	dev_maps = rcu_dereference(dev->xps_maps);
+	if (dev_maps) {
+		map = rcu_dereference(
+		    dev_maps->cpu_map[raw_smp_processor_id()]);
+		if (map) {
+			if (map->len == 1)
+				queue_index = map->queues[0];
+			else {
+				u32 hash;
+				if (skb->sk && skb->sk->sk_hash)
+					hash = skb->sk->sk_hash;
+				else
+					hash = (__force u16) skb->protocol ^
+					    skb->rxhash;
+				hash = jhash_1word(hash, hashrnd);
+				queue_index = map->queues[
+				    ((u64)hash * map->len) >> 32];
+			}
+			if (unlikely(queue_index >= dev->real_num_tx_queues))
+				queue_index = -1;
+		}
+	}
+	rcu_read_unlock();
+
+	return queue_index;
+#else
+	return -1;
+#endif
+}
+
+u16 __netdev_pick_tx(struct net_device *dev, struct sk_buff *skb)
+{
+	struct sock *sk = skb->sk;
+	int queue_index = sk_tx_queue_get(sk);
+
+	if (queue_index < 0 || skb->ooo_okay ||
+	    queue_index >= dev->real_num_tx_queues) {
+		int new_index = get_xps_queue(dev, skb);
+		if (new_index < 0)
+			new_index = skb_tx_hash(dev, skb);
+
+		if (queue_index != new_index && sk) {
+			struct dst_entry *dst =
+				    rcu_dereference_check(sk->sk_dst_cache, 1);
+
+			if (dst && skb_dst(skb) == dst)
+				sk_tx_queue_set(sk, queue_index);
+
+		}
+
+		queue_index = new_index;
+	}
+
+	return queue_index;
+}
+EXPORT_SYMBOL(__netdev_pick_tx);
+
+struct netdev_queue *netdev_pick_tx(struct net_device *dev,
+				    struct sk_buff *skb)
+{
+	int queue_index = 0;
+
+	if (dev->real_num_tx_queues != 1) {
+		const struct net_device_ops *ops = dev->netdev_ops;
+		if (ops->ndo_select_queue)
+			queue_index = ops->ndo_select_queue(dev, skb);
+		else
+			queue_index = __netdev_pick_tx(dev, skb);
+		queue_index = dev_cap_txqueue(dev, queue_index);
+	}
+
+	skb_set_queue_mapping(skb, queue_index);
+	return netdev_get_tx_queue(dev, queue_index);
+}
+
+static int __init initialize_hashrnd(void)
+{
+	get_random_bytes(&hashrnd, sizeof(hashrnd));
+	return 0;
+}
+
+late_initcall_sync(initialize_hashrnd);

^ permalink raw reply related

* Re: IPsec AH use of ahash
From: Tom St Denis @ 2013-01-21 10:20 UTC (permalink / raw)
  To: David Dillow; +Cc: Borislav Petkov, linux-kernel, netdev, Steven Rostedt
In-Reply-To: <1358759881.2595.15.camel@obelisk.thedillows.org>



----- Original Message -----
> From: "David Dillow" <dave@thedillows.org>
> To: "Tom St Denis" <tstdenis@elliptictech.com>
> Cc: "Borislav Petkov" <bp@alien8.de>, linux-kernel@vger.kernel.org, netdev@vger.kernel.org, "Steven Rostedt"
> <rostedt@goodmis.org>
> Sent: Monday, 21 January, 2013 4:18:01 AM
> Subject: Re: IPsec AH use of ahash
> 
> On Sun, 2013-01-20 at 19:40 -0500, Tom St Denis wrote:
> > The problem is for me to add the ()'s is a no brainer.
> 
> It was more than just the ()'s. You completely botched the
> indentation
> in the parts of code you didn't copy from xcbc.c, among other issues.

Leaving coding indentation aside [I assume you mean the use of braces because my tab stops should match given the patchset for the other files was minimal] that's not really a good use of time here.
 
> > For me to re-write complete statements for coding style reasons
> > means
> > I have to actually go out and test it again.
> 
> Well, for some of the code you submitted, that would be the first
> testing it got, even compile testing AFAICT. I don't doubt that you
> tested against your hardware, but it is obvious that you didn't run
> the
> algorithm tests you added, or even tried to compile them. You were
> missing a semicolon after your test data, and you were also missing a
> "\x" in there, so your test data was wrong.

The missing semi-colon is in fact missing and for that I apologize.  This btw is the first legitimate gripe with the code thus far.

Though I must say this code has "compiled" in 3.6, 3.6.7, 3.7, and 3.8 without error so it's not surprising it wasn't caught.  After having consulted the "documentation" I never really did figure out how to get testmgr to run so I took a bit of leap of faith there that everything was fine.  Not really an excuse but it is at least an observable hole in the build documentation.

I couldn't spot the missing \x but I don't doubt you.  That format for vector data is so backwards that it's easy to make that mistake.  After having worked on crypto code for 10+ years I've never seen anyone use that format and I've seen stupid formats before (NIST CAVP anyone?).

Again all valid critiques of the code and valid reasons to do a re-spin.  I apologize for the oversight there.  Having "used the source" I found the build symbol required to activate the test manager so I should be good to go now.

> I know this, because I just spent the five minutes required to fix up
> the checkpatch warnings to prove to myself that you could have done
> it
> faster than sending one considered message to the list about how much
> we
> suck. Of course, that assumes you are trying to have a discussion
> instead of trolling; it's much easier to spew bile than to think
> before
> you post.

This wasn't about how you all suck.  Quite the contrary it was about how good people are missing perspective.  You all started this by harping on the coding style "problems" but as a new developer to the kernel (well at least a new submitter...) I used the source as a guide so that I wouldn't deviate from what I perceived as the norm.  I was legitimately frustrated because performing a re-spin solely to work past coding style problems is not something a business case could be made for.  I'd like to contribute properly but at the same time you can't throw red flags on the play each time someone plays the game like you do.

At least the testmgr errors are something I can work on whenever without setting up a lab so likely that'll be something I can tackle today actually.

Tom

^ permalink raw reply

* Re: [PATCH] net: net_cls: fd passed in SCM_RIGHTS datagram not set correctly
From: Daniel Wagner @ 2013-01-21 10:16 UTC (permalink / raw)
  To: Li Zefan
  Cc: netdev, cgroups, Daniel Wagner, David S. Miller,
	Eric W. Biederman, Al Viro, John Fastabend, Neil Horman
In-Reply-To: <50FD1058.2000306@huawei.com>

On 21.01.2013 10:54, Li Zefan wrote:
> On 2013/1/21 17:38, Daniel Wagner wrote:
>> From: Daniel Wagner <daniel.wagner@bmw-carit.de>
>>
>> Commit 6a328d8c6f03501657ad580f6f98bf9a42583ff7 changed the update
>> logic for the socket but it does not update the SCM_RIGHTS update
>> as well. This patch is based on the net_prio fix commit
>>
>> 48a87cc26c13b68f6cce4e9d769fcb17a6b3e4b8
>>
>>      net: netprio: fd passed in SCM_RIGHTS datagram not set correctly
>>
>>      A socket fd passed in a SCM_RIGHTS datagram was not getting
>>      updated with the new tasks cgrp prioidx. This leaves IO on
>>      the socket tagged with the old tasks priority.
>>
>>      To fix this add a check in the scm recvmsg path to update the
>>      sock cgrp prioidx with the new tasks value.
>>
>> Let's apply the same fix for net_cls.
>>
>> Reported-by: Li Zefan <lizefan@huawei.com>
> 
> Acutally I didn't report this. 

You made me look into this, so you reported it at least in my eyes :)

> I was about to send exactly the same
> patch and then I noticed the shared socket issue. ;)

I don't mind if you want your patch to be applied. I just felt
responsible for the changes I did.

thanks,
daniel

^ permalink raw reply

* [PATCH 20/33] net: Convert to devm_ioremap_resource()
From: Thierry Reding @ 2013-01-21 10:09 UTC (permalink / raw)
  To: linux-kernel
  Cc: Greg Kroah-Hartman, Dmitry Torokhov, Arnd Bergmann, Wolfram Sang,
	David S. Miller, netdev
In-Reply-To: <1358762966-20791-1-git-send-email-thierry.reding@avionic-design.de>

Convert all uses of devm_request_and_ioremap() to the newly introduced
devm_ioremap_resource() which provides more consistent error handling.

devm_ioremap_resource() provides its own error messages so all explicit
error messages can be removed from the failure code paths.

Signed-off-by: Thierry Reding <thierry.reding@avionic-design.de>
Cc: David S. Miller <davem@davemloft.net>
Cc: netdev@vger.kernel.org
---
 drivers/net/can/grcan.c                               | 8 ++++----
 drivers/net/ethernet/stmicro/stmmac/stmmac_platform.c | 9 ++++-----
 2 files changed, 8 insertions(+), 9 deletions(-)

diff --git a/drivers/net/can/grcan.c b/drivers/net/can/grcan.c
index 17fbc7a..4c3a7dd 100644
--- a/drivers/net/can/grcan.c
+++ b/drivers/net/can/grcan.c
@@ -26,6 +26,7 @@
  * Contributors: Andreas Larsson <andreas@gaisler.com>
  */
 
+#include <linux/err.h>
 #include <linux/kernel.h>
 #include <linux/module.h>
 #include <linux/interrupt.h>
@@ -1683,10 +1684,9 @@ static int grcan_probe(struct platform_device *ofdev)
 	}
 
 	res = platform_get_resource(ofdev, IORESOURCE_MEM, 0);
-	base = devm_request_and_ioremap(&ofdev->dev, res);
-	if (!base) {
-		dev_err(&ofdev->dev, "couldn't map IO resource\n");
-		err = -EADDRNOTAVAIL;
+	base = devm_ioremap_resource(&ofdev->dev, res);
+	if (IS_ERR(base)) {
+		err = PTR_ERR(base);
 		goto exit_error;
 	}
 
diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_platform.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_platform.c
index b43d68b..a3431aa 100644
--- a/drivers/net/ethernet/stmicro/stmmac/stmmac_platform.c
+++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_platform.c
@@ -22,6 +22,7 @@
   Author: Giuseppe Cavallaro <peppe.cavallaro@st.com>
 *******************************************************************************/
 
+#include <linux/err.h>
 #include <linux/platform_device.h>
 #include <linux/io.h>
 #include <linux/of.h>
@@ -88,11 +89,9 @@ static int stmmac_pltfr_probe(struct platform_device *pdev)
 	if (!res)
 		return -ENODEV;
 
-	addr = devm_request_and_ioremap(dev, res);
-	if (!addr) {
-		pr_err("%s: ERROR: memory mapping failed", __func__);
-		return -ENOMEM;
-	}
+	addr = devm_ioremap_resource(dev, res);
+	if (IS_ERR(addr))
+		return PTR_ERR(addr);
 
 	if (pdev->dev.of_node) {
 		plat_dat = devm_kzalloc(&pdev->dev,
-- 
1.8.1.1

^ permalink raw reply related

* Re: [PATCH] net: fec: Add support for multiple phys on mdiobus
From: Sascha Hauer @ 2013-01-21 10:07 UTC (permalink / raw)
  To: Wolfgang Grandegger; +Cc: netdev, linux-arm-kernel, shawn.guo, davem
In-Reply-To: <50FD02B8.8080401@grandegger.com>

On Mon, Jan 21, 2013 at 09:56:24AM +0100, Wolfgang Grandegger wrote:
> On 01/21/2013 09:37 AM, Sascha Hauer wrote:
> > There may be multiple phys on an mdio bus. This series adds support
> > for this to the fec driver. I recently had a board which has a switch
> > connected to the fec's mdio bus, so I had to pick the correct phy.
> 
> Pick one PHY from a switch port? Well, does a PHY-less (or fixed-link)
> configuration for a switch not make more sense?

Yes, you're probably right.

> Various ARM Ethernet
> contoller drivers do not support it. I recently needed a hack for an
> AT91 board.

I wonder how we want to proceed. Should there be a devicetree property
'fixed-link' like done for fs_enet (and not recommended for new code,
stated in the comment above of_phy_connect_fixed_link)?

Currently I have a property 'phy' in the fec binding which has a phandle
to a phy provided by the fec's mdio bus, but this could equally well
point to a fixed dummy phy:

	phy = &fixed-phy;

Currently there seems to be no common convention for the devicetree how
to handle such situations, or am I missing something?

Sascha

-- 
Pengutronix e.K.                           |                             |
Industrial Linux Solutions                 | http://www.pengutronix.de/  |
Peiner Str. 6-8, 31137 Hildesheim, Germany | Phone: +49-5121-206917-0    |
Amtsgericht Hildesheim, HRA 2686           | Fax:   +49-5121-206917-5555 |

^ permalink raw reply

* Re: [BUG] Bug in netprio_cgroup and netcls_cgroup ?
From: Li Zefan @ 2013-01-21  9:57 UTC (permalink / raw)
  To: Daniel Wagner
  Cc: John Fastabend, Neil Horman, Daniel Wagner, LKML, netdev, Cgroups
In-Reply-To: <50FD09FD.4010804@monom.org>

On 2013/1/21 17:27, Daniel Wagner wrote:
> On 21.01.2013 10:01, Li Zefan wrote:
>> On 2013/1/21 16:50, Daniel Wagner wrote:
>>> Hi Li,
>>>
>>> On 21.01.2013 07:08, Li Zefan wrote:
>>>> I'm not a network developer, so correct me if I'm wrong.
>>>>
>>>> Since commit 7955490f732c2b8
>>>> ("net: netprio_cgroup: rework update socket logic"), sock->sk->sk_cgrp_prioidx
>>>> is set when the socket is created, and won't be updated unless the task is
>>>> moved to another cgroup.
>>>>
>>>> Now the problem is, a socket can be _shared_ by multiple processes (fork, SCM_RIGHT).
>>>> If we place those processes in different cgroups, and each cgroup has
>>>> different configs, but all of the processes will send data via this socket
>>>> with the same network priority.
>>>
>>> Wouldn't that be addressed by 48a87cc26c13b68f6cce4e9d769fcb17a6b3e4b8
>>>
>>>     net: netprio: fd passed in SCM_RIGHTS datagram not set correctly
>>>
>>>      A socket fd passed in a SCM_RIGHTS datagram was not getting
>>>      updated with the new tasks cgrp prioidx. This leaves IO on
>>>      the socket tagged with the old tasks priority.
>>>
>>>      To fix this add a check in the scm recvmsg path to update the
>>>      sock cgrp prioidx with the new tasks value.
>>>
>>> As I read this this should work for net_prio.
>>>
>>
>> But after process A passed the socket fd to B, both A and B can use the
>> same socket to send data, right? Then if A and B were placed in different
>> cgroups with differnt configs, A's config won't take effect anymore.
>>
>> Am I missing something?
> 
> I don't know. I guess at one point the socket resources are shared and then
> one configuration is taking preference. As you can see I am far away of
> being
> an expert in this field. Hopefully someone who understands this bits
> can chip in.
> 
> BTW, isn't this a similar to what should happen with the block io cgroup?
> What is the behavior with a fd writing to a file in the scenario you
> describe above?
> 

It forbids task moving in this case:

/*
 * We cannot support shared io contexts, as we have no mean to support
 * two tasks with the same ioc in two different groups without major rework
 * of the main cic data structures.  For now we allow a task to change
 * its cgroup only if it's the only owner of its ioc.
 */
static int blkcg_can_attach(struct cgroup *cgrp, struct cgroup_taskset *tset)

^ permalink raw reply

* RE: [PATCH for 3.8] iproute2: Add "ip netns pids" and "ip netns identify"
From: David Laight @ 2013-01-21  9:52 UTC (permalink / raw)
  To: Eric W. Biederman, Ben Hutchings
  Cc: Stephen Hemminger, netdev, Serge E. Hallyn
In-Reply-To: <87ehhiqqb3.fsf@xmission.com>

> >> >> >> +		if (!isdigit(ch))
> >> >> >
> >> >> > ch must be cast to unsigned char before passing to isdigit().
> >> >>
> >> >> isdigit is defined to take an int.  A legacy of the implicit casts in
> >> >> the K&R C days.  Casting to unsigned char would be pointless and silly.
> >> > [...]
> >> >
> >> > It's not pointless.  This is explained in the very first line of the
> >> > description in the manual page...
> >>
> >> If it's not pointless it is an implementation bug.
> >
> > You can either get in your time machine and go back to 1978 and fix it,
> > or add the cast like every C programmer who knows what the C standards
> > say about these functions.
> 
> So I took a moment to look. The C standard is indeed does not say
> anything about this and supporting signed char becomes a quality of
> implementation issue.  glibc supports being passed signed character
> values.

You must have looked in the wrong place.
The standards documentation on all the ctype functions is very clear
about the valid input domain.

> > Testing on one implementation doesn't prove anything.  'char' can be
> > signed or unsigned depending on the architecture, and some C libraries
> > work around buggy applications that .  That's no reason to write another
> > buggy application.
> 
> This code by it's very nature is not portable.  The code is not suid
> so insane level of paranoia don't need to be maintained.

What!!!! You still don't want core dumps due to invalid input.
Especially if the input might be from a file.
I did the full trawl of NetBSD's 'src' tree because of issues with
one of the shells faulting.

> The definition
> in the C standard is a least common denominator requirement.  Posix
> copies that least common denominator requirement.  Glibc does not
> implment the least common denominator.

Unless you writes 'standards compliant' programs, you will eventually
fall foul of these sort of problems.

Are you sure that glibc will always be used? What about newlib?

There may be strict requirements on isdigit() (I think you are
allowed to subtract '0' to get a number). The same is not true
of isprint(), isprint(EOF) is FALSE, isprint(255) may be TRUE
(ij ligature).

	David

^ permalink raw reply

* Re: [PATCH] net: net_cls: fd passed in SCM_RIGHTS datagram not set correctly
From: Li Zefan @ 2013-01-21  9:54 UTC (permalink / raw)
  To: Daniel Wagner
  Cc: netdev-u79uwXL29TY76Z2rM5mHXA, cgroups-u79uwXL29TY76Z2rM5mHXA,
	Daniel Wagner, David S. Miller, Eric W. Biederman, Al Viro,
	John Fastabend, Neil Horman
In-Reply-To: <1358761102-7765-1-git-send-email-wagi-kQCPcA+X3s7YtjvyW6yDsg@public.gmane.org>

On 2013/1/21 17:38, Daniel Wagner wrote:
> From: Daniel Wagner <daniel.wagner-98C5kh4wR6ohFhg+JK9F0w@public.gmane.org>
> 
> Commit 6a328d8c6f03501657ad580f6f98bf9a42583ff7 changed the update
> logic for the socket but it does not update the SCM_RIGHTS update
> as well. This patch is based on the net_prio fix commit
> 
> 48a87cc26c13b68f6cce4e9d769fcb17a6b3e4b8
> 
>     net: netprio: fd passed in SCM_RIGHTS datagram not set correctly
> 
>     A socket fd passed in a SCM_RIGHTS datagram was not getting
>     updated with the new tasks cgrp prioidx. This leaves IO on
>     the socket tagged with the old tasks priority.
> 
>     To fix this add a check in the scm recvmsg path to update the
>     sock cgrp prioidx with the new tasks value.
> 
> Let's apply the same fix for net_cls.
> 
> Reported-by: Li Zefan <lizefan-hv44wF8Li93QT0dZR+AlfA@public.gmane.org>

Acutally I didn't report this. I was about to send exactly the same
patch and then I noticed the shared socket issue. ;)

> Cc: "David S. Miller" <davem-fT/PcQaiUtIeIZ0/mPfg9Q@public.gmane.org>
> Cc: "Eric W. Biederman" <ebiederm-aS9lmoZGLiVWk0Htik3J/w@public.gmane.org>
> Cc: Al Viro <viro-RmSDqhL/yNMiFSDQTTA3OLVCufUGDwFn@public.gmane.org>
> Cc: John Fastabend <john.r.fastabend-ral2JQCrhuEAvxtiuMwx3w@public.gmane.org>
> Cc: Neil Horman <nhorman-2XuSBdqkA4R54TAoqtyWWQ@public.gmane.org>
> Cc: netdev-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
> Cc: cgroups-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
> ---
>  net/core/scm.c | 5 ++++-
>  1 file changed, 4 insertions(+), 1 deletion(-)

^ permalink raw reply

* Re: [BUG] Bug in netprio_cgroup and netcls_cgroup ?
From: Li Zefan @ 2013-01-21  9:52 UTC (permalink / raw)
  To: John Fastabend
  Cc: Daniel Wagner, John Fastabend, Neil Horman, Daniel Wagner, LKML,
	netdev-u79uwXL29TY76Z2rM5mHXA, Cgroups
In-Reply-To: <50FD0893.1050805-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org>

On 2013/1/21 17:21, John Fastabend wrote:
> On 01/21/2013 01:01 AM, Li Zefan wrote:
>> On 2013/1/21 16:50, Daniel Wagner wrote:
>>> Hi Li,
>>>
>>> On 21.01.2013 07:08, Li Zefan wrote:
>>>> I'm not a network developer, so correct me if I'm wrong.
>>>>
>>>> Since commit 7955490f732c2b8
>>>> ("net: netprio_cgroup: rework update socket logic"), sock->sk->sk_cgrp_prioidx
>>>> is set when the socket is created, and won't be updated unless the task is
>>>> moved to another cgroup.
>>>>
>>>> Now the problem is, a socket can be _shared_ by multiple processes (fork, SCM_RIGHT).
>>>> If we place those processes in different cgroups, and each cgroup has
>>>> different configs, but all of the processes will send data via this socket
>>>> with the same network priority.
>>>
>>> Wouldn't that be addressed by 48a87cc26c13b68f6cce4e9d769fcb17a6b3e4b8
>>>
>>>     net: netprio: fd passed in SCM_RIGHTS datagram not set correctly
>>>
>>>      A socket fd passed in a SCM_RIGHTS datagram was not getting
>>>      updated with the new tasks cgrp prioidx. This leaves IO on
>>>      the socket tagged with the old tasks priority.
>>>
>>>      To fix this add a check in the scm recvmsg path to update the
>>>      sock cgrp prioidx with the new tasks value.
>>>
>>> As I read this this should work for net_prio.
>>>
>>
>> But after process A passed the socket fd to B, both A and B can use the
>> same socket to send data, right? Then if A and B were placed in different
>> cgroups with differnt configs, A's config won't take effect anymore.
>>
>> Am I missing something?
>>
>>
> 
> Hi Zefan,
> 
> Neil and I discusses this here, http://patchwork.ozlabs.org/patch/172343/
> look towards the bottom of the thread. Quoted here.
> 

So this is a known issue. Why not document this behavior in
Documentation/cgroups/netprio.txt?

^ permalink raw reply

* [RFC] State resolution packet queue for IPsec
From: Steffen Klassert @ 2013-01-21  9:48 UTC (permalink / raw)
  To: David Miller, Herbert Xu; +Cc: netdev

I did a implementation of a state resolution packet queue for IPsec.
The original idea is described in git commit 14e50e57a
([XFRM]: Allow packet drops during larval state resolution.)

Since we don't have any notifiers for xfrm state resolution, I used
a timer that does a relookup in given intervals. This is mainly to speed
up the start of tcp connections, so I tried to do the relookup in a higher
rate that tcp would resend the syn packet. However, the relookup intervals,
the queue size and the timeout value are choosen by gut instincts, so
could be suboptimal. If anyone has some insight on good choices of these
values, please let me know. All other comment are welcome too, of course.


Subject: [PATCH] xfrm: Add a state resolution packet queue

As the default, we blackhole packets until the key manager resolves
the states. This patch implements a packet queue where IPsec packets
are queued until the states are resolved. We generate a dummy xfrm
bundle, the output routine of the returned route enqueues the packet
to a per policy queue and arms a timer that checks for state resolution
when dst_output() is called. Once the states are resolved, the packets
are sent out of the queue. If the states are not resolved after some
time, the queue is flushed.

This patch keeps the defaut behaviour to blackhole packets as long
as we have no states. To enable the packet queue the sysctl
xfrm_larval_drop must be switched off.

Signed-off-by: Steffen Klassert <steffen.klassert@secunet.com>
---
 include/net/dst.h      |    1 +
 include/net/xfrm.h     |    7 ++
 net/xfrm/xfrm_policy.c |  229 +++++++++++++++++++++++++++++++++++++++++++++++-
 3 files changed, 233 insertions(+), 4 deletions(-)

diff --git a/include/net/dst.h b/include/net/dst.h
index 9a78810..3da47e0 100644
--- a/include/net/dst.h
+++ b/include/net/dst.h
@@ -61,6 +61,7 @@ struct dst_entry {
 #define DST_NOPEER		0x0040
 #define DST_FAKE_RTABLE		0x0080
 #define DST_XFRM_TUNNEL		0x0100
+#define DST_XFRM_QUEUE		0x0200
 
 	unsigned short		pending_confirm;
 
diff --git a/include/net/xfrm.h b/include/net/xfrm.h
index 63445ed..4273a8f 100644
--- a/include/net/xfrm.h
+++ b/include/net/xfrm.h
@@ -501,6 +501,12 @@ struct xfrm_policy_walk {
 	u32 seq;
 };
 
+struct xfrm_policy_queue {
+	struct sk_buff_head	hold_queue;
+	struct timer_list	hold_timer;
+	unsigned long		timeout;
+};
+
 struct xfrm_policy {
 #ifdef CONFIG_NET_NS
 	struct net		*xp_net;
@@ -522,6 +528,7 @@ struct xfrm_policy {
 	struct xfrm_lifetime_cfg lft;
 	struct xfrm_lifetime_cur curlft;
 	struct xfrm_policy_walk_entry walk;
+	struct xfrm_policy_queue polq;
 	u8			type;
 	u8			action;
 	u8			flags;
diff --git a/net/xfrm/xfrm_policy.c b/net/xfrm/xfrm_policy.c
index 41eabc4..456b11b 100644
--- a/net/xfrm/xfrm_policy.c
+++ b/net/xfrm/xfrm_policy.c
@@ -35,6 +35,10 @@
 
 #include "xfrm_hash.h"
 
+#define XFRM_QUEUE_TMO_MIN ((unsigned)(HZ/10))
+#define XFRM_QUEUE_TMO_MAX ((unsigned)(60*HZ))
+#define XFRM_MAX_QUEUE_LEN	100
+
 DEFINE_MUTEX(xfrm_cfg_mutex);
 EXPORT_SYMBOL(xfrm_cfg_mutex);
 
@@ -51,7 +55,7 @@ static struct kmem_cache *xfrm_dst_cache __read_mostly;
 static void xfrm_init_pmtu(struct dst_entry *dst);
 static int stale_bundle(struct dst_entry *dst);
 static int xfrm_bundle_ok(struct xfrm_dst *xdst);
-
+static void xfrm_policy_queue_process(unsigned long arg);
 
 static struct xfrm_policy *__xfrm_policy_unlink(struct xfrm_policy *pol,
 						int dir);
@@ -287,8 +291,11 @@ struct xfrm_policy *xfrm_policy_alloc(struct net *net, gfp_t gfp)
 		INIT_HLIST_NODE(&policy->byidx);
 		rwlock_init(&policy->lock);
 		atomic_set(&policy->refcnt, 1);
+		skb_queue_head_init(&policy->polq.hold_queue);
 		setup_timer(&policy->timer, xfrm_policy_timer,
 				(unsigned long)policy);
+		setup_timer(&policy->polq.hold_timer, xfrm_policy_queue_process,
+			    (unsigned long)policy);
 		policy->flo.ops = &xfrm_policy_fc_ops;
 	}
 	return policy;
@@ -309,6 +316,16 @@ void xfrm_policy_destroy(struct xfrm_policy *policy)
 }
 EXPORT_SYMBOL(xfrm_policy_destroy);
 
+static void xfrm_queue_purge(struct sk_buff_head *list)
+{
+	struct sk_buff *skb;
+
+	while ((skb = skb_dequeue(list)) != NULL) {
+		dev_put(skb->dev);
+		kfree_skb(skb);
+	}
+}
+
 /* Rule must be locked. Release descentant resources, announce
  * entry dead. The rule must be unlinked from lists to the moment.
  */
@@ -319,6 +336,9 @@ static void xfrm_policy_kill(struct xfrm_policy *policy)
 
 	atomic_inc(&policy->genid);
 
+	del_timer(&policy->polq.hold_timer);
+	xfrm_queue_purge(&policy->polq.hold_queue);
+
 	if (del_timer(&policy->timer))
 		xfrm_pol_put(policy);
 
@@ -562,6 +582,31 @@ static inline int selector_cmp(struct xfrm_selector *s1, struct xfrm_selector *s
 	return 0;
 }
 
+static void xfrm_policy_requeue(struct xfrm_policy *old,
+				struct xfrm_policy *new)
+{
+	struct xfrm_policy_queue *pq = &old->polq;
+	struct sk_buff_head list;
+
+	__skb_queue_head_init(&list);
+
+	spin_lock_bh(&pq->hold_queue.lock);
+	skb_queue_splice_init(&pq->hold_queue, &list);
+	del_timer(&pq->hold_timer);
+	spin_unlock_bh(&pq->hold_queue.lock);
+
+	if (skb_queue_empty(&list))
+		return;
+
+	pq = &new->polq;
+
+	spin_lock_bh(&pq->hold_queue.lock);
+	skb_queue_splice(&list, &pq->hold_queue);
+	pq->timeout = XFRM_QUEUE_TMO_MIN;
+	mod_timer(&pq->hold_timer, jiffies);
+	spin_unlock_bh(&pq->hold_queue.lock);
+}
+
 int xfrm_policy_insert(int dir, struct xfrm_policy *policy, int excl)
 {
 	struct net *net = xp_net(policy);
@@ -603,8 +648,10 @@ int xfrm_policy_insert(int dir, struct xfrm_policy *policy, int excl)
 	net->xfrm.policy_count[dir]++;
 	atomic_inc(&flow_cache_genid);
 	rt_genid_bump(net);
-	if (delpol)
+	if (delpol) {
+		xfrm_policy_requeue(delpol, policy);
 		__xfrm_policy_unlink(delpol, dir);
+	}
 	policy->index = delpol ? delpol->index : xfrm_gen_index(net, dir);
 	hlist_add_head(&policy->byidx, net->xfrm.policy_byidx+idx_hash(net, policy->index));
 	policy->curlft.add_time = get_seconds();
@@ -1115,11 +1162,15 @@ int xfrm_sk_policy_insert(struct sock *sk, int dir, struct xfrm_policy *pol)
 		pol->index = xfrm_gen_index(net, XFRM_POLICY_MAX+dir);
 		__xfrm_policy_link(pol, XFRM_POLICY_MAX+dir);
 	}
-	if (old_pol)
+	if (old_pol) {
+		if (pol)
+			xfrm_policy_requeue(old_pol, pol);
+
 		/* Unlinking succeeds always. This is the only function
 		 * allowed to delete or replace socket policy.
 		 */
 		__xfrm_policy_unlink(old_pol, XFRM_POLICY_MAX+dir);
+	}
 	write_unlock_bh(&xfrm_policy_lock);
 
 	if (old_pol) {
@@ -1310,6 +1361,8 @@ static struct flow_cache_object *xfrm_bundle_flo_get(struct flow_cache_object *f
 		 * It means we need to try again resolving. */
 		if (xdst->num_xfrms > 0)
 			return NULL;
+	} else if (dst->flags & DST_XFRM_QUEUE) {
+		return NULL;
 	} else {
 		/* Real bundle */
 		if (stale_bundle(dst))
@@ -1673,6 +1726,171 @@ xfrm_resolve_and_create_bundle(struct xfrm_policy **pols, int num_pols,
 	return xdst;
 }
 
+static void xfrm_policy_queue_process(unsigned long arg)
+{
+	int err = 0;
+	struct sk_buff *skb;
+	struct sock *sk;
+	struct dst_entry *dst;
+	struct net_device *dev;
+	struct xfrm_policy *pol = (struct xfrm_policy *)arg;
+	struct xfrm_policy_queue *pq = &pol->polq;
+	struct flowi fl;
+	struct sk_buff_head list;
+
+	spin_lock(&pq->hold_queue.lock);
+	skb = skb_peek(&pq->hold_queue);
+	dst = skb_dst(skb);
+	sk = skb->sk;
+	xfrm_decode_session(skb, &fl, dst->ops->family);
+	spin_unlock(&pq->hold_queue.lock);
+
+	dst_hold(dst->path);
+	dst = xfrm_lookup(xp_net(pol), dst->path, &fl,
+			  sk, 0);
+	if (IS_ERR(dst))
+		goto purge_queue;
+
+	if (dst->flags & DST_XFRM_QUEUE) {
+		dst_release(dst);
+
+		if (pq->timeout >= XFRM_QUEUE_TMO_MAX)
+			goto purge_queue;
+
+		pq->timeout = pq->timeout << 1;
+		mod_timer(&pq->hold_timer, jiffies + pq->timeout);
+		return;
+	}
+
+	dst_release(dst);
+
+	__skb_queue_head_init(&list);
+
+	spin_lock(&pq->hold_queue.lock);
+	pq->timeout = 0;
+	skb_queue_splice_init(&pq->hold_queue, &list);
+	spin_unlock(&pq->hold_queue.lock);
+
+	while (!skb_queue_empty(&list)) {
+		skb = __skb_dequeue(&list);
+
+		xfrm_decode_session(skb, &fl, skb_dst(skb)->ops->family);
+		dst_hold(skb_dst(skb)->path);
+		dst = xfrm_lookup(xp_net(pol), skb_dst(skb)->path,
+				  &fl, skb->sk, 0);
+		if (IS_ERR(dst)) {
+			dev_put(skb->dev);
+			kfree_skb(skb);
+			continue;
+		}
+
+		nf_reset(skb);
+		skb_dst_drop(skb);
+		skb_dst_set(skb, dst);
+
+		dev = skb->dev;
+		err = dst_output(skb);
+		dev_put(dev);
+	}
+
+	return;
+
+purge_queue:
+	pq->timeout = 0;
+	xfrm_queue_purge(&pq->hold_queue);
+}
+
+static int xdst_queue_output(struct sk_buff *skb)
+{
+	unsigned long sched_next;
+	struct dst_entry *dst = skb_dst(skb);
+	struct xfrm_dst *xdst = (struct xfrm_dst *) dst;
+	struct xfrm_policy_queue *pq = &xdst->pols[0]->polq;
+
+	if (pq->hold_queue.qlen > XFRM_MAX_QUEUE_LEN) {
+		kfree_skb(skb);
+		return -EAGAIN;
+	}
+
+	skb_dst_force(skb);
+	dev_hold(skb->dev);
+
+	spin_lock_bh(&pq->hold_queue.lock);
+
+	if (!pq->timeout)
+		pq->timeout = XFRM_QUEUE_TMO_MIN;
+
+	sched_next = jiffies + pq->timeout;
+
+	if (del_timer(&pq->hold_timer)) {
+		if (time_before(pq->hold_timer.expires, sched_next))
+			sched_next = pq->hold_timer.expires;
+	}
+
+	__skb_queue_tail(&pq->hold_queue, skb);
+	mod_timer(&pq->hold_timer, sched_next);
+
+	spin_unlock_bh(&pq->hold_queue.lock);
+
+	return 0;
+}
+
+static struct xfrm_dst *xfrm_create_dummy_bundle(struct net *net,
+						 struct dst_entry *dst,
+						 const struct flowi *fl,
+						 int num_xfrms,
+						 u16 family)
+{
+	int err;
+	struct net_device *dev;
+	struct dst_entry *dst1;
+	struct xfrm_dst *xdst;
+
+	xdst = xfrm_alloc_dst(net, family);
+	if (IS_ERR(xdst))
+		return xdst;
+
+	if (net->xfrm.sysctl_larval_drop || num_xfrms <= 0 ||
+	    (fl->flowi_flags & FLOWI_FLAG_CAN_SLEEP))
+		return xdst;
+
+	dst1 = &xdst->u.dst;
+	dst_hold(dst);
+	xdst->route = dst;
+
+	dst_copy_metrics(dst1, dst);
+
+	dst1->obsolete = DST_OBSOLETE_FORCE_CHK;
+	dst1->flags |= DST_HOST | DST_XFRM_QUEUE;
+	dst1->lastuse = jiffies;
+
+	dst1->input = dst_discard;
+	dst1->output = xdst_queue_output;
+
+	dst_hold(dst);
+	dst1->child = dst;
+	dst1->path = dst;
+
+	xfrm_init_path((struct xfrm_dst *)dst1, dst, 0);
+
+	err = -ENODEV;
+	dev = dst->dev;
+	if (!dev)
+		goto free_dst;
+
+	err = xfrm_fill_dst(xdst, dev, fl);
+	if (err)
+		goto free_dst;
+
+out:
+	return xdst;
+
+free_dst:
+	dst_release(dst1);
+	xdst = ERR_PTR(err);
+	goto out;
+}
+
 static struct flow_cache_object *
 xfrm_bundle_lookup(struct net *net, const struct flowi *fl, u16 family, u8 dir,
 		   struct flow_cache_object *oldflo, void *ctx)
@@ -1751,7 +1969,7 @@ make_dummy_bundle:
 	/* We found policies, but there's no bundles to instantiate:
 	 * either because the policy blocks, has no transformations or
 	 * we could not build template (no xfrm_states).*/
-	xdst = xfrm_alloc_dst(net, family);
+	xdst = xfrm_create_dummy_bundle(net, dst_orig, fl, num_xfrms, family);
 	if (IS_ERR(xdst)) {
 		xfrm_pols_put(pols, num_pols);
 		return ERR_CAST(xdst);
@@ -2359,6 +2577,9 @@ static int xfrm_bundle_ok(struct xfrm_dst *first)
 	    (dst->dev && !netif_running(dst->dev)))
 		return 0;
 
+	if (dst->flags & DST_XFRM_QUEUE)
+		return 1;
+
 	last = NULL;
 
 	do {
-- 
1.7.9.5

^ permalink raw reply related

* [PATCH] net: ethernet: davinci: Fix build breakage
From: Thierry Reding @ 2013-01-21  9:38 UTC (permalink / raw)
  To: David S. Miller; +Cc: Mugunthan V N, netdev, linux-kernel

The correct name of the transmit DMA channel field in struct emac_priv
is txchan, not txch.

Signed-off-by: Thierry Reding <thierry.reding@avionic-design.de>
---
 drivers/net/ethernet/ti/davinci_emac.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/net/ethernet/ti/davinci_emac.c b/drivers/net/ethernet/ti/davinci_emac.c
index 1c97c81..242ec55 100644
--- a/drivers/net/ethernet/ti/davinci_emac.c
+++ b/drivers/net/ethernet/ti/davinci_emac.c
@@ -1102,7 +1102,7 @@ static int emac_dev_xmit(struct sk_buff *skb, struct net_device *ndev)
 	/* If there is no more tx desc left free then we need to
 	 * tell the kernel to stop sending us tx frames.
 	 */
-	if (unlikely(cpdma_check_free_tx_desc(priv->txch)))
+	if (unlikely(cpdma_check_free_tx_desc(priv->txchan)))
 		netif_stop_queue(ndev);
 
 	return NETDEV_TX_OK;
-- 
1.8.1.1

^ permalink raw reply related

* [PATCH] net: net_cls: fd passed in SCM_RIGHTS datagram not set correctly
From: Daniel Wagner @ 2013-01-21  9:38 UTC (permalink / raw)
  To: netdev-u79uwXL29TY76Z2rM5mHXA, cgroups-u79uwXL29TY76Z2rM5mHXA
  Cc: lizefan-hv44wF8Li93QT0dZR+AlfA, Daniel Wagner, David S. Miller,
	Eric W. Biederman, Al Viro, John Fastabend, Neil Horman

From: Daniel Wagner <daniel.wagner-98C5kh4wR6ohFhg+JK9F0w@public.gmane.org>

Commit 6a328d8c6f03501657ad580f6f98bf9a42583ff7 changed the update
logic for the socket but it does not update the SCM_RIGHTS update
as well. This patch is based on the net_prio fix commit

48a87cc26c13b68f6cce4e9d769fcb17a6b3e4b8

    net: netprio: fd passed in SCM_RIGHTS datagram not set correctly

    A socket fd passed in a SCM_RIGHTS datagram was not getting
    updated with the new tasks cgrp prioidx. This leaves IO on
    the socket tagged with the old tasks priority.

    To fix this add a check in the scm recvmsg path to update the
    sock cgrp prioidx with the new tasks value.

Let's apply the same fix for net_cls.

Reported-by: Li Zefan <lizefan-hv44wF8Li93QT0dZR+AlfA@public.gmane.org>
Cc: "David S. Miller" <davem-fT/PcQaiUtIeIZ0/mPfg9Q@public.gmane.org>
Cc: "Eric W. Biederman" <ebiederm-aS9lmoZGLiVWk0Htik3J/w@public.gmane.org>
Cc: Al Viro <viro-RmSDqhL/yNMiFSDQTTA3OLVCufUGDwFn@public.gmane.org>
Cc: John Fastabend <john.r.fastabend-ral2JQCrhuEAvxtiuMwx3w@public.gmane.org>
Cc: Neil Horman <nhorman-2XuSBdqkA4R54TAoqtyWWQ@public.gmane.org>
Cc: netdev-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
Cc: cgroups-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
---
 net/core/scm.c | 5 ++++-
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/net/core/scm.c b/net/core/scm.c
index 57fb1ee..905dcc6 100644
--- a/net/core/scm.c
+++ b/net/core/scm.c
@@ -35,6 +35,7 @@
 #include <net/sock.h>
 #include <net/compat.h>
 #include <net/scm.h>
+#include <net/cls_cgroup.h>
 
 
 /*
@@ -302,8 +303,10 @@ void scm_detach_fds(struct msghdr *msg, struct scm_cookie *scm)
 		}
 		/* Bump the usage count and install the file. */
 		sock = sock_from_file(fp[i], &err);
-		if (sock)
+		if (sock) {
 			sock_update_netprioidx(sock->sk, current);
+			sock_update_classid(sock->sk, current);
+		}
 		fd_install(new_fd, get_file(fp[i]));
 	}
 
-- 
1.8.0.rc0

^ permalink raw reply related

* Re: [BUG] Bug in netprio_cgroup and netcls_cgroup ?
From: Daniel Wagner @ 2013-01-21  9:27 UTC (permalink / raw)
  To: Li Zefan
  Cc: John Fastabend, Neil Horman, Daniel Wagner, LKML,
	netdev-u79uwXL29TY76Z2rM5mHXA, Cgroups
In-Reply-To: <50FD0402.6060400-hv44wF8Li93QT0dZR+AlfA@public.gmane.org>

On 21.01.2013 10:01, Li Zefan wrote:
> On 2013/1/21 16:50, Daniel Wagner wrote:
>> Hi Li,
>>
>> On 21.01.2013 07:08, Li Zefan wrote:
>>> I'm not a network developer, so correct me if I'm wrong.
>>>
>>> Since commit 7955490f732c2b8
>>> ("net: netprio_cgroup: rework update socket logic"), sock->sk->sk_cgrp_prioidx
>>> is set when the socket is created, and won't be updated unless the task is
>>> moved to another cgroup.
>>>
>>> Now the problem is, a socket can be _shared_ by multiple processes (fork, SCM_RIGHT).
>>> If we place those processes in different cgroups, and each cgroup has
>>> different configs, but all of the processes will send data via this socket
>>> with the same network priority.
>>
>> Wouldn't that be addressed by 48a87cc26c13b68f6cce4e9d769fcb17a6b3e4b8
>>
>>     net: netprio: fd passed in SCM_RIGHTS datagram not set correctly
>>
>>      A socket fd passed in a SCM_RIGHTS datagram was not getting
>>      updated with the new tasks cgrp prioidx. This leaves IO on
>>      the socket tagged with the old tasks priority.
>>
>>      To fix this add a check in the scm recvmsg path to update the
>>      sock cgrp prioidx with the new tasks value.
>>
>> As I read this this should work for net_prio.
>>
> 
> But after process A passed the socket fd to B, both A and B can use the
> same socket to send data, right? Then if A and B were placed in different
> cgroups with differnt configs, A's config won't take effect anymore.
> 
> Am I missing something?

I don't know. I guess at one point the socket resources are shared and then
one configuration is taking preference. As you can see I am far away of
being
an expert in this field. Hopefully someone who understands this bits
can chip in.

BTW, isn't this a similar to what should happen with the block io cgroup?
What is the behavior with a fd writing to a file in the scenario you
describe above?

^ permalink raw reply

* Re: [BUG] Bug in netprio_cgroup and netcls_cgroup ?
From: John Fastabend @ 2013-01-21  9:21 UTC (permalink / raw)
  To: Li Zefan
  Cc: Daniel Wagner, John Fastabend, Neil Horman, Daniel Wagner, LKML,
	netdev-u79uwXL29TY76Z2rM5mHXA, Cgroups
In-Reply-To: <50FD0402.6060400-hv44wF8Li93QT0dZR+AlfA@public.gmane.org>

On 01/21/2013 01:01 AM, Li Zefan wrote:
> On 2013/1/21 16:50, Daniel Wagner wrote:
>> Hi Li,
>>
>> On 21.01.2013 07:08, Li Zefan wrote:
>>> I'm not a network developer, so correct me if I'm wrong.
>>>
>>> Since commit 7955490f732c2b8
>>> ("net: netprio_cgroup: rework update socket logic"), sock->sk->sk_cgrp_prioidx
>>> is set when the socket is created, and won't be updated unless the task is
>>> moved to another cgroup.
>>>
>>> Now the problem is, a socket can be _shared_ by multiple processes (fork, SCM_RIGHT).
>>> If we place those processes in different cgroups, and each cgroup has
>>> different configs, but all of the processes will send data via this socket
>>> with the same network priority.
>>
>> Wouldn't that be addressed by 48a87cc26c13b68f6cce4e9d769fcb17a6b3e4b8
>>
>>     net: netprio: fd passed in SCM_RIGHTS datagram not set correctly
>>
>>      A socket fd passed in a SCM_RIGHTS datagram was not getting
>>      updated with the new tasks cgrp prioidx. This leaves IO on
>>      the socket tagged with the old tasks priority.
>>
>>      To fix this add a check in the scm recvmsg path to update the
>>      sock cgrp prioidx with the new tasks value.
>>
>> As I read this this should work for net_prio.
>>
> 
> But after process A passed the socket fd to B, both A and B can use the
> same socket to send data, right? Then if A and B were placed in different
> cgroups with differnt configs, A's config won't take effect anymore.
> 
> Am I missing something?
> 
> 

Hi Zefan,

Neil and I discusses this here, http://patchwork.ozlabs.org/patch/172343/
look towards the bottom of the thread. Quoted here.

>> I like the idea, but IIRC last time we tried this I think it caused problems
>> with processes that shared sockets.  That is to say, if you have a parent and
>> child process that dup an socket descriptior, and put them in separate cgroups,
>> you get unpredictable results, as the socket gets assigned a priority based on
>> the last processed that moved cgroups.
>>
>> Neil
>>
> 
> Shared sockets creates strange behavior as it exists today. If a dup
> of the socket fd is created the private data is still shared right. So
> in this case the sk_cgrp_prioidx value is going to get updated by both
> threads and then it is a race to see what it happens to be set to in
> the xmit path.
> 
> With this patch at least the behavior is deterministic. Without it
> I can create the above scenario but have no way to determine what the
> skb priority will actually be set to.
> 

Its unfortunate but I'm not sure how to fix it off hand with the shared
value
in the socket.

.John

-- 
John Fastabend         Intel Corporation

^ permalink raw reply

* Re: IPsec AH use of ahash
From: David Dillow @ 2013-01-21  9:18 UTC (permalink / raw)
  To: Tom St Denis; +Cc: Borislav Petkov, linux-kernel, netdev, Steven Rostedt
In-Reply-To: <861997288.94032.1358728848956.JavaMail.root@elliptictech.com>

On Sun, 2013-01-20 at 19:40 -0500, Tom St Denis wrote:
> The problem is for me to add the ()'s is a no brainer.

It was more than just the ()'s. You completely botched the indentation
in the parts of code you didn't copy from xcbc.c, among other issues.

> For me to re-write complete statements for coding style reasons means
> I have to actually go out and test it again.

Well, for some of the code you submitted, that would be the first
testing it got, even compile testing AFAICT. I don't doubt that you
tested against your hardware, but it is obvious that you didn't run the
algorithm tests you added, or even tried to compile them. You were
missing a semicolon after your test data, and you were also missing a
"\x" in there, so your test data was wrong.

I know this, because I just spent the five minutes required to fix up
the checkpatch warnings to prove to myself that you could have done it
faster than sending one considered message to the list about how much we
suck. Of course, that assumes you are trying to have a discussion
instead of trolling; it's much easier to spew bile than to think before
you post.

^ permalink raw reply

* Re: [B.A.T.M.A.N.] batman-adv: Unable to add interface in LXC
From: Pau Koning @ 2013-01-21  9:11 UTC (permalink / raw)
  To: Marek Lindner; +Cc: b.a.t.m.a.n, netdev
In-Reply-To: <201212311511.24877.lindner_marek@yahoo.de>

> Did you check your kernel log messages ? I'd expect batman-adv to print
> something there in case of an error.

No output at all

^ permalink raw reply

* Re: [BUG] Bug in netprio_cgroup and netcls_cgroup ?
From: Li Zefan @ 2013-01-21  9:01 UTC (permalink / raw)
  To: Daniel Wagner
  Cc: John Fastabend, Neil Horman, Daniel Wagner, LKML,
	netdev-u79uwXL29TY76Z2rM5mHXA, Cgroups
In-Reply-To: <50FD0144.1000401-kQCPcA+X3s7YtjvyW6yDsg@public.gmane.org>

On 2013/1/21 16:50, Daniel Wagner wrote:
> Hi Li,
> 
> On 21.01.2013 07:08, Li Zefan wrote:
>> I'm not a network developer, so correct me if I'm wrong.
>>
>> Since commit 7955490f732c2b8
>> ("net: netprio_cgroup: rework update socket logic"), sock->sk->sk_cgrp_prioidx
>> is set when the socket is created, and won't be updated unless the task is
>> moved to another cgroup.
>>
>> Now the problem is, a socket can be _shared_ by multiple processes (fork, SCM_RIGHT).
>> If we place those processes in different cgroups, and each cgroup has
>> different configs, but all of the processes will send data via this socket
>> with the same network priority.
> 
> Wouldn't that be addressed by 48a87cc26c13b68f6cce4e9d769fcb17a6b3e4b8
> 
>    net: netprio: fd passed in SCM_RIGHTS datagram not set correctly
> 
>     A socket fd passed in a SCM_RIGHTS datagram was not getting
>     updated with the new tasks cgrp prioidx. This leaves IO on
>     the socket tagged with the old tasks priority.
> 
>     To fix this add a check in the scm recvmsg path to update the
>     sock cgrp prioidx with the new tasks value.
> 
> As I read this this should work for net_prio.
> 

But after process A passed the socket fd to B, both A and B can use the
same socket to send data, right? Then if A and B were placed in different
cgroups with differnt configs, A's config won't take effect anymore.

Am I missing something?

^ permalink raw reply

* Re: [PATCH] net: fec: Add support for multiple phys on mdiobus
From: Wolfgang Grandegger @ 2013-01-21  8:56 UTC (permalink / raw)
  To: Sascha Hauer; +Cc: netdev, shawn.guo, davem, linux-arm-kernel
In-Reply-To: <1358757475-21035-1-git-send-email-s.hauer@pengutronix.de>

On 01/21/2013 09:37 AM, Sascha Hauer wrote:
> There may be multiple phys on an mdio bus. This series adds support
> for this to the fec driver. I recently had a board which has a switch
> connected to the fec's mdio bus, so I had to pick the correct phy.

Pick one PHY from a switch port? Well, does a PHY-less (or fixed-link)
configuration for a switch not make more sense? Various ARM Ethernet
contoller drivers do not support it. I recently needed a hack for an
AT91 board.

Wolfgang.

^ permalink raw reply

* Re: [BUG] Bug in netprio_cgroup and netcls_cgroup ?
From: Daniel Wagner @ 2013-01-21  8:50 UTC (permalink / raw)
  To: Li Zefan
  Cc: John Fastabend, Neil Horman, Daniel Wagner, LKML,
	netdev-u79uwXL29TY76Z2rM5mHXA, Cgroups
In-Reply-To: <50FCDB5C.4050608-hv44wF8Li93QT0dZR+AlfA@public.gmane.org>

Hi Li,

On 21.01.2013 07:08, Li Zefan wrote:
> I'm not a network developer, so correct me if I'm wrong.
> 
> Since commit 7955490f732c2b8
> ("net: netprio_cgroup: rework update socket logic"), sock->sk->sk_cgrp_prioidx
> is set when the socket is created, and won't be updated unless the task is
> moved to another cgroup.
> 
> Now the problem is, a socket can be _shared_ by multiple processes (fork, SCM_RIGHT).
> If we place those processes in different cgroups, and each cgroup has
> different configs, but all of the processes will send data via this socket
> with the same network priority.

Wouldn't that be addressed by 48a87cc26c13b68f6cce4e9d769fcb17a6b3e4b8

   net: netprio: fd passed in SCM_RIGHTS datagram not set correctly

    A socket fd passed in a SCM_RIGHTS datagram was not getting
    updated with the new tasks cgrp prioidx. This leaves IO on
    the socket tagged with the old tasks priority.

    To fix this add a check in the scm recvmsg path to update the
    sock cgrp prioidx with the new tasks value.

As I read this this should work for net_prio.

> Similar with cls cgroup.

but not for cls_cgroup because I forgot to apply that fix as well. Just
a sec, about to
send a patch for this.

Thanks for looking into this!

cheers,
daniel

^ permalink raw reply

* [PATCH 2/2] net: fec: Add support for phys from devicetree
From: Sascha Hauer @ 2013-01-21  8:37 UTC (permalink / raw)
  To: netdev; +Cc: linux-arm-kernel, shawn.guo, davem, Sascha Hauer
In-Reply-To: <1358757475-21035-1-git-send-email-s.hauer@pengutronix.de>

This adds support for specifying the phy for the fec driver through the
devicetree. Possible usecases are:

- The fec internal MDIO bus has multiple phys connected and a particular
  one has to be chosen which is physically connected to the (RG)MII interface.
- The phy is connected to an external MDIO bus.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 Documentation/devicetree/bindings/net/fsl-fec.txt |   20 +++++++
 drivers/net/ethernet/freescale/fec.c              |   61 +++++++++++++--------
 drivers/net/ethernet/freescale/fec.h              |    1 +
 3 files changed, 59 insertions(+), 23 deletions(-)

diff --git a/Documentation/devicetree/bindings/net/fsl-fec.txt b/Documentation/devicetree/bindings/net/fsl-fec.txt
index d536392..ec7060b 100644
--- a/Documentation/devicetree/bindings/net/fsl-fec.txt
+++ b/Documentation/devicetree/bindings/net/fsl-fec.txt
@@ -15,6 +15,9 @@ Optional properties:
   only if property "phy-reset-gpios" is available.  Missing the property
   will have the duration be 1 millisecond.  Numbers greater than 1000 are
   invalid and 1 millisecond will be used instead.
+- phy : a phandle for the PHY device used for the fec. Used to specify an
+  external phy or to specify a particular address if the mdio bus has multiple
+  phys on it.
 
 Example:
 
@@ -26,3 +29,20 @@ ethernet@83fec000 {
 	phy-reset-gpios = <&gpio2 14 0>; /* GPIO2_14 */
 	local-mac-address = [00 04 9F 01 1B B9];
 };
+
+Example with specific phy address:
+
+ethernet@83fec000 {
+	compatible = "fsl,imx51-fec", "fsl,imx27-fec";
+	reg = <0x83fec000 0x4000>;
+	interrupts = <87>;
+	phy-mode = "mii";
+	phy-reset-gpios = <&gpio2 14 0>; /* GPIO2_14 */
+	local-mac-address = [00 04 9F 01 1B B9];
+	phy = &phy3;
+
+	phy3: ethernet-phy@3 {
+		reg = <3>;
+		device_type = "ethernet-phy";
+	};
+};
diff --git a/drivers/net/ethernet/freescale/fec.c b/drivers/net/ethernet/freescale/fec.c
index 2f86557..54a8506 100644
--- a/drivers/net/ethernet/freescale/fec.c
+++ b/drivers/net/ethernet/freescale/fec.c
@@ -48,6 +48,7 @@
 #include <linux/of_device.h>
 #include <linux/of_gpio.h>
 #include <linux/of_net.h>
+#include <linux/of_mdio.h>
 #include <linux/pinctrl/consumer.h>
 #include <linux/regulator/consumer.h>
 
@@ -950,31 +951,38 @@ static int fec_enet_mii_probe(struct net_device *ndev)
 
 	fep->phy_dev = NULL;
 
-	/* check for attached phy */
-	for (phy_id = 0; (phy_id < PHY_MAX_ADDR); phy_id++) {
-		if ((fep->mii_bus->phy_mask & (1 << phy_id)))
-			continue;
-		if (fep->mii_bus->phy_map[phy_id] == NULL)
-			continue;
-		if (fep->mii_bus->phy_map[phy_id]->phy_id == 0)
-			continue;
-		if (dev_id--)
-			continue;
-		strncpy(mdio_bus_id, fep->mii_bus->id, MII_BUS_ID_SIZE);
-		break;
-	}
+	if (fep->phy_node) {
+		phy_dev = of_phy_connect(ndev, fep->phy_node, &fec_enet_adjust_link, 0,
+			      fep->phy_interface);
+	} else {
+		/* check for attached phy */
+		for (phy_id = 0; (phy_id < PHY_MAX_ADDR); phy_id++) {
+			if ((fep->mii_bus->phy_mask & (1 << phy_id)))
+				continue;
+			if (fep->mii_bus->phy_map[phy_id] == NULL)
+				continue;
+			if (fep->mii_bus->phy_map[phy_id]->phy_id == 0)
+				continue;
+			if (dev_id--)
+				continue;
+			strncpy(mdio_bus_id, fep->mii_bus->id, MII_BUS_ID_SIZE);
+			break;
+		}
+
+		if (phy_id >= PHY_MAX_ADDR) {
+			printk(KERN_INFO
+				"%s: no PHY, assuming direct connection to switch\n",
+				ndev->name);
+			strncpy(mdio_bus_id, "fixed-0", MII_BUS_ID_SIZE);
+			phy_id = 0;
+		}
+
+		snprintf(phy_name, sizeof(phy_name), PHY_ID_FMT, mdio_bus_id, phy_id);
 
-	if (phy_id >= PHY_MAX_ADDR) {
-		printk(KERN_INFO
-			"%s: no PHY, assuming direct connection to switch\n",
-			ndev->name);
-		strncpy(mdio_bus_id, "fixed-0", MII_BUS_ID_SIZE);
-		phy_id = 0;
+		phy_dev = phy_connect(ndev, phy_name, &fec_enet_adjust_link, 0,
+				      fep->phy_interface);
 	}
 
-	snprintf(phy_name, sizeof(phy_name), PHY_ID_FMT, mdio_bus_id, phy_id);
-	phy_dev = phy_connect(ndev, phy_name, &fec_enet_adjust_link, 0,
-			      fep->phy_interface);
 	if (IS_ERR(phy_dev)) {
 		printk(KERN_ERR "%s: could not attach to PHY\n", ndev->name);
 		return PTR_ERR(phy_dev);
@@ -1076,7 +1084,12 @@ static int fec_enet_mii_init(struct platform_device *pdev)
 	for (i = 0; i < PHY_MAX_ADDR; i++)
 		fep->mii_bus->irq[i] = PHY_POLL;
 
-	if (mdiobus_register(fep->mii_bus))
+	if (fep->phy_node)
+		err = of_mdiobus_register(fep->mii_bus, pdev->dev.of_node);
+	else
+		err = mdiobus_register(fep->mii_bus);
+
+	if (err)
 		goto err_out_free_mdio_irq;
 
 	mii_cnt++;
@@ -1493,6 +1506,8 @@ static int fec_probe_dt(struct fec_enet_private *fep)
 
 	fep->phy_interface = of_get_phy_mode(np);
 
+	fep->phy_node = of_parse_phandle(np, "phy", 0);
+
 	return -ENODEV;
 }
 
diff --git a/drivers/net/ethernet/freescale/fec.h b/drivers/net/ethernet/freescale/fec.h
index c5a3bc1..0120ea6 100644
--- a/drivers/net/ethernet/freescale/fec.h
+++ b/drivers/net/ethernet/freescale/fec.h
@@ -236,6 +236,7 @@ struct fec_enet_private {
 	/* Phylib and MDIO interface */
 	struct	mii_bus *mii_bus;
 	struct	phy_device *phy_dev;
+	struct	device_node *phy_node;
 	int	mii_timeout;
 	uint	phy_speed;
 	phy_interface_t	phy_interface;
-- 
1.7.10.4

^ permalink raw reply related

* [PATCH 1/2] net: fec: refactor dt probing
From: Sascha Hauer @ 2013-01-21  8:37 UTC (permalink / raw)
  To: netdev; +Cc: linux-arm-kernel, shawn.guo, davem, Sascha Hauer
In-Reply-To: <1358757475-21035-1-git-send-email-s.hauer@pengutronix.de>

For devicetree parsing only the fec_get_phy_mode_dt() is
available. Rename it to fec_probe_dt() to be able to add more devicetree
parsing to it.

Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
---
 drivers/net/ethernet/freescale/fec.c |   16 ++++++++--------
 1 file changed, 8 insertions(+), 8 deletions(-)

diff --git a/drivers/net/ethernet/freescale/fec.c b/drivers/net/ethernet/freescale/fec.c
index 0704bca..2f86557 100644
--- a/drivers/net/ethernet/freescale/fec.c
+++ b/drivers/net/ethernet/freescale/fec.c
@@ -1484,12 +1484,14 @@ static int fec_enet_init(struct net_device *ndev)
 }
 
 #ifdef CONFIG_OF
-static int fec_get_phy_mode_dt(struct platform_device *pdev)
+static int fec_probe_dt(struct fec_enet_private *fep)
 {
-	struct device_node *np = pdev->dev.of_node;
+	struct device_node *np = fep->pdev->dev.of_node;
 
-	if (np)
-		return of_get_phy_mode(np);
+	if (!np)
+		return -ENODEV;
+
+	fep->phy_interface = of_get_phy_mode(np);
 
 	return -ENODEV;
 }
@@ -1519,7 +1521,7 @@ static void fec_reset_phy(struct platform_device *pdev)
 	gpio_set_value(phy_reset, 1);
 }
 #else /* CONFIG_OF */
-static inline int fec_get_phy_mode_dt(struct platform_device *pdev)
+static inline int fec_probe_dt(struct fec_enet_private *fep)
 {
 	return -ENODEV;
 }
@@ -1581,15 +1583,13 @@ fec_probe(struct platform_device *pdev)
 
 	platform_set_drvdata(pdev, ndev);
 
-	ret = fec_get_phy_mode_dt(pdev);
+	ret = fec_probe_dt(fep);
 	if (ret < 0) {
 		pdata = pdev->dev.platform_data;
 		if (pdata)
 			fep->phy_interface = pdata->phy;
 		else
 			fep->phy_interface = PHY_INTERFACE_MODE_MII;
-	} else {
-		fep->phy_interface = ret;
 	}
 
 	for (i = 0; i < FEC_IRQ_NUM; i++) {
-- 
1.7.10.4

^ permalink raw reply related

* [PATCH] net: fec: Add support for multiple phys on mdiobus
From: Sascha Hauer @ 2013-01-21  8:37 UTC (permalink / raw)
  To: netdev; +Cc: linux-arm-kernel, shawn.guo, davem

There may be multiple phys on an mdio bus. This series adds support
for this to the fec driver. I recently had a board which has a switch
connected to the fec's mdio bus, so I had to pick the correct phy.

This series should be in line with other network drivers supporting
this (Marvell Armada for example)

Sascha

----------------------------------------------------------------
Sascha Hauer (2):
      net: fec: refactor dt probing
      net: fec: Add support for phys from devicetree

 Documentation/devicetree/bindings/net/fsl-fec.txt |   20 ++++++
 drivers/net/ethernet/freescale/fec.c              |   77 ++++++++++++---------
 drivers/net/ethernet/freescale/fec.h              |    1 +
 3 files changed, 67 insertions(+), 31 deletions(-)

^ permalink raw reply

* Re: [PATCH net] net: cdc_ncm: workaround for missing CDC Union
From: Bjørn Mork @ 2013-01-21  8:31 UTC (permalink / raw)
  To: Alexey Orishko
  Cc: Oliver Neukum, netdev-u79uwXL29TY76Z2rM5mHXA,
	linux-usb-u79uwXL29TY76Z2rM5mHXA, Greg Suarez, Alexey Orishko
In-Reply-To: <CAL_Kpj1B=_+eN3Y0n3d9_r4JoeHD2LQFSU+b+taCZL0G4icu6A-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>

Alexey Orishko <alexey.orishko-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org> writes:
> On Fri, Jan 18, 2013 at 10:17 PM, Bjørn Mork <bjorn-yOkvZcmFvRU@public.gmane.org> wrote:
>
>>>> Some Sierra Wireless firmwares support CDC MBIM but have no CDC
>>>> Union funtional descriptor. This violates the MBIM specification,
>
> I don't believe Sierra Wireless violates MBIM specification.
> See in the specification: "there are two ways to group interfaces: the
> WHCM Union functional descriptor and IAD."

I disagree.  This is not about the WHCM Union descriptor, it's about the
CDC Union descriptor.  WHCM is of course not mandatory.

Quoting that whole section from the MBIM specification:

<quote>
  6.1 OVERVIEW
  
  A USB MBIM function is implemented as a USB CDC function with two
  interfaces.  Functions shall provide a CDC Union functional descriptor
  to group these two interfaces.  See [USBWMC11].
  
  A Communication Class interface, with class 02h and subclass 0Eh, and
  a Data Class interface combine to form a single functional unit
  representing the USB MBIM device.  The Communication Class interface
  includes a single endpoint for event notification; it also uses the
  device’s default pipe for control messages.  The Data Class interface
  includes two bulk endpoints for data traffic.
  
  There are two ways to group interfaces: the WHCM Union Functional
  Descriptor (see [USBWMC11]) and the IAD.  Devices may also provide an
  IAD.  If an IAD is provided, the information in the IAD for MBIM
  functions shall be consistent with the information in the CDC Union
  descriptor and Communication Class interface descriptor.
</quote>


The "Functions shall provide a CDC Union functional descriptor to group
these two interfaces." is pretty clear IMHO.  You also have table 6‐2
listing the HEADER, UNION and MBIM functional descriptors as "Required".

There is absolutely not way to make this anything but a firmware bug.

But I am all for working around it, of course.  There also seems to be a
couple more oddities with the MBIM mode of this device compared to the
other I've seen, but those are more likely revealing driver bugs.  I
intend to fix them as well.



Bjørn
--
To unsubscribe from this list: send the line "unsubscribe linux-usb" in
the body of a message to majordomo-u79uwXL29TY76Z2rM5mHXA@public.gmane.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply


This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox