summaryrefslogtreecommitdiffstats
path: root/drivers/net/ppp.c
diff options
context:
space:
mode:
authorRalf Baechle <ralf@linux-mips.org>1999-01-04 16:03:48 +0000
committerRalf Baechle <ralf@linux-mips.org>1999-01-04 16:03:48 +0000
commit78c388aed2b7184182c08428db1de6c872d815f5 (patch)
tree4b2003b1b4ceb241a17faa995da8dd1004bb8e45 /drivers/net/ppp.c
parenteb7a5bf93aaa4be1d7c6181100ab7639e74d67f7 (diff)
Merge with Linux 2.1.131 and more MIPS goodies.
(Did I mention that CVS is buggy ...)
Diffstat (limited to 'drivers/net/ppp.c')
-rw-r--r--drivers/net/ppp.c56
1 files changed, 40 insertions, 16 deletions
diff --git a/drivers/net/ppp.c b/drivers/net/ppp.c
index 590a0df97..c578ba87d 100644
--- a/drivers/net/ppp.c
+++ b/drivers/net/ppp.c
@@ -4,7 +4,7 @@
* Al Longyear <longyear@netcom.com>
* Extensively rewritten by Paul Mackerras <paulus@cs.anu.edu.au>
*
- * ==FILEVERSION 980704==
+ * ==FILEVERSION 981004==
*
* NOTE TO MAINTAINERS:
* If you modify this file at all, please set the number above to the
@@ -115,6 +115,7 @@ static void ppp_receive_error(struct ppp *ppp);
static void ppp_output_wakeup(struct ppp *ppp);
static void ppp_send_ctrl(struct ppp *ppp, struct sk_buff *skb);
static void ppp_send_frame(struct ppp *ppp, struct sk_buff *skb);
+static void ppp_send_frames(struct ppp *ppp);
static struct sk_buff *ppp_vj_compress(struct ppp *ppp, struct sk_buff *skb);
static struct ppp *ppp_find (int pid_value);
@@ -439,6 +440,8 @@ ppp_tty_close (struct tty_struct *tty)
return;
if (ppp->backup_tty) {
ppp->tty = ppp->backup_tty;
+ if (ppp_tty_push(ppp))
+ ppp_output_wakeup(ppp);
} else {
ppp->tty = 0;
ppp->sc_xfer = 0;
@@ -448,7 +451,6 @@ ppp_tty_close (struct tty_struct *tty)
ppp_async_release(ppp);
ppp_release(ppp);
- ppp->inuse = 0;
MOD_DEC_USE_COUNT;
}
}
@@ -505,7 +507,6 @@ ppp_tty_read(struct tty_struct *tty, struct file *file, __u8 * buf,
if (file->f_flags & O_NONBLOCK)
break;
- current->timeout = 0;
interruptible_sleep_on(&ppp->read_wait);
err = -EINTR;
if (signal_pending(current))
@@ -1289,6 +1290,9 @@ ppp_dev_close (struct device *dev)
CHECK_PPP_MAGIC(ppp);
+ /* ppp_dev_close may be called with tbusy==1 so we must set it to 0 */
+ dev->tbusy=0;
+
MOD_DEC_USE_COUNT;
return 0;
@@ -1386,6 +1390,7 @@ ppp_ioctl(struct ppp *ppp, unsigned int param2, unsigned long param3)
break;
if (temp_i < PPP_MRU)
temp_i = PPP_MRU;
+ ppp->mru = temp_i;
if (ppp->flags & SC_DEBUG)
printk(KERN_INFO
"ppp_ioctl: set mru to %x\n", temp_i);
@@ -2112,8 +2117,8 @@ extern inline __u8 * store_long (register __u8 *p, register int value) {
/*
* Compress and send an frame to the peer.
- * Should be called with dev->tbusy == 1, having been set by the caller.
- * That is, we use dev->tbusy as a lock to prevent reentry of this
+ * Should be called with xmit_busy == 1, having been set by the caller.
+ * That is, we use xmit_busy as a lock to prevent reentry of this
* procedure.
*/
static void
@@ -2185,7 +2190,7 @@ ppp_send_frame(struct ppp *ppp, struct sk_buff *skb)
if (new_skb == NULL) {
printk(KERN_ERR "ppp_send_frame: no memory\n");
kfree_skb(skb);
- ppp->dev.tbusy = 0;
+ ppp->xmit_busy = 0;
return;
}
@@ -2214,9 +2219,9 @@ ppp_send_frame(struct ppp *ppp, struct sk_buff *skb)
ret = ppp_async_send(ppp, skb);
if (ret > 0) {
/* we can release the lock */
- ppp->dev.tbusy = 0;
+ ppp->xmit_busy = 0;
} else if (ret < 0) {
- /* this can't happen, since the caller got the tbusy lock */
+ /* can't happen, since the caller got the xmit_busy lock */
printk(KERN_ERR "ppp: ppp_async_send didn't accept pkt\n");
}
}
@@ -2275,15 +2280,18 @@ ppp_send_frames(struct ppp *ppp)
{
struct sk_buff *skb;
- while (!test_and_set_bit(0, &ppp->dev.tbusy)) {
+ while (!test_and_set_bit(0, &ppp->xmit_busy)) {
skb = skb_dequeue(&ppp->xmt_q);
if (skb == NULL) {
- ppp->dev.tbusy = 0;
- mark_bh(NET_BH);
+ ppp->xmit_busy = 0;
break;
}
ppp_send_frame(ppp, skb);
}
+ if (!ppp->xmit_busy && ppp->dev.tbusy) {
+ ppp->dev.tbusy = 0;
+ mark_bh(NET_BH);
+ }
}
/*
@@ -2295,11 +2303,11 @@ ppp_output_wakeup(struct ppp *ppp)
{
CHECK_PPP_VOID();
- if (!ppp->dev.tbusy) {
- printk(KERN_ERR "ppp_output_wakeup called but tbusy==0\n");
+ if (!ppp->xmit_busy) {
+ printk(KERN_ERR "ppp_output_wakeup called but xmit_busy==0\n");
return;
}
- ppp->dev.tbusy = 0;
+ ppp->xmit_busy = 0;
ppp_send_frames(ppp);
}
@@ -2424,9 +2432,15 @@ ppp_dev_xmit(struct sk_buff *skb, struct device *dev)
* The dev->tbusy field acts as a lock to allow only
* one packet to be processed at a time. If we can't
* get the lock, try again later.
+ * We deliberately queue as little as possible inside
+ * the ppp driver in order to minimize the latency
+ * for high-priority packets.
*/
- if (test_and_set_bit(0, &dev->tbusy))
+ if (test_and_set_bit(0, &ppp->xmit_busy)) {
+ dev->tbusy = 1; /* can't take it now */
return 1;
+ }
+ dev->tbusy = 0;
/*
* Put the 4-byte PPP header on the packet.
@@ -2440,7 +2454,8 @@ ppp_dev_xmit(struct sk_buff *skb, struct device *dev)
printk(KERN_ERR "%s: skb hdr alloc failed\n",
ppp->name);
dev_kfree_skb(skb);
- dev->tbusy = 0;
+ ppp->xmit_busy = 0;
+ ppp_send_frames(ppp);
return 0;
}
skb_reserve(new_skb, PPP_HDRLEN);
@@ -2456,6 +2471,8 @@ ppp_dev_xmit(struct sk_buff *skb, struct device *dev)
hdr[3] = proto;
ppp_send_frame(ppp, skb);
+ if (!ppp->xmit_busy)
+ ppp_send_frames(ppp);
return 0;
}
@@ -2599,6 +2616,7 @@ ppp_generic_init(struct ppp *ppp)
ppp->last_xmit = jiffies;
ppp->last_recv = jiffies;
+ ppp->xmit_busy = 0;
/* clear statistics */
memset(&ppp->stats, 0, sizeof (struct pppstat));
@@ -2639,6 +2657,12 @@ ppp_release(struct ppp *ppp)
kfree_skb(skb);
while ((skb = skb_dequeue(&ppp->xmt_q)) != NULL)
kfree_skb(skb);
+
+ ppp->inuse = 0;
+ if (ppp->dev.tbusy) {
+ ppp->dev.tbusy = 0;
+ mark_bh(NET_BH);
+ }
}
/*