* Re: [PATCH v3 2/2] sctp: optimize the sctp_sysctl_net_register
From: Neil Horman @ 2014-02-13 12:44 UTC (permalink / raw)
To: Wang Weidong; +Cc: davem, vyasevich, dborkman, sergei.shtylyov, netdev
In-Reply-To: <52FC1D9D.3090500@huawei.com>
On Thu, Feb 13, 2014 at 09:19:25AM +0800, Wang Weidong wrote:
> On 2014/2/12 19:53, Neil Horman wrote:
> > On Wed, Feb 12, 2014 at 09:44:44AM +0800, Wang Weidong wrote:
> >> Here, when the net is init_net, we needn't to kmemdup the ctl_table
> >> again. So add a check for net. Also we can save some memory.
> >>
> >> Signed-off-by: Wang Weidong <wangweidong1@huawei.com>
> >> ---
> >> net/sctp/sysctl.c | 17 ++++++++++-------
> >> 1 file changed, 10 insertions(+), 7 deletions(-)
> >>
> >> diff --git a/net/sctp/sysctl.c b/net/sctp/sysctl.c
> >> index d354de5..35c8923 100644
> >> --- a/net/sctp/sysctl.c
> >> +++ b/net/sctp/sysctl.c
> >> @@ -402,15 +402,18 @@ static int proc_sctp_do_rto_max(struct ctl_table *ctl, int write,
> >>
> >> int sctp_sysctl_net_register(struct net *net)
> >> {
> >> - struct ctl_table *table;
> >> - int i;
> >> + struct ctl_table *table = sctp_net_table;
> >> +
> >> + if (!net_eq(net, &init_net)) {
> >> + int i;
> >>
> >> - table = kmemdup(sctp_net_table, sizeof(sctp_net_table), GFP_KERNEL);
> >> - if (!table)
> >> - return -ENOMEM;
> >> + table = kmemdup(sctp_net_table, sizeof(sctp_net_table), GFP_KERNEL);
> >> + if (!table)
> >> + return -ENOMEM;
> >>
> >> - for (i = 0; table[i].data; i++)
> >> - table[i].data += (char *)(&net->sctp) - (char *)&init_net.sctp;
> >> + for (i = 0; table[i].data; i++)
> >> + table[i].data += (char *)(&net->sctp) - (char *)&init_net.sctp;
> >> + }
> >>
> > In the first version of this patch you complained about a lockdep issue. Did
> > you figure out what that was, and if it related to these changes?
> >
> > Neil
> >
> >
> Hi Neil,
>
> The lockdep issue doesn't relate to these changes. I should send it
> by the another email. Sorry for confusing you.
>
> Regards
> Wang
>
Then you probably don't need to mention it in the same note that you're
proposing changes.
Acked-by: Neil Horman <nhorman@tuxdriver.com>
^ permalink raw reply
* Re: [PATCH v5] can: add Renesas R-Car CAN driver
From: Marc Kleine-Budde @ 2014-02-13 12:12 UTC (permalink / raw)
To: Sergei Shtylyov, netdev, wg, linux-can; +Cc: linux-sh, vksavl
In-Reply-To: <52E3148E.2010608@cogentembedded.com>
[-- Attachment #1: Type: text/plain, Size: 3825 bytes --]
On 01/25/2014 02:34 AM, Sergei Shtylyov wrote:
> Hello.
>
> On 01/20/2014 12:18 PM, Marc Kleine-Budde wrote:
>
>>> Add support for the CAN controller found in Renesas R-Car SoCs.
>
>>> Signed-off-by: Sergei Shtylyov <sergei.shtylyov@cogentembedded.com>
>
>>> ---
>>> The patch is against the 'linux-can-next.git' repo.
>
> [...]
>>> Index: linux-can-next/drivers/net/can/rcar_can.c
>>> ===================================================================
>>> --- /dev/null
>>> +++ linux-can-next/drivers/net/can/rcar_can.c
>>> @@ -0,0 +1,857 @@
> [...]
>>> +/* Mailbox registers structure */
>>> +struct rcar_can_mbox_regs {
>>> + u32 id; /* IDE and RTR bits, SID and EID */
>>> + u8 stub; /* Not used */
>>> + u8 dlc; /* Data Length Code - bits [0..3] */
>>> + u8 data[8]; /* Data Bytes */
>>> + u8 tsh; /* Time Stamp Higher Byte */
>>> + u8 tsl; /* Time Stamp Lower Byte */
>>> +} __packed;
>
>> If you have contact to the hardware designer please blame him for
>
> Unfortunately, we don't.
>
>> placing the data register unaligned into the register space. :)
>
> It's not even the only one or worst example of questionable register
> design in this module IMO.
>
> [...]
>>> +static void rcar_can_tx_done(struct net_device *ndev)
>>> +{
>>> + struct rcar_can_priv *priv = netdev_priv(ndev);
>>> + struct net_device_stats *stats = &ndev->stats;
>>> + int i;
>>> +
>>> + spin_lock(&priv->skb_lock);
>>> + for (i = 0; i < priv->frames_queued; i++)
>>> + can_get_echo_skb(ndev, i);
>>> + stats->tx_bytes += priv->bytes_queued;
>>> + stats->tx_packets += priv->frames_queued;
>>> + priv->bytes_queued = 0;
>>> + priv->frames_queued = 0;
>>> + spin_unlock(&priv->skb_lock);
>
>> This looks broken. What happens if you send 2 CAN frames in a row, the
>> first one is send, a TX complete interrupt is issued and you handle it
>> here? You assume, that all CAN frames have been sent.
>
> TX interrupt will be issued only when TX FIFO gets empty (all 2 frames
> have been transmitted in this case). Please see the comment to the
> RCAR_CAN_MIER1_TXFIT bit.
Does the hardware have a TX complete interrupt? If you only have TX FIFO
empty, you have to limit the FIFO depth to 1.
>>> +static irqreturn_t rcar_can_interrupt(int irq, void *dev_id)
>>> +{
>>> + struct net_device *ndev = (struct net_device *)dev_id;
>
>> the cast is not needed
>
> Removed.
>
> [...]
>>> +static void rcar_can_set_bittiming(struct net_device *dev)
>>> +{
>>> + struct rcar_can_priv *priv = netdev_priv(dev);
>>> + struct can_bittiming *bt = &priv->can.bittiming;
>>> + u32 bcr;
>>> + u8 clkr;
>>> +
>>> + /* Don't overwrite CLKR with 32-bit BCR access */
>>> + /* CLKR has 8-bit access */
>
>> Can you explain the register layout here? Why do you access BCR with 32
>> bits when the register is defined as 3x8 bit? Can't you make it a
>> standard 32 bit register?
>
> 1. According to documentation BCR is the 24-bit register.
> Actually we can consider some 32-bit register that combines BCR and
> CLKR but according to documentation there are two separate registers.
> 2. BCR has 8- ,16-, and 32-bit access (according to documentation).
> 3. This is the algorithm that the documentation suggests.
> 4. We had a driver version with byte access but 32-bit access seems
> shorter.
Please use a normal read-modify-write 32 bit access.
Marc
--
Pengutronix e.K. | Marc Kleine-Budde |
Industrial Linux Solutions | Phone: +49-231-2826-924 |
Vertretung West/Dortmund | Fax: +49-5121-206917-5555 |
Amtsgericht Hildesheim, HRA 2686 | http://www.pengutronix.de |
[-- Attachment #2: OpenPGP digital signature --]
[-- Type: application/pgp-signature, Size: 242 bytes --]
^ permalink raw reply
* Re: [PATCH ipsec-next v3] xfrm: avoid creating temporary SA when there are no listeners
From: Steffen Klassert @ 2014-02-13 12:08 UTC (permalink / raw)
To: Horia Geanta; +Cc: David S. Miller, netdev
In-Reply-To: <1392214806-21966-1-git-send-email-horia.geanta@freescale.com>
On Wed, Feb 12, 2014 at 04:20:06PM +0200, Horia Geanta wrote:
> In the case when KMs have no listeners, km_query() will fail and
> temporary SAs are garbage collected immediately after their allocation.
> This causes strain on memory allocation, leading even to OOM since
> temporary SA alloc/free cycle is performed for every packet
> and garbage collection does not keep up the pace.
>
> The sane thing to do is to make sure we have audience before
> temporary SA allocation.
>
> Signed-off-by: Horia Geanta <horia.geanta@freescale.com>
Applied to ipsec-next, thanks!
^ permalink raw reply
* [PATCH next resend] tcp: use zero-window when free_space is low
From: Florian Westphal @ 2014-02-13 11:52 UTC (permalink / raw)
To: netdev; +Cc: Florian Westphal, Neal Cardwell, Eric Dumazet, Yuchung Cheng
Currently the kernel tries to announce a zero window when free_space
is below the current receiver mss estimate.
When a sender is transmitting small packets and reader consumes data
slowly (or not at all), receiver might be unable to shrink the receive
win because
a) we cannot withdraw already-commited receive window, and,
b) we have to round the current rwin up to a multiple of the wscale
factor, else we would shrink the current window.
This causes the receive buffer to fill up until the rmem limit is hit.
When this happens, we start dropping packets.
Moreover, tcp_clamp_window may continue to grow sk_rcvbuf towards rmem[2]
even if socket is not being read from.
As we cannot avoid the "current_win is rounded up to multiple of mss"
issue [we would violate a) above] at least try to prevent the receive buf
growth towards tcp_rmem[2] limit by attempting to move to zero-window
announcement when free_space becomes less than 1/16 of the current
allowed receive buffer maximum. If tcp_rmem[2] is large, this will
increase our chances to get a zero-window announcement out in time.
Reproducer:
On server:
$ nc -l -p 12345
<suspend it: CTRL-Z>
Client:
#!/usr/bin/env python
import socket
import time
sock = socket.socket()
sock.setsockopt(socket.IPPROTO_TCP, socket.TCP_NODELAY, 1)
sock.connect(("192.168.4.1", 12345));
while True:
sock.send('A' * 23)
time.sleep(0.005)
socket buffer on server-side will grow until tcp_rmem[2] is hit,
at which point the client rexmits data until -EDTIMEOUT:
tcp_data_queue invokes tcp_try_rmem_schedule which will call
tcp_prune_queue which calls tcp_clamp_window(). And that function will
grow sk->sk_rcvbuf up until it eventually hits tcp_rmem[2].
Cc: Neal Cardwell <ncardwell@google.com>
Cc: Eric Dumazet <eric.dumazet@gmail.com>
Cc: Yuchung Cheng <ycheng@google.com>
Signed-off-by: Florian Westphal <fw@strlen.de>
---
V1 of this patch was deferred, resending to get discussion going again.
Changes since v1:
- add reproducer to commit message
Unfortunately I couldn't come up with something that has no magic
('allowed >> 4') value. I chose >>4 (1/16th) because it didn't cause
tput limitations in my 'full-mss-sized, steady state' netcat tests.
Maybe someone has better idea?
diff --git a/net/ipv4/tcp_output.c b/net/ipv4/tcp_output.c
index 2a69f42..fd8d821 100644
--- a/net/ipv4/tcp_output.c
+++ b/net/ipv4/tcp_output.c
@@ -2145,7 +2145,8 @@ u32 __tcp_select_window(struct sock *sk)
*/
int mss = icsk->icsk_ack.rcv_mss;
int free_space = tcp_space(sk);
- int full_space = min_t(int, tp->window_clamp, tcp_full_space(sk));
+ int allowed_space = tcp_full_space(sk);
+ int full_space = min_t(int, tp->window_clamp, allowed_space);
int window;
if (mss > full_space)
@@ -2158,7 +2159,19 @@ u32 __tcp_select_window(struct sock *sk)
tp->rcv_ssthresh = min(tp->rcv_ssthresh,
4U * tp->advmss);
- if (free_space < mss)
+ /* free_space might become our new window, make sure we don't
+ * increase it due to wscale.
+ */
+ free_space = round_down(free_space, 1 << tp->rx_opt.rcv_wscale);
+
+ /* if free space is less than mss estimate, or is below 1/16th
+ * of the maximum allowed, try to move to zero-window, else
+ * tcp_clamp_window() will grow rcv buf up to tcp_rmem[2], and
+ * new incoming data is dropped due to memory limits.
+ * With large window, mss test triggers way too late in order
+ * to announce zero window in time before rmem limit kicks in.
+ */
+ if (free_space < (allowed_space >> 4) || free_space < mss)
return 0;
}
--
1.8.1.5
^ permalink raw reply related
* [net-next 15/15] i40evf: refactor reset handling
From: Aaron Brown @ 2014-02-13 11:48 UTC (permalink / raw)
To: davem
Cc: Mitch Williams, netdev, gospo, sassmann, Jesse Brandeburg,
Aaron Brown
In-Reply-To: <1392292133-32120-1-git-send-email-aaron.f.brown@intel.com>
From: Mitch Williams <mitch.a.williams@intel.com>
Respond better to a VF reset event. When a reset is signaled by the
PF, or detected by the watchdog task, prevent the watchdog from
processing admin queue requests, and schedule the reset task.
In the reset task, wait first for the reset to start, then for it to
complete, then reinit the driver.
If the reset never appears to complete after a long, long time (>10
seconds is possible depending on what's going on with the PF driver),
then set a flag to indicate that PF communications have failed.
If this flag is set, check for the reset to complete in the watchdog,
and attempt to do a full reinitialization of the driver from scratch.
With these changes the VF driver correctly handles a PF reset event
while running on bare metal, or in a VM.
Also update copyrights.
Change-ID: I93513efd0b50523a8345e7f6a33a5e4f8a2a5996
Signed-off-by: Mitch Williams <mitch.a.williams@intel.com>
Signed-off-by: Jesse Brandeburg <jesse.brandeburg@intel.com>
Tested-by: Sibai Li <sibai.li@intel.com>
Signed-off-by: Aaron Brown <aaron.f.brown@intel.com>
---
drivers/net/ethernet/intel/i40evf/i40evf.h | 6 +-
drivers/net/ethernet/intel/i40evf/i40evf_main.c | 148 ++++++++++++++++-----
.../net/ethernet/intel/i40evf/i40evf_virtchnl.c | 15 ++-
3 files changed, 130 insertions(+), 39 deletions(-)
diff --git a/drivers/net/ethernet/intel/i40evf/i40evf.h b/drivers/net/ethernet/intel/i40evf/i40evf.h
index 5e0a344..a30c4a9 100644
--- a/drivers/net/ethernet/intel/i40evf/i40evf.h
+++ b/drivers/net/ethernet/intel/i40evf/i40evf.h
@@ -164,15 +164,14 @@ struct i40evf_vlan_filter {
/* Driver state. The order of these is important! */
enum i40evf_state_t {
__I40EVF_STARTUP, /* driver loaded, probe complete */
- __I40EVF_FAILED, /* PF communication failed. Fatal. */
__I40EVF_REMOVE, /* driver is being unloaded */
__I40EVF_INIT_VERSION_CHECK, /* aq msg sent, awaiting reply */
__I40EVF_INIT_GET_RESOURCES, /* aq msg sent, awaiting reply */
__I40EVF_INIT_SW, /* got resources, setting up structs */
+ __I40EVF_RESETTING, /* in reset */
/* Below here, watchdog is running */
__I40EVF_DOWN, /* ready, can be opened */
__I40EVF_TESTING, /* in ethtool self-test */
- __I40EVF_RESETTING, /* in reset */
__I40EVF_RUNNING, /* opened, working */
};
@@ -214,6 +213,8 @@ struct i40evf_adapter {
#define I40EVF_FLAG_IMIR_ENABLED (u32)(1 << 5)
#define I40EVF_FLAG_MQ_CAPABLE (u32)(1 << 6)
#define I40EVF_FLAG_NEED_LINK_UPDATE (u32)(1 << 7)
+#define I40EVF_FLAG_PF_COMMS_FAILED (u32)(1 << 8)
+#define I40EVF_FLAG_RESET_PENDING (u32)(1 << 9)
/* duplcates for common code */
#define I40E_FLAG_FDIR_ATR_ENABLED 0
#define I40E_FLAG_DCB_ENABLED 0
@@ -231,6 +232,7 @@ struct i40evf_adapter {
#define I40EVF_FLAG_AQ_CONFIGURE_QUEUES (u32)(1 << 6)
#define I40EVF_FLAG_AQ_MAP_VECTORS (u32)(1 << 7)
#define I40EVF_FLAG_AQ_HANDLE_RESET (u32)(1 << 8)
+
/* OS defined structs */
struct net_device *netdev;
struct pci_dev *pdev;
diff --git a/drivers/net/ethernet/intel/i40evf/i40evf_main.c b/drivers/net/ethernet/intel/i40evf/i40evf_main.c
index d271d3a..fe2271e 100644
--- a/drivers/net/ethernet/intel/i40evf/i40evf_main.c
+++ b/drivers/net/ethernet/intel/i40evf/i40evf_main.c
@@ -964,16 +964,18 @@ void i40evf_down(struct i40evf_adapter *adapter)
struct net_device *netdev = adapter->netdev;
struct i40evf_mac_filter *f;
- /* remove all MAC filters from the VSI */
+ /* remove all MAC filters */
list_for_each_entry(f, &adapter->mac_filter_list, list) {
f->remove = true;
}
- adapter->aq_required |= I40EVF_FLAG_AQ_DEL_MAC_FILTER;
- /* disable receives */
- adapter->aq_required |= I40EVF_FLAG_AQ_DISABLE_QUEUES;
- mod_timer_pending(&adapter->watchdog_timer, jiffies + 1);
- msleep(20);
-
+ if (!(adapter->flags & I40EVF_FLAG_PF_COMMS_FAILED) &&
+ adapter->state != __I40EVF_RESETTING) {
+ adapter->aq_required |= I40EVF_FLAG_AQ_DEL_MAC_FILTER;
+ /* disable receives */
+ adapter->aq_required |= I40EVF_FLAG_AQ_DISABLE_QUEUES;
+ mod_timer_pending(&adapter->watchdog_timer, jiffies + 1);
+ msleep(20);
+ }
netif_tx_disable(netdev);
netif_tx_stop_all_queues(netdev);
@@ -1292,19 +1294,47 @@ static void i40evf_watchdog_task(struct work_struct *work)
watchdog_task);
struct i40e_hw *hw = &adapter->hw;
- if (adapter->state < __I40EVF_DOWN)
+ if (test_and_set_bit(__I40EVF_IN_CRITICAL_TASK, &adapter->crit_section))
+ goto restart_watchdog;
+
+ if (adapter->flags & I40EVF_FLAG_PF_COMMS_FAILED) {
+ dev_info(&adapter->pdev->dev, "Checking for redemption\n");
+ if ((rd32(hw, I40E_VFGEN_RSTAT) & 0x3) == I40E_VFR_VFACTIVE) {
+ /* A chance for redemption! */
+ dev_err(&adapter->pdev->dev, "Hardware came out of reset. Attempting reinit.\n");
+ adapter->state = __I40EVF_STARTUP;
+ adapter->flags &= ~I40EVF_FLAG_PF_COMMS_FAILED;
+ schedule_delayed_work(&adapter->init_task, 10);
+ clear_bit(__I40EVF_IN_CRITICAL_TASK,
+ &adapter->crit_section);
+ /* Don't reschedule the watchdog, since we've restarted
+ * the init task. When init_task contacts the PF and
+ * gets everything set up again, it'll restart the
+ * watchdog for us. Down, boy. Sit. Stay. Woof.
+ */
+ return;
+ }
+ adapter->aq_pending = 0;
+ adapter->aq_required = 0;
+ adapter->current_op = I40E_VIRTCHNL_OP_UNKNOWN;
goto watchdog_done;
+ }
- if (test_and_set_bit(__I40EVF_IN_CRITICAL_TASK, &adapter->crit_section))
+ if ((adapter->state < __I40EVF_DOWN) ||
+ (adapter->flags & I40EVF_FLAG_RESET_PENDING))
goto watchdog_done;
- /* check for unannounced reset */
- if ((adapter->state != __I40EVF_RESETTING) &&
+ /* check for reset */
+ if (!(adapter->flags & I40EVF_FLAG_RESET_PENDING) &&
(rd32(hw, I40E_VFGEN_RSTAT) & 0x3) != I40E_VFR_VFACTIVE) {
adapter->state = __I40EVF_RESETTING;
+ adapter->flags |= I40EVF_FLAG_RESET_PENDING;
+ dev_err(&adapter->pdev->dev, "Hardware reset detected.\n");
+ dev_info(&adapter->pdev->dev, "Scheduling reset task\n");
schedule_work(&adapter->reset_task);
- dev_info(&adapter->pdev->dev, "%s: hardware reset detected\n",
- __func__);
+ adapter->aq_pending = 0;
+ adapter->aq_required = 0;
+ adapter->current_op = I40E_VIRTCHNL_OP_UNKNOWN;
goto watchdog_done;
}
@@ -1359,13 +1389,15 @@ static void i40evf_watchdog_task(struct work_struct *work)
i40evf_irq_enable(adapter, true);
i40evf_fire_sw_int(adapter, 0xFF);
+
watchdog_done:
+ clear_bit(__I40EVF_IN_CRITICAL_TASK, &adapter->crit_section);
+restart_watchdog:
if (adapter->aq_required)
mod_timer(&adapter->watchdog_timer,
jiffies + msecs_to_jiffies(20));
else
mod_timer(&adapter->watchdog_timer, jiffies + (HZ * 2));
- clear_bit(__I40EVF_IN_CRITICAL_TASK, &adapter->crit_section);
schedule_work(&adapter->adminq_task);
}
@@ -1412,6 +1444,8 @@ static void i40evf_configure_rss(struct i40evf_adapter *adapter)
i40e_flush(hw);
}
+#define I40EVF_RESET_WAIT_MS 100
+#define I40EVF_RESET_WAIT_COUNT 200
/**
* i40evf_reset_task - Call-back task to handle hardware reset
* @work: pointer to work_struct
@@ -1422,8 +1456,9 @@ static void i40evf_configure_rss(struct i40evf_adapter *adapter)
**/
static void i40evf_reset_task(struct work_struct *work)
{
- struct i40evf_adapter *adapter =
- container_of(work, struct i40evf_adapter, reset_task);
+ struct i40evf_adapter *adapter = container_of(work,
+ struct i40evf_adapter,
+ reset_task);
struct i40e_hw *hw = &adapter->hw;
int i = 0, err;
uint32_t rstat_val;
@@ -1431,22 +1466,56 @@ static void i40evf_reset_task(struct work_struct *work)
while (test_and_set_bit(__I40EVF_IN_CRITICAL_TASK,
&adapter->crit_section))
udelay(500);
+ /* poll until we see the reset actually happen */
+ for (i = 0; i < I40EVF_RESET_WAIT_COUNT; i++) {
+ rstat_val = rd32(hw, I40E_VFGEN_RSTAT) &
+ I40E_VFGEN_RSTAT_VFR_STATE_MASK;
+ if (rstat_val != I40E_VFR_VFACTIVE) {
+ dev_info(&adapter->pdev->dev, "Reset now occurring\n");
+ break;
+ } else {
+ msleep(I40EVF_RESET_WAIT_MS);
+ }
+ }
+ if (i == I40EVF_RESET_WAIT_COUNT) {
+ dev_err(&adapter->pdev->dev, "Reset was not detected\n");
+ adapter->flags &= ~I40EVF_FLAG_RESET_PENDING;
+ goto continue_reset; /* act like the reset happened */
+ }
- /* wait until the reset is complete */
- for (i = 0; i < 20; i++) {
+ /* wait until the reset is complete and the PF is responding to us */
+ for (i = 0; i < I40EVF_RESET_WAIT_COUNT; i++) {
rstat_val = rd32(hw, I40E_VFGEN_RSTAT) &
I40E_VFGEN_RSTAT_VFR_STATE_MASK;
- if (rstat_val == I40E_VFR_COMPLETED)
+ if (rstat_val == I40E_VFR_VFACTIVE) {
+ dev_info(&adapter->pdev->dev, "Reset is complete. Reinitializing.\n");
break;
- else
- mdelay(100);
+ } else {
+ msleep(I40EVF_RESET_WAIT_MS);
+ }
}
- if (i == 20) {
+ if (i == I40EVF_RESET_WAIT_COUNT) {
/* reset never finished */
- dev_info(&adapter->pdev->dev, "%s: reset never finished: %x\n",
- __func__, rstat_val);
- /* carry on anyway */
+ dev_err(&adapter->pdev->dev, "Reset never finished (%x). PF driver is dead, and so am I.\n",
+ rstat_val);
+ adapter->flags |= I40EVF_FLAG_PF_COMMS_FAILED;
+
+ if (netif_running(adapter->netdev))
+ i40evf_close(adapter->netdev);
+
+ i40evf_free_misc_irq(adapter);
+ i40evf_reset_interrupt_capability(adapter);
+ i40evf_free_queues(adapter);
+ kfree(adapter->vf_res);
+ i40evf_shutdown_adminq(hw);
+ adapter->netdev->flags &= ~IFF_UP;
+ clear_bit(__I40EVF_IN_CRITICAL_TASK, &adapter->crit_section);
+ return; /* Do not attempt to reinit. It's dead, Jim. */
}
+
+continue_reset:
+ adapter->flags &= ~I40EVF_FLAG_RESET_PENDING;
+
i40evf_down(adapter);
adapter->state = __I40EVF_RESETTING;
@@ -1506,6 +1575,9 @@ static void i40evf_adminq_task(struct work_struct *work)
i40e_status ret;
u16 pending;
+ if (adapter->flags & I40EVF_FLAG_PF_COMMS_FAILED)
+ return;
+
event.msg_size = I40EVF_MAX_AQ_BUF_SIZE;
event.msg_buf = kzalloc(event.msg_size, GFP_KERNEL);
if (!event.msg_buf) {
@@ -1637,6 +1709,10 @@ static int i40evf_open(struct net_device *netdev)
struct i40evf_adapter *adapter = netdev_priv(netdev);
int err;
+ if (adapter->flags & I40EVF_FLAG_PF_COMMS_FAILED) {
+ dev_err(&adapter->pdev->dev, "Unable to open device due to PF driver failure.\n");
+ return -EIO;
+ }
if (adapter->state != __I40EVF_DOWN)
return -EBUSY;
@@ -1691,8 +1767,12 @@ static int i40evf_close(struct net_device *netdev)
{
struct i40evf_adapter *adapter = netdev_priv(netdev);
+ if (adapter->state <= __I40EVF_DOWN)
+ return 0;
+
/* signal that we are down to the interrupt handler */
adapter->state = __I40EVF_DOWN;
+
set_bit(__I40E_DOWN, &adapter->vsi.state);
i40evf_down(adapter);
@@ -1843,6 +1923,8 @@ static void i40evf_init_task(struct work_struct *work)
switch (adapter->state) {
case __I40EVF_STARTUP:
/* driver loaded, probe complete */
+ adapter->flags &= ~I40EVF_FLAG_PF_COMMS_FAILED;
+ adapter->flags &= ~I40EVF_FLAG_RESET_PENDING;
err = i40e_set_mac_type(hw);
if (err) {
dev_info(&pdev->dev, "%s: set_mac_type failed: %d\n",
@@ -2006,9 +2088,11 @@ static void i40evf_init_task(struct work_struct *work)
adapter->vsi.tx_itr_setting = I40E_ITR_DYNAMIC;
adapter->vsi.netdev = adapter->netdev;
- err = register_netdev(netdev);
- if (err)
- goto err_register;
+ if (!adapter->netdev_registered) {
+ err = register_netdev(netdev);
+ if (err)
+ goto err_register;
+ }
adapter->netdev_registered = true;
@@ -2032,17 +2116,16 @@ err_register:
i40evf_free_misc_irq(adapter);
err_sw_init:
i40evf_reset_interrupt_capability(adapter);
- adapter->state = __I40EVF_FAILED;
err_alloc:
kfree(adapter->vf_res);
adapter->vf_res = NULL;
err:
+ if (hw->aq.asq.count)
+ i40evf_shutdown_adminq(hw); /* ignore error */
/* Things went into the weeds, so try again later */
if (++adapter->aq_wait_count > I40EVF_AQ_MAX_ERR) {
dev_err(&pdev->dev, "Failed to communicate with PF; giving up.\n");
- if (hw->aq.asq.count)
- i40evf_shutdown_adminq(hw); /* ignore error */
- adapter->state = __I40EVF_FAILED;
+ adapter->flags |= I40EVF_FLAG_PF_COMMS_FAILED;
return; /* do not reschedule */
}
schedule_delayed_work(&adapter->init_task, HZ * 3);
@@ -2272,6 +2355,7 @@ static void i40evf_remove(struct pci_dev *pdev)
struct i40e_hw *hw = &adapter->hw;
cancel_delayed_work_sync(&adapter->init_task);
+ cancel_work_sync(&adapter->reset_task);
if (adapter->netdev_registered) {
unregister_netdev(netdev);
diff --git a/drivers/net/ethernet/intel/i40evf/i40evf_virtchnl.c b/drivers/net/ethernet/intel/i40evf/i40evf_virtchnl.c
index e6978d7..93891a1 100644
--- a/drivers/net/ethernet/intel/i40evf/i40evf_virtchnl.c
+++ b/drivers/net/ethernet/intel/i40evf/i40evf_virtchnl.c
@@ -1,7 +1,7 @@
/*******************************************************************************
*
* Intel Ethernet Controller XL710 Family Linux Virtual Function Driver
- * Copyright(c) 2013 Intel Corporation.
+ * Copyright(c) 2013 - 2014 Intel Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms and conditions of the GNU General Public License,
@@ -43,6 +43,9 @@ static int i40evf_send_pf_msg(struct i40evf_adapter *adapter,
struct i40e_hw *hw = &adapter->hw;
i40e_status err;
+ if (adapter->flags & I40EVF_FLAG_PF_COMMS_FAILED)
+ return 0; /* nothing to see here, move along */
+
err = i40e_aq_send_msg_to_pf(hw, op, 0, msg, len, NULL);
if (err)
dev_err(&adapter->pdev->dev, "Unable to send opcode %d to PF, error %d, aq status %d\n",
@@ -689,10 +692,12 @@ void i40evf_virtchnl_completion(struct i40evf_adapter *adapter,
}
break;
case I40E_VIRTCHNL_EVENT_RESET_IMPENDING:
- adapter->state = __I40EVF_RESETTING;
- schedule_work(&adapter->reset_task);
- dev_info(&adapter->pdev->dev,
- "%s: hardware reset pending\n", __func__);
+ dev_info(&adapter->pdev->dev, "PF reset warning received\n");
+ if (!(adapter->flags & I40EVF_FLAG_RESET_PENDING)) {
+ adapter->flags |= I40EVF_FLAG_RESET_PENDING;
+ dev_info(&adapter->pdev->dev, "Scheduling reset task\n");
+ schedule_work(&adapter->reset_task);
+ }
break;
default:
dev_err(&adapter->pdev->dev,
--
1.8.5.GIT
^ permalink raw reply related
* [net-next 11/15] i40evf: clean up adapter struct
From: Aaron Brown @ 2014-02-13 11:48 UTC (permalink / raw)
To: davem
Cc: Mitch Williams, netdev, gospo, sassmann, Jesse Brandeburg,
Aaron Brown
In-Reply-To: <1392292133-32120-1-git-send-email-aaron.f.brown@intel.com>
From: Mitch Williams <mitch.a.williams@intel.com>
Remove a bunch of unused structure members that are just wasting
space. Remove a completely unused info structure definition as well.
Also update copyrights.
Change-ID: I028ab92d9b7bd13a832cf3363bd1dc6610d8a535
Signed-off-by: Mitch Williams <mitch.a.williams@intel.com>
Signed-off-by: Jesse Brandeburg <jesse.brandeburg@intel.com>
Tested-by: Sibai Li <sibai.li@intel.com>
Signed-off-by: Aaron Brown <aaron.f.brown@intel.com>
---
drivers/net/ethernet/intel/i40evf/i40evf.h | 29 +----------------------------
1 file changed, 1 insertion(+), 28 deletions(-)
diff --git a/drivers/net/ethernet/intel/i40evf/i40evf.h b/drivers/net/ethernet/intel/i40evf/i40evf.h
index ff6529b..05969b3 100644
--- a/drivers/net/ethernet/intel/i40evf/i40evf.h
+++ b/drivers/net/ethernet/intel/i40evf/i40evf.h
@@ -1,7 +1,7 @@
/*******************************************************************************
*
* Intel Ethernet Controller XL710 Family Linux Virtual Function Driver
- * Copyright(c) 2013 Intel Corporation.
+ * Copyright(c) 2013 - 2014 Intel Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms and conditions of the GNU General Public License,
@@ -185,7 +185,6 @@ enum i40evf_critical_section_t {
/* board specific private data structure */
struct i40evf_adapter {
struct timer_list watchdog_timer;
- struct vlan_group *vlgrp;
struct work_struct reset_task;
struct work_struct adminq_task;
struct delayed_work init_task;
@@ -193,38 +192,19 @@ struct i40evf_adapter {
struct list_head vlan_filter_list;
char name[MAX_MSIX_COUNT][IFNAMSIZ + 9];
- /* Interrupt Throttle Rate */
- u32 itr_setting;
- u16 eitr_low;
- u16 eitr_high;
-
/* TX */
struct i40e_ring *tx_rings[I40E_MAX_VSI_QP];
- u64 restart_queue;
- u64 hw_csum_tx_good;
- u64 lsc_int;
- u64 hw_tso_ctxt;
- u64 hw_tso6_ctxt;
u32 tx_timeout_count;
struct list_head mac_filter_list;
-#ifdef DEBUG
- bool detect_tx_hung;
-#endif /* DEBUG */
/* RX */
struct i40e_ring *rx_rings[I40E_MAX_VSI_QP];
int txd_count;
int rxd_count;
u64 hw_csum_rx_error;
- u64 hw_rx_no_dma_resources;
- u64 hw_csum_rx_good;
- u64 non_eop_descs;
int num_msix_vectors;
struct msix_entry *msix_entries;
- u64 rx_hdr_split;
-
- u32 init_state;
volatile unsigned long flags;
#define I40EVF_FLAG_RX_CSUM_ENABLED (u32)(1)
#define I40EVF_FLAG_RX_1BUF_CAPABLE (u32)(1 << 1)
@@ -261,11 +241,9 @@ struct i40evf_adapter {
enum i40evf_state_t state;
volatile unsigned long crit_section;
- u64 tx_busy;
struct work_struct watchdog_task;
bool netdev_registered;
- bool dev_closed;
bool link_up;
enum i40e_virtchnl_ops current_op;
struct i40e_virtchnl_vf_resource *vf_res; /* incl. all VSIs */
@@ -276,11 +254,6 @@ struct i40evf_adapter {
u32 aq_wait_count;
};
-struct i40evf_info {
- enum i40e_mac_type mac;
- unsigned int flags;
-};
-
/* needed by i40evf_ethtool.c */
extern char i40evf_driver_name[];
--
1.8.5.GIT
^ permalink raw reply related
* [net-next 14/15] i40evf: change type of flags variable
From: Aaron Brown @ 2014-02-13 11:48 UTC (permalink / raw)
To: davem
Cc: Mitch Williams, netdev, gospo, sassmann, Jesse Brandeburg,
Dan Carpenter, Aaron Brown
In-Reply-To: <1392292133-32120-1-git-send-email-aaron.f.brown@intel.com>
From: Mitch Williams <mitch.a.williams@intel.com>
As pointed out by Dan Carpenter (from Oracle), the flags variable is
declared as a 64-bit long but all of the flags are defined as u32,
which may lead to unintended consequences. Fix this by declaring flags
as u32 (since we don't need any more than about a dozen flags right
now), and remove the volatile qualifier, since it's unnecessary and
just makes checkpatch cry.
Change-ID: I137d3bb1842bf7e9456b5929ca54e3b0ed45dcab
Signed-off-by: Mitch Williams <mitch.a.williams@intel.com>
Signed-off-by: Jesse Brandeburg <jesse.brandeburg@intel.com>
CC: Dan Carpenter <dan.carpenter@oracle.com>
Tested-by: Sibai Li <sibai.li@intel.com>
Signed-off-by: Aaron Brown <aaron.f.brown@intel.com>
---
drivers/net/ethernet/intel/i40evf/i40evf.h | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/net/ethernet/intel/i40evf/i40evf.h b/drivers/net/ethernet/intel/i40evf/i40evf.h
index 696c9d1..5e0a344 100644
--- a/drivers/net/ethernet/intel/i40evf/i40evf.h
+++ b/drivers/net/ethernet/intel/i40evf/i40evf.h
@@ -205,7 +205,7 @@ struct i40evf_adapter {
int num_msix_vectors;
struct msix_entry *msix_entries;
- volatile unsigned long flags;
+ u32 flags;
#define I40EVF_FLAG_RX_CSUM_ENABLED (u32)(1)
#define I40EVF_FLAG_RX_1BUF_CAPABLE (u32)(1 << 1)
#define I40EVF_FLAG_RX_PS_CAPABLE (u32)(1 << 2)
--
1.8.5.GIT
^ permalink raw reply related
* [net-next 13/15] i40evf: don't store unnecessary array of strings
From: Aaron Brown @ 2014-02-13 11:48 UTC (permalink / raw)
To: davem
Cc: Mitch Williams, netdev, gospo, sassmann, Jesse Brandeburg,
Aaron Brown
In-Reply-To: <1392292133-32120-1-git-send-email-aaron.f.brown@intel.com>
From: Mitch Williams <mitch.a.williams@intel.com>
Since we store the traffic vector names in the queue vector struct, we
don't need to maintain an array of strings for these names in the
adapter structure. Replace this array with a single string and use it
when allocating the misc irq vector.
Also update copyrights.
Change-ID: I664f096c3c008210d6a04a487163e8aa934fee5b
Signed-off-by: Mitch Williams <mitch.a.williams@intel.com>
Signed-off-by: Jesse Brandeburg <jesse.brandeburg@intel.com>
Tested-by: Sibai Li <sibai.li@intel.com>
Signed-off-by: Aaron Brown <aaron.f.brown@intel.com>
---
drivers/net/ethernet/intel/i40evf/i40evf.h | 2 +-
drivers/net/ethernet/intel/i40evf/i40evf_main.c | 7 ++++---
2 files changed, 5 insertions(+), 4 deletions(-)
diff --git a/drivers/net/ethernet/intel/i40evf/i40evf.h b/drivers/net/ethernet/intel/i40evf/i40evf.h
index 37f5877..696c9d1 100644
--- a/drivers/net/ethernet/intel/i40evf/i40evf.h
+++ b/drivers/net/ethernet/intel/i40evf/i40evf.h
@@ -190,7 +190,7 @@ struct i40evf_adapter {
struct delayed_work init_task;
struct i40e_q_vector *q_vector[MAX_MSIX_Q_VECTORS];
struct list_head vlan_filter_list;
- char name[MAX_MSIX_COUNT][IFNAMSIZ + 9];
+ char misc_vector_name[IFNAMSIZ + 9];
/* TX */
struct i40e_ring *tx_rings[I40E_MAX_VSI_QP];
diff --git a/drivers/net/ethernet/intel/i40evf/i40evf_main.c b/drivers/net/ethernet/intel/i40evf/i40evf_main.c
index f5caf44..d271d3a 100644
--- a/drivers/net/ethernet/intel/i40evf/i40evf_main.c
+++ b/drivers/net/ethernet/intel/i40evf/i40evf_main.c
@@ -1,7 +1,7 @@
/*******************************************************************************
*
* Intel Ethernet Controller XL710 Family Linux Virtual Function Driver
- * Copyright(c) 2013 Intel Corporation.
+ * Copyright(c) 2013 - 2014 Intel Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms and conditions of the GNU General Public License,
@@ -511,9 +511,10 @@ static int i40evf_request_misc_irq(struct i40evf_adapter *adapter)
struct net_device *netdev = adapter->netdev;
int err;
- sprintf(adapter->name[0], "i40evf:mbx");
+ sprintf(adapter->misc_vector_name, "i40evf:mbx");
err = request_irq(adapter->msix_entries[0].vector,
- &i40evf_msix_aq, 0, adapter->name[0], netdev);
+ &i40evf_msix_aq, 0,
+ adapter->misc_vector_name, netdev);
if (err) {
dev_err(&adapter->pdev->dev,
"request_irq for msix_aq failed: %d\n", err);
--
1.8.5.GIT
^ permalink raw reply related
* [net-next 07/15] i40e: set VF state to active when reset is complete
From: Aaron Brown @ 2014-02-13 11:48 UTC (permalink / raw)
To: davem
Cc: Mitch Williams, netdev, gospo, sassmann, Jesse Brandeburg,
Aaron Brown
In-Reply-To: <1392292133-32120-1-git-send-email-aaron.f.brown@intel.com>
From: Mitch Williams <mitch.a.williams@intel.com>
Without this, the VF can never communicate with the PF after a VF
reset.
Change-ID: I8d10f1d0d0638d50d39f0aff263422e05d83ad83
Signed-off-by: Mitch Williams <mitch.a.williams@intel.com>
Signed-off-by: Jesse Brandeburg <jesse.brandeburg@intel.com>
Tested-by: Sibai Li <sibai.li@intel.com>
Signed-off-by: Aaron Brown <aaron.f.brown@intel.com>
---
drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c | 1 +
1 file changed, 1 insertion(+)
diff --git a/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c b/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
index 299372b..052be06 100644
--- a/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
+++ b/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
@@ -674,6 +674,7 @@ complete_reset:
mdelay(10);
i40e_alloc_vf_res(vf);
i40e_enable_vf_mappings(vf);
+ set_bit(I40E_VF_STAT_ACTIVE, &vf->vf_states);
/* tell the VF the reset is done */
wr32(hw, I40E_VFGEN_RSTAT1(vf->vf_id), I40E_VFR_VFACTIVE);
--
1.8.5.GIT
^ permalink raw reply related
* [net-next 10/15] i40e: don't handle VF reset on unload
From: Aaron Brown @ 2014-02-13 11:48 UTC (permalink / raw)
To: davem
Cc: Mitch Williams, netdev, gospo, sassmann, Jesse Brandeburg,
Aaron Brown
In-Reply-To: <1392292133-32120-1-git-send-email-aaron.f.brown@intel.com>
From: Mitch Williams <mitch.a.williams@intel.com>
Set the DOWN flag before attempting to disable VFs when unloading the
driver. Also, don't attempt to reset the VFs when the driver is
unloading, because the switch configuration will fail. This fixes a
panic on unload when VFs are enabled.
Change-ID: I25a6567e89c9687145f510ff4f630932412c5c5d
Signed-off-by: Mitch Williams <mitch.a.williams@intel.com>
Signed-off-by: Jesse Brandeburg <jesse.brandeburg@intel.com>
Tested-by: Sibai Li <sibai.li@intel.com>
Signed-off-by: Aaron Brown <aaron.f.brown@intel.com>
---
drivers/net/ethernet/intel/i40e/i40e_main.c | 10 +++++-----
drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c | 3 ++-
2 files changed, 7 insertions(+), 6 deletions(-)
diff --git a/drivers/net/ethernet/intel/i40e/i40e_main.c b/drivers/net/ethernet/intel/i40e/i40e_main.c
index 897452d..628e917 100644
--- a/drivers/net/ethernet/intel/i40e/i40e_main.c
+++ b/drivers/net/ethernet/intel/i40e/i40e_main.c
@@ -8181,16 +8181,16 @@ static void i40e_remove(struct pci_dev *pdev)
i40e_ptp_stop(pf);
- if (pf->flags & I40E_FLAG_SRIOV_ENABLED) {
- i40e_free_vfs(pf);
- pf->flags &= ~I40E_FLAG_SRIOV_ENABLED;
- }
-
/* no more scheduling of any task */
set_bit(__I40E_DOWN, &pf->state);
del_timer_sync(&pf->service_timer);
cancel_work_sync(&pf->service_task);
+ if (pf->flags & I40E_FLAG_SRIOV_ENABLED) {
+ i40e_free_vfs(pf);
+ pf->flags &= ~I40E_FLAG_SRIOV_ENABLED;
+ }
+
i40e_fdir_teardown(pf);
/* If there is a switch structure or any orphans, remove them.
diff --git a/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c b/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
index 9074f63..7d133fa 100644
--- a/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
+++ b/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
@@ -1868,7 +1868,8 @@ int i40e_vc_process_vflr_event(struct i40e_pf *pf)
/* clear the bit in GLGEN_VFLRSTAT */
wr32(hw, I40E_GLGEN_VFLRSTAT(reg_idx), (1 << bit_idx));
- i40e_reset_vf(vf, true);
+ if (!test_bit(__I40E_DOWN, &pf->state))
+ i40e_reset_vf(vf, true);
}
}
--
1.8.5.GIT
^ permalink raw reply related
* [net-next 09/15] i40e: enable extant VFs
From: Aaron Brown @ 2014-02-13 11:48 UTC (permalink / raw)
To: davem
Cc: Mitch Williams, netdev, gospo, sassmann, Jesse Brandeburg,
Aaron Brown
In-Reply-To: <1392292133-32120-1-git-send-email-aaron.f.brown@intel.com>
From: Mitch Williams <mitch.a.williams@intel.com>
If VFs are present when the driver loads, then set up some resources
so they can function.
Change-ID: I485916a811609a9990ce663d06dc645f625b07ff
Signed-off-by: Mitch Williams <mitch.a.williams@intel.com>
Signed-off-by: Jesse Brandeburg <jesse.brandeburg@intel.com>
Tested-by: Sibai Li <sibai.li@intel.com>
Signed-off-by: Aaron Brown <aaron.f.brown@intel.com>
---
drivers/net/ethernet/intel/i40e/i40e_main.c | 10 ++++++++++
drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c | 18 ++++++++++--------
drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.h | 1 +
3 files changed, 21 insertions(+), 8 deletions(-)
diff --git a/drivers/net/ethernet/intel/i40e/i40e_main.c b/drivers/net/ethernet/intel/i40e/i40e_main.c
index 21d46f4..897452d 100644
--- a/drivers/net/ethernet/intel/i40e/i40e_main.c
+++ b/drivers/net/ethernet/intel/i40e/i40e_main.c
@@ -8076,6 +8076,16 @@ static int i40e_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
val &= ~I40E_PFGEN_PORTMDIO_NUM_VFLINK_STAT_ENA_MASK;
wr32(hw, I40E_PFGEN_PORTMDIO_NUM, val);
i40e_flush(hw);
+
+ if (pci_num_vf(pdev)) {
+ dev_info(&pdev->dev,
+ "Active VFs found, allocating resources.\n");
+ err = i40e_alloc_vfs(pf, pci_num_vf(pdev));
+ if (err)
+ dev_info(&pdev->dev,
+ "Error %d allocating resources for existing VFs\n",
+ err);
+ }
}
pfs_found++;
diff --git a/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c b/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
index 052be06..9074f63 100644
--- a/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
+++ b/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
@@ -840,7 +840,7 @@ void i40e_free_vfs(struct i40e_pf *pf)
*
* allocate vf resources
**/
-static int i40e_alloc_vfs(struct i40e_pf *pf, u16 num_alloc_vfs)
+int i40e_alloc_vfs(struct i40e_pf *pf, u16 num_alloc_vfs)
{
struct i40e_vf *vfs;
int i, ret = 0;
@@ -848,14 +848,16 @@ static int i40e_alloc_vfs(struct i40e_pf *pf, u16 num_alloc_vfs)
/* Disable interrupt 0 so we don't try to handle the VFLR. */
i40e_irq_dynamic_disable_icr0(pf);
- ret = pci_enable_sriov(pf->pdev, num_alloc_vfs);
- if (ret) {
- dev_err(&pf->pdev->dev,
- "pci_enable_sriov failed with error %d!\n", ret);
- pf->num_alloc_vfs = 0;
- goto err_iov;
+ /* Check to see if we're just allocating resources for extant VFs */
+ if (pci_num_vf(pf->pdev) != num_alloc_vfs) {
+ ret = pci_enable_sriov(pf->pdev, num_alloc_vfs);
+ if (ret) {
+ dev_err(&pf->pdev->dev,
+ "Failed to enable SR-IOV, error %d.\n", ret);
+ pf->num_alloc_vfs = 0;
+ goto err_iov;
+ }
}
-
/* allocate memory */
vfs = kzalloc(num_alloc_vfs * sizeof(struct i40e_vf), GFP_KERNEL);
if (!vfs) {
diff --git a/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.h b/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.h
index cc1feee..bedf0ba 100644
--- a/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.h
+++ b/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.h
@@ -102,6 +102,7 @@ struct i40e_vf {
void i40e_free_vfs(struct i40e_pf *pf);
int i40e_pci_sriov_configure(struct pci_dev *dev, int num_vfs);
+int i40e_alloc_vfs(struct i40e_pf *pf, u16 num_alloc_vfs);
int i40e_vc_process_vf_msg(struct i40e_pf *pf, u16 vf_id, u32 v_opcode,
u32 v_retval, u8 *msg, u16 msglen);
int i40e_vc_process_vflr_event(struct i40e_pf *pf);
--
1.8.5.GIT
^ permalink raw reply related
* [net-next 08/15] i40e: reset VFs after PF reset
From: Aaron Brown @ 2014-02-13 11:48 UTC (permalink / raw)
To: davem
Cc: Mitch Williams, netdev, gospo, sassmann, Jesse Brandeburg,
Aaron Brown
In-Reply-To: <1392292133-32120-1-git-send-email-aaron.f.brown@intel.com>
From: Mitch Williams <mitch.a.williams@intel.com>
Reset all of the VFs after a PF reset, so that they are in a known
state, and the VF driver can detect the reset and reinit itself.
Change-ID: I93c5b3a0f8b1371d0da078f92de948b9d3a6413f
Signed-off-by: Mitch Williams <mitch.a.williams@intel.com>
Signed-off-by: Jesse Brandeburg <jesse.brandeburg@intel.com>
Tested-by: Sibai Li <sibai.li@intel.com>
Signed-off-by: Aaron Brown <aaron.f.brown@intel.com>
---
drivers/net/ethernet/intel/i40e/i40e_main.c | 5 +++++
1 file changed, 5 insertions(+)
diff --git a/drivers/net/ethernet/intel/i40e/i40e_main.c b/drivers/net/ethernet/intel/i40e/i40e_main.c
index 8e44411..21d46f4 100644
--- a/drivers/net/ethernet/intel/i40e/i40e_main.c
+++ b/drivers/net/ethernet/intel/i40e/i40e_main.c
@@ -5332,6 +5332,11 @@ static void i40e_reset_and_rebuild(struct i40e_pf *pf, bool reinit)
/* restart the VSIs that were rebuilt and running before the reset */
i40e_pf_unquiesce_all_vsi(pf);
+ if (pf->num_alloc_vfs) {
+ for (v = 0; v < pf->num_alloc_vfs; v++)
+ i40e_reset_vf(&pf->vf[v], true);
+ }
+
/* tell the firmware that we're starting */
dv.major_version = DRV_VERSION_MAJOR;
dv.minor_version = DRV_VERSION_MINOR;
--
1.8.5.GIT
^ permalink raw reply related
* [net-next 12/15] i40evf: fix bogus comment
From: Aaron Brown @ 2014-02-13 11:48 UTC (permalink / raw)
To: davem
Cc: Mitch Williams, netdev, gospo, sassmann, Jesse Brandeburg,
Aaron Brown
In-Reply-To: <1392292133-32120-1-git-send-email-aaron.f.brown@intel.com>
From: Mitch Williams <mitch.a.williams@intel.com>
Locate the structure in the correct header file.
Change-ID: Ic7853131728812093a44a75d6b70953311a48dab
Signed-off-by: Mitch Williams <mitch.a.williams@intel.com>
Signed-off-by: Jesse Brandeburg <jesse.brandeburg@intel.com>
Tested-by: Sibai Li <sibai.li@intel.com>
Signed-off-by: Aaron Brown <aaron.f.brown@intel.com>
---
drivers/net/ethernet/intel/i40evf/i40evf.h | 3 +--
1 file changed, 1 insertion(+), 2 deletions(-)
diff --git a/drivers/net/ethernet/intel/i40evf/i40evf.h b/drivers/net/ethernet/intel/i40evf/i40evf.h
index 05969b3..37f5877 100644
--- a/drivers/net/ethernet/intel/i40evf/i40evf.h
+++ b/drivers/net/ethernet/intel/i40evf/i40evf.h
@@ -236,8 +236,7 @@ struct i40evf_adapter {
struct pci_dev *pdev;
struct net_device_stats net_stats;
- /* structs defined in i40e_vf.h */
- struct i40e_hw hw;
+ struct i40e_hw hw; /* defined in i40e_type.h */
enum i40evf_state_t state;
volatile unsigned long crit_section;
--
1.8.5.GIT
^ permalink raw reply related
* [net-next 01/15] i40e: spelling error
From: Aaron Brown @ 2014-02-13 11:48 UTC (permalink / raw)
To: davem; +Cc: Jesse Brandeburg, netdev, gospo, sassmann, Aaron Brown
In-Reply-To: <1392292133-32120-1-git-send-email-aaron.f.brown@intel.com>
From: Jesse Brandeburg <jesse.brandeburg@intel.com>
Fix a spelling error, s/extention/extension/.
Signed-off-by: Jesse Brandeburg <jesse.brandeburg@intel.com>
Tested-by: Kavindya Deegala <kavindya.s.deegala@intel.com>
Signed-off-by: Aaron Brown <aaron.f.brown@intel.com>
---
drivers/net/ethernet/intel/i40e/i40e_txrx.c | 2 +-
drivers/net/ethernet/intel/i40evf/i40e_txrx.c | 2 +-
2 files changed, 2 insertions(+), 2 deletions(-)
diff --git a/drivers/net/ethernet/intel/i40e/i40e_txrx.c b/drivers/net/ethernet/intel/i40e/i40e_txrx.c
index d4bb482..19af4ce 100644
--- a/drivers/net/ethernet/intel/i40e/i40e_txrx.c
+++ b/drivers/net/ethernet/intel/i40e/i40e_txrx.c
@@ -892,7 +892,7 @@ static inline void i40e_rx_checksum(struct i40e_vsi *vsi,
rx_status & (1 << I40E_RX_DESC_STATUS_L3L4P_SHIFT)))
return;
- /* likely incorrect csum if alternate IP extention headers found */
+ /* likely incorrect csum if alternate IP extension headers found */
if (rx_status & (1 << I40E_RX_DESC_STATUS_IPV6EXADD_SHIFT))
return;
diff --git a/drivers/net/ethernet/intel/i40evf/i40e_txrx.c b/drivers/net/ethernet/intel/i40evf/i40e_txrx.c
index ffdb01d..3bb7558 100644
--- a/drivers/net/ethernet/intel/i40evf/i40e_txrx.c
+++ b/drivers/net/ethernet/intel/i40evf/i40e_txrx.c
@@ -722,7 +722,7 @@ static inline void i40e_rx_checksum(struct i40e_vsi *vsi,
rx_status & (1 << I40E_RX_DESC_STATUS_L3L4P_SHIFT)))
return;
- /* likely incorrect csum if alternate IP extention headers found */
+ /* likely incorrect csum if alternate IP extension headers found */
if (rx_status & (1 << I40E_RX_DESC_STATUS_IPV6EXADD_SHIFT))
return;
--
1.8.5.GIT
^ permalink raw reply related
* [net-next 05/15] i40e: Setting i40e_down bit for tx_timeout
From: Aaron Brown @ 2014-02-13 11:48 UTC (permalink / raw)
To: davem
Cc: Akeem G Abodunrin, netdev, gospo, sassmann, Jesse Brandeburg,
Aaron Brown
In-Reply-To: <1392292133-32120-1-git-send-email-aaron.f.brown@intel.com>
From: Akeem G Abodunrin <akeem.g.abodunrin@intel.com>
If tx_timeout recovery failed, then it becomes necessary to set
i40e_down bit before actually shutdown the connection.
Change-ID: Iaac81df0e302116571827aa0cff450697fbb7fa3
Signed-off-by: Akeem G Abodunrin <akeem.g.abodunrin@intel.com>
Signed-off-by: Jesse Brandeburg <jesse.brandeburg@intel.com>
Tested-by: Kavindya Deegala <kavindya.s.deegala@intel.com>
Signed-off-by: Aaron Brown <aaron.f.brown@intel.com>
---
drivers/net/ethernet/intel/i40e/i40e_main.c | 1 +
1 file changed, 1 insertion(+)
diff --git a/drivers/net/ethernet/intel/i40e/i40e_main.c b/drivers/net/ethernet/intel/i40e/i40e_main.c
index f596f74c..8e44411 100644
--- a/drivers/net/ethernet/intel/i40e/i40e_main.c
+++ b/drivers/net/ethernet/intel/i40e/i40e_main.c
@@ -305,6 +305,7 @@ static void i40e_tx_timeout(struct net_device *netdev)
break;
default:
netdev_err(netdev, "tx_timeout recovery unsuccessful\n");
+ set_bit(__I40E_DOWN, &vsi->state);
i40e_down(vsi);
break;
}
--
1.8.5.GIT
^ permalink raw reply related
* [net-next 06/15] i40e: remove dead code
From: Aaron Brown @ 2014-02-13 11:48 UTC (permalink / raw)
To: davem
Cc: Mitch Williams, netdev, gospo, sassmann, Jesse Brandeburg,
Aaron Brown
In-Reply-To: <1392292133-32120-1-git-send-email-aaron.f.brown@intel.com>
From: Mitch Williams <mitch.a.williams@intel.com>
This looks like a cut and paste error. The code makes no sense where
it is, and accomplishes nothing. Since we've removed the goto, we can
also get rid of the extraneous brackets.
Change-ID: I9315e3eafeee0a5713c94b0dc57b58b60a849124
Signed-off-by: Mitch Williams <mitch.a.williams@intel.com>
Signed-off-by: Jesse Brandeburg <jesse.brandeburg@intel.com>
Tested-by: Sibai Li <sibai.li@intel.com>
Signed-off-by: Aaron Brown <aaron.f.brown@intel.com>
---
drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c | 10 +---------
1 file changed, 1 insertion(+), 9 deletions(-)
diff --git a/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c b/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
index b9d1c1c..299372b 100644
--- a/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
+++ b/drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c
@@ -408,18 +408,10 @@ static int i40e_alloc_vsi_res(struct i40e_vf *vf, enum i40e_vsi_type type)
"Could not allocate VF broadcast filter\n");
}
- if (!f) {
- dev_err(&pf->pdev->dev, "Unable to add ucast filter\n");
- ret = -ENOMEM;
- goto error_alloc_vsi_res;
- }
-
/* program mac filter */
ret = i40e_sync_vsi_filters(vsi);
- if (ret) {
+ if (ret)
dev_err(&pf->pdev->dev, "Unable to program ucast filters\n");
- goto error_alloc_vsi_res;
- }
error_alloc_vsi_res:
return ret;
--
1.8.5.GIT
^ permalink raw reply related
* [net-next 04/15] i40evf: clean up memsets
From: Aaron Brown @ 2014-02-13 11:48 UTC (permalink / raw)
To: davem
Cc: Mitch Williams, netdev, gospo, sassmann, Kevin Scott,
Jesse Brandeburg, Aaron Brown
In-Reply-To: <1392292133-32120-1-git-send-email-aaron.f.brown@intel.com>
From: Mitch Williams <mitch.a.williams@intel.com>
As politely pointed out by Dave Miller, calls to memset do not need a
void pointer cast. Additionally, it is preferred to use sizeof(*the
actual object) instead of sizeof(type).
Change-ID: Id6a02429b7040111531f3865ea03fbe619167cb3
Signed-off-by: Mitch Williams <mitch.a.williams@intel.com>
Signed-off-by: Kevin Scott <kevin.c.scott@intel.com>
Signed-off-by: Jesse Brandeburg <jesse.brandeburg@intel.com>
Tested-by: Kavindya Deegala <kavindya.s.deegala@intel.com>
Signed-off-by: Aaron Brown <aaron.f.brown@intel.com>
---
drivers/net/ethernet/intel/i40e/i40e_adminq.c | 5 ++---
1 file changed, 2 insertions(+), 3 deletions(-)
diff --git a/drivers/net/ethernet/intel/i40e/i40e_adminq.c b/drivers/net/ethernet/intel/i40e/i40e_adminq.c
index a50e6b3..ed3902b 100644
--- a/drivers/net/ethernet/intel/i40e/i40e_adminq.c
+++ b/drivers/net/ethernet/intel/i40e/i40e_adminq.c
@@ -647,9 +647,8 @@ static u16 i40e_clean_asq(struct i40e_hw *hw)
desc_cb = *desc;
cb_func(hw, &desc_cb);
}
- memset((void *)desc, 0, sizeof(struct i40e_aq_desc));
- memset((void *)details, 0,
- sizeof(struct i40e_asq_cmd_details));
+ memset(desc, 0, sizeof(*desc));
+ memset(details, 0, sizeof(*details));
ntc++;
if (ntc == asq->count)
ntc = 0;
--
1.8.5.GIT
^ permalink raw reply related
* [net-next 03/15] i40evf: trivial fixes
From: Aaron Brown @ 2014-02-13 11:48 UTC (permalink / raw)
To: davem; +Cc: Jesse Brandeburg, netdev, gospo, sassmann, Aaron Brown
In-Reply-To: <1392292133-32120-1-git-send-email-aaron.f.brown@intel.com>
From: Jesse Brandeburg <jesse.brandeburg@intel.com>
This change moves one operator up to the previous line and deletes
the duplicate declaration of ETH_ALEN.
Also update copyrights.
Change-ID: I88de73093b584e0f3b29d481ccd83fc4b1a1afa5
Signed-off-by: Jesse Brandeburg <jesse.brandeburg@intel.com>
Tested-by: Kavindya Deegala <kavindya.s.deegala@intel.com>
Signed-off-by: Aaron Brown <aaron.f.brown@intel.com>
---
drivers/net/ethernet/intel/i40evf/i40e_txrx.c | 6 +++---
drivers/net/ethernet/intel/i40evf/i40e_type.h | 4 +---
2 files changed, 4 insertions(+), 6 deletions(-)
diff --git a/drivers/net/ethernet/intel/i40evf/i40e_txrx.c b/drivers/net/ethernet/intel/i40evf/i40e_txrx.c
index 3bb7558..827bb5f 100644
--- a/drivers/net/ethernet/intel/i40evf/i40e_txrx.c
+++ b/drivers/net/ethernet/intel/i40evf/i40e_txrx.c
@@ -1,7 +1,7 @@
/*******************************************************************************
*
* Intel Ethernet Controller XL710 Family Linux Virtual Function Driver
- * Copyright(c) 2013 Intel Corporation.
+ * Copyright(c) 2013 - 2014 Intel Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms and conditions of the GNU General Public License,
@@ -807,8 +807,8 @@ static int i40e_clean_rx_irq(struct i40e_ring *rx_ring, int budget)
rx_desc = I40E_RX_DESC(rx_ring, i);
qword = le64_to_cpu(rx_desc->wb.qword1.status_error_len);
- rx_status = (qword & I40E_RXD_QW1_STATUS_MASK)
- >> I40E_RXD_QW1_STATUS_SHIFT;
+ rx_status = (qword & I40E_RXD_QW1_STATUS_MASK) >>
+ I40E_RXD_QW1_STATUS_SHIFT;
while (rx_status & (1 << I40E_RX_DESC_STATUS_DD_SHIFT)) {
union i40e_rx_desc *next_rxd;
diff --git a/drivers/net/ethernet/intel/i40evf/i40e_type.h b/drivers/net/ethernet/intel/i40evf/i40e_type.h
index 3bffac0..092aace 100644
--- a/drivers/net/ethernet/intel/i40evf/i40e_type.h
+++ b/drivers/net/ethernet/intel/i40evf/i40e_type.h
@@ -1,7 +1,7 @@
/*******************************************************************************
*
* Intel Ethernet Controller XL710 Family Linux Virtual Function Driver
- * Copyright(c) 2013 Intel Corporation.
+ * Copyright(c) 2013 - 2014 Intel Corporation.
*
* This program is free software; you can redistribute it and/or modify it
* under the terms and conditions of the GNU General Public License,
@@ -64,8 +64,6 @@
struct i40e_hw;
typedef void (*I40E_ADMINQ_CALLBACK)(struct i40e_hw *, struct i40e_aq_desc *);
-#define ETH_ALEN 6
-
/* Data type manipulation macros. */
#define I40E_DESC_UNUSED(R) \
--
1.8.5.GIT
^ permalink raw reply related
* [net-next 00/15] Intel Wired LAN Driver Updates
From: Aaron Brown @ 2014-02-13 11:48 UTC (permalink / raw)
To: davem; +Cc: Aaron Brown, netdev, gospo, sassmann
This series contains updates to i40e and i40evf, primarily reset
handling / refactoring along with a fair amount of minor cleanup.
Jesse fixes some spelling, bumps the version and other trivial fixes.
Akeem sets a bit that is needed before shutdown in the case of
tx_timeout recovery failure. Mitch refactors reset handling along
with a whole bunch of clean up.
Jesse Brandeburg (3):
i40e: spelling error
i40e: bump driver version
i40evf: trivial fixes
Akeem G Abodunrin (1):
i40e: Setting i40e_down bit for tx_timeout
Mitch Williams (11):
i40evf: clean up memsets
i40e: remove dead code
i40e: set VF state to active when reset is complete
i40e: reset VFs after PF reset
i40e: enable extant VFs
i40e: don't handle VF reset on unload
i40evf: clean up adapter struct
i40evf: fix bogus comment
i40evf: don't store unnecessary array of strings
i40evf: change type of flags variable
i40evf: refactor reset handling
drivers/net/ethernet/intel/i40e/i40e_adminq.c | 5 +-
drivers/net/ethernet/intel/i40e/i40e_main.c | 28 +++-
drivers/net/ethernet/intel/i40e/i40e_txrx.c | 2 +-
drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c | 32 ++---
drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.h | 1 +
drivers/net/ethernet/intel/i40evf/i40e_txrx.c | 8 +-
drivers/net/ethernet/intel/i40evf/i40e_type.h | 4 +-
drivers/net/ethernet/intel/i40evf/i40evf.h | 42 ++----
drivers/net/ethernet/intel/i40evf/i40evf_main.c | 155 ++++++++++++++++-----
.../net/ethernet/intel/i40evf/i40evf_virtchnl.c | 15 +-
10 files changed, 183 insertions(+), 109 deletions(-)
--
1.8.5.GIT
^ permalink raw reply
* [net-next 02/15] i40e: bump driver version
From: Aaron Brown @ 2014-02-13 11:48 UTC (permalink / raw)
To: davem; +Cc: Jesse Brandeburg, netdev, gospo, sassmann, Aaron Brown
In-Reply-To: <1392292133-32120-1-git-send-email-aaron.f.brown@intel.com>
From: Jesse Brandeburg <jesse.brandeburg@intel.com>
Update the driver version to 0.3.31-k.
Signed-off-by: Jesse Brandeburg <jesse.brandeburg@intel.com>
Tested-by: Kavindya Deegala <kavindya.s.deegala@intel.com>
Signed-off-by: Aaron Brown <aaron.f.brown@intel.com>
---
drivers/net/ethernet/intel/i40e/i40e_main.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/net/ethernet/intel/i40e/i40e_main.c b/drivers/net/ethernet/intel/i40e/i40e_main.c
index b901371..f596f74c 100644
--- a/drivers/net/ethernet/intel/i40e/i40e_main.c
+++ b/drivers/net/ethernet/intel/i40e/i40e_main.c
@@ -38,7 +38,7 @@ static const char i40e_driver_string[] =
#define DRV_VERSION_MAJOR 0
#define DRV_VERSION_MINOR 3
-#define DRV_VERSION_BUILD 30
+#define DRV_VERSION_BUILD 31
#define DRV_VERSION __stringify(DRV_VERSION_MAJOR) "." \
__stringify(DRV_VERSION_MINOR) "." \
__stringify(DRV_VERSION_BUILD) DRV_KERN
--
1.8.5.GIT
^ permalink raw reply related
* Re: [PATCH net-next v2 07/10] net: bcmgenet: add MDIO routines
From: Mark Rutland @ 2014-02-13 11:50 UTC (permalink / raw)
To: Florian Fainelli
Cc: netdev@vger.kernel.org, davem@davemloft.net, cernekee@gmail.com,
devicetree@vger.kernel.org
In-Reply-To: <1392269395-23513-8-git-send-email-f.fainelli@gmail.com>
On Thu, Feb 13, 2014 at 05:29:52AM +0000, Florian Fainelli wrote:
> This patch adds support for configuring the port multiplexer hardware
> which resides in front of the GENET Ethernet MAC controller. This allows
> us to support:
>
> - internal PHYs (using drivers/net/phy/bcm7xxx.c)
> - MoCA PHYs which are an entirely separate hardware block not covered
> here
> - external PHYs and switches
>
> Note that MoCA and switches are currently supported using the emulated
> "fixed PHY" driver.
>
> Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
> ---
> Changes since v1:
> - fixed MDIO crash/warning when Device Tree probing fails
> - removed the use of priv->phy_type and use priv->phy_interface
> directly
>
> drivers/net/ethernet/broadcom/genet/bcmmii.c | 481 +++++++++++++++++++++++++++
> 1 file changed, 481 insertions(+)
> create mode 100644 drivers/net/ethernet/broadcom/genet/bcmmii.c
[...]
> +static int bcmgenet_mii_of_init(struct bcmgenet_priv *priv)
> +{
> + struct device_node *dn = priv->pdev->dev.of_node;
> + struct device *kdev = &priv->pdev->dev;
> + struct device_node *mdio_dn;
> + const __be32 *fixed_link;
This looks a bit odd. Could we not have a common parser for fixed-link
properties?
> + u32 propval;
> + int ret, sz;
> +
> + mdio_dn = of_get_next_child(dn, NULL);
> + if (!mdio_dn) {
> + dev_err(kdev, "unable to find MDIO bus node\n");
> + return -ENODEV;
> + }
Could you please check that this is the node you expect (by looking at
the compatible string list).
> +
> + ret = of_mdiobus_register(priv->mii_bus, mdio_dn);
> + if (ret) {
> + dev_err(kdev, "failed to register MDIO bus\n");
> + return ret;
> + }
> +
> + /* Check if we have an internal or external PHY */
> + priv->phy_dn = of_parse_phandle(dn, "phy-handle", 0);
> + if (priv->phy_dn) {
> + if (!of_property_read_u32(priv->phy_dn, "max-speed", &propval))
> + priv->phy_speed = propval;
Is there no way to find this out without reading values directly off of
the PHY? It seems like something we should have an abstraction for.
> + } else {
> + /* Read the link speed from the fixed-link property */
> + fixed_link = of_get_property(dn, "fixed-link", &sz);
> + if (!fixed_link || sz < sizeof(*fixed_link)) {
> + ret = -ENODEV;
> + goto out;
> + }
> +
> + priv->phy_speed = be32_to_cpu(fixed_link[2]);
Similarly can we not have a common fixed-link parser? Or abstraction
such that you query the phy regardless of what it is and how its binding
represents this?
Thanks,
Mark.
^ permalink raw reply
* RE: [PATCH] usbnet: remove generic hard_header_len check
From: David Laight @ 2014-02-13 11:49 UTC (permalink / raw)
To: 'Emil Goode', Bjørn Mork
Cc: Steve Glendinning, Oliver Neukum, David S. Miller, Freddy Xin,
Eric Dumazet, Ming Lei, Paul Gortmaker, Jeff Kirsher,
Liu Junliang, Octavian Purdila, linux-usb@vger.kernel.org,
netdev@vger.kernel.org, linux-kernel@vger.kernel.org
In-Reply-To: <20140213112016.GA4245@lianli>
From: Emil Goode
> > > int rndis_rx_fixup(struct usbnet *dev, struct sk_buff *skb)
> > > {
> > > + /* This check is no longer done by usbnet */
> > > + if (skb->len < dev->net->hard_header_len)
> > > + return 0;
> > > +
> >
> > Wouldn't it be better to test against ETH_HLEN, since that is a constant
> > and "obviously correct" in this case?
>
> Some minidrivers change the default hard_header_len value so using it
> guarantees that the patch will not make any change to how the code is
> currently working. Using ETH_HLEN could be more informative about what
> the minidriver should check before passing skbs to usbnet_skb_return().
> Then I think the comment should be changed as well. My intention was to
> not make any changes that affect how the code works for devices I cannot
> test, but I think either way is fine and if you insist on changing it
> let me know.
I think that test is to ensure that the data passed to the mini-driver
contains the ethernet frame encapsulation header (this typically
contains the actual frame length and some flags) so that the minidriver
won't read off the end of the usb data.
Any check for stupidly short ethernet frames would be later on.
IIRC the absolute minimum 802.3 ethernet frame is 17 bytes
(after frame padding has been stripped).
David
^ permalink raw reply
* Re: [PATCH net-next v2 06/10] net: bcmgenet: add main driver file
From: Mark Rutland @ 2014-02-13 11:38 UTC (permalink / raw)
To: Florian Fainelli
Cc: netdev@vger.kernel.org, davem@davemloft.net, cernekee@gmail.com,
devicetree@vger.kernel.org
In-Reply-To: <1392269395-23513-7-git-send-email-f.fainelli@gmail.com>
On Thu, Feb 13, 2014 at 05:29:51AM +0000, Florian Fainelli wrote:
> This patch adds the BCMGENET main driver file which supports the
> following:
>
> - GENET hardware from V1 to V4
> - support for reading the UniMAC MIB counters statistics
> - support for the 5 transmit queues
> - support for RX/TX checksum offload and SG
>
> Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
> ---
> Changes since v1:
> - use module_platform_driver boilerplate macro
> - renamed bcmgenet_plat_drv to bcmgenet_driver
> - renamed bcmgenet_drv_{probe,remove} to bcmgenet_{probe,remove}
> - removed priv->phy_type usage and use priv->phy_interface which
> contains the exact same value
> - removed debug module parameters, unused
> - added MODULDE_{AUTHOR,ALIAS,DESCRIPTION} macros
> - remove hardcoded queue index check in bcmgenet_xmit
[...]
> +static int bcmgenet_probe(struct platform_device *pdev)
> +{
> + struct device_node *dn = pdev->dev.of_node;
> + struct bcmgenet_priv *priv;
> + struct net_device *dev;
> + const void *macaddr;
> + struct resource *r;
> + int err = -EIO;
> +
> + /* Up to GENET_MAX_MQ_CNT + 1 TX queues and a single RX queue */
> + dev = alloc_etherdev_mqs(sizeof(*priv), GENET_MAX_MQ_CNT + 1, 1);
> + if (!dev) {
> + dev_err(&pdev->dev, "can't allocate net device\n");
> + return -ENOMEM;
> + }
> +
> + priv = netdev_priv(dev);
> + priv->irq0 = platform_get_irq(pdev, 0);
> + priv->irq1 = platform_get_irq(pdev, 1);
> + if (!priv->irq0 || !priv->irq1) {
> + dev_err(&pdev->dev, "can't find IRQs\n");
> + err = -EINVAL;
> + goto err;
> + }
The binding did not describe that there were two interrupts. What are
each of them for? Are they named in the documentation?
> +
> + macaddr = of_get_mac_address(dn);
> + if (!macaddr) {
> + dev_err(&pdev->dev, "can't find MAC address\n");
> + err = -EINVAL;
> + goto err;
> + }
> +
> + r = platform_get_resource(pdev, IORESOURCE_MEM, 0);
> + priv->base = devm_request_and_ioremap(&pdev->dev, r);
> + if (!priv->base) {
> + dev_err(&pdev->dev, "can't ioremap\n");
> + err = -EINVAL;
> + goto err;
> + }
> +
> + dev->base_addr = (unsigned long)priv->base;
Does the net core actually need this?
I can't see anywhere else it's used in this file.
[...]
> + if (of_device_is_compatible(dn, "brcm,genet-v4"))
> + priv->version = GENET_V4;
> + else if (of_device_is_compatible(dn, "brcm,genet-v3"))
> + priv->version = GENET_V3;
> + else if (of_device_is_compatible(dn, "brcm,genet-v2"))
> + priv->version = GENET_V2;
> + else if (of_device_is_compatible(dn, "brcm,genet-v1"))
> + priv->version = GENET_V1;
> + else {
> + dev_err(&pdev->dev, "unknown GENET version\n");
> + err = -EINVAL;
> + goto err;
Surely you can't have probed if none of these are in the compatible
list?
Might it make more sense to place this value in of_device_id::data? You
can get it it with of_match_node, and you only have to place the strings
in one place, so no possible typo issues.
> + }
> +
> + bcmgenet_set_hw_params(priv);
> +
> + spin_lock_init(&priv->lock);
> + spin_lock_init(&priv->bh_lock);
> + mutex_init(&priv->mib_mutex);
> + /* Mii wait queue */
> + init_waitqueue_head(&priv->wq);
> + /* Always use RX_BUF_LENGTH (2KB) buffer for all chips */
> + priv->rx_buf_len = RX_BUF_LENGTH;
> + INIT_WORK(&priv->bcmgenet_irq_work, bcmgenet_irq_task);
> +
> + priv->clk = devm_clk_get(&priv->pdev->dev, "enet");
> + if (IS_ERR(priv->clk))
> + dev_warn(&priv->pdev->dev, "failed to get enet clock\n");
This wasn't in the binding.
> +
> + priv->clk_wol = devm_clk_get(&priv->pdev->dev, "enet-wol");
> + if (IS_ERR(priv->clk_wol))
> + dev_warn(&priv->pdev->dev, "failed to get enet-wol clock\n");
This is also missing from the binding.
> + /* Turn off the clocks */
> + if (!IS_ERR(priv->clk))
> + clk_disable_unprepare(priv->clk);
Either the comment is misleading (s/clocks/clock/), or you're forgetting
about the enet-wol clock here.
Thanks,
Mark.
^ permalink raw reply
* Re: [PATCH] usbnet: remove generic hard_header_len check
From: Bjørn Mork @ 2014-02-13 11:36 UTC (permalink / raw)
To: Emil Goode
Cc: Steve Glendinning, Oliver Neukum, David S. Miller, Freddy Xin,
Eric Dumazet, Ming Lei, Paul Gortmaker, Jeff Kirsher,
Liu Junliang, Octavian Purdila, linux-usb, netdev, linux-kernel
In-Reply-To: <20140213112016.GA4245@lianli>
Emil Goode <emilgoode@gmail.com> writes:
> Yes I should have put a comment in the changelog about this. All skbs that
> are passed to rx_process have their state set to rx_cleanup and just because
> the skb was cloned doesn't mean that we should free the original in a
> different way. As it is I think we are acctually missing a call to
> usb_free_urb that is called on the common rx_cleanup path.
Yes, I wondered about that as well, thinking that this part actually
should be a separate patch for net+stable.
But then I wondered how we could possibly have had a bug like that
living here for so long, and the answer is we haven't. You don't want
to free the URB. It is already resubmitted with a different skb as its
buffer. The call to usb_free_urb in the rx_cleanup path is there only
for the cases where the URB is not resubmitted. The rx_complete callback
is controlling this by updating entry->urb as appropriate. So it will
always be NULL if rx_process is called, and the call to usb_free_urb has
no effect.
Rearranging this code to always take the same cleanup path is still a
very nice cleanup IMHO.
Bjørn
^ permalink raw reply
* Re: [RFC 2/2] xen-netback: disable multicast and use a random hw MAC address
From: Ian Campbell @ 2014-02-13 11:35 UTC (permalink / raw)
To: Luis R. Rodriguez
Cc: netdev@vger.kernel.org, xen-devel, Paul Durrant, Wei Liu, kvm,
linux-kernel@vger.kernel.org
In-Reply-To: <CAB=NE6WFDWW1faoCYJP9zh6rPPvET+dbHxjHnGkYXtRx6z2LOQ@mail.gmail.com>
On Wed, 2014-02-12 at 14:05 -0800, Luis R. Rodriguez wrote:
> > I meant the PV protocol extension which allows guests (netfront) to
> > register to receive multicast frames across the PV ring -- i.e. for
> > multicast to work from the guests PoV.
>
> Not quite sure I understand, ipv6 works on guests so multicast works,
> so its unclear what you mean by multicast frames across the PV ring.
> Is there any code or or documents I can look at ?
xen/include/public/io/netif.h talks about 'feature-multicast-control'
and XEN_NETIF_EXTRA_TYPE_MCAST_{ADD,DEL}.
Looking at it now in the absence of those then flooding is the
default...
> > (maybe that was just an optimisation though and the default is to flood
> > everything, it was a long time ago)
>
> From a networking perspective everything is being flooded as I've seen
> it so far.
... which is why it works ;-)
Ian.
^ 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