forked from Minki/linux
s390/qeth: allow configuration of TX queues for IQD devices
Similar to the support for z/VM NICs, but we need to take extra care about the dedicated mcast queue: 1. netdev_pick_tx() is unaware of this limitation and might select the mcast txq. Catch this. 2. require at least _two_ TX queues - one for ucast, one for mcast. 3. when reducing the number of TX queues, there's a potential race where netdev_cap_txqueue() over-rules the selected txq index and falls back to index 0. This would place ucast traffic on the mcast queue, and result in TX errors. So for IQD, reject a reduction while the interface is running. Signed-off-by: Julian Wiedmann <jwi@linux.ibm.com> Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
parent
fcc2df8b87
commit
66cddf1019
@ -6644,9 +6644,13 @@ EXPORT_SYMBOL_GPL(qeth_get_stats64);
|
||||
u16 qeth_iqd_select_queue(struct net_device *dev, struct sk_buff *skb,
|
||||
u8 cast_type, struct net_device *sb_dev)
|
||||
{
|
||||
u16 txq;
|
||||
|
||||
if (cast_type != RTN_UNICAST)
|
||||
return QETH_IQD_MCAST_TXQ;
|
||||
return QETH_IQD_MIN_UCAST_TXQ;
|
||||
|
||||
txq = netdev_pick_tx(dev, skb, sb_dev);
|
||||
return (txq == QETH_IQD_MCAST_TXQ) ? QETH_IQD_MIN_UCAST_TXQ : txq;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(qeth_iqd_select_queue);
|
||||
|
||||
|
@ -180,14 +180,27 @@ static int qeth_set_channels(struct net_device *dev,
|
||||
{
|
||||
struct qeth_card *card = dev->ml_priv;
|
||||
|
||||
if (IS_IQD(card) || !IS_VM_NIC(card))
|
||||
return -EOPNOTSUPP;
|
||||
|
||||
if (channels->rx_count == 0 || channels->tx_count == 0)
|
||||
return -EINVAL;
|
||||
if (channels->tx_count > card->qdio.no_out_queues)
|
||||
return -EINVAL;
|
||||
|
||||
if (IS_IQD(card)) {
|
||||
if (channels->tx_count < QETH_IQD_MIN_TXQ)
|
||||
return -EINVAL;
|
||||
|
||||
/* Reject downgrade while running. It could push displaced
|
||||
* ucast flows onto txq0, which is reserved for mcast.
|
||||
*/
|
||||
if (netif_running(dev) &&
|
||||
channels->tx_count < dev->real_num_tx_queues)
|
||||
return -EPERM;
|
||||
} else {
|
||||
/* OSA still uses the legacy prio-queue mechanism: */
|
||||
if (!IS_VM_NIC(card))
|
||||
return -EOPNOTSUPP;
|
||||
}
|
||||
|
||||
return netif_set_real_num_tx_queues(dev, channels->tx_count);
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user