Skip to content

Commit 2bdfe0b

Browse files
Stephen HemmingerDavid S. Miller
authored andcommitted
netpoll retry cleanup
The netpoll beast was still not happy. If the beast got clogged pipes, it tended to stare blankly off in space for a long time. The problem couldn't be completely fixed because the beast talked with irq's disabled. But it could be made less painful and shorter. Signed-off-by: Stephen Hemminger <[email protected]>
1 parent 6c43ff1 commit 2bdfe0b

File tree

2 files changed

+33
-39
lines changed

2 files changed

+33
-39
lines changed

include/linux/netpoll.h

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,6 @@ struct netpoll_info {
2828
atomic_t refcnt;
2929
spinlock_t poll_lock;
3030
int poll_owner;
31-
int tries;
3231
int rx_flags;
3332
spinlock_t rx_lock;
3433
struct netpoll *rx_np; /* netpoll that registered an rx_hook */

net/core/netpoll.c

Lines changed: 33 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -34,12 +34,12 @@
3434
#define MAX_UDP_CHUNK 1460
3535
#define MAX_SKBS 32
3636
#define MAX_QUEUE_DEPTH (MAX_SKBS / 2)
37-
#define MAX_RETRIES 20000
3837

3938
static struct sk_buff_head skb_pool;
4039

4140
static atomic_t trapped;
4241

42+
#define USEC_PER_POLL 50
4343
#define NETPOLL_RX_ENABLED 1
4444
#define NETPOLL_RX_DROP 2
4545

@@ -72,6 +72,7 @@ static void queue_process(void *p)
7272
schedule_delayed_work(&npinfo->tx_work, HZ/10);
7373
return;
7474
}
75+
7576
netif_tx_unlock_bh(dev);
7677
}
7778
}
@@ -244,50 +245,44 @@ static struct sk_buff *find_skb(struct netpoll *np, int len, int reserve)
244245

245246
static void netpoll_send_skb(struct netpoll *np, struct sk_buff *skb)
246247
{
247-
int status;
248-
struct netpoll_info *npinfo;
248+
int status = NETDEV_TX_BUSY;
249+
unsigned long tries;
250+
struct net_device *dev = np->dev;
251+
struct netpoll_info *npinfo = np->dev->npinfo;
252+
253+
if (!npinfo || !netif_running(dev) || !netif_device_present(dev)) {
254+
__kfree_skb(skb);
255+
return;
256+
}
257+
258+
/* don't get messages out of order, and no recursion */
259+
if ( !(np->drop == netpoll_queue && skb_queue_len(&npinfo->txq))
260+
&& npinfo->poll_owner != smp_processor_id()
261+
&& netif_tx_trylock(dev)) {
262+
263+
/* try until next clock tick */
264+
for(tries = jiffies_to_usecs(1)/USEC_PER_POLL; tries > 0; --tries) {
265+
if (!netif_queue_stopped(dev))
266+
status = dev->hard_start_xmit(skb, dev);
267+
268+
if (status == NETDEV_TX_OK)
269+
break;
249270

250-
if (!np || !np->dev || !netif_running(np->dev)) {
251-
__kfree_skb(skb);
252-
return;
253-
}
271+
/* tickle device maybe there is some cleanup */
272+
netpoll_poll(np);
254273

255-
npinfo = np->dev->npinfo;
274+
udelay(USEC_PER_POLL);
275+
}
276+
netif_tx_unlock(dev);
277+
}
256278

257-
/* avoid recursion */
258-
if (npinfo->poll_owner == smp_processor_id() ||
259-
np->dev->xmit_lock_owner == smp_processor_id()) {
279+
if (status != NETDEV_TX_OK) {
280+
/* requeue for later */
260281
if (np->drop)
261282
np->drop(skb);
262283
else
263284
__kfree_skb(skb);
264-
return;
265285
}
266-
267-
do {
268-
npinfo->tries--;
269-
netif_tx_lock(np->dev);
270-
271-
/*
272-
* network drivers do not expect to be called if the queue is
273-
* stopped.
274-
*/
275-
status = NETDEV_TX_BUSY;
276-
if (!netif_queue_stopped(np->dev))
277-
status = np->dev->hard_start_xmit(skb, np->dev);
278-
279-
netif_tx_unlock(np->dev);
280-
281-
/* success */
282-
if(!status) {
283-
npinfo->tries = MAX_RETRIES; /* reset */
284-
return;
285-
}
286-
287-
/* transmit busy */
288-
netpoll_poll(np);
289-
udelay(50);
290-
} while (npinfo->tries > 0);
291286
}
292287

293288
void netpoll_send_udp(struct netpoll *np, const char *msg, int len)
@@ -649,7 +644,7 @@ int netpoll_setup(struct netpoll *np)
649644
npinfo->rx_np = NULL;
650645
spin_lock_init(&npinfo->poll_lock);
651646
npinfo->poll_owner = -1;
652-
npinfo->tries = MAX_RETRIES;
647+
653648
spin_lock_init(&npinfo->rx_lock);
654649
skb_queue_head_init(&npinfo->arp_tx);
655650
skb_queue_head_init(&npinfo->txq);

0 commit comments

Comments
 (0)