summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGuy Martin <gmsoft@gentoo.org>2005-01-10 17:44:18 +0000
committerGuy Martin <gmsoft@gentoo.org>2005-01-10 17:44:18 +0000
commitcdca06bba0b0eab3b43cb8e19125cbbc69fef10b (patch)
treea5e3f821292ea3c03b0d06334454a8ff0b53751e /sys-kernel/hppa-sources
parentStable on sparc (diff)
downloadhistorical-cdca06bba0b0eab3b43cb8e19125cbbc69fef10b.tar.gz
historical-cdca06bba0b0eab3b43cb8e19125cbbc69fef10b.tar.bz2
historical-cdca06bba0b0eab3b43cb8e19125cbbc69fef10b.zip
Version bump. Fix security issues (#77094, #77025). Remove old sources.
Diffstat (limited to 'sys-kernel/hppa-sources')
-rw-r--r--sys-kernel/hppa-sources/ChangeLog14
-rw-r--r--sys-kernel/hppa-sources/Manifest28
-rw-r--r--sys-kernel/hppa-sources/files/AF_UNIX-security.patch24
-rw-r--r--sys-kernel/hppa-sources/files/CAN-2004-0394.patch11
-rw-r--r--sys-kernel/hppa-sources/files/CAN-2004-0495-2.4-sparse.patch655
-rw-r--r--sys-kernel/hppa-sources/files/CAN-2004-0497.patch23
-rw-r--r--sys-kernel/hppa-sources/files/CAN-2004-0535-2.4-e1000.patch12
-rw-r--r--sys-kernel/hppa-sources/files/CAN-2004-0814.patch2805
-rw-r--r--sys-kernel/hppa-sources/files/CAN-2004-0882-0883.patch97
-rw-r--r--sys-kernel/hppa-sources/files/CAN-2004-1074.patch63
-rw-r--r--sys-kernel/hppa-sources/files/CAN-2004-1235.patch303
-rw-r--r--sys-kernel/hppa-sources/files/CAN-2004-685.patch83
-rw-r--r--sys-kernel/hppa-sources/files/LKA-20050107.patch163
-rw-r--r--sys-kernel/hppa-sources/files/NFS-XDR-security.patch48
-rw-r--r--sys-kernel/hppa-sources/files/binfmt_elf-loader-security.patch72
-rw-r--r--sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.26_p6-r13
-rw-r--r--sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.26_p74
-rw-r--r--sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.26_p7-r15
-rw-r--r--sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.27_p44
-rw-r--r--sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.27_p4-r14
-rw-r--r--sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.27_p4-r24
-rw-r--r--sys-kernel/hppa-sources/files/digest-hppa-sources-2.6.10_p102
-rw-r--r--sys-kernel/hppa-sources/files/security-proc-cmdline.patch24
-rw-r--r--sys-kernel/hppa-sources/hppa-sources-2.6.10_p10.ebuild17
24 files changed, 505 insertions, 3963 deletions
diff --git a/sys-kernel/hppa-sources/ChangeLog b/sys-kernel/hppa-sources/ChangeLog
index e83c4d292dc8..3abab071a455 100644
--- a/sys-kernel/hppa-sources/ChangeLog
+++ b/sys-kernel/hppa-sources/ChangeLog
@@ -1,6 +1,18 @@
# ChangeLog for sys-kernel/hppa-sources
# Copyright 2002-2005 Gentoo Foundation; Distributed under the GPL v2
-# $Header: /var/cvsroot/gentoo-x86/sys-kernel/hppa-sources/ChangeLog,v 1.50 2005/01/09 01:45:52 gmsoft Exp $
+# $Header: /var/cvsroot/gentoo-x86/sys-kernel/hppa-sources/ChangeLog,v 1.51 2005/01/10 17:44:18 gmsoft Exp $
+
+*hppa-sources-2.6.10_p10 (10 Jan 2005)
+
+ 10 Jan 2005; Guy Martin <gmsoft@gentoo.org> -files/AF_UNIX-security.patch,
+ -files/CAN-2004-0394.patch, -files/CAN-2004-0495-2.4-sparse.patch,
+ -files/CAN-2004-0497.patch, -files/CAN-2004-0535-2.4-e1000.patch,
+ -files/CAN-2004-0814.patch, -files/CAN-2004-0882-0883.patch,
+ -files/CAN-2004-1074.patch, +files/CAN-2004-1235.patch,
+ -files/CAN-2004-685.patch, +files/LKA-20050107.patch,
+ -files/NFS-XDR-security.patch, -files/binfmt_elf-loader-security.patch,
+ -files/security-proc-cmdline.patch, +hppa-sources-2.6.10_p10.ebuild:
+ Version bump. Fix security issues (#77094, #77025). Remove old sources.
*hppa-sources-2.6.10_p6 (09 Jan 2005)
diff --git a/sys-kernel/hppa-sources/Manifest b/sys-kernel/hppa-sources/Manifest
index 02fd2d3e6a04..d5e8cfc12d6a 100644
--- a/sys-kernel/hppa-sources/Manifest
+++ b/sys-kernel/hppa-sources/Manifest
@@ -1,34 +1,20 @@
+MD5 f176b7d1c3f6ed8055e2d49209e0fa90 hppa-sources-2.6.10_p10.ebuild 781
+MD5 fbfd4f9cf611b51f445dc4d48ae0b3da ChangeLog 9407
MD5 cbcc313360e342751159394094cc7a91 hppa-sources-2.4.26_p6-r1.ebuild 2292
MD5 6065b6be713a1b35043dc723a2a4113e hppa-sources-2.4.26_p7-r1.ebuild 2788
-MD5 d8189a6d07a8c842dc8bda25932e315b hppa-sources-2.4.26_p7.ebuild 2470
-MD5 9cfa49a935c84e6fd5ac3bd761ec17a2 hppa-sources-2.4.27_p4.ebuild 2077
MD5 05ed5731534e9423f109cbec1aa7e993 metadata.xml 223
+MD5 d8189a6d07a8c842dc8bda25932e315b hppa-sources-2.4.26_p7.ebuild 2470
MD5 10fd255ebe40865f3882ba5eb379a572 hppa-sources-2.4.27_p4-r1.ebuild 2419
MD5 3acd524873881040a638ee146acab19b hppa-sources-2.4.27_p4-r2.ebuild 2482
-MD5 0a4ebd23dbdbec245c59ff529772e6ee ChangeLog 8756
MD5 dcf6adc464035c767d3183e5f7774b26 hppa-sources-2.6.10_p1.ebuild 692
MD5 074dd720871b3b04b90e6f39c3664c7c hppa-sources-2.6.10_p2.ebuild 717
MD5 ca691817130aedfb73c935b3cda1e75b hppa-sources-2.6.10_p4.ebuild 717
MD5 53ec312f4db825cb5bf2971f99f3d35f hppa-sources-2.6.10_p6.ebuild 717
-MD5 d4a740ae56c2049247083af387a22a85 files/CAN-2004-0394.patch 350
-MD5 dc18e982f8149588a291956481885a8c files/CAN-2004-0495-2.4-sparse.patch 17549
-MD5 3bdf00d5f80fe9dfbfe8220e076cd04c files/CAN-2004-0497.patch 707
-MD5 0f66013f643c79c97fda489618a4e2fd files/CAN-2004-0535-2.4-e1000.patch 476
-MD5 60d25ff310fc6abfdce39ec9e47345af files/CAN-2004-685.patch 2809
-MD5 ff11f350435d0871b62d2f7a62bc463c files/digest-hppa-sources-2.4.26_p6-r1 224
-MD5 cf38cb04fc6f56768ff1fce46e5da41c files/digest-hppa-sources-2.4.26_p7 302
-MD5 fac8b9be67d8fe295b751bbf2b6c608c files/digest-hppa-sources-2.4.26_p7-r1 378
-MD5 c449f3e3ac5fd27c7771268cb03ee5ae files/digest-hppa-sources-2.4.27_p4 302
-MD5 222e890035f4ad3152f0c2a625a9ea67 files/security-proc-cmdline.patch 693
-MD5 4b99df79dcc18b17eb41489b96ff9689 files/CAN-2004-0814.patch 81529
-MD5 2b3ddb8b8b15f8da35ade38544b57857 files/NFS-XDR-security.patch 1499
-MD5 1e1fe7bb98c80db4644f4b7fd7dd5d32 files/CAN-2004-0882-0883.patch 3434
-MD5 24c53f49954dab29cfc172d4a3ba1a31 files/binfmt_elf-loader-security.patch 1928
-MD5 c449f3e3ac5fd27c7771268cb03ee5ae files/digest-hppa-sources-2.4.27_p4-r1 302
+MD5 9cfa49a935c84e6fd5ac3bd761ec17a2 hppa-sources-2.4.27_p4.ebuild 2077
+MD5 bd7b5cad7b0cadde6daab1e2c3abd13e files/digest-hppa-sources-2.6.10_p10 132
+MD5 cd0a7533c43364e377348613c6d76bb7 files/CAN-2004-1235.patch 9736
+MD5 b4f71191d0b9bc4439cdb8645ff474a7 files/LKA-20050107.patch 6122
MD5 001b0a631c9fc28133013a1f8f78f74c files/CAN-2004-1056.patch 8458
-MD5 b0a1f80aff51d6601e8924329023b241 files/AF_UNIX-security.patch 515
-MD5 39df49f91309f3c7b23bf87194885f5d files/CAN-2004-1074.patch 1877
-MD5 c449f3e3ac5fd27c7771268cb03ee5ae files/digest-hppa-sources-2.4.27_p4-r2 302
MD5 9d48df2d294a63b45bb9159d718000a2 files/digest-hppa-sources-2.6.10_p1 131
MD5 818ff61f20404922a662b3383416b453 files/digest-hppa-sources-2.6.10_p2 131
MD5 47f5d83813a16f62c031edd2e0c1b79b files/digest-hppa-sources-2.6.10_p4 131
diff --git a/sys-kernel/hppa-sources/files/AF_UNIX-security.patch b/sys-kernel/hppa-sources/files/AF_UNIX-security.patch
deleted file mode 100644
index 6ced78404a2d..000000000000
--- a/sys-kernel/hppa-sources/files/AF_UNIX-security.patch
+++ /dev/null
@@ -1,24 +0,0 @@
---- linux-2.4.27/net/unix/af_unix.c 2004-11-24 08:23:21 -08:00
-+++ linux-2.4.28/net/unix/af_unix.c 2004-11-24 08:23:21 -08:00
-@@ -1403,9 +1403,11 @@
-
- msg->msg_namelen = 0;
-
-+ down(&sk->protinfo.af_unix.readsem);
-+
- skb = skb_recv_datagram(sk, flags, noblock, &err);
- if (!skb)
-- goto out;
-+ goto out_unlock;
-
- wake_up_interruptible(&sk->protinfo.af_unix.peer_wait);
-
-@@ -1449,6 +1451,8 @@
-
- out_free:
- skb_free_datagram(sk,skb);
-+out_unlock:
-+ up(&sk->protinfo.af_unix.readsem);
- out:
- return err;
- }
diff --git a/sys-kernel/hppa-sources/files/CAN-2004-0394.patch b/sys-kernel/hppa-sources/files/CAN-2004-0394.patch
deleted file mode 100644
index 273f1a52046f..000000000000
--- a/sys-kernel/hppa-sources/files/CAN-2004-0394.patch
+++ /dev/null
@@ -1,11 +0,0 @@
---- linux-2.4.22-oM3-orig/kernel/panic.c Tue Mar 30 15:37:18 2004
-+++ linux-2.4.22-oM3-mod/kernel/panic.c Mon May 17 18:44:01 2004
-@@ -51,7 +51,7 @@
-
- bust_spinlocks(1);
- va_start(args, fmt);
-- vsprintf(buf, fmt, args);
-+ vsnprintf(buf, sizeof(buf), fmt, args);
- va_end(args);
- printk(KERN_EMERG "Kernel panic: %s\n",buf);
- if (in_interrupt())
diff --git a/sys-kernel/hppa-sources/files/CAN-2004-0495-2.4-sparse.patch b/sys-kernel/hppa-sources/files/CAN-2004-0495-2.4-sparse.patch
deleted file mode 100644
index bea80eac69a9..000000000000
--- a/sys-kernel/hppa-sources/files/CAN-2004-0495-2.4-sparse.patch
+++ /dev/null
@@ -1,655 +0,0 @@
---- linux/net/decnet/dn_dev.c.bak Wed Jun 16 14:42:24 2004
-+++ linux/net/decnet/dn_dev.c Wed Jun 16 14:42:34 2004
-@@ -1070,31 +1070,39 @@ int dnet_gifconf(struct net_device *dev,
- {
- struct dn_dev *dn_db = (struct dn_dev *)dev->dn_ptr;
- struct dn_ifaddr *ifa;
-- struct ifreq *ifr = (struct ifreq *)buf;
-+ char buffer[DN_IFREQ_SIZE];
-+ struct ifreq *ifr = (struct ifreq *)buffer;
-+ struct sockaddr_dn *addr = (struct sockaddr_dn *)&ifr->ifr_addr;
- int done = 0;
-
- if ((dn_db == NULL) || ((ifa = dn_db->ifa_list) == NULL))
- return 0;
-
- for(; ifa; ifa = ifa->ifa_next) {
-- if (!ifr) {
-+ if (!buf) {
- done += sizeof(DN_IFREQ_SIZE);
- continue;
- }
- if (len < DN_IFREQ_SIZE)
- return done;
-- memset(ifr, 0, DN_IFREQ_SIZE);
-+ memset(buffer, 0, DN_IFREQ_SIZE);
-
- if (ifa->ifa_label)
- strcpy(ifr->ifr_name, ifa->ifa_label);
- else
- strcpy(ifr->ifr_name, dev->name);
-
-- (*(struct sockaddr_dn *) &ifr->ifr_addr).sdn_family = AF_DECnet;
-- (*(struct sockaddr_dn *) &ifr->ifr_addr).sdn_add.a_len = 2;
-- (*(dn_address *)(*(struct sockaddr_dn *) &ifr->ifr_addr).sdn_add.a_addr) = ifa->ifa_local;
-+ addr->sdn_family = AF_DECnet;
-+ addr->sdn_add.a_len = 2;
-+ memcpy(addr->sdn_add.a_addr, &ifa->ifa_local,
-+ sizeof(dn_address));
-
-- ifr = (struct ifreq *)((char *)ifr + DN_IFREQ_SIZE);
-+ if (copy_to_user(buf, buffer, DN_IFREQ_SIZE)) {
-+ done = -EFAULT;
-+ break;
-+ }
-+
-+ buf += DN_IFREQ_SIZE;
- len -= DN_IFREQ_SIZE;
- done += DN_IFREQ_SIZE;
- }
---- linux-2.4.21/drivers/net/wireless/airo.c 2003-06-13 15:51:35.000000000 +0100
-+++ linux-2.4.21/drivers/net/wireless/airo.c.plasmaroo 2004-06-24 11:09:08.260352168 +0100
-@@ -3012,19 +3012,22 @@
- size_t len,
- loff_t *offset )
- {
-- int i;
-- int pos;
-+ loff_t pos = *offset;
- struct proc_data *priv = (struct proc_data*)file->private_data;
-
-- if( !priv->rbuffer ) return -EINVAL;
-+ if (!priv->rbuffer)
-+ return -EINVAL;
-
-- pos = *offset;
-- for( i = 0; i+pos < priv->readlen && i < len; i++ ) {
-- if (put_user( priv->rbuffer[i+pos], buffer+i ))
-- return -EFAULT;
-- }
-- *offset += i;
-- return i;
-+ if (pos < 0)
-+ return -EINVAL;
-+ if (pos >= priv->readlen)
-+ return 0;
-+ if (len > priv->readlen - pos)
-+ len = priv->readlen - pos;
-+ if (copy_to_user(buffer, priv->rbuffer + pos, len))
-+ return -EFAULT;
-+ *offset = pos + len;
-+ return len;
- }
-
- /*
-@@ -3036,24 +3039,24 @@
- size_t len,
- loff_t *offset )
- {
-- int i;
-- int pos;
-+ loff_t pos = *offset;
- struct proc_data *priv = (struct proc_data*)file->private_data;
-
-- if ( !priv->wbuffer ) {
-+ if (!priv->wbuffer)
- return -EINVAL;
-- }
--
-- pos = *offset;
-
-- for( i = 0; i + pos < priv->maxwritelen &&
-- i < len; i++ ) {
-- if (get_user( priv->wbuffer[i+pos], buffer + i ))
-- return -EFAULT;
-- }
-- if ( i+pos > priv->writelen ) priv->writelen = i+file->f_pos;
-- *offset += i;
-- return i;
-+ if (pos < 0)
-+ return -EINVAL;
-+ if (pos >= priv->maxwritelen)
-+ return 0;
-+ if (len > priv->maxwritelen - pos)
-+ len = priv->maxwritelen - pos;
-+ if (copy_from_user(priv->wbuffer + pos, buffer, len))
-+ return -EFAULT;
-+ if (pos + len > priv->writelen)
-+ priv->writelen = pos + len;
-+ *offset = pos + len;
-+ return len;
- }
-
- static int proc_status_open( struct inode *inode, struct file *file ) {
---- linux/drivers/sound/mpu401.c.bak Wed Jun 16 14:42:24 2004
-+++ linux/drivers/sound/mpu401.c Wed Jun 16 14:42:34 2004
-@@ -1493,14 +1493,16 @@ static unsigned long mpu_timer_get_time(
- static int mpu_timer_ioctl(int dev, unsigned int command, caddr_t arg)
- {
- int midi_dev = sound_timer_devs[dev]->devlink;
-+ int *p = (int *)arg;
-
- switch (command)
- {
- case SNDCTL_TMR_SOURCE:
- {
- int parm;
--
-- parm = *(int *) arg;
-+
-+ if (get_user(parm, p))
-+ return -EFAULT;
- parm &= timer_caps;
-
- if (parm != 0)
-@@ -1512,7 +1514,9 @@ static int mpu_timer_ioctl(int dev, unsi
- else if (timer_mode & TMR_MODE_SMPTE)
- mpu_cmd(midi_dev, 0x3d, 0); /* Use SMPTE sync */
- }
-- return (*(int *) arg = timer_mode);
-+ if (put_user(timer_mode, p))
-+ return -EFAULT;
-+ return timer_mode;
- }
- break;
-
-@@ -1537,10 +1541,13 @@ static int mpu_timer_ioctl(int dev, unsi
- {
- int val;
-
-- val = *(int *) arg;
-+ if (get_user(val, p))
-+ return -EFAULT;
- if (val)
- set_timebase(midi_dev, val);
-- return (*(int *) arg = curr_timebase);
-+ if (put_user(curr_timebase, p))
-+ return -EFAULT;
-+ return curr_timebase;
- }
- break;
-
-@@ -1549,7 +1556,8 @@ static int mpu_timer_ioctl(int dev, unsi
- int val;
- int ret;
-
-- val = *(int *) arg;
-+ if (get_user(val, p))
-+ return -EFAULT;
-
- if (val)
- {
-@@ -1564,7 +1572,9 @@ static int mpu_timer_ioctl(int dev, unsi
- }
- curr_tempo = val;
- }
-- return (*(int *) arg = curr_tempo);
-+ if (put_user(curr_tempo, p))
-+ return -EFAULT;
-+ return curr_tempo;
- }
- break;
-
-@@ -1572,18 +1582,25 @@ static int mpu_timer_ioctl(int dev, unsi
- {
- int val;
-
-- val = *(int *) arg;
-+ if (get_user(val, p))
-+ return -EFAULT;
- if (val != 0) /* Can't change */
- return -EINVAL;
-- return (*(int *) arg = ((curr_tempo * curr_timebase) + 30) / 60);
-+ val = (curr_tempo * curr_timebase + 30) / 60;
-+ if (put_user(val, p))
-+ return -EFAULT;
-+ return val;
- }
- break;
-
- case SNDCTL_SEQ_GETTIME:
-- return (*(int *) arg = curr_ticks);
-+ if (put_user(curr_ticks, p))
-+ return -EFAULT;
-+ return curr_ticks;
-
- case SNDCTL_TMR_METRONOME:
-- metronome_mode = *(int *) arg;
-+ if (get_user(metronome_mode, p))
-+ return -EFAULT;
- setup_metronome(midi_dev);
- return 0;
-
---- linux/drivers/sound/msnd.c.bak Wed Jun 16 14:42:24 2004
-+++ linux/drivers/sound/msnd.c Wed Jun 16 14:42:34 2004
-@@ -155,13 +155,10 @@ void msnd_fifo_make_empty(msnd_fifo *f)
- f->len = f->tail = f->head = 0;
- }
-
--int msnd_fifo_write(msnd_fifo *f, const char *buf, size_t len, int user)
-+int msnd_fifo_write(msnd_fifo *f, const char *buf, size_t len)
- {
- int count = 0;
-
-- if (f->len == f->n)
-- return 0;
--
- while ((count < len) && (f->len != f->n)) {
-
- int nwritten;
-@@ -177,11 +174,7 @@ int msnd_fifo_write(msnd_fifo *f, const
- nwritten = len - count;
- }
-
-- if (user) {
-- if (copy_from_user(f->data + f->tail, buf, nwritten))
-- return -EFAULT;
-- } else
-- isa_memcpy_fromio(f->data + f->tail, (unsigned long) buf, nwritten);
-+ isa_memcpy_fromio(f->data + f->tail, (unsigned long) buf, nwritten);
-
- count += nwritten;
- buf += nwritten;
-@@ -193,13 +186,10 @@ int msnd_fifo_write(msnd_fifo *f, const
- return count;
- }
-
--int msnd_fifo_read(msnd_fifo *f, char *buf, size_t len, int user)
-+int msnd_fifo_read(msnd_fifo *f, char *buf, size_t len)
- {
- int count = 0;
-
-- if (f->len == 0)
-- return f->len;
--
- while ((count < len) && (f->len > 0)) {
-
- int nread;
-@@ -215,11 +205,7 @@ int msnd_fifo_read(msnd_fifo *f, char *b
- nread = len - count;
- }
-
-- if (user) {
-- if (copy_to_user(buf, f->data + f->head, nread))
-- return -EFAULT;
-- } else
-- isa_memcpy_toio((unsigned long) buf, f->data + f->head, nread);
-+ isa_memcpy_toio((unsigned long) buf, f->data + f->head, nread);
-
- count += nread;
- buf += nread;
---- linux/drivers/sound/msnd.h.bak Wed Jun 16 14:42:24 2004
-+++ linux/drivers/sound/msnd.h Wed Jun 16 14:42:34 2004
-@@ -266,8 +266,8 @@ void msnd_fifo_init(msnd_fifo *f);
- void msnd_fifo_free(msnd_fifo *f);
- int msnd_fifo_alloc(msnd_fifo *f, size_t n);
- void msnd_fifo_make_empty(msnd_fifo *f);
--int msnd_fifo_write(msnd_fifo *f, const char *buf, size_t len, int user);
--int msnd_fifo_read(msnd_fifo *f, char *buf, size_t len, int user);
-+int msnd_fifo_write(msnd_fifo *f, const char *buf, size_t len);
-+int msnd_fifo_read(msnd_fifo *f, char *buf, size_t len);
-
- int msnd_wait_TXDE(multisound_dev_t *dev);
- int msnd_wait_HC0(multisound_dev_t *dev);
---- linux/drivers/sound/msnd_pinnacle.c.bak Wed Jun 16 14:42:24 2004
-+++ linux/drivers/sound/msnd_pinnacle.c Wed Jun 16 14:42:34 2004
-@@ -804,7 +804,7 @@ static int dev_release(struct inode *ino
-
- static __inline__ int pack_DARQ_to_DARF(register int bank)
- {
-- register int size, n, timeout = 3;
-+ register int size, timeout = 3;
- register WORD wTmp;
- LPDAQD DAQD;
-
-@@ -825,13 +825,10 @@ static __inline__ int pack_DARQ_to_DARF(
- /* Read data from the head (unprotected bank 1 access okay
- since this is only called inside an interrupt) */
- outb(HPBLKSEL_1, dev.io + HP_BLKS);
-- if ((n = msnd_fifo_write(
-+ msnd_fifo_write(
- &dev.DARF,
- (char *)(dev.base + bank * DAR_BUFF_SIZE),
-- size, 0)) <= 0) {
-- outb(HPBLKSEL_0, dev.io + HP_BLKS);
-- return n;
-- }
-+ size);
- outb(HPBLKSEL_0, dev.io + HP_BLKS);
-
- return 1;
-@@ -853,21 +850,16 @@ static __inline__ int pack_DAPF_to_DAPQ(
- if (protect) {
- /* Critical section: protect fifo in non-interrupt */
- spin_lock_irqsave(&dev.lock, flags);
-- if ((n = msnd_fifo_read(
-+ n = msnd_fifo_read(
- &dev.DAPF,
- (char *)(dev.base + bank_num * DAP_BUFF_SIZE),
-- DAP_BUFF_SIZE, 0)) < 0) {
-- spin_unlock_irqrestore(&dev.lock, flags);
-- return n;
-- }
-+ DAP_BUFF_SIZE);
- spin_unlock_irqrestore(&dev.lock, flags);
- } else {
-- if ((n = msnd_fifo_read(
-+ n = msnd_fifo_read(
- &dev.DAPF,
- (char *)(dev.base + bank_num * DAP_BUFF_SIZE),
-- DAP_BUFF_SIZE, 0)) < 0) {
-- return n;
-- }
-+ DAP_BUFF_SIZE);
- }
- if (!n)
- break;
-@@ -894,30 +886,43 @@ static __inline__ int pack_DAPF_to_DAPQ(
- static int dsp_read(char *buf, size_t len)
- {
- int count = len;
-+ char *page = (char *)__get_free_page(PAGE_SIZE);
-+
-+ if (!page)
-+ return -ENOMEM;
-
- while (count > 0) {
-- int n;
-+ int n, k;
- unsigned long flags;
-
-+ k = PAGE_SIZE;
-+ if (k > count)
-+ k = count;
-+
- /* Critical section: protect fifo in non-interrupt */
- spin_lock_irqsave(&dev.lock, flags);
-- if ((n = msnd_fifo_read(&dev.DARF, buf, count, 1)) < 0) {
-- printk(KERN_WARNING LOGNAME ": FIFO read error\n");
-- spin_unlock_irqrestore(&dev.lock, flags);
-- return n;
-- }
-+ n = msnd_fifo_read(&dev.DARF, page, k);
- spin_unlock_irqrestore(&dev.lock, flags);
-+ if (copy_to_user(buf, page, n)) {
-+ free_page((unsigned long)page);
-+ return -EFAULT;
-+ }
- buf += n;
- count -= n;
-
-+ if (n == k && count)
-+ continue;
-+
- if (!test_bit(F_READING, &dev.flags) && dev.mode & FMODE_READ) {
- dev.last_recbank = -1;
- if (chk_send_dsp_cmd(&dev, HDEX_RECORD_START) == 0)
- set_bit(F_READING, &dev.flags);
- }
-
-- if (dev.rec_ndelay)
-+ if (dev.rec_ndelay) {
-+ free_page((unsigned long)page);
- return count == len ? -EAGAIN : len - count;
-+ }
-
- if (count > 0) {
- set_bit(F_READBLOCK, &dev.flags);
-@@ -926,41 +931,57 @@ static int dsp_read(char *buf, size_t le
- get_rec_delay_jiffies(DAR_BUFF_SIZE)))
- clear_bit(F_READING, &dev.flags);
- clear_bit(F_READBLOCK, &dev.flags);
-- if (signal_pending(current))
-+ if (signal_pending(current)) {
-+ free_page((unsigned long)page);
- return -EINTR;
-+ }
- }
- }
--
-+ free_page((unsigned long)page);
- return len - count;
- }
-
- static int dsp_write(const char *buf, size_t len)
- {
- int count = len;
-+ char *page = (char *)__get_free_page(GFP_KERNEL);
-+
-+ if (!page)
-+ return -ENOMEM;
-
- while (count > 0) {
-- int n;
-+ int n, k;
- unsigned long flags;
-
-+ k = PAGE_SIZE;
-+ if (k > count)
-+ k = count;
-+
-+ if (copy_from_user(page, buf, k)) {
-+ free_page((unsigned long)page);
-+ return -EFAULT;
-+ }
-+
- /* Critical section: protect fifo in non-interrupt */
- spin_lock_irqsave(&dev.lock, flags);
-- if ((n = msnd_fifo_write(&dev.DAPF, buf, count, 1)) < 0) {
-- printk(KERN_WARNING LOGNAME ": FIFO write error\n");
-- spin_unlock_irqrestore(&dev.lock, flags);
-- return n;
-- }
-+ n = msnd_fifo_write(&dev.DAPF, page, k);
- spin_unlock_irqrestore(&dev.lock, flags);
- buf += n;
- count -= n;
-
-+ if (count && n == k)
-+ continue;
-+
- if (!test_bit(F_WRITING, &dev.flags) && (dev.mode & FMODE_WRITE)) {
- dev.last_playbank = -1;
- if (pack_DAPF_to_DAPQ(1) > 0)
- set_bit(F_WRITING, &dev.flags);
- }
-
-- if (dev.play_ndelay)
-+ if (dev.play_ndelay) {
-+ free_page((unsigned long)page);
- return count == len ? -EAGAIN : len - count;
-+ }
-
- if (count > 0) {
- set_bit(F_WRITEBLOCK, &dev.flags);
-@@ -968,11 +989,14 @@ static int dsp_write(const char *buf, si
- &dev.writeblock,
- get_play_delay_jiffies(DAP_BUFF_SIZE));
- clear_bit(F_WRITEBLOCK, &dev.flags);
-- if (signal_pending(current))
-+ if (signal_pending(current)) {
-+ free_page((unsigned long)page);
- return -EINTR;
-+ }
- }
- }
-
-+ free_page((unsigned long)page);
- return len - count;
- }
-
---- linux/drivers/sound/pss.c.bak Wed Jun 16 14:42:24 2004
-+++ linux/drivers/sound/pss.c Wed Jun 16 14:42:34 2004
-@@ -450,20 +450,36 @@ static void pss_mixer_reset(pss_confdata
- }
- }
-
--static void arg_to_volume_mono(unsigned int volume, int *aleft)
-+static int set_volume_mono(caddr_t p, int *aleft)
- {
- int left;
-+ unsigned volume;
-+ if (get_user(volume, (unsigned *)p))
-+ return -EFAULT;
-
-- left = volume & 0x00ff;
-+ left = volume & 0xff;
- if (left > 100)
- left = 100;
- *aleft = left;
-+ return 0;
- }
-
--static void arg_to_volume_stereo(unsigned int volume, int *aleft, int *aright)
-+static int set_volume_stereo(caddr_t p, int *aleft, int *aright)
- {
-- arg_to_volume_mono(volume, aleft);
-- arg_to_volume_mono(volume >> 8, aright);
-+ int left, right;
-+ unsigned volume;
-+ if (get_user(volume, (unsigned *)p))
-+ return -EFAULT;
-+
-+ left = volume & 0xff;
-+ if (left > 100)
-+ left = 100;
-+ right = (volume >> 8) & 0xff;
-+ if (right > 100)
-+ right = 100;
-+ *aleft = left;
-+ *aright = right;
-+ return 0;
- }
-
- static int ret_vol_mono(int left)
-@@ -510,33 +526,38 @@ static int pss_mixer_ioctl (int dev, uns
- return call_ad_mixer(devc, cmd, arg);
- else
- {
-- if (*(int *)arg != 0)
-+ int v;
-+ if (get_user(v, (int *)arg))
-+ return -EFAULT;
-+ if (v != 0)
- return -EINVAL;
- return 0;
- }
- case SOUND_MIXER_VOLUME:
-- arg_to_volume_stereo(*(unsigned int *)arg, &devc->mixer.volume_l,
-- &devc->mixer.volume_r);
-+ if (set_volume_stereo(arg,
-+ &devc->mixer.volume_l,
-+ &devc->mixer.volume_r))
-+ return -EFAULT;
- set_master_volume(devc, devc->mixer.volume_l,
- devc->mixer.volume_r);
- return ret_vol_stereo(devc->mixer.volume_l,
- devc->mixer.volume_r);
-
- case SOUND_MIXER_BASS:
-- arg_to_volume_mono(*(unsigned int *)arg,
-- &devc->mixer.bass);
-+ if (set_volume_mono(arg, &devc->mixer.bass))
-+ return -EFAULT;
- set_bass(devc, devc->mixer.bass);
- return ret_vol_mono(devc->mixer.bass);
-
- case SOUND_MIXER_TREBLE:
-- arg_to_volume_mono(*(unsigned int *)arg,
-- &devc->mixer.treble);
-+ if (set_volume_mono(arg, &devc->mixer.treble))
-+ return -EFAULT;
- set_treble(devc, devc->mixer.treble);
- return ret_vol_mono(devc->mixer.treble);
-
- case SOUND_MIXER_SYNTH:
-- arg_to_volume_mono(*(unsigned int *)arg,
-- &devc->mixer.synth);
-+ if (set_volume_mono(arg, &devc->mixer.synth))
-+ return -EFAULT;
- set_synth_volume(devc, devc->mixer.synth);
- return ret_vol_mono(devc->mixer.synth);
-
-@@ -546,54 +567,67 @@ static int pss_mixer_ioctl (int dev, uns
- }
- else
- {
-+ int val, and_mask = 0, or_mask = 0;
- /*
- * Return parameters
- */
- switch (cmdf)
- {
--
- case SOUND_MIXER_DEVMASK:
- if (call_ad_mixer(devc, cmd, arg) == -EINVAL)
-- *(int *)arg = 0; /* no mixer devices */
-- return (*(int *)arg |= SOUND_MASK_VOLUME | SOUND_MASK_BASS | SOUND_MASK_TREBLE | SOUND_MASK_SYNTH);
-+ break;
-+ and_mask = ~0;
-+ or_mask = SOUND_MASK_VOLUME | SOUND_MASK_BASS | SOUND_MASK_TREBLE | SOUND_MASK_SYNTH;
-+ break;
-
- case SOUND_MIXER_STEREODEVS:
- if (call_ad_mixer(devc, cmd, arg) == -EINVAL)
-- *(int *)arg = 0; /* no stereo devices */
-- return (*(int *)arg |= SOUND_MASK_VOLUME);
-+ break;
-+ and_mask = ~0;
-+ or_mask = SOUND_MASK_VOLUME;
-+ break;
-
- case SOUND_MIXER_RECMASK:
- if (devc->ad_mixer_dev != NO_WSS_MIXER)
- return call_ad_mixer(devc, cmd, arg);
-- else
-- return (*(int *)arg = 0); /* no record devices */
-+ break;
-
- case SOUND_MIXER_CAPS:
- if (devc->ad_mixer_dev != NO_WSS_MIXER)
- return call_ad_mixer(devc, cmd, arg);
-- else
-- return (*(int *)arg = SOUND_CAP_EXCL_INPUT);
-+ or_mask = SOUND_CAP_EXCL_INPUT;
-+ break;
-
- case SOUND_MIXER_RECSRC:
- if (devc->ad_mixer_dev != NO_WSS_MIXER)
- return call_ad_mixer(devc, cmd, arg);
-- else
-- return (*(int *)arg = 0); /* no record source */
-+ break;
-
- case SOUND_MIXER_VOLUME:
-- return (*(int *)arg = ret_vol_stereo(devc->mixer.volume_l, devc->mixer.volume_r));
-+ or_mask = ret_vol_stereo(devc->mixer.volume_l, devc->mixer.volume_r);
-+ break;
-
- case SOUND_MIXER_BASS:
-- return (*(int *)arg = ret_vol_mono(devc->mixer.bass));
-+ or_mask = ret_vol_mono(devc->mixer.bass);
-+ break;
-
- case SOUND_MIXER_TREBLE:
-- return (*(int *)arg = ret_vol_mono(devc->mixer.treble));
-+ or_mask = ret_vol_mono(devc->mixer.treble);
-+ break;
-
- case SOUND_MIXER_SYNTH:
-- return (*(int *)arg = ret_vol_mono(devc->mixer.synth));
-+ or_mask = ret_vol_mono(devc->mixer.synth);
-+ break;
- default:
- return -EINVAL;
- }
-+ if (get_user(val, (int *)arg))
-+ return -EFAULT;
-+ val &= and_mask;
-+ val |= or_mask;
-+ if (put_user(val, (int *)arg))
-+ return -EFAULT;
-+ return val;
- }
- }
-
diff --git a/sys-kernel/hppa-sources/files/CAN-2004-0497.patch b/sys-kernel/hppa-sources/files/CAN-2004-0497.patch
deleted file mode 100644
index 9503e9efe57b..000000000000
--- a/sys-kernel/hppa-sources/files/CAN-2004-0497.patch
+++ /dev/null
@@ -1,23 +0,0 @@
-# ChangeSet
-#
-# fs/attr.c
-# 2004/07/03 18:28:30-03:00 marcelo@logos.cnet +1 -0
-# Thomas Biege: Fix missing DAC check on sys_chown
-#
-# fs/attr.c
-# 2004/07/03 19:28:29-03:00 marcelo@logos.cnet +1 -1
-# Add missing bracket to inode_change_ok() fix
-#
-diff -Nru a/fs/attr.c b.plasmaroo/fs/attr.c
---- a/fs/attr.c 2004-07-08 17:05:20 -07:00
-+++ b.plasmaroo/fs/attr.c 2004-07-08 17:05:20 -07:00
-@@ -35,7 +35,8 @@
-
- /* Make sure caller can chgrp. */
- if ((ia_valid & ATTR_GID) &&
-- (!in_group_p(attr->ia_gid) && attr->ia_gid != inode->i_gid) &&
-+ (current->fsuid != inode->i_uid ||
-+ (!in_group_p(attr->ia_gid) && attr->ia_gid != inode->i_gid)) &&
- !capable(CAP_CHOWN))
- goto error;
-
diff --git a/sys-kernel/hppa-sources/files/CAN-2004-0535-2.4-e1000.patch b/sys-kernel/hppa-sources/files/CAN-2004-0535-2.4-e1000.patch
deleted file mode 100644
index 669fc5fd32fb..000000000000
--- a/sys-kernel/hppa-sources/files/CAN-2004-0535-2.4-e1000.patch
+++ /dev/null
@@ -1,12 +0,0 @@
---- drivers/net/e1000/e1000_ethtool.c 2003-06-13 15:51:34.000000000 +0100
-+++ drivers/net/e1000/e1000_ethtool.c.plasmaroo 2004-06-24 11:23:32.524963976 +0100
-@@ -468,6 +468,9 @@
-
- if(copy_from_user(&regs, addr, sizeof(regs)))
- return -EFAULT;
-+ memset(regs_buff, 0, sizeof(regs_buff));
-+ if (regs.len > E1000_REGS_LEN)
-+ regs.len = E1000_REGS_LEN;
- e1000_ethtool_gregs(adapter, &regs, regs_buff);
- if(copy_to_user(addr, &regs, sizeof(regs)))
- return -EFAULT;
diff --git a/sys-kernel/hppa-sources/files/CAN-2004-0814.patch b/sys-kernel/hppa-sources/files/CAN-2004-0814.patch
deleted file mode 100644
index bf62e3540583..000000000000
--- a/sys-kernel/hppa-sources/files/CAN-2004-0814.patch
+++ /dev/null
@@ -1,2805 +0,0 @@
-diff -Nur linux-2.4.27/Documentation/tty.txt linux-2.4.27-plasmaroo/Documentation/tty.txt
---- linux-2.4.27/Documentation/tty.txt 1970-01-01 01:00:00.000000000 +0100
-+++ linux-2.4.27-plasmaroo/Documentation/tty.txt 2004-11-07 14:02:20.344653040 +0000
-@@ -0,0 +1,194 @@
-+
-+ The Lockronomicon
-+
-+Your guide to the ancient and twisted locking policies of the tty layer and
-+the warped logic behind them. Beware all ye who read on.
-+
-+FIXME: still need to work out the full set of BKL assumptions and document
-+them so they can eventually be killed off.
-+
-+
-+Line Discipline
-+---------------
-+
-+Line disciplines are registered with tty_register_ldisc() passing the
-+discipline number and the ldisc structure. At the point of registration the
-+discipline must be ready to use and it is possible it will get used before
-+the call returns success. If the call returns an error then it won't get
-+called. Do not re-use ldisc numbers as they are part of the userspace ABI
-+and writing over an existing ldisc will cause demons to eat your computer.
-+After the return the ldisc data has been copied so you may free your own
-+copy of the structure. You must not re-register over the top of the line
-+discipline even with the same data or your computer again will be eaten by
-+demons.
-+
-+In order to remove a line discipline call tty_register_ldisc passing NULL.
-+In ancient times this always worked. In modern times the function will
-+return -EBUSY if the ldisc is currently in use. Since the ldisc referencing
-+code manages the module counts this should not usually be a concern.
-+
-+Heed this warning: the reference count field of the registered copies of the
-+tty_ldisc structure in the ldisc table counts the number of lines using this
-+discipline. The reference count of the tty_ldisc structure within a tty
-+counts the number of active users of the ldisc at this instant. In effect it
-+counts the number of threads of execution within an ldisc method (plus those
-+about to enter and exit although this detail matters not).
-+
-+Line Discipline Methods
-+-----------------------
-+
-+TTY side interfaces:
-+
-+close() - This is called on a terminal when the line
-+ discipline is being unplugged. At the point of
-+ execution no further users will enter the
-+ ldisc code for this tty. Can sleep.
-+
-+open() - Called when the line discipline is attached to
-+ the terminal. No other call into the line
-+ discipline for this tty will occur until it
-+ completes successfully. Can sleep.
-+
-+write() - A process is writing data from user space
-+ through the line discipline. Multiple write calls
-+ are serialized by the tty layer for the ldisc. May
-+ sleep.
-+
-+flush_buffer() - May be called at any point between open and close.
-+
-+chars_in_buffer() - Report the number of bytes in the buffer.
-+
-+set_termios() - Called on termios structure changes. The caller
-+ passes the old termios data and the current data
-+ is in the tty. Currently can be parallel entered
-+ and ordering isn't predictable - FIXME
-+
-+read() - Move data from the line discipline to the user.
-+ Multiple read calls may occur in parallel and the
-+ ldisc must deal with serialization issues. May
-+ sleep.
-+
-+poll() - Check the status for the poll/select calls. Multiple
-+ poll calls may occur in parallel. May sleep.
-+
-+ioctl() - Called when an ioctl is handed to the tty layer
-+ that might be for the ldisc. Multiple ioctl calls
-+ may occur in parallel. May sleep.
-+
-+Driver Side Interfaces:
-+
-+receive_buf() - Hand buffers of bytes from the driver to the ldisc
-+ for processing. Semantics currently rather
-+ mysterious 8(
-+
-+receive_room() - Can be called by the driver layer at any time when
-+ the ldisc is opened. The ldisc must be able to
-+ handle the reported amount of data at that instant.
-+ Synchronization between active receive_buf and
-+ receive_room calls is down to the driver not the
-+ ldisc. Must not sleep.
-+
-+write_wakeup() - May be called at any point between open and close.
-+ The TTY_DO_WRITE_WAKEUP flag indicates if a call
-+ is needed but always races versus calls. Thus the
-+ ldisc must be careful about setting order and to
-+ handle unexpected calls. Must not sleep.
-+
-+
-+Locking
-+
-+Callers to the line discipline functions from the tty layer are required to
-+take line discipline locks. The same is true of calls from the driver side
-+but not yet enforced.
-+
-+Three calls are now provided
-+
-+ ldisc = tty_ldisc_ref(tty);
-+
-+takes a handle to the line discipline in the tty and returns it. If no ldisc
-+is currently attached or the ldisc is being closed and re-opened at this
-+point then NULL is returned. While this handle is held the ldisc will not
-+change or go away.
-+
-+ tty_ldisc_deref(ldisc)
-+
-+Returns the ldisc reference and allows the ldisc to be closed. Returning the
-+reference takes away your right to call the ldisc functions until you take
-+a new reference.
-+
-+ ldisc = tty_ldisc_ref_wait(tty);
-+
-+Performs the same function as tty_ldisc_ref except that it will wait for an
-+ldisc change to complete and then return a reference to the new ldisc.
-+
-+While these functions are slightly slower than the old code they should have
-+minimal impact as most receive logic uses the flip buffers and they only
-+need to take a reference when they push bits up through the driver.
-+
-+A caution: The ldisc->open(), ldisc->close() and driver->set_ldisc
-+functions are called with the ldisc unavailable. Thus tty_ldisc_ref will
-+fail in this situation if used within these functions. Ldisc and driver
-+code calling its own functions must be careful in this case.
-+
-+
-+Driver Interface
-+----------------
-+
-+open() - Called when a device is opened. May sleep
-+
-+close() - Called when a device is closed. At the point of
-+ return from this call the driver must make no
-+ further ldisc calls of any kind. May sleep
-+
-+write() - Called to write bytes to the device. May not
-+ sleep. May occur in parallel in special cases.
-+ Because this includes panic paths drivers generally
-+ shouldn't try and do clever locking here.
-+
-+put_char() - Stuff a single character onto the queue. The
-+ driver is guaranteed following up calls to
-+ flush_chars.
-+
-+flush_chars() - Ask the kernel to write put_char queue
-+
-+write_room() - Return the number of characters tht can be stuffed
-+ into the port buffers without overflow (or less).
-+ The ldisc is responsible for being intelligent
-+ about multi-threading of write_room/write calls
-+
-+ioctl() - Called when an ioctl may be for the driver
-+
-+set_termios() - Called on termios change, may get parallel calls,
-+ may block for now (may change that)
-+
-+set_ldisc() - Notifier for discipline change. At the point this
-+ is done the discipline is not yet usable. Can now
-+ sleep (I think)
-+
-+throttle() - Called by the ldisc to ask the driver to do flow
-+ control. Serialization including with unthrottle
-+ is the job of the ldisc layer.
-+
-+unthrottle() - Called by the ldisc to ask the driver to stop flow
-+ control.
-+
-+stop() - Ldisc notifier to the driver to stop output. As with
-+ throttle the serializations with start() are down
-+ to the ldisc layer.
-+
-+start() - Ldisc notifier to the driver to start output.
-+
-+hangup() - Ask the tty driver to cause a hangup initiated
-+ from the host side. [Can sleep ??]
-+
-+break_ctl() - Send RS232 break. Can sleep. Can get called in
-+ parallel, driver must serialize (for now), and
-+ with write calls.
-+
-+wait_until_sent() - Wait for characters to exit the hardware queue
-+ of the driver. Can sleep
-+
-+send_xchar() - Send XON/XOFF and if possible jump the queue with
-+ it in order to get fast flow control responses.
-+ Cannot sleep ??
-+
-diff -Nur linux-2.4.27/drivers/bluetooth/hci_ldisc.c linux-2.4.27-plasmaroo/drivers/bluetooth/hci_ldisc.c
---- linux-2.4.27/drivers/bluetooth/hci_ldisc.c 2004-08-08 00:26:04.000000000 +0100
-+++ linux-2.4.27-plasmaroo/drivers/bluetooth/hci_ldisc.c 2004-11-07 14:02:20.343653192 +0000
-@@ -181,6 +181,7 @@
- {
- struct hci_uart *hu = (struct hci_uart *) hdev->driver_data;
- struct tty_struct *tty = hu->tty;
-+ struct tty_ldisc *ld = tty_ldisc_ref(tty);
-
- BT_DBG("hdev %p tty %p", hdev, tty);
-
-@@ -188,9 +189,11 @@
- kfree_skb(hu->tx_skb); hu->tx_skb = NULL;
- }
-
-- /* Flush any pending characters in the driver and discipline. */
-- if (tty->ldisc.flush_buffer)
-- tty->ldisc.flush_buffer(tty);
-+ if (ld) {
-+ if(ld->flush_buffer)
-+ ld->flush_buffer(tty);
-+ tty_ldisc_deref(ld);
-+ }
-
- if (tty->driver.flush_buffer)
- tty->driver.flush_buffer(tty);
-@@ -283,7 +286,9 @@
-
- spin_lock_init(&hu->rx_lock);
-
-- /* Flush any pending characters in the driver and line discipline */
-+ /* Flush any pending characters in the driver and line discipline. */
-+ /* FIXME: why is this needed. Note don't use ldisc_ref here as the
-+ open path is before the ldisc is referencable */
- if (tty->ldisc.flush_buffer)
- tty->ldisc.flush_buffer(tty);
-
-diff -Nur linux-2.4.27/drivers/char/amiserial.c linux-2.4.27-plasmaroo/drivers/char/amiserial.c
---- linux-2.4.27/drivers/char/amiserial.c 2002-11-28 23:53:12.000000000 +0000
-+++ linux-2.4.27-plasmaroo/drivers/char/amiserial.c 2004-11-07 14:02:20.143683592 +0000
-@@ -575,9 +575,7 @@
- return;
-
- if (test_and_clear_bit(RS_EVENT_WRITE_WAKEUP, &info->event)) {
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
-+ tty_wakeup(tty);
- wake_up_interruptible(&tty->write_wait);
- }
- }
-@@ -1041,9 +1039,7 @@
- info->xmit.head = info->xmit.tail = 0;
- restore_flags(flags);
- wake_up_interruptible(&tty->write_wait);
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
-+ tty_wakeup(tty);
- }
-
- /*
-@@ -1526,6 +1522,7 @@
- struct async_struct * info = (struct async_struct *)tty->driver_data;
- struct serial_state *state;
- unsigned long flags;
-+ struct tty_ldisc *ld;
-
- if (!info || serial_paranoia_check(info, tty->device, "rs_close"))
- return;
-@@ -1608,8 +1605,12 @@
- shutdown(info);
- if (tty->driver.flush_buffer)
- tty->driver.flush_buffer(tty);
-- if (tty->ldisc.flush_buffer)
-- tty->ldisc.flush_buffer(tty);
-+ ld = tty_ldisc_ref(tty);
-+ if (ld != NULL) {
-+ if (ld->flush_buffer)
-+ ld->flush_buffer(tty);
-+ tty_ldisc_deref(ld);
-+ }
- tty->closing = 0;
- info->event = 0;
- info->tty = 0;
-diff -Nur linux-2.4.27/drivers/char/cyclades.c linux-2.4.27-plasmaroo/drivers/char/cyclades.c
---- linux-2.4.27/drivers/char/cyclades.c 2003-06-13 15:51:32.000000000 +0100
-+++ linux-2.4.27-plasmaroo/drivers/char/cyclades.c 2004-11-07 14:02:20.157681464 +0000
-@@ -1000,10 +1000,7 @@
- wake_up_interruptible(&info->delta_msr_wait);
- }
- if (test_and_clear_bit(Cy_EVENT_WRITE_WAKEUP, &info->event)) {
-- if((tty->flags & (1<< TTY_DO_WRITE_WAKEUP))
-- && tty->ldisc.write_wakeup){
-- (tty->ldisc.write_wakeup)(tty);
-- }
-+ tty_wakeup(tty);
- wake_up_interruptible(&tty->write_wait);
- }
- #ifdef Z_WAKE
-@@ -2801,6 +2798,7 @@
- cy_close(struct tty_struct *tty, struct file *filp)
- {
- struct cyclades_port *info = (struct cyclades_port *)tty->driver_data;
-+ struct tty_ldisc *ld;
- unsigned long flags;
-
- #ifdef CY_DEBUG_OTHER
-@@ -2918,8 +2916,13 @@
- shutdown(info);
- if (tty->driver.flush_buffer)
- tty->driver.flush_buffer(tty);
-- if (tty->ldisc.flush_buffer)
-- tty->ldisc.flush_buffer(tty);
-+
-+ ld = tty_ldisc_ref(tty);
-+ if (ld) {
-+ if (ld->flush_buffer)
-+ ld->flush_buffer(tty);
-+ tty_ldisc_deref(ld);
-+ }
- CY_LOCK(info, flags);
-
- tty->closing = 0;
-@@ -4689,10 +4692,8 @@
- }
- CY_UNLOCK(info, flags);
- }
-+ tty_wakeup(tty);
- wake_up_interruptible(&tty->write_wait);
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP))
-- && tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
- } /* cy_flush_buffer */
-
-
-diff -Nur linux-2.4.27/drivers/char/dz.c linux-2.4.27-plasmaroo/drivers/char/dz.c
---- linux-2.4.27/drivers/char/dz.c 2004-02-18 13:36:31.000000000 +0000
-+++ linux-2.4.27-plasmaroo/drivers/char/dz.c 2004-11-07 14:02:20.289661400 +0000
-@@ -1112,10 +1112,10 @@
- info->event = 0;
- info->tty = 0;
-
-- if (tty->ldisc.num != ldiscs[N_TTY].num) {
-+ if (tty->ldisc.num != N_TTY) {
- if (tty->ldisc.close)
- (tty->ldisc.close) (tty);
-- tty->ldisc = ldiscs[N_TTY];
-+ tty->ldisc = *(tty_ldisc_get(N_TTY));
- tty->termios->c_line = N_TTY;
- if (tty->ldisc.open)
- (tty->ldisc.open) (tty);
-diff -Nur linux-2.4.27/drivers/char/epca.c linux-2.4.27-plasmaroo/drivers/char/epca.c
---- linux-2.4.27/drivers/char/epca.c 2003-06-13 15:51:33.000000000 +0100
-+++ linux-2.4.27-plasmaroo/drivers/char/epca.c 2004-11-07 14:02:20.182677664 +0000
-@@ -524,6 +524,7 @@
-
- if ((ch = verifyChannel(tty)) != NULL)
- { /* Begin if ch != NULL */
-+ struct tty_ldisc *ld;
-
- save_flags(flags);
- cli();
-@@ -585,8 +586,12 @@
- if (tty->driver.flush_buffer)
- tty->driver.flush_buffer(tty);
-
-- if (tty->ldisc.flush_buffer)
-- tty->ldisc.flush_buffer(tty);
-+ ld = tty_ldisc_ref(tty);
-+ if (ld != NULL) {
-+ if(ld->flush_buffer)
-+ ld->flush_buffer(tty);
-+ tty_ldisc_deref(ld);
-+ }
-
- shutdown(ch);
- tty->closing = 0;
-@@ -687,12 +692,20 @@
- { /* Begin if ch != NULL */
-
- unsigned long flags;
-+ struct tty_ldisc *ld;
-
- save_flags(flags);
- cli();
- if (tty->driver.flush_buffer)
- tty->driver.flush_buffer(tty);
-
-+ ld = tty_ldisc_ref(tty);
-+ if (ld != NULL) {
-+ if (ld->flush_buffer)
-+ ld->flush_buffer(tty);
-+ tty_ldisc_deref(ld);
-+ }
-+
- if (tty->ldisc.flush_buffer)
- tty->ldisc.flush_buffer(tty);
-
-@@ -1176,8 +1189,7 @@
- restore_flags(flags);
-
- wake_up_interruptible(&tty->write_wait);
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) && tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
-+ tty_wakeup(tty);
-
- } /* End pc_flush_buffer */
-
-@@ -2383,9 +2395,7 @@
- { /* Begin if LOWWAIT */
-
- ch->statusflags &= ~LOWWAIT;
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
-+ tty_wakeup(tty);
- wake_up_interruptible(&tty->write_wait);
-
- } /* End if LOWWAIT */
-@@ -2402,9 +2412,7 @@
- { /* Begin if EMPTYWAIT */
-
- ch->statusflags &= ~EMPTYWAIT;
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
-+ tty_wakeup(tty);
-
- wake_up_interruptible(&tty->write_wait);
-
-@@ -3255,6 +3263,7 @@
- }
- else
- {
-+ /* ldisc lock already held in ioctl */
- if (tty->ldisc.flush_buffer)
- tty->ldisc.flush_buffer(tty);
- }
-diff -Nur linux-2.4.27/drivers/char/generic_serial.c linux-2.4.27-plasmaroo/drivers/char/generic_serial.c
---- linux-2.4.27/drivers/char/generic_serial.c 2002-11-28 23:53:12.000000000 +0000
-+++ linux-2.4.27-plasmaroo/drivers/char/generic_serial.c 2004-11-07 14:02:20.187676904 +0000
-@@ -440,9 +440,7 @@
- restore_flags(flags);
-
- wake_up_interruptible(&tty->write_wait);
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
-+ tty_wakeup(tty);
- func_exit ();
- }
-
-@@ -582,9 +580,7 @@
- if (!tty) return;
-
- if (test_and_clear_bit(RS_EVENT_WRITE_WAKEUP, &port->event)) {
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
-+ tty_wakeup(tty);
- wake_up_interruptible(&tty->write_wait);
- }
- func_exit ();
-@@ -729,8 +725,9 @@
- {
- unsigned long flags;
- struct gs_port *port;
--
-- func_enter ();
-+ struct tty_ldisc *ld;
-+
-+ func_enter();
-
- if (!tty) return;
-
-@@ -803,8 +800,12 @@
-
- if (tty->driver.flush_buffer)
- tty->driver.flush_buffer(tty);
-- if (tty->ldisc.flush_buffer)
-- tty->ldisc.flush_buffer(tty);
-+ ld = tty_ldisc_ref(tty);
-+ if (ld != NULL) {
-+ if (ld->flush_buffer)
-+ ld->flush_buffer(tty);
-+ tty_ldisc_deref(ld);
-+ }
- tty->closing = 0;
-
- port->event = 0;
-diff -Nur linux-2.4.27/drivers/char/isicom.c linux-2.4.27-plasmaroo/drivers/char/isicom.c
---- linux-2.4.27/drivers/char/isicom.c 2003-06-13 15:51:33.000000000 +0100
-+++ linux-2.4.27-plasmaroo/drivers/char/isicom.c 2004-11-07 14:02:20.195675688 +0000
-@@ -502,10 +502,8 @@
-
- if (!tty)
- return;
--
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
-+
-+ tty_wakeup(tty);
- wake_up_interruptible(&tty->write_wait);
- }
-
-@@ -1144,6 +1142,7 @@
- struct isi_port * port = (struct isi_port *) tty->driver_data;
- struct isi_board * card = port->card;
- unsigned long flags;
-+ struct tty_ldisc *ld;
-
- if (!port)
- return;
-@@ -1199,6 +1198,12 @@
- isicom_shutdown_port(port);
- if (tty->driver.flush_buffer)
- tty->driver.flush_buffer(tty);
-+ ld = tty_ldisc_ref(tty);
-+ if (ld != NULL) {
-+ if (ld->flush_buffer)
-+ ld->flush_buffer(tty);
-+ tty_ldisc_deref(ld);
-+ }
- if (tty->ldisc.flush_buffer)
- tty->ldisc.flush_buffer(tty);
- tty->closing = 0;
-@@ -1671,9 +1676,7 @@
- restore_flags(flags);
-
- wake_up_interruptible(&tty->write_wait);
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
-+ tty_wakeup(tty);
- }
-
-
-diff -Nur linux-2.4.27/drivers/char/moxa.c linux-2.4.27-plasmaroo/drivers/char/moxa.c
---- linux-2.4.27/drivers/char/moxa.c 2001-10-25 21:53:47.000000000 +0100
-+++ linux-2.4.27-plasmaroo/drivers/char/moxa.c 2004-11-07 14:02:20.200674928 +0000
-@@ -620,6 +620,7 @@
- {
- struct moxa_str *ch;
- int port;
-+ struct tty_ldisc *ld;
-
- port = PORTNO(tty);
- if (port == MAX_PORTS) {
-@@ -677,8 +678,13 @@
-
- if (tty->driver.flush_buffer)
- tty->driver.flush_buffer(tty);
-- if (tty->ldisc.flush_buffer)
-- tty->ldisc.flush_buffer(tty);
-+
-+ ld = tty_ldisc_ref(tty);
-+ if (ld != NULL) {
-+ if (ld->flush_buffer)
-+ ld->flush_buffer(tty);
-+ tty_ldisc_deref(ld);
-+ }
- tty->closing = 0;
- ch->event = 0;
- ch->tty = 0;
-@@ -754,9 +760,7 @@
- if (ch == NULL)
- return;
- MoxaPortFlushData(ch->port, 1);
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup) (tty);
-+ tty_wakeup(tty);
- wake_up_interruptible(&tty->write_wait);
- }
-
-@@ -992,7 +996,6 @@
- moxaTimer.function = moxa_poll;
- moxaTimer.expires = jiffies + (HZ / 50);
- moxaTimer_on = 1;
-- add_timer(&moxaTimer);
- return;
- }
- for (card = 0; card < MAX_BOARDS; card++) {
-@@ -1011,9 +1014,7 @@
- if (MoxaPortTxQueue(ch->port) <= WAKEUP_CHARS) {
- if (!tp->stopped) {
- ch->statusflags &= ~LOWWAIT;
-- if ((tp->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tp->ldisc.write_wakeup)
-- (tp->ldisc.write_wakeup) (tp);
-+ tty_wakeup(tp);
- wake_up_interruptible(&tp->write_wait);
- }
- }
-@@ -1203,9 +1204,7 @@
- if (ch->tty && (ch->statusflags & EMPTYWAIT)) {
- if (MoxaPortTxQueue(ch->port) == 0) {
- ch->statusflags &= ~EMPTYWAIT;
-- if ((ch->tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- ch->tty->ldisc.write_wakeup)
-- (ch->tty->ldisc.write_wakeup) (ch->tty);
-+ tty_wakeup(ch->tty);
- wake_up_interruptible(&ch->tty->write_wait);
- return;
- }
-diff -Nur linux-2.4.27/drivers/char/mxser.c linux-2.4.27-plasmaroo/drivers/char/mxser.c
---- linux-2.4.27/drivers/char/mxser.c 2002-11-28 23:53:12.000000000 +0000
-+++ linux-2.4.27-plasmaroo/drivers/char/mxser.c 2004-11-07 14:02:20.212673104 +0000
-@@ -725,9 +725,7 @@
- tty = info->tty;
- if (tty) {
- if (test_and_clear_bit(MXSER_EVENT_TXLOW, &info->event)) {
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup) (tty);
-+ tty_wakeup(tty);
- wake_up_interruptible(&tty->write_wait);
- }
- if (test_and_clear_bit(MXSER_EVENT_HANGUP, &info->event)) {
-@@ -810,6 +808,7 @@
- struct mxser_struct *info = (struct mxser_struct *) tty->driver_data;
- unsigned long flags;
- unsigned long timeout;
-+ struct tty_ldisc *ld;
-
- if (PORTNO(tty) == MXSER_PORTS)
- return;
-@@ -890,6 +889,12 @@
- mxser_shutdown(info);
- if (tty->driver.flush_buffer)
- tty->driver.flush_buffer(tty);
-+ ld = tty_ldisc_ref(tty);
-+ if (ld) {
-+ if (ld->flush_buffer)
-+ ld->flush_buffer(tty);
-+ tty_ldisc_deref(ld);
-+ }
- if (tty->ldisc.flush_buffer)
- tty->ldisc.flush_buffer(tty);
- tty->closing = 0;
-@@ -1051,9 +1056,7 @@
- info->xmit_cnt = info->xmit_head = info->xmit_tail = 0;
- restore_flags(flags);
- wake_up_interruptible(&tty->write_wait);
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup) (tty);
-+ tty_wakeup(tty);
- }
-
- static int mxser_ioctl(struct tty_struct *tty, struct file *file,
-diff -Nur linux-2.4.27/drivers/char/n_tty.c linux-2.4.27-plasmaroo/drivers/char/n_tty.c
---- linux-2.4.27/drivers/char/n_tty.c 2003-08-25 12:44:41.000000000 +0100
-+++ linux-2.4.27-plasmaroo/drivers/char/n_tty.c 2004-11-07 14:02:20.219672040 +0000
-@@ -112,11 +112,18 @@
- spin_unlock_irqrestore(&tty->read_lock, flags);
- }
-
--/*
-- * Check whether to call the driver.unthrottle function.
-- * We test the TTY_THROTTLED bit first so that it always
-- * indicates the current state.
-+/**
-+ * check_unthrottle - allow new receive data
-+ * @tty; tty device
-+ *
-+ * Check whether to call the driver.unthrottle function.
-+ * We test the TTY_THROTTLED bit first so that it always
-+ * indicates the current state. The decision about whether
-+ * it is worth allowing more input has been taken by the caller.
-+ * Can sleep, may be called under the atomic_read semaphore but
-+ * this is not guaranteed.
- */
-+
- static void check_unthrottle(struct tty_struct * tty)
- {
- if (tty->count &&
-@@ -125,10 +132,13 @@
- tty->driver.unthrottle(tty);
- }
-
--/*
-- * Reset the read buffer counters, clear the flags,
-- * and make sure the driver is unthrottled. Called
-- * from n_tty_open() and n_tty_flush_buffer().
-+/**
-+ * reset_buffer_flags - reset buffer state
-+ * @tty: terminal to reset
-+ *
-+ * Reset the read buffer counters, clear the flags,
-+ * and make sure the driver is unthrottled. Called
-+ * from n_tty_open() and n_tty_flush_buffer().
- */
- static void reset_buffer_flags(struct tty_struct *tty)
- {
-@@ -142,9 +152,19 @@
- check_unthrottle(tty);
- }
-
--/*
-- * Flush the input buffer
-+/**
-+ * n_tty_flush_buffer - clean input queue
-+ * @tty: terminal device
-+ *
-+ * Flush the input buffer. Called when the line discipline is
-+ * being closed, when the tty layer wants the buffer flushed (eg
-+ * at hangup) or when the N_TTY line discipline internally has to
-+ * clean the pending queue (for example some signals).
-+ *
-+ * FIXME: tty->ctrl_status is not spinlocked and relies on
-+ * lock_kernel() still.
- */
-+
- void n_tty_flush_buffer(struct tty_struct * tty)
- {
- /* clear everything and unthrottle the driver */
-@@ -159,9 +179,14 @@
- }
- }
-
--/*
-- * Return number of characters buffered to be delivered to user
-+/**
-+ * n_tty_chars_in_buffer - report available bytes
-+ * @tty: tty device
-+ *
-+ * Report the number of characters buffered to be delivered to user
-+ * at this instant in time.
- */
-+
- ssize_t n_tty_chars_in_buffer(struct tty_struct *tty)
- {
- unsigned long flags;
-@@ -242,10 +267,20 @@
- return 0;
- }
-
--/*
-- * opost_block --- to speed up block console writes, among other
-- * things.
-+/**
-+ * opost_block - block postprocess
-+ * @tty: terminal device
-+ * @inbuf: user buffer
-+ * @nr: number of bytes
-+ *
-+ * This path is used to speed up block console writes, among other
-+ * things when processing blocks of output data. It handles only
-+ * the simple cases normally found and helps to generate blocks of
-+ * symbols for the console driver and thus improve performance.
-+ *
-+ * Called from write_chan under the tty layer write lock.
- */
-+
- static ssize_t opost_block(struct tty_struct * tty,
- const unsigned char * inbuf, unsigned int nr)
- {
-@@ -334,6 +369,16 @@
- }
- }
-
-+/**
-+ * eraser - handle erase function
-+ * @c: character input
-+ * @tty: terminal device
-+ *
-+ * Perform erase and neccessary output when an erase character is
-+ * present in the stream from the driver layer. Handles the complexities
-+ * of UTF-8 multibyte symbols.
-+ */
-+
- static void eraser(unsigned char c, struct tty_struct *tty)
- {
- enum { ERASE, WERASE, KILL } kill_type;
-@@ -450,6 +495,18 @@
- finish_erasing(tty);
- }
-
-+/**
-+ * isig - handle the ISIG optio
-+ * @sig: signal
-+ * @tty: terminal
-+ * @flush: force flush
-+ *
-+ * Called when a signal is being sent due to terminal input. This
-+ * may caus terminal flushing to take place according to the termios
-+ * settings and character used. Called from the driver receive_buf
-+ * path so serialized.
-+ */
-+
- static inline void isig(int sig, struct tty_struct *tty, int flush)
- {
- if (tty->pgrp > 0)
-@@ -461,6 +518,16 @@
- }
- }
-
-+/**
-+ * n_tty_receive_break - handle break
-+ * @tty: terminal
-+ *
-+ * An RS232 break event has been hit in the incoming bitstream. This
-+ * can cause a variety of events depending upon the termios settings.
-+ *
-+ * Called from the receive_buf path so single threaded.
-+ */
-+
- static inline void n_tty_receive_break(struct tty_struct *tty)
- {
- if (I_IGNBRK(tty))
-@@ -477,19 +544,40 @@
- wake_up_interruptible(&tty->read_wait);
- }
-
-+/**
-+ * n_tty_receive_overrun - handle overrun reporting
-+ * @tty: terminal
-+ *
-+ * Data arrived faster than we could process it. While the tty
-+ * driver has flagged this the bits that were missed are gone
-+ * forever.
-+ *
-+ * Called from the receive_buf path so single threaded. Does not
-+ * need locking as num_overrun and overrun_time are function
-+ * private.
-+ */
-+
- static inline void n_tty_receive_overrun(struct tty_struct *tty)
- {
- char buf[64];
-
- tty->num_overrun++;
- if (time_before(tty->overrun_time, jiffies - HZ)) {
-- printk("%s: %d input overrun(s)\n", tty_name(tty, buf),
-+ printk(KERN_WARNING "%s: %d input overrun(s)\n", tty_name(tty, buf),
- tty->num_overrun);
- tty->overrun_time = jiffies;
- tty->num_overrun = 0;
- }
- }
-
-+/**
-+ * n_tty_receive_parity_error - error notifier
-+ * @tty: terminal device
-+ * @c: character
-+ *
-+ * Process a parity error and queue the right data to indicate
-+ * the error case if neccessary. Locking as per n_tty_receive_buf.
-+ */
- static inline void n_tty_receive_parity_error(struct tty_struct *tty,
- unsigned char c)
- {
-@@ -507,6 +595,16 @@
- wake_up_interruptible(&tty->read_wait);
- }
-
-+/**
-+ * n_tty_receive_char - perform processing
-+ * @tty: terminal device
-+ * @c: character
-+ *
-+ * Process an individual character of input received from the driver.
-+ * This is serialized with respect to itself by the rules for the
-+ * driver above.
-+ */
-+
- static inline void n_tty_receive_char(struct tty_struct *tty, unsigned char c)
- {
- unsigned long flags;
-@@ -698,6 +796,16 @@
- put_tty_queue(c, tty);
- }
-
-+/**
-+ * n_tty_receive_room - receive space
-+ * @tty: terminal
-+ *
-+ * Called by the driver to find out how much data it is
-+ * permitted to feed to the line discipline without any being lost
-+ * and thus to manage flow control. Not serialized. Answers for the
-+ * "instant".
-+ */
-+
- static int n_tty_receive_room(struct tty_struct *tty)
- {
- int left = N_TTY_BUF_SIZE - tty->read_cnt - 1;
-@@ -716,10 +824,13 @@
- return 0;
- }
-
--/*
-- * Required for the ptys, serial driver etc. since processes
-- * that attach themselves to the master and rely on ASYNC
-- * IO must be woken up
-+/**
-+ * n_tty_write_wakeup - asynchronous I/O notifier
-+ * @tty: tty device
-+ *
-+ * Required for the ptys, serial driver etc. since processes
-+ * that attach themselves to the master and rely on ASYNC
-+ * IO must be woken up
- */
-
- static void n_tty_write_wakeup(struct tty_struct *tty)
-@@ -732,6 +843,19 @@
- return;
- }
-
-+/**
-+ * n_tty_receive_buf - data receive
-+ * @tty: terminal device
-+ * @cp: buffer
-+ * @fp: flag buffer
-+ * @count: characters
-+ *
-+ * Called by the terminal driver when a block of characters has
-+ * been received. This function must be called from soft contexts
-+ * not from interrupt context. The driver is responsible for making
-+ * calls one at a time and in order (or using queue_ldisc)
-+ */
-+
- static void n_tty_receive_buf(struct tty_struct *tty, const unsigned char *cp,
- char *fp, int count)
- {
-@@ -813,6 +937,18 @@
- current->sig->action[sig-1].sa.sa_handler == SIG_IGN);
- }
-
-+/**
-+ * n_tty_set_termios - termios data changed
-+ * @tty: terminal
-+ * @old: previous data
-+ *
-+ * Called by the tty layer when the user changes termios flags so
-+ * that the line discipline can plan ahead. This function cannot sleep
-+ * and is protected from re-entry by the tty layer. The user is
-+ * guaranteed that this function will not be re-entered or in progress
-+ * when the ldisc is closed.
-+ */
-+
- static void n_tty_set_termios(struct tty_struct *tty, struct termios * old)
- {
- if (!tty)
-@@ -828,7 +964,6 @@
- I_ICRNL(tty) || I_INLCR(tty) || L_ICANON(tty) ||
- I_IXON(tty) || L_ISIG(tty) || L_ECHO(tty) ||
- I_PARMRK(tty)) {
-- cli();
- memset(tty->process_char_map, 0, 256/8);
-
- if (I_IGNCR(tty) || I_ICRNL(tty))
-@@ -864,7 +999,6 @@
- set_bit(SUSP_CHAR(tty), &tty->process_char_map);
- }
- clear_bit(__DISABLED_CHAR, &tty->process_char_map);
-- sti();
- tty->raw = 0;
- tty->real_raw = 0;
- } else {
-@@ -878,6 +1012,16 @@
- }
- }
-
-+/**
-+ * n_tty_close - close the ldisc for this tty
-+ * @tty: device
-+ *
-+ * Called from the terminal layer when this line discipline is
-+ * being shut down, either because of a close or becsuse of a
-+ * discipline change. The function will not be called while other
-+ * ldisc methods are in progress.
-+ */
-+
- static void n_tty_close(struct tty_struct *tty)
- {
- n_tty_flush_buffer(tty);
-@@ -887,11 +1031,22 @@
- }
- }
-
-+/**
-+ * n_tty_open - open an ldisc
-+ * @tty: terminal to open
-+ *
-+ * Called when this line discipline is being attached to the
-+ * terminal device. Can sleep. Called serialized so that no
-+ * other events will occur in parallel. No further open will occur
-+ * until a close.
-+ */
-+
- static int n_tty_open(struct tty_struct *tty)
- {
- if (!tty)
- return -EINVAL;
-
-+ /* This one is ugly. Currently a malloc failure here can panic */
- if (!tty->read_buf) {
- tty->read_buf = alloc_buf();
- if (!tty->read_buf)
-@@ -917,14 +1072,23 @@
- return 0;
- }
-
--/*
-- * Helper function to speed up read_chan. It is only called when
-- * ICANON is off; it copies characters straight from the tty queue to
-- * user space directly. It can be profitably called twice; once to
-- * drain the space from the tail pointer to the (physical) end of the
-- * buffer, and once to drain the space from the (physical) beginning of
-- * the buffer to head pointer.
-+/**
-+ * copy_from_read_buf - copy read data directly
-+ * @tty: terminal device
-+ * @b: user data
-+ * @nr: size of data
-+ *
-+ * Helper function to speed up read_chan. It is only called when
-+ * ICANON is off; it copies characters straight from the tty queue to
-+ * user space directly. It can be profitably called twice; once to
-+ * drain the space from the tail pointer to the (physical) end of the
-+ * buffer, and once to drain the space from the (physical) beginning of
-+ * the buffer to head pointer.
-+ *
-+ * Called under the tty->atomic_read sem and with TTY_DONT_FLIP set
-+ *
- */
-+
- static inline int copy_from_read_buf(struct tty_struct *tty,
- unsigned char **b,
- size_t *nr)
-@@ -952,25 +1116,18 @@
- return retval;
- }
-
--static ssize_t read_chan(struct tty_struct *tty, struct file *file,
-- unsigned char *buf, size_t nr)
--{
-- unsigned char *b = buf;
-- DECLARE_WAITQUEUE(wait, current);
-- int c;
-- int minimum, time;
-- ssize_t retval = 0;
-- ssize_t size;
-- long timeout;
-- unsigned long flags;
--
--do_it_again:
--
-- if (!tty->read_buf) {
-- printk("n_tty_read_chan: called with read_buf == NULL?!?\n");
-- return -EIO;
-- }
-+/**
-+ * job_control - check job control
-+ * @tty: tty
-+ * @file: file handle
-+ *
-+ * Perform job control management checks on this file/tty descriptor
-+ * and if appropriate send any needed signals and return a negative
-+ * error code if action should be taken.
-+ */
-
-+static int job_control(struct tty_struct *tty, struct file *file)
-+{
- /* Job control check -- must be done at start and after
- every sleep (POSIX.1 7.1.1.4). */
- /* NOTE: not yet done after every sleep pending a thorough
-@@ -989,7 +1146,48 @@
- return -ERESTARTSYS;
- }
- }
-+ return 0;
-+}
-+
-
-+/**
-+ * read_chan - read function for tty
-+ * @tty: tty device
-+ * @file: file object
-+ * @buf: userspace buffer pointer
-+ * @nr: size of I/O
-+ *
-+ * Perform reads for the line discipline. We are guaranteed that the
-+ * line discipline will not be closed under us but we may get multiple
-+ * parallel readers and must handle this ourselves. We may also get
-+ * a hangup. Always called in user context, may sleep.
-+ *
-+ * This code must be sure never to sleep through a hangup.
-+ */
-+
-+static ssize_t read_chan(struct tty_struct *tty, struct file *file,
-+ unsigned char __user *buf, size_t nr)
-+{
-+ unsigned char __user *b = buf;
-+ DECLARE_WAITQUEUE(wait, current);
-+ int c;
-+ int minimum, time;
-+ ssize_t retval = 0;
-+ ssize_t size;
-+ long timeout;
-+ unsigned long flags;
-+
-+do_it_again:
-+
-+ if (!tty->read_buf) {
-+ printk("n_tty_read_chan: called with read_buf == NULL?!?\n");
-+ return -EIO;
-+ }
-+
-+ c = job_control(tty, file);
-+ if(c < 0)
-+ return c;
-+
- minimum = time = 0;
- timeout = MAX_SCHEDULE_TIMEOUT;
- if (!tty->icanon) {
-@@ -1011,6 +1209,9 @@
- }
- }
-
-+ /*
-+ * Internal serialization of reads.
-+ */
- if (file->f_flags & O_NONBLOCK) {
- if (down_trylock(&tty->atomic_read))
- return -EAGAIN;
-@@ -1146,6 +1347,21 @@
- return retval;
- }
-
-+/**
-+ * write_chan - write function for tty
-+ * @tty: tty device
-+ * @file: file object
-+ * @buf: userspace buffer pointer
-+ * @nr: size of I/O
-+ *
-+ * Write function of the terminal device. This is serialized with
-+ * respect to other write callers but not to termios changes, reads
-+ * and other such events. We must be careful with N_TTY as the receive
-+ * code will echo characters, thus calling driver write methods.
-+ *
-+ * This code must be sure never to sleep through a hangup.
-+ */
-+
- static ssize_t write_chan(struct tty_struct * tty, struct file * file,
- const unsigned char * buf, size_t nr)
- {
-@@ -1217,7 +1433,25 @@
- return (b - buf) ? b - buf : retval;
- }
-
--/* Called without the kernel lock held - fine */
-+/**
-+ * normal_poll - poll method for N_TTY
-+ * @tty: terminal device
-+ * @file: file accessing it
-+ * @wait: poll table
-+ *
-+ * Called when the line discipline is asked to poll() for data or
-+ * for special events. This code is not serialized with respect to
-+ * other events save open/close.
-+ *
-+ * This code must be sure never to sleep through a hangup.
-+ * Called without the kernel lock held - fine
-+ *
-+ * FIXME: if someone changes the VMIN or discipline settings for the
-+ * terminal while another process is in poll() the poll does not
-+ * recompute the new limits. Possibly set_termios should issue
-+ * a read wakeup to fix this bug.
-+ */
-+
- static unsigned int normal_poll(struct tty_struct * tty, struct file * file, poll_table *wait)
- {
- unsigned int mask = 0;
-diff -Nur linux-2.4.27/drivers/char/pcmcia/synclink_cs.c linux-2.4.27-plasmaroo/drivers/char/pcmcia/synclink_cs.c
---- linux-2.4.27/drivers/char/pcmcia/synclink_cs.c 2003-11-28 18:26:20.000000000 +0000
-+++ linux-2.4.27-plasmaroo/drivers/char/pcmcia/synclink_cs.c 2004-11-07 14:02:20.108688912 +0000
-@@ -553,6 +553,40 @@
- static void* mgslpc_get_text_ptr(void);
- static void* mgslpc_get_text_ptr() {return mgslpc_get_text_ptr;}
-
-+/**
-+ * line discipline callback wrappers
-+ *
-+ * The wrappers maintain line discipline references
-+ * while calling into the line discipline.
-+ *
-+ * ldisc_flush_buffer - flush line discipline receive buffers
-+ * ldisc_receive_buf - pass receive data to line discipline
-+ */
-+
-+static void ldisc_flush_buffer(struct tty_struct *tty)
-+{
-+ struct tty_ldisc *ld = tty_ldisc_ref(tty);
-+ if (ld) {
-+ if (ld->flush_buffer)
-+ ld->flush_buffer(tty);
-+ tty_ldisc_deref(ld);
-+ }
-+}
-+
-+static void ldisc_receive_buf(struct tty_struct *tty,
-+ const __u8 *data, char *flags, int count)
-+{
-+ struct tty_ldisc *ld;
-+ if (!tty)
-+ return;
-+ ld = tty_ldisc_ref(tty);
-+ if (ld) {
-+ if (ld->receive_buf)
-+ ld->receive_buf(tty, data, flags, count);
-+ tty_ldisc_deref(ld);
-+ }
-+}
-+
- static dev_link_t *mgslpc_attach(void)
- {
- MGSLPC_INFO *info;
-@@ -1027,13 +1061,7 @@
- printk("bh_transmit() entry on %s\n", info->device_name);
-
- if (tty) {
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup) {
-- if ( debug_level >= DEBUG_LEVEL_BH )
-- printk( "%s(%d):calling ldisc.write_wakeup on %s\n",
-- __FILE__,__LINE__,info->device_name);
-- (tty->ldisc.write_wakeup)(tty);
-- }
-+ tty_wakeup(tty);
- wake_up_interruptible(&tty->write_wait);
- }
- }
-@@ -1917,11 +1945,9 @@
- info->tx_count = info->tx_put = info->tx_get = 0;
- del_timer(&info->tx_timer);
- spin_unlock_irqrestore(&info->lock,flags);
--
-+
- wake_up_interruptible(&tty->write_wait);
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
-+ tty_wakeup(tty);
- }
-
- /* Send a high-priority XON/XOFF character
-@@ -2685,9 +2711,8 @@
-
- if (tty->driver.flush_buffer)
- tty->driver.flush_buffer(tty);
--
-- if (tty->ldisc.flush_buffer)
-- tty->ldisc.flush_buffer(tty);
-+
-+ ldisc_flush_buffer(tty);
-
- shutdown(info);
-
-@@ -4199,11 +4224,7 @@
- }
- else
- #endif
-- {
-- /* Call the line discipline receive callback directly. */
-- if (tty && tty->ldisc.receive_buf)
-- tty->ldisc.receive_buf(tty, buf->data, info->flag_buf, framesize);
-- }
-+ ldisc_receive_buf(tty, buf->data, info->flag_buf, framesize);
- }
- }
-
-diff -Nur linux-2.4.27/drivers/char/pcxx.c linux-2.4.27-plasmaroo/drivers/char/pcxx.c
---- linux-2.4.27/drivers/char/pcxx.c 2002-11-28 23:53:12.000000000 +0000
-+++ linux-2.4.27-plasmaroo/drivers/char/pcxx.c 2004-11-07 14:02:20.296660336 +0000
-@@ -632,10 +632,10 @@
- ** please send me a note. brian@ilinx.com
- ** Don't know either what this is supposed to do christoph@lameter.com.
- */
-- if(tty->ldisc.num != ldiscs[N_TTY].num) {
-+ if(tty->ldisc.num != N_TTY) {
- if(tty->ldisc.close)
- (tty->ldisc.close)(tty);
-- tty->ldisc = ldiscs[N_TTY];
-+ tty->ldisc = *(tty_ldisc_get(N_TTY));
- tty->termios->c_line = N_TTY;
- if(tty->ldisc.open)
- (tty->ldisc.open)(tty);
-diff -Nur linux-2.4.27/drivers/char/pty.c linux-2.4.27-plasmaroo/drivers/char/pty.c
---- linux-2.4.27/drivers/char/pty.c 2002-08-03 01:39:43.000000000 +0100
-+++ linux-2.4.27-plasmaroo/drivers/char/pty.c 2004-11-07 14:02:20.220671888 +0000
-@@ -137,6 +137,10 @@
- * (2) avoid redundant copying for cases where count >> receive_room
- * N.B. Calls from user space may now return an error code instead of
- * a count.
-+ *
-+ * FIXME: Our pty_write method is called with our ldisc lock held but
-+ * not our partners. We can't just take the other one blindly without
-+ * risking deadlocks. There is also the small matter of TTY_DONT_FLIP
- */
- static int pty_write(struct tty_struct * tty, int from_user,
- const unsigned char *buf, int count)
-diff -Nur linux-2.4.27/drivers/char/riscom8.c linux-2.4.27-plasmaroo/drivers/char/riscom8.c
---- linux-2.4.27/drivers/char/riscom8.c 2001-09-13 23:21:32.000000000 +0100
-+++ linux-2.4.27-plasmaroo/drivers/char/riscom8.c 2004-11-07 14:02:20.231670216 +0000
-@@ -1133,6 +1133,7 @@
- struct riscom_board *bp;
- unsigned long flags;
- unsigned long timeout;
-+ struct tty_ldisc *ld;
-
- if (!port || rc_paranoia_check(port, tty->device, "close"))
- return;
-@@ -1200,6 +1201,12 @@
- rc_shutdown_port(bp, port);
- if (tty->driver.flush_buffer)
- tty->driver.flush_buffer(tty);
-+ ld = tty_ldisc_ref(tty);
-+ if (ld != NULL) {
-+ if(ld->flush_buffer)
-+ ld->flush_buffer(tty);
-+ tty_ldisc_deref(ld);
-+ }
- if (tty->ldisc.flush_buffer)
- tty->ldisc.flush_buffer(tty);
- tty->closing = 0;
-@@ -1375,9 +1382,7 @@
- restore_flags(flags);
-
- wake_up_interruptible(&tty->write_wait);
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
-+ tty_wakeup(tty);
- }
-
- static int rc_get_modem_info(struct riscom_port * port, unsigned int *value)
-@@ -1734,9 +1739,7 @@
- return;
-
- if (test_and_clear_bit(RS_EVENT_WRITE_WAKEUP, &port->event)) {
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
-+ tty_wakeup(tty);
- wake_up_interruptible(&tty->write_wait);
- }
- }
-diff -Nur linux-2.4.27/drivers/char/selection.c linux-2.4.27-plasmaroo/drivers/char/selection.c
---- linux-2.4.27/drivers/char/selection.c 2001-09-07 17:28:38.000000000 +0100
-+++ linux-2.4.27-plasmaroo/drivers/char/selection.c 2004-11-07 14:02:20.236669456 +0000
-@@ -290,9 +290,11 @@
- {
- struct vt_struct *vt = (struct vt_struct *) tty->driver_data;
- int pasted = 0, count;
-+ struct tty_ldisc *ld;
- DECLARE_WAITQUEUE(wait, current);
-
- poke_blanked_console();
-+ ld = tty_ldisc_ref_wait(tty);
- add_wait_queue(&vt->paste_wait, &wait);
- while (sel_buffer && sel_buffer_lth > pasted) {
- set_current_state(TASK_INTERRUPTIBLE);
-@@ -307,6 +309,8 @@
- }
- remove_wait_queue(&vt->paste_wait, &wait);
- current->state = TASK_RUNNING;
-+
-+ tty_ldisc_deref(ld);
- return 0;
- }
-
-diff -Nur linux-2.4.27/drivers/char/serial167.c linux-2.4.27-plasmaroo/drivers/char/serial167.c
---- linux-2.4.27/drivers/char/serial167.c 2002-11-28 23:53:12.000000000 +0000
-+++ linux-2.4.27-plasmaroo/drivers/char/serial167.c 2004-11-07 14:02:20.300659728 +0000
-@@ -1920,10 +1920,10 @@
- tty->ldisc.flush_buffer(tty);
- info->event = 0;
- info->tty = 0;
-- if (tty->ldisc.num != ldiscs[N_TTY].num) {
-+ if (tty->ldisc.num != N_TTY) {
- if (tty->ldisc.close)
- (tty->ldisc.close)(tty);
-- tty->ldisc = ldiscs[N_TTY];
-+ tty->ldisc = *(tty_ldisc_get(N_TTY));
- tty->termios->c_line = N_TTY;
- if (tty->ldisc.open)
- (tty->ldisc.open)(tty);
-diff -Nur linux-2.4.27/drivers/char/sgiserial.c linux-2.4.27-plasmaroo/drivers/char/sgiserial.c
---- linux-2.4.27/drivers/char/sgiserial.c 2004-02-18 13:36:31.000000000 +0000
-+++ linux-2.4.27-plasmaroo/drivers/char/sgiserial.c 2004-11-07 14:02:20.303659272 +0000
-@@ -1498,10 +1498,10 @@
- tty->closing = 0;
- info->event = 0;
- info->tty = 0;
-- if (tty->ldisc.num != ldiscs[N_TTY].num) {
-+ if (tty->ldisc.num != N_TTY) {
- if (tty->ldisc.close)
- (tty->ldisc.close)(tty);
-- tty->ldisc = ldiscs[N_TTY];
-+ tty->ldisc = *(tty_ldisc_get(N_TTY));
- tty->termios->c_line = N_TTY;
- if (tty->ldisc.open)
- (tty->ldisc.open)(tty);
-diff -Nur linux-2.4.27/drivers/char/synclink.c linux-2.4.27-plasmaroo/drivers/char/synclink.c
---- linux-2.4.27/drivers/char/synclink.c 2003-11-28 18:26:20.000000000 +0000
-+++ linux-2.4.27-plasmaroo/drivers/char/synclink.c 2004-11-07 14:02:20.270664288 +0000
-@@ -1011,6 +1011,40 @@
- return 0;
- }
-
-+/**
-+ * line discipline callback wrappers
-+ *
-+ * The wrappers maintain line discipline references
-+ * while calling into the line discipline.
-+ *
-+ * ldisc_flush_buffer - flush line discipline receive buffers
-+ * ldisc_receive_buf - pass receive data to line discipline
-+ */
-+
-+static void ldisc_flush_buffer(struct tty_struct *tty)
-+{
-+ struct tty_ldisc *ld = tty_ldisc_ref(tty);
-+ if (ld) {
-+ if (ld->flush_buffer)
-+ ld->flush_buffer(tty);
-+ tty_ldisc_deref(ld);
-+ }
-+}
-+
-+static void ldisc_receive_buf(struct tty_struct *tty,
-+ const __u8 *data, char *flags, int count)
-+{
-+ struct tty_ldisc *ld;
-+ if (!tty)
-+ return;
-+ ld = tty_ldisc_ref(tty);
-+ if (ld) {
-+ if (ld->receive_buf)
-+ ld->receive_buf(tty, data, flags, count);
-+ tty_ldisc_deref(ld);
-+ }
-+}
-+
- /* mgsl_stop() throttle (stop) transmitter
- *
- * Arguments: tty pointer to tty info structure
-@@ -1170,13 +1204,7 @@
- __FILE__,__LINE__,info->device_name);
-
- if (tty) {
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup) {
-- if ( debug_level >= DEBUG_LEVEL_BH )
-- printk( "%s(%d):calling ldisc.write_wakeup on %s\n",
-- __FILE__,__LINE__,info->device_name);
-- (tty->ldisc.write_wakeup)(tty);
-- }
-+ tty_wakeup(tty);
- wake_up_interruptible(&tty->write_wait);
- }
-
-@@ -2434,11 +2462,8 @@
- spin_unlock_irqrestore(&info->irq_spinlock,flags);
-
- wake_up_interruptible(&tty->write_wait);
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
--
--} /* end of mgsl_flush_buffer() */
-+ tty_wakeup(tty);
-+}
-
- /* mgsl_send_xchar()
- *
-@@ -3342,9 +3367,8 @@
-
- if (tty->driver.flush_buffer)
- tty->driver.flush_buffer(tty);
--
-- if (tty->ldisc.flush_buffer)
-- tty->ldisc.flush_buffer(tty);
-+
-+ ldisc_flush_buffer(tty);
-
- shutdown(info);
-
-@@ -7007,11 +7031,7 @@
- }
- else
- #endif
-- {
-- /* Call the line discipline receive callback directly. */
-- if ( tty && tty->ldisc.receive_buf )
-- tty->ldisc.receive_buf(tty, info->intermediate_rxbuffer, info->flag_buf, framesize);
-- }
-+ ldisc_receive_buf(tty, info->intermediate_rxbuffer, info->flag_buf, framesize);
- }
- }
- /* Free the buffers used by this frame. */
-@@ -7183,9 +7203,7 @@
- memcpy( info->intermediate_rxbuffer, pBufEntry->virt_addr, framesize);
- info->icount.rxok++;
-
-- /* Call the line discipline receive callback directly. */
-- if ( tty && tty->ldisc.receive_buf )
-- tty->ldisc.receive_buf(tty, info->intermediate_rxbuffer, info->flag_buf, framesize);
-+ ldisc_receive_buf(tty, info->intermediate_rxbuffer, info->flag_buf, framesize);
- }
-
- /* Free the buffers used by this frame. */
-diff -Nur linux-2.4.27/drivers/char/synclinkmp.c linux-2.4.27-plasmaroo/drivers/char/synclinkmp.c
---- linux-2.4.27/drivers/char/synclinkmp.c 2003-11-28 18:26:20.000000000 +0000
-+++ linux-2.4.27-plasmaroo/drivers/char/synclinkmp.c 2004-11-07 14:02:20.281662616 +0000
-@@ -735,6 +735,40 @@
- return 0;
- }
-
-+/**
-+ * line discipline callback wrappers
-+ *
-+ * The wrappers maintain line discipline references
-+ * while calling into the line discipline.
-+ *
-+ * ldisc_flush_buffer - flush line discipline receive buffers
-+ * ldisc_receive_buf - pass receive data to line discipline
-+ */
-+
-+static void ldisc_flush_buffer(struct tty_struct *tty)
-+{
-+ struct tty_ldisc *ld = tty_ldisc_ref(tty);
-+ if (ld) {
-+ if (ld->flush_buffer)
-+ ld->flush_buffer(tty);
-+ tty_ldisc_deref(ld);
-+ }
-+}
-+
-+static void ldisc_receive_buf(struct tty_struct *tty,
-+ const __u8 *data, char *flags, int count)
-+{
-+ struct tty_ldisc *ld;
-+ if (!tty)
-+ return;
-+ ld = tty_ldisc_ref(tty);
-+ if (ld) {
-+ if (ld->receive_buf)
-+ ld->receive_buf(tty, data, flags, count);
-+ tty_ldisc_deref(ld);
-+ }
-+}
-+
- /* tty callbacks */
-
- /* Called when a port is opened. Init and enable port.
-@@ -906,8 +940,7 @@
- if (tty->driver.flush_buffer)
- tty->driver.flush_buffer(tty);
-
-- if (tty->ldisc.flush_buffer)
-- tty->ldisc.flush_buffer(tty);
-+ ldisc_flush_buffer(tty);
-
- shutdown(info);
-
-@@ -1315,9 +1348,7 @@
- spin_unlock_irqrestore(&info->lock,flags);
-
- wake_up_interruptible(&tty->write_wait);
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
-+ tty_wakeup(tty);
- }
-
- /* throttle (stop) transmitter
-@@ -1983,13 +2014,7 @@
- __FILE__,__LINE__,info->device_name);
-
- if (tty) {
-- if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
-- tty->ldisc.write_wakeup) {
-- if ( debug_level >= DEBUG_LEVEL_BH )
-- printk( "%s(%d):%s calling ldisc.write_wakeup\n",
-- __FILE__,__LINE__,info->device_name);
-- (tty->ldisc.write_wakeup)(tty);
-- }
-+ tty_wakeup(tty);
- wake_up_interruptible(&tty->write_wait);
- }
- }
-@@ -4986,15 +5011,8 @@
- }
- else
- #endif
-- {
-- if ( tty && tty->ldisc.receive_buf ) {
-- /* Call the line discipline receive callback directly. */
-- tty->ldisc.receive_buf(tty,
-- info->tmp_rx_buf,
-- info->flag_buf,
-- framesize);
-- }
-- }
-+ ldisc_receive_buf(tty,info->tmp_rx_buf,
-+ info->flag_buf, framesize);
- }
- }
- /* Free the buffers used by this frame. */
-diff -Nur linux-2.4.27/drivers/char/tty_io.c linux-2.4.27-plasmaroo/drivers/char/tty_io.c
---- linux-2.4.27/drivers/char/tty_io.c 2004-04-14 14:05:29.000000000 +0100
-+++ linux-2.4.27-plasmaroo/drivers/char/tty_io.c 2004-11-07 14:02:20.113688152 +0000
-@@ -118,9 +118,10 @@
- #define TTY_PARANOIA_CHECK 1
- #define CHECK_TTY_COUNT 1
-
-+/* Lock for tty_termios changes - private to tty_io/tty_ioctl */
-+spinlock_t tty_termios_lock = SPIN_LOCK_UNLOCKED;
- struct termios tty_std_termios; /* for the benefit of tty drivers */
- struct tty_driver *tty_drivers; /* linked list of tty drivers */
--struct tty_ldisc ldiscs[NR_LDISCS]; /* line disc dispatch table */
-
- #ifdef CONFIG_UNIX98_PTYS
- extern struct tty_driver ptm_driver[]; /* Unix98 pty masters; for /dev/ptmx */
-@@ -260,46 +261,264 @@
- return 0;
- }
-
-+/*
-+ * This is probably overkill for real world processors but
-+ * they are not on hot paths so a little discipline won't do
-+ * any harm.
-+ */
-+
-+static void tty_set_termios_ldisc(struct tty_struct *tty, int num)
-+{
-+ unsigned long flags;
-+ spin_lock_irqsave(&tty_termios_lock, flags);
-+ tty->termios->c_line = num;
-+ spin_unlock_irqrestore(&tty_termios_lock, flags);
-+}
-+
-+/*
-+ * This guards the refcounted line discipline lists. The lock
-+ * must be taken with irqs off because there are hangup path
-+ * callers who will do ldisc lookups and cannot sleep.
-+ */
-+
-+spinlock_t tty_ldisc_lock = SPIN_LOCK_UNLOCKED;
-+DECLARE_WAIT_QUEUE_HEAD(tty_ldisc_wait);
-+struct tty_ldisc tty_ldiscs[NR_LDISCS]; /* line disc dispatch table */
-+
- int tty_register_ldisc(int disc, struct tty_ldisc *new_ldisc)
- {
-+
-+ unsigned long flags;
-+ int ret = 0;
-+
- if (disc < N_TTY || disc >= NR_LDISCS)
- return -EINVAL;
--
-+
-+ spin_lock_irqsave(&tty_ldisc_lock, flags);
- if (new_ldisc) {
-- ldiscs[disc] = *new_ldisc;
-- ldiscs[disc].flags |= LDISC_FLAG_DEFINED;
-- ldiscs[disc].num = disc;
-- } else
-- memset(&ldiscs[disc], 0, sizeof(struct tty_ldisc));
-+ tty_ldiscs[disc] = *new_ldisc;
-+ tty_ldiscs[disc].num = disc;
-+ tty_ldiscs[disc].flags |= LDISC_FLAG_DEFINED;
-+ tty_ldiscs[disc].refcount = 0;
-+ } else {
-+ if(tty_ldiscs[disc].refcount)
-+ ret = -EBUSY;
-+ else
-+ tty_ldiscs[disc].flags &= ~LDISC_FLAG_DEFINED;
-+ }
-+ spin_unlock_irqrestore(&tty_ldisc_lock, flags);
-
-- return 0;
-+ return ret;
-+
- }
-
-+
- EXPORT_SYMBOL(tty_register_ldisc);
-
--/* Set the discipline of a tty line. */
-+struct tty_ldisc *tty_ldisc_get(int disc)
-+{
-+ unsigned long flags;
-+ struct tty_ldisc *ld;
-+
-+ if (disc < N_TTY || disc >= NR_LDISCS)
-+ return NULL;
-+
-+ spin_lock_irqsave(&tty_ldisc_lock, flags);
-+
-+ ld = &tty_ldiscs[disc];
-+ /* Check the entry is defined */
-+ if(ld->flags & LDISC_FLAG_DEFINED)
-+ ld->refcount++;
-+ else
-+ ld = NULL;
-+ spin_unlock_irqrestore(&tty_ldisc_lock, flags);
-+ return ld;
-+}
-+
-+EXPORT_SYMBOL_GPL(tty_ldisc_get);
-+
-+void tty_ldisc_put(int disc)
-+{
-+ struct tty_ldisc *ld;
-+ unsigned long flags;
-+
-+ if (disc < N_TTY || disc >= NR_LDISCS)
-+ BUG();
-+
-+ spin_lock_irqsave(&tty_ldisc_lock, flags);
-+ ld = &tty_ldiscs[disc];
-+ if(ld->refcount <= 0)
-+ BUG();
-+ ld->refcount--;
-+ spin_unlock_irqrestore(&tty_ldisc_lock, flags);
-+}
-+
-+EXPORT_SYMBOL_GPL(tty_ldisc_put);
-+
-+void tty_ldisc_assign(struct tty_struct *tty, struct tty_ldisc *ld)
-+{
-+ tty->ldisc = *ld;
-+ tty->ldisc.refcount = 0;
-+}
-+
-+/**
-+ * tty_ldisc_try - internal helper
-+ * @tty: the tty
-+ *
-+ * Make a single attempt to grab and bump the refcount on
-+ * the tty ldisc. Return 0 on failure or 1 on success. This is
-+ * used to implement both the waiting and non waiting versions
-+ * of tty_ldisc_ref
-+ */
-+
-+static int tty_ldisc_try(struct tty_struct *tty)
-+{
-+ unsigned long flags;
-+ struct tty_ldisc *ld;
-+ int ret = 0;
-+
-+ spin_lock_irqsave(&tty_ldisc_lock, flags);
-+ ld = &tty->ldisc;
-+ if(test_bit(TTY_LDISC, &tty->flags))
-+ {
-+ ld->refcount++;
-+ ret = 1;
-+ }
-+ spin_unlock_irqrestore(&tty_ldisc_lock, flags);
-+ return ret;
-+}
-+
-+/**
-+ * tty_ldisc_ref_wait - wait for the tty ldisc
-+ * @tty: tty device
-+ *
-+ * Dereference the line discipline for the terminal and take a
-+ * reference to it. If the line discipline is in flux then
-+ * wait patiently until it changes.
-+ *
-+ * Note: Must not be called from an IRQ/timer context. The caller
-+ * must also be careful not to hold other locks that will deadlock
-+ * against a discipline change, such as an existing ldisc reference
-+ * (which we check for)
-+ */
-+
-+struct tty_ldisc *tty_ldisc_ref_wait(struct tty_struct *tty)
-+{
-+ /* wait_event is a macro */
-+ wait_event(tty_ldisc_wait, tty_ldisc_try(tty));
-+ return &tty->ldisc;
-+}
-+
-+EXPORT_SYMBOL_GPL(tty_ldisc_ref_wait);
-+
-+/**
-+ * tty_ldisc_ref - get the tty ldisc
-+ * @tty: tty device
-+ *
-+ * Dereference the line discipline for the terminal and take a
-+ * reference to it. If the line discipline is in flux then
-+ * return NULL. Can be called from IRQ and timer functions.
-+ */
-+
-+struct tty_ldisc *tty_ldisc_ref(struct tty_struct *tty)
-+{
-+ if(tty_ldisc_try(tty))
-+ return &tty->ldisc;
-+ return NULL;
-+}
-+
-+EXPORT_SYMBOL_GPL(tty_ldisc_ref);
-+
-+
-+void tty_ldisc_deref(struct tty_ldisc *ld)
-+{
-+
-+ unsigned long flags;
-+
-+ if(ld == NULL)
-+ BUG();
-+
-+ spin_lock_irqsave(&tty_ldisc_lock, flags);
-+ if(ld->refcount == 0)
-+ printk(KERN_EMERG "tty_ldisc_deref: no references.\n");
-+ else
-+ ld->refcount--;
-+ if(ld->refcount == 0)
-+ wake_up(&tty_ldisc_wait);
-+ spin_unlock_irqrestore(&tty_ldisc_lock, flags);
-+}
-+
-+EXPORT_SYMBOL_GPL(tty_ldisc_deref);
-+
-+/**
-+ * tty_set_ldisc - set line discipline
-+ * @tty: the terminal to set
-+ * @ldisc: the line discipline
-+ *
-+ * Set the discipline of a tty line. Must be called from a process
-+ * context.
-+ */
-+
- static int tty_set_ldisc(struct tty_struct *tty, int ldisc)
- {
- int retval = 0;
- struct tty_ldisc o_ldisc;
- char buf[64];
-+ int work;
-+ unsigned long flags;
-+ struct tty_ldisc *ld;
-
- if ((ldisc < N_TTY) || (ldisc >= NR_LDISCS))
- return -EINVAL;
-+
-+restart:
-+
-+ if (tty->ldisc.num == ldisc)
-+ return 0; /* We are already in the desired discipline */
-+
-+ ld = tty_ldisc_get(ldisc);
- /* Eduardo Blanco <ejbs@cs.cs.com.uy> */
- /* Cyrus Durgin <cider@speakeasy.org> */
-- if (!(ldiscs[ldisc].flags & LDISC_FLAG_DEFINED)) {
-+ if (ld == NULL)
-+ {
- char modname [20];
-- sprintf(modname, "tty-ldisc-%d", ldisc);
-- request_module (modname);
-+ sprintf(modname, "tty-ldisc-%d", ldisc);
-+ request_module (modname);
-+ ld = tty_ldisc_get(ldisc);
- }
-- if (!(ldiscs[ldisc].flags & LDISC_FLAG_DEFINED))
-+
-+ if (ld == NULL)
- return -EINVAL;
-
-- if (tty->ldisc.num == ldisc)
-- return 0; /* We are already in the desired discipline */
-- o_ldisc = tty->ldisc;
-+ /*
-+ * Make sure we don't change while someone holds a
-+ * reference to the line discipline. The TTY_LDISC bit
-+ * prevents anyone taking a reference once it is clear.
-+ * We need the lock to avoid racing reference takers.
-+ */
-+
-+ spin_lock_irqsave(&tty_ldisc_lock, flags);
-+ if(tty->ldisc.refcount)
-+ {
-+ /* Free the new ldisc we grabbed. Must drop the lock
-+ first. */
-+ spin_unlock_irqrestore(&tty_ldisc_lock, flags);
-+ tty_ldisc_put(ldisc);
-+ if(wait_event_interruptible(tty_ldisc_wait, tty->ldisc.refcount == 0) < 0)
-+ return -ERESTARTSYS;
-+ goto restart;
-+ }
-+ clear_bit(TTY_LDISC, &tty->flags);
-+ clear_bit(TTY_DONT_FLIP, &tty->flags);
-+ spin_unlock_irqrestore(&tty_ldisc_lock, flags);
-
-+ /*
-+ * From this point on we know nobody has an ldisc
-+ * usage reference, nor can they obtain one until
-+ * we say so later on.
-+ */
-+
-+ o_ldisc = tty->ldisc;
- tty_wait_until_sent(tty, 0);
-
- /* Shutdown the current discipline. */
-@@ -307,16 +526,20 @@
- (tty->ldisc.close)(tty);
-
- /* Now set up the new line discipline. */
-- tty->ldisc = ldiscs[ldisc];
-- tty->termios->c_line = ldisc;
-+ tty_ldisc_assign(tty, ld);
-+ tty_set_termios_ldisc(tty, ldisc);
- if (tty->ldisc.open)
- retval = (tty->ldisc.open)(tty);
- if (retval < 0) {
-- tty->ldisc = o_ldisc;
-- tty->termios->c_line = tty->ldisc.num;
-+ tty_ldisc_put(ldisc);
-+ /* There is an outstanding reference here so this is safe */
-+ tty_ldisc_assign(tty, tty_ldisc_get(o_ldisc.num));
-+ tty_set_termios_ldisc(tty, tty->ldisc.num);
- if (tty->ldisc.open && (tty->ldisc.open(tty) < 0)) {
-- tty->ldisc = ldiscs[N_TTY];
-- tty->termios->c_line = N_TTY;
-+ tty_ldisc_put(o_ldisc.num);
-+ /* This driver is always present */
-+ tty_ldisc_assign(tty, tty_ldisc_get(N_TTY));
-+ tty_set_termios_ldisc(tty, N_TTY);
- if (tty->ldisc.open) {
- int r = tty->ldisc.open(tty);
-
-@@ -327,8 +550,23 @@
- }
- }
- }
-+ /* At this point we hold a reference to the new ldisc and a
-+ reference to the old ldisc. If we ended up flipping back
-+ to the existing ldisc we have two references to it */
-+
- if (tty->ldisc.num != o_ldisc.num && tty->driver.set_ldisc)
- tty->driver.set_ldisc(tty);
-+
-+ tty_ldisc_put(o_ldisc.num);
-+
-+ /*
-+ * Allow ldisc referencing to occur as soon as the driver
-+ * ldisc callback completes.
-+ */
-+
-+ set_bit(TTY_LDISC, &tty->flags);
-+ wake_up(&tty_ldisc_wait);
-+
- return retval;
- }
-
-@@ -430,6 +668,27 @@
-
- static spinlock_t redirect_lock = SPIN_LOCK_UNLOCKED;
- static struct file *redirect;
-+
-+/*
-+ * Internal and external helper for wakeups of tty
-+ */
-+
-+void tty_wakeup(struct tty_struct *tty)
-+{
-+ struct tty_ldisc *ld;
-+
-+ if (test_bit(TTY_DO_WRITE_WAKEUP, &tty->flags)) {
-+ ld = tty_ldisc_ref(tty);
-+ if(ld) {
-+ if(ld->write_wakeup)
-+ ld->write_wakeup(tty);
-+ tty_ldisc_deref(ld);
-+ }
-+ }
-+}
-+
-+EXPORT_SYMBOL_GPL(tty_wakeup);
-+
- /*
- * This can be called by the "eventd" kernel thread. That is process synchronous,
- * but doesn't hold any locks, so we need to make sure we have the appropriate
-@@ -442,6 +701,7 @@
- struct file *f = NULL;
- struct task_struct *p;
- struct list_head *l;
-+ struct tty_ldisc *ld;
- int closecount = 0, n;
-
- if (!tty)
-@@ -475,18 +735,17 @@
- file_list_unlock();
-
- /* FIXME! What are the locking issues here? This may me overdoing things.. */
-+ ld = tty_ldisc_ref(tty);
-+ if(ld != NULL)
- {
-- unsigned long flags;
--
-- save_flags(flags); cli();
-- if (tty->ldisc.flush_buffer)
-- tty->ldisc.flush_buffer(tty);
-+ if (ld->flush_buffer)
-+ ld->flush_buffer(tty);
- if (tty->driver.flush_buffer)
- tty->driver.flush_buffer(tty);
-- if ((test_bit(TTY_DO_WRITE_WAKEUP, &tty->flags)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
-- restore_flags(flags);
-+ if ((test_bit(TTY_DO_WRITE_WAKEUP, &tty->flags)) && ld->write_wakeup)
-+ ld->write_wakeup(tty);
-+ //if (ld->hangup)
-+ // ld->hangup(tty);
- }
-
- wake_up_interruptible(&tty->write_wait);
-@@ -496,21 +755,18 @@
- * Shutdown the current line discipline, and reset it to
- * N_TTY.
- */
-+
- if (tty->driver.flags & TTY_DRIVER_RESET_TERMIOS)
-- *tty->termios = tty->driver.init_termios;
-- if (tty->ldisc.num != ldiscs[N_TTY].num) {
-- if (tty->ldisc.close)
-- (tty->ldisc.close)(tty);
-- tty->ldisc = ldiscs[N_TTY];
-- tty->termios->c_line = N_TTY;
-- if (tty->ldisc.open) {
-- int i = (tty->ldisc.open)(tty);
-- if (i < 0)
-- printk(KERN_ERR "do_tty_hangup: N_TTY open: "
-- "error %d\n", -i);
-- }
-+ {
-+ unsigned long flags;
-+ spin_lock_irqsave(&tty_termios_lock, flags);
-+ *tty->termios = tty->driver.init_termios;
-+ spin_unlock_irqrestore(&tty_termios_lock, flags);
- }
--
-+
-+ /* Defer ldisc switch */
-+ /* tty_deferred_ldisc_switch(N_TTY);
-+
- read_lock(&tasklist_lock);
- for_each_task(p) {
- if ((tty->session > 0) && (p->session == tty->session) &&
-@@ -541,6 +797,15 @@
- tty->driver.close(tty, cons_filp);
- } else if (tty->driver.hangup)
- (tty->driver.hangup)(tty);
-+
-+ /* We don't want to have driver/ldisc interactions beyond
-+ the ones we did here. The driver layer expects no
-+ calls after ->hangup() from the ldisc side. However we
-+ can't yet guarantee all that */
-+
-+ set_bit(TTY_HUPPED, &tty->flags);
-+ if(ld)
-+ tty_ldisc_deref(ld);
- unlock_kernel();
- if (f)
- fput(f);
-@@ -644,9 +909,8 @@
- }
- if (tty->driver.start)
- (tty->driver.start)(tty);
-- if ((test_bit(TTY_DO_WRITE_WAKEUP, &tty->flags)) &&
-- tty->ldisc.write_wakeup)
-- (tty->ldisc.write_wakeup)(tty);
-+ /* If we have a running line discipline it may need kicking */
-+ tty_wakeup(tty);
- wake_up_interruptible(&tty->write_wait);
- }
-
-@@ -656,6 +920,7 @@
- int i;
- struct tty_struct * tty;
- struct inode *inode;
-+ struct tty_ldisc *ld;
-
- /* Can't seek (pread) on ttys. */
- if (ppos != &file->f_pos)
-@@ -684,11 +949,15 @@
- return -ERESTARTSYS;
- }
- #endif
-+ /* We want to wait for the line discipline to sort out in this
-+ situation */
-+ ld = tty_ldisc_ref_wait(tty);
- lock_kernel();
-- if (tty->ldisc.read)
-- i = (tty->ldisc.read)(tty,file,buf,count);
-+ if (ld->read)
-+ i = (ld->read)(tty,file,buf,count);
- else
- i = -EIO;
-+ tty_ldisc_deref(ld);
- unlock_kernel();
- if (i > 0)
- inode->i_atime = CURRENT_TIME;
-@@ -757,6 +1026,8 @@
- int is_console;
- struct tty_struct * tty;
- struct inode *inode = file->f_dentry->d_inode;
-+ ssize_t ret;
-+ struct tty_ldisc *ld;
-
- /* Can't seek (pwrite) on ttys. */
- if (ppos != &file->f_pos)
-@@ -803,10 +1074,15 @@
- }
- }
- #endif
-- if (!tty->ldisc.write)
-- return -EIO;
-- return do_tty_write(tty->ldisc.write, tty, file,
-- (const unsigned char *)buf, count);
-+
-+ ld = tty_ldisc_ref_wait(tty);
-+ if (!ld->write)
-+ ret = -EIO;
-+ else
-+ ret = do_tty_write(ld->write, tty, file,
-+ (const unsigned char __user *)buf, count);
-+ tty_ldisc_deref(ld);
-+ return ret;
- }
-
- /* Semaphore to protect creating and releasing a tty */
-@@ -971,7 +1247,9 @@
- (tty->ldisc.close)(tty);
- goto release_mem_out;
- }
-+ set_bit(TTY_LDISC, &o_tty->flags);
- }
-+ set_bit(TTY_LDISC, &tty->flags);
- goto success;
-
- /*
-@@ -999,7 +1277,9 @@
- }
- tty->count++;
- tty->driver = *driver; /* N.B. why do this every time?? */
--
-+ /* FIXME */
-+ if(!test_bit(TTY_LDISC, &tty->flags))
-+ printk(KERN_ERR "init_dev but no ldisc\n");
- success:
- *ret_tty = tty;
-
-@@ -1080,6 +1360,7 @@
- int pty_master, tty_closing, o_tty_closing, do_sleep;
- int idx;
- char buf[64];
-+ unsigned long flags;
-
- tty = (struct tty_struct *)filp->private_data;
- if (tty_paranoia_check(tty, filp->f_dentry->d_inode->i_rdev, "release_dev"))
-@@ -1272,17 +1553,51 @@
- #endif
-
- /*
-+ * Prevent flush_to_ldisc() from rescheduling the work for later. Then
-+ * kill any delayed work. As this is the final close it does not
-+ * race with the set_ldisc code path.
-+ */
-+ clear_bit(TTY_LDISC, &tty->flags);
-+ clear_bit(TTY_DONT_FLIP, &tty->flags);
-+
-+ /*
-+ * Wait for any short term users (we know they are just driver
-+ * side waiters as the file is closing so user count on the file
-+ * side is zero.
-+ */
-+
-+ spin_lock_irqsave(&tty_ldisc_lock, flags);
-+ while(tty->ldisc.refcount)
-+ {
-+ spin_unlock_irqrestore(&tty_ldisc_lock, flags);
-+ wait_event(tty_ldisc_wait, tty->ldisc.refcount == 0);
-+ spin_lock_irqsave(&tty_ldisc_lock, flags);
-+ }
-+ spin_unlock_irqrestore(&tty_ldisc_lock, flags);
-+
-+ /*
- * Shutdown the current line discipline, and reset it to N_TTY.
- * N.B. why reset ldisc when we're releasing the memory??
-+ * FIXME: this MUST get fixed for the new reflocking
- */
- if (tty->ldisc.close)
- (tty->ldisc.close)(tty);
-- tty->ldisc = ldiscs[N_TTY];
-- tty->termios->c_line = N_TTY;
-+ tty_ldisc_put(tty->ldisc.num);
-+
-+ /*
-+ * Switch the line discipline back
-+ */
-+ tty_ldisc_assign(tty, tty_ldisc_get(N_TTY));
-+ tty_set_termios_ldisc(tty,N_TTY);
-+
- if (o_tty) {
-+ /* FIXME: could o_tty be in setldisc here ? */
-+ clear_bit(TTY_LDISC, &o_tty->flags);
- if (o_tty->ldisc.close)
- (o_tty->ldisc.close)(o_tty);
-- o_tty->ldisc = ldiscs[N_TTY];
-+ tty_ldisc_put(o_tty->ldisc.num);
-+ tty_ldisc_assign(o_tty, tty_ldisc_get(N_TTY));
-+ tty_set_termios_ldisc(o_tty,N_TTY);
- }
-
- /*
-@@ -1464,14 +1779,18 @@
- static unsigned int tty_poll(struct file * filp, poll_table * wait)
- {
- struct tty_struct * tty;
-+ struct tty_ldisc *ld;
-+ int ret = 0;
-
- tty = (struct tty_struct *)filp->private_data;
- if (tty_paranoia_check(tty, filp->f_dentry->d_inode->i_rdev, "tty_poll"))
- return 0;
-
-- if (tty->ldisc.poll)
-- return (tty->ldisc.poll)(tty, filp, wait);
-- return 0;
-+ ld = tty_ldisc_ref_wait(tty);
-+ if (ld->poll)
-+ ret = (ld->poll)(tty, filp, wait);
-+ tty_ldisc_deref(ld);
-+ return ret;
- }
-
- static int tty_fasync(int fd, struct file * filp, int on)
-@@ -1505,12 +1824,15 @@
- static int tiocsti(struct tty_struct *tty, char * arg)
- {
- char ch, mbz = 0;
-+ struct tty_ldisc *ld;
-
- if ((current->tty != tty) && !suser())
- return -EPERM;
- if (get_user(ch, arg))
- return -EFAULT;
-- tty->ldisc.receive_buf(tty, &ch, &mbz, 1);
-+ ld = tty_ldisc_ref_wait(tty);
-+ ld->receive_buf(tty, &ch, &mbz, 1);
-+ tty_ldisc_deref(ld);
- return 0;
- }
-
-@@ -1718,6 +2040,7 @@
- {
- struct tty_struct *tty, *real_tty;
- int retval;
-+ struct tty_ldisc *ld;
-
- tty = (struct tty_struct *)file->private_data;
- if (tty_paranoia_check(tty, inode->i_rdev, "tty_ioctl"))
-@@ -1808,6 +2131,7 @@
- case TIOCGSID:
- return tiocgsid(tty, real_tty, (pid_t *) arg);
- case TIOCGETD:
-+ /* FIXME: check this is ok */
- return put_user(tty->ldisc.num, (int *) arg);
- case TIOCSETD:
- return tiocsetd(tty, (int *) arg);
-@@ -1841,16 +2165,20 @@
- return send_break(tty, arg ? arg*(HZ/10) : HZ/4);
- }
- if (tty->driver.ioctl) {
-- int retval = (tty->driver.ioctl)(tty, file, cmd, arg);
-+ retval = (tty->driver.ioctl)(tty, file, cmd, arg);
- if (retval != -ENOIOCTLCMD)
- return retval;
- }
-- if (tty->ldisc.ioctl) {
-- int retval = (tty->ldisc.ioctl)(tty, file, cmd, arg);
-- if (retval != -ENOIOCTLCMD)
-- return retval;
-+ ld = tty_ldisc_ref_wait(tty);
-+ retval = -EINVAL;
-+ if (ld->ioctl) {
-+ if(likely(test_bit(TTY_LDISC, &tty->flags)))
-+ retval = ld->ioctl(tty, file, cmd, arg);
-+ if (retval == -ENOIOCTLCMD)
-+ retval = -EINVAL;
- }
-- return -EINVAL;
-+ tty_ldisc_deref(ld);
-+ return retval;
- }
-
-
-@@ -1883,14 +2211,20 @@
- int session;
- int i;
- struct file *filp;
-+ struct tty_ldisc *disc;
-
- if (!tty)
- return;
- session = tty->session;
-- if (tty->ldisc.flush_buffer)
-- tty->ldisc.flush_buffer(tty);
-+ /* We don't want an ldisc switch during this */
-+ disc = tty_ldisc_ref(tty);
-+ if (disc && disc->flush_buffer)
-+ disc->flush_buffer(tty);
-+ tty_ldisc_deref(disc);
-+
- if (tty->driver.flush_buffer)
- tty->driver.flush_buffer(tty);
-+
- read_lock(&tasklist_lock);
- for_each_task(p) {
- if ((p->tty == tty) ||
-@@ -1942,11 +2276,16 @@
- unsigned char *cp;
- char *fp;
- int count;
-- unsigned long flags;
-+ unsigned long flags;
-+ struct tty_ldisc *disc;
-+
-+ disc = tty_ldisc_ref(tty);
-+ if (disc == NULL) /* !TTY_LDISC */
-+ return;
-
- if (test_bit(TTY_DONT_FLIP, &tty->flags)) {
- queue_task(&tty->flip.tqueue, &tq_timer);
-- return;
-+ goto out;
- }
- if (tty->flip.buf_num) {
- cp = tty->flip.char_buf + TTY_FLIPBUF_SIZE;
-@@ -1969,7 +2308,31 @@
- tty->flip.count = 0;
- restore_flags(flags);
-
-- tty->ldisc.receive_buf(tty, cp, fp, count);
-+ disc->receive_buf(tty, cp, fp, count);
-+out:
-+ tty_ldisc_deref(disc);
-+}
-+
-+/*
-+ * Call the ldisc flush directly from a driver. This function may
-+ * return an error and need retrying by the user.
-+ */
-+
-+int tty_push_data(struct tty_struct *tty, unsigned char *cp, unsigned char *fp, int count)
-+{
-+ int ret = 0;
-+ struct tty_ldisc *disc;
-+
-+ disc = tty_ldisc_ref(tty);
-+ if(test_bit(TTY_DONT_FLIP, &tty->flags))
-+ ret = -EAGAIN;
-+ else if(disc == NULL)
-+ ret = -EIO;
-+ else
-+ disc->receive_buf(tty, cp, fp, count);
-+ tty_ldisc_deref(disc);
-+ return ret;
-+
- }
-
- /*
-@@ -2032,7 +2395,7 @@
- {
- memset(tty, 0, sizeof(struct tty_struct));
- tty->magic = TTY_MAGIC;
-- tty->ldisc = ldiscs[N_TTY];
-+ tty_ldisc_assign(tty, tty_ldisc_get(N_TTY));
- tty->pgrp = -1;
- tty->flip.char_buf_ptr = tty->flip.char_buf;
- tty->flip.flag_buf_ptr = tty->flip.flag_buf;
-@@ -2217,7 +2580,7 @@
- void __init console_init(void)
- {
- /* Setup the default TTY line discipline. */
-- memset(ldiscs, 0, sizeof(ldiscs));
-+ memset(tty_ldiscs, 0, NR_LDISCS*sizeof(struct tty_ldisc));
- (void) tty_register_ldisc(N_TTY, &tty_ldisc_N_TTY);
-
- /*
-diff -Nur linux-2.4.27/drivers/char/tty_ioctl.c linux-2.4.27-plasmaroo/drivers/char/tty_ioctl.c
---- linux-2.4.27/drivers/char/tty_ioctl.c 2002-11-28 23:53:12.000000000 +0000
-+++ linux-2.4.27-plasmaroo/drivers/char/tty_ioctl.c 2004-11-07 14:03:04.506939352 +0000
-@@ -29,6 +29,8 @@
-
- #undef DEBUG
-
-+extern spinlock_t tty_termios_lock;
-+
- /*
- * Internal flag options for termios setting behavior
- */
-@@ -96,8 +98,17 @@
- {
- int canon_change;
- struct termios old_termios = *tty->termios;
-+ struct tty_ldisc *ld;
-+ unsigned long flags;
-+
-+ /*
-+ * Perform the actual termios internal changes under lock.
-+ */
-+
-+ /* FIXME: we need to decide on some locking/ordering semantics
-+ for the set_termios notification eventually */
-+ spin_lock_irqsave(&tty_termios_lock, flags);
-
-- cli();
- *tty->termios = *new_termios;
- unset_locked_termios(tty->termios, &old_termios, tty->termios_locked);
- canon_change = (old_termios.c_lflag ^ tty->termios->c_lflag) & ICANON;
-@@ -107,7 +118,6 @@
- tty->canon_data = 0;
- tty->erasing = 0;
- }
-- sti();
- if (canon_change && !L_ICANON(tty) && tty->read_cnt)
- /* Get characters left over from canonical mode. */
- wake_up_interruptible(&tty->read_wait);
-@@ -131,16 +141,20 @@
- }
- }
-
-- if (tty->driver.set_termios)
-- (*tty->driver.set_termios)(tty, &old_termios);
-+ ld = tty_ldisc_ref(tty);
-+ if (ld != NULL) {
-+ if (ld->set_termios)
-+ (ld->set_termios)(tty, &old_termios);
-+ tty_ldisc_deref(ld);
-+ }
-+ spin_unlock_irqrestore(&tty_termios_lock, flags);
-
-- if (tty->ldisc.set_termios)
-- (*tty->ldisc.set_termios)(tty, &old_termios);
- }
-
- static int set_termios(struct tty_struct * tty, unsigned long arg, int opt)
- {
- struct termios tmp_termios;
-+ struct tty_ldisc *ld;
- int retval = tty_check_change(tty);
-
- if (retval)
-@@ -157,8 +171,13 @@
- return -EFAULT;
- }
-
-- if ((opt & TERMIOS_FLUSH) && tty->ldisc.flush_buffer)
-- tty->ldisc.flush_buffer(tty);
-+ ld = tty_ldisc_ref(tty);
-+
-+ if (ld != NULL) {
-+ if ((opt & TERMIOS_FLUSH) && ld->flush_buffer)
-+ ld->flush_buffer(tty);
-+ tty_ldisc_deref(ld);
-+ }
-
- if (opt & TERMIOS_WAIT) {
- tty_wait_until_sent(tty, 0);
-@@ -223,12 +242,16 @@
- static int get_sgttyb(struct tty_struct * tty, struct sgttyb * sgttyb)
- {
- struct sgttyb tmp;
-+ unsigned long flags;
-
-+ spin_lock_irqsave(&tty_termios_lock, flags);
- tmp.sg_ispeed = 0;
- tmp.sg_ospeed = 0;
- tmp.sg_erase = tty->termios->c_cc[VERASE];
- tmp.sg_kill = tty->termios->c_cc[VKILL];
- tmp.sg_flags = get_sgflags(tty);
-+ spin_unlock_irqrestore(&tty_termios_lock, flags);
-+
- return copy_to_user(sgttyb, &tmp, sizeof(tmp)) ? -EFAULT : 0;
- }
-
-@@ -263,16 +286,19 @@
- int retval;
- struct sgttyb tmp;
- struct termios termios;
-+ unsigned long flags;
-
- retval = tty_check_change(tty);
- if (retval)
- return retval;
-- termios = *tty->termios;
- if (copy_from_user(&tmp, sgttyb, sizeof(tmp)))
- return -EFAULT;
-+ spin_lock_irqsave(&tty_termios_lock, flags);
-+ termios = *tty->termios;
- termios.c_cc[VERASE] = tmp.sg_erase;
- termios.c_cc[VKILL] = tmp.sg_kill;
- set_sgflags(&termios, tmp.sg_flags);
-+ spin_unlock_irqrestore(&tty_termios_lock, flags);
- change_termios(tty, &termios);
- return 0;
- }
-@@ -362,6 +388,8 @@
- {
- struct tty_struct * real_tty;
- int retval;
-+ struct tty_ldisc *ld;
-+ unsigned long flags;
-
- if (tty->driver.type == TTY_DRIVER_TYPE_PTY &&
- tty->driver.subtype == PTY_TYPE_MASTER)
-@@ -440,22 +468,26 @@
- retval = tty_check_change(tty);
- if (retval)
- return retval;
-+
-+ ld = tty_ldisc_ref(tty);
- switch (arg) {
- case TCIFLUSH:
-- if (tty->ldisc.flush_buffer)
-- tty->ldisc.flush_buffer(tty);
-+ if (ld->flush_buffer)
-+ ld->flush_buffer(tty);
- break;
- case TCIOFLUSH:
-- if (tty->ldisc.flush_buffer)
-- tty->ldisc.flush_buffer(tty);
-+ if (ld->flush_buffer)
-+ ld->flush_buffer(tty);
- /* fall through */
- case TCOFLUSH:
- if (tty->driver.flush_buffer)
- tty->driver.flush_buffer(tty);
- break;
- default:
-+ tty_ldisc_deref(ld);
- return -EINVAL;
- }
-+ tty_ldisc_deref(ld);
- return 0;
- case TIOCOUTQ:
- return put_user(tty->driver.chars_in_buffer ?
-@@ -501,9 +533,11 @@
- case TIOCSSOFTCAR:
- if (get_user(arg, (unsigned int *) arg))
- return -EFAULT;
-+ spin_lock_irqsave(&tty_termios_lock, flags);
- tty->termios->c_cflag =
- ((tty->termios->c_cflag & ~CLOCAL) |
- (arg ? CLOCAL : 0));
-+ spin_unlock_irqrestore(&tty_termios_lock, flags);
- return 0;
- default:
- return -ENOIOCTLCMD;
-diff -Nur linux-2.4.27/drivers/net/ppp_async.c linux-2.4.27-plasmaroo/drivers/net/ppp_async.c
---- linux-2.4.27/drivers/net/ppp_async.c 2002-08-03 01:39:44.000000000 +0100
-+++ linux-2.4.27-plasmaroo/drivers/net/ppp_async.c 2004-11-07 14:02:20.057696664 +0000
-@@ -117,6 +117,9 @@
- * frees the memory that ppp_asynctty_receive is using. The best
- * way to fix this is to use a rwlock in the tty struct, but for now
- * we use a single global rwlock for all ttys in ppp line discipline.
-+ *
-+ * FIXME: this is no longer true. The _close path for the ldisc is
-+ * now guaranteed to be sane.
- */
- static rwlock_t disc_data_lock = RW_LOCK_UNLOCKED;
-
-@@ -139,7 +142,8 @@
- }
-
- /*
-- * Called when a tty is put into PPP line discipline.
-+ * Called when a tty is put into PPP line discipline. Called in process
-+ * context.
- */
- static int
- ppp_asynctty_open(struct tty_struct *tty)
-@@ -248,6 +252,11 @@
- return -EAGAIN;
- }
-
-+/*
-+ * Called in process context only. May be re-entered by multiple
-+ * ioctl calling threads.
-+ */
-+
- static int
- ppp_asynctty_ioctl(struct tty_struct *tty, struct file *file,
- unsigned int cmd, unsigned long arg)
-@@ -714,7 +723,8 @@
-
- /*
- * Flush output from our internal buffers.
-- * Called for the TCFLSH ioctl.
-+ * Called for the TCFLSH ioctl. Can be entered in parallel
-+ * but this is covered by the xmit_lock.
- */
- static void
- ppp_async_flush_output(struct asyncppp *ap)
-@@ -819,7 +829,9 @@
- ppp_input_error(&ap->chan, code);
- }
-
--/* called when the tty driver has data for us. */
-+/* Called when the tty driver has data for us. Runs parallel with the
-+ other ldisc functions but will not be re-entered */
-+
- static void
- ppp_async_input(struct asyncppp *ap, const unsigned char *buf,
- char *flags, int count)
-diff -Nur linux-2.4.27/drivers/net/ppp_synctty.c linux-2.4.27-plasmaroo/drivers/net/ppp_synctty.c
---- linux-2.4.27/drivers/net/ppp_synctty.c 2002-08-03 01:39:44.000000000 +0100
-+++ linux-2.4.27-plasmaroo/drivers/net/ppp_synctty.c 2004-11-07 14:02:20.077693624 +0000
-@@ -172,6 +172,8 @@
- * frees the memory that ppp_synctty_receive is using. The best
- * way to fix this is to use a rwlock in the tty struct, but for now
- * we use a single global rwlock for all ttys in ppp line discipline.
-+ *
-+ * FIXME: Fixed in tty_io nowdays.
- */
- static rwlock_t disc_data_lock = RW_LOCK_UNLOCKED;
-
-diff -Nur linux-2.4.27/drivers/net/slip.c linux-2.4.27-plasmaroo/drivers/net/slip.c
---- linux-2.4.27/drivers/net/slip.c 2002-11-28 23:53:14.000000000 +0000
-+++ linux-2.4.27-plasmaroo/drivers/net/slip.c 2004-11-07 14:02:20.086692256 +0000
-@@ -670,7 +670,9 @@
- * Handle the 'receiver data ready' interrupt.
- * This function is called by the 'tty_io' module in the kernel when
- * a block of SLIP data has been received, which can now be decapsulated
-- * and sent on to some IP layer for further processing.
-+ * and sent on to some IP layer for further processing. This will not
-+ * be re-entered while running but other ldisc functions may be called
-+ * in parallel
- */
-
- static void slip_receive_buf(struct tty_struct *tty, const unsigned char *cp, char *fp, int count)
-@@ -826,9 +828,11 @@
- * SLIP line discipline is called for. Because we are
- * sure the tty line exists, we only have to link it to
- * a free SLIP channel...
-+ *
-+ * Called in process context serialized from other ldisc calls.
- */
--static int
--slip_open(struct tty_struct *tty)
-+
-+static int slip_open(struct tty_struct *tty)
- {
- struct slip *sl;
- int err;
-@@ -910,6 +914,9 @@
- }
-
- /*
-+
-+ FIXME: 1,2 are fixed 3 was never true anyway.
-+
- Let me to blame a bit.
- 1. TTY module calls this funstion on soft interrupt.
- 2. TTY module calls this function WITH MASKED INTERRUPTS!
-@@ -928,9 +935,8 @@
-
- /*
- * Close down a SLIP channel.
-- * This means flushing out any pending queues, and then restoring the
-- * TTY line discipline to what it was before it got hooked to SLIP
-- * (which usually is TTY again).
-+ * This means flushing out any pending queues, and then returning. This
-+ * call is serialized against other ldisc functions.
- */
- static void
- slip_close(struct tty_struct *tty)
-diff -Nur linux-2.4.27/drivers/sbus/char/zs.c linux-2.4.27-plasmaroo/drivers/sbus/char/zs.c
---- linux-2.4.27/drivers/sbus/char/zs.c 2002-08-03 01:39:44.000000000 +0100
-+++ linux-2.4.27-plasmaroo/drivers/sbus/char/zs.c 2004-11-07 14:02:20.331655016 +0000
-@@ -1605,10 +1605,10 @@
- tty->closing = 0;
- info->event = 0;
- info->tty = 0;
-- if (tty->ldisc.num != ldiscs[N_TTY].num) {
-+ if (tty->ldisc.num != N_TTY) {
- if (tty->ldisc.close)
- (tty->ldisc.close)(tty);
-- tty->ldisc = ldiscs[N_TTY];
-+ tty->ldisc = *(tty_ldisc_get(N_TTY));
- tty->termios->c_line = N_TTY;
- if (tty->ldisc.open)
- (tty->ldisc.open)(tty);
-diff -Nur linux-2.4.27/fs/proc/proc_tty.c linux-2.4.27-plasmaroo/fs/proc/proc_tty.c
---- linux-2.4.27/fs/proc/proc_tty.c 2000-04-21 23:17:57.000000000 +0100
-+++ linux-2.4.27-plasmaroo/fs/proc/proc_tty.c 2004-11-07 14:02:20.042698944 +0000
-@@ -15,8 +15,6 @@
- #include <asm/bitops.h>
-
- extern struct tty_driver *tty_drivers; /* linked list of tty drivers */
--extern struct tty_ldisc ldiscs[];
--
-
- static int tty_drivers_read_proc(char *page, char **start, off_t off,
- int count, int *eof, void *data);
-@@ -106,12 +104,15 @@
- int i;
- int len = 0;
- off_t begin = 0;
--
-+ struct tty_ldisc *ld;
-+
- for (i=0; i < NR_LDISCS; i++) {
-- if (!(ldiscs[i].flags & LDISC_FLAG_DEFINED))
-+ ld = tty_ldisc_get(i);
-+ if (ld == NULL)
- continue;
- len += sprintf(page+len, "%-10s %2d\n",
-- ldiscs[i].name ? ldiscs[i].name : "???", i);
-+ ld->name ? ld->name : "???", i);
-+ tty_ldisc_put(i);
- if (len+begin > off+count)
- break;
- if (len+begin < off) {
-diff -Nur linux-2.4.27/include/linux/tty.h linux-2.4.27-plasmaroo/include/linux/tty.h
---- linux-2.4.27/include/linux/tty.h 2003-06-13 15:51:39.000000000 +0100
-+++ linux-2.4.27-plasmaroo/include/linux/tty.h 2004-11-07 14:02:20.043698792 +0000
-@@ -322,26 +322,28 @@
- * tty->write. Thus, you must use the inline functions set_bit() and
- * clear_bit() to make things atomic.
- */
--#define TTY_THROTTLED 0
--#define TTY_IO_ERROR 1
--#define TTY_OTHER_CLOSED 2
--#define TTY_EXCLUSIVE 3
--#define TTY_DEBUG 4
--#define TTY_DO_WRITE_WAKEUP 5
--#define TTY_PUSH 6
--#define TTY_CLOSING 7
--#define TTY_DONT_FLIP 8
--#define TTY_HW_COOK_OUT 14
--#define TTY_HW_COOK_IN 15
--#define TTY_PTY_LOCK 16
--#define TTY_NO_WRITE_SPLIT 17
-+#define TTY_THROTTLED 0 /* Call unthrottle() at threshold min */
-+#define TTY_IO_ERROR 1 /* Canse an I/O error (may be no ldisc too) */
-+#define TTY_OTHER_CLOSED 2 /* Other side (if any) has closed */
-+#define TTY_EXCLUSIVE 3 /* Exclusive open mode */
-+#define TTY_DEBUG 4 /* Debugging */
-+#define TTY_DO_WRITE_WAKEUP 5 /* Call write_wakeup after queuing new */
-+#define TTY_PUSH 6 /* n_tty private */
-+#define TTY_CLOSING 7 /* ->close() in progress */
-+#define TTY_DONT_FLIP 8 /* Defer buffer flip */
-+#define TTY_LDISC 9 /* Line discipline attached */
-+#define TTY_HW_COOK_OUT 14 /* Hardware can do output cooking */
-+#define TTY_HW_COOK_IN 15 /* Hardware can do input cooking */
-+#define TTY_PTY_LOCK 16 /* pty private */
-+#define TTY_NO_WRITE_SPLIT 17 /* Preserve write boundaries to driver */
-+#define TTY_HUPPED 18 /* Post driver->hangup() */
-
- #define TTY_WRITE_FLUSH(tty) tty_write_flush((tty))
-
- extern void tty_write_flush(struct tty_struct *);
-
- extern struct termios tty_std_termios;
--extern struct tty_ldisc ldiscs[];
-+extern struct tty_ldisc tty_ldiscs[];
- extern int fg_console, last_console, want_console;
-
- extern int kmsg_redirect;
-@@ -396,6 +398,16 @@
- extern void tty_flip_buffer_push(struct tty_struct *tty);
- extern int tty_get_baud_rate(struct tty_struct *tty);
-
-+extern struct tty_ldisc *tty_ldisc_ref(struct tty_struct *);
-+extern void tty_ldisc_deref(struct tty_ldisc *);
-+extern struct tty_ldisc *tty_ldisc_ref_wait(struct tty_struct *);
-+
-+extern struct tty_ldisc *tty_ldisc_get(int);
-+extern void tty_ldisc_put(int);
-+
-+extern void tty_wakeup(struct tty_struct *tty);
-+
-+
- /* n_tty.c */
- extern struct tty_ldisc tty_ldisc_N_TTY;
-
-diff -Nur linux-2.4.27/include/linux/tty_ldisc.h linux-2.4.27-plasmaroo/include/linux/tty_ldisc.h
---- linux-2.4.27/include/linux/tty_ldisc.h 2001-11-22 19:46:19.000000000 +0000
-+++ linux-2.4.27-plasmaroo/include/linux/tty_ldisc.h 2004-11-07 14:02:20.044698640 +0000
-@@ -129,6 +129,7 @@
- char *fp, int count);
- int (*receive_room)(struct tty_struct *);
- void (*write_wakeup)(struct tty_struct *);
-+ int refcount;
- };
-
- #define TTY_LDISC_MAGIC 0x5403
diff --git a/sys-kernel/hppa-sources/files/CAN-2004-0882-0883.patch b/sys-kernel/hppa-sources/files/CAN-2004-0882-0883.patch
deleted file mode 100644
index 63c5ba30403f..000000000000
--- a/sys-kernel/hppa-sources/files/CAN-2004-0882-0883.patch
+++ /dev/null
@@ -1,97 +0,0 @@
-diff -ur linux-2.4.27/fs/smbfs/proc.c linux-2.4.28/fs/smbfs/proc.c
---- linux-2.4.27/fs/smbfs/proc.c 2004-11-12 19:32:24.000000000 +0000
-+++ linux-2.4.28/fs/smbfs/proc.c 2004-11-19 20:18:27.000000000 +0000
-@@ -1289,10 +1289,12 @@
- data_len = WVAL(buf, 1);
-
- /* we can NOT simply trust the data_len given by the server ... */
-- if (data_len > server->packet_size - (buf+3 - server->packet)) {
-- printk(KERN_ERR "smb_proc_read: invalid data length!! "
-- "%d > %d - (%p - %p)\n",
-- data_len, server->packet_size, buf+3, server->packet);
-+ if (data_len > count ||
-+ (buf+3 - server->packet) + data_len > server->packet_size) {
-+ printk(KERN_ERR "smb_proc_read: invalid data length/offset!! "
-+ "%d > %d || (%p - %p) + %d > %d\n",
-+ data_len, count,
-+ buf+3, server->packet, data_len, server->packet_size);
- result = -EIO;
- goto out;
- }
-@@ -1378,10 +1380,12 @@
- buf = smb_base(server->packet) + data_off;
-
- /* we can NOT simply trust the info given by the server ... */
-- if (data_len > server->packet_size - (buf - server->packet)) {
-- printk(KERN_ERR "smb_proc_read: invalid data length!! "
-- "%d > %d - (%p - %p)\n",
-- data_len, server->packet_size, buf, server->packet);
-+ if (data_len > count ||
-+ (buf - server->packet) + data_len > server->packet_size) {
-+ printk(KERN_ERR "smb_proc_readX: invalid data length/offset!! "
-+ "%d > %d || (%p - %p) + %d > %d\n",
-+ data_len, count,
-+ buf, server->packet, data_len, server->packet_size);
- result = -EIO;
- goto out;
- }
-diff -ur linux-2.4.27/fs/smbfs/sock.c linux-2.4.28/fs/smbfs/sock.c
---- linux-2.4.27/fs/smbfs/sock.c 2004-11-12 19:32:24.000000000 +0000
-+++ linux-2.4.28/fs/smbfs/sock.c 2004-11-19 20:18:27.000000000 +0000
-@@ -571,7 +571,11 @@
- parm_disp, parm_offset, parm_count,
- data_disp, data_offset, data_count);
- *parm = base + parm_offset;
-+ if (*parm - inbuf + parm_tot > server->packet_size)
-+ goto out_bad_parm;
- *data = base + data_offset;
-+ if (*data - inbuf + data_tot > server->packet_size)
-+ goto out_bad_data;
- goto success;
- }
-
-@@ -591,6 +595,8 @@
- rcv_buf = smb_vmalloc(buf_len);
- if (!rcv_buf)
- goto out_no_mem;
-+ memset(rcv_buf, 0, buf_len);
-+
- *parm = rcv_buf;
- *data = rcv_buf + total_p;
- } else if (data_tot > total_d || parm_tot > total_p)
-@@ -598,8 +604,12 @@
-
- if (parm_disp + parm_count > total_p)
- goto out_bad_parm;
-+ if (parm_offset + parm_count > server->packet_size)
-+ goto out_bad_parm;
- if (data_disp + data_count > total_d)
- goto out_bad_data;
-+ if (data_offset + data_count > server->packet_size)
-+ goto out_bad_data;
- memcpy(*parm + parm_disp, base + parm_offset, parm_count);
- memcpy(*data + data_disp, base + data_offset, data_count);
-
-@@ -610,8 +620,11 @@
- * Check whether we've received all of the data. Note that
- * we use the packet totals -- total lengths might shrink!
- */
-- if (data_len >= data_tot && parm_len >= parm_tot)
-+ if (data_len >= data_tot && parm_len >= parm_tot) {
-+ data_len = data_tot;
-+ parm_len = parm_tot;
- break;
-+ }
- }
-
- /*
-@@ -625,6 +638,9 @@
- server->packet = rcv_buf;
- rcv_buf = inbuf;
- } else {
-+ if (parm_len + data_len > buf_len)
-+ goto out_data_grew;
-+
- PARANOIA("copying data, old size=%d, new size=%u\n",
- server->packet_size, buf_len);
- memcpy(inbuf, rcv_buf, parm_len + data_len);
diff --git a/sys-kernel/hppa-sources/files/CAN-2004-1074.patch b/sys-kernel/hppa-sources/files/CAN-2004-1074.patch
deleted file mode 100644
index 11846801b90d..000000000000
--- a/sys-kernel/hppa-sources/files/CAN-2004-1074.patch
+++ /dev/null
@@ -1,63 +0,0 @@
-diff -uNr linux-2.4.27-pa4-r2.orig/fs/binfmt_aout.c linux-2.4.27-pa4-r2/fs/binfmt_aout.c
---- linux-2.4.27-pa4-r2.orig/fs/binfmt_aout.c 2004-12-08 18:24:03.899156592 +0100
-+++ linux-2.4.27-pa4-r2/fs/binfmt_aout.c 2004-12-08 18:24:25.898812136 +0100
-@@ -39,13 +39,18 @@
- NULL, THIS_MODULE, load_aout_binary, load_aout_library, aout_core_dump, PAGE_SIZE
- };
-
--static void set_brk(unsigned long start, unsigned long end)
-+#define BAD_ADDR(x) ((unsigned long)(x) >= TASK_SIZE)
-+
-+static int set_brk(unsigned long start, unsigned long end)
- {
- start = PAGE_ALIGN(start);
- end = PAGE_ALIGN(end);
-- if (end <= start)
-- return;
-- do_brk(start, end - start);
-+ if (end > start) {
-+ unsigned long addr = do_brk(start, end - start);
-+ if (BAD_ADDR(addr))
-+ return addr;
-+ }
-+ return 0;
- }
-
- /*
-@@ -405,7 +410,11 @@
- beyond_if:
- set_binfmt(&aout_format);
-
-- set_brk(current->mm->start_brk, current->mm->brk);
-+ retval = set_brk(current->mm->start_brk, current->mm->brk);
-+ if (retval < 0) {
-+ send_sig(SIGKILL, current, 0);
-+ return retval;
-+ }
-
- retval = setup_arg_pages(bprm);
- if (retval < 0) {
-diff -uNr linux-2.4.27-pa4-r2.orig/fs/exec.c linux-2.4.27-pa4-r2/fs/exec.c
---- linux-2.4.27-pa4-r2.orig/fs/exec.c 2004-12-08 18:24:03.808170424 +0100
-+++ linux-2.4.27-pa4-r2/fs/exec.c 2004-12-08 18:26:20.552382144 +0100
-@@ -382,6 +382,7 @@
-
- down_write(&current->mm->mmap_sem);
- {
-+ struct vm_area_struct *vma;
- mpnt->vm_mm = mm;
- #ifdef ARCH_STACK_GROWSUP
- mpnt->vm_start = stack_base;
-@@ -397,6 +398,12 @@
- mpnt->vm_pgoff = 0;
- mpnt->vm_file = NULL;
- mpnt->vm_private_data = (void *) 0;
-+ vma = find_vma(current->mm, mpnt->vm_start);
-+ if (vma) {
-+ up_write(&current->mm->mmap_sem);
-+ kmem_cache_free(vm_area_cachep, mpnt);
-+ return -ENOMEM;
-+ }
- insert_vm_struct(mm, mpnt);
- mm->total_vm = (mpnt->vm_end - mpnt->vm_start) >> PAGE_SHIFT;
- }
diff --git a/sys-kernel/hppa-sources/files/CAN-2004-1235.patch b/sys-kernel/hppa-sources/files/CAN-2004-1235.patch
new file mode 100644
index 000000000000..6095e844d5f1
--- /dev/null
+++ b/sys-kernel/hppa-sources/files/CAN-2004-1235.patch
@@ -0,0 +1,303 @@
+diff -ur linux-2.6.10/arch/mips/kernel/irixelf.c linux-2.6.10.plasmaroo/arch/mips/kernel/irixelf.c
+--- linux-2.6.10/arch/mips/kernel/irixelf.c 2004-12-24 21:35:50.000000000 +0000
++++ linux-2.6.10.plasmaroo/arch/mips/kernel/irixelf.c 2005-01-07 15:36:00.383356800 +0000
+@@ -127,7 +127,7 @@
+ end = PAGE_ALIGN(end);
+ if (end <= start)
+ return;
+- do_brk(start, end - start);
++ do_brk_locked(start, end - start);
+ }
+
+
+@@ -375,7 +375,7 @@
+
+ /* Map the last of the bss segment */
+ if (last_bss > len) {
+- do_brk(len, (last_bss - len));
++ do_brk_locked(len, (last_bss - len));
+ }
+ kfree(elf_phdata);
+
+@@ -562,7 +562,7 @@
+ unsigned long v;
+ struct prda *pp;
+
+- v = do_brk (PRDA_ADDRESS, PAGE_SIZE);
++ v = do_brk_locked (PRDA_ADDRESS, PAGE_SIZE);
+
+ if (v < 0)
+ return;
+@@ -853,7 +853,7 @@
+ len = (elf_phdata->p_filesz + elf_phdata->p_vaddr+ 0xfff) & 0xfffff000;
+ bss = elf_phdata->p_memsz + elf_phdata->p_vaddr;
+ if (bss > len)
+- do_brk(len, bss-len);
++ do_brk_locked(len, bss-len);
+ kfree(elf_phdata);
+ return 0;
+ }
+diff -ur linux-2.6.10/arch/sparc64/kernel/binfmt_aout32.c linux-2.6.10.plasmaroo/arch/sparc64/kernel/binfmt_aout32.c
+--- linux-2.6.10/arch/sparc64/kernel/binfmt_aout32.c 2004-12-24 21:34:45.000000000 +0000
++++ linux-2.6.10.plasmaroo/arch/sparc64/kernel/binfmt_aout32.c 2005-01-07 15:36:00.432349352 +0000
+@@ -49,7 +49,7 @@
+ end = PAGE_ALIGN(end);
+ if (end <= start)
+ return;
+- do_brk(start, end - start);
++ do_brk_locked(start, end - start);
+ }
+
+ /*
+@@ -246,10 +246,10 @@
+ if (N_MAGIC(ex) == NMAGIC) {
+ loff_t pos = fd_offset;
+ /* Fuck me plenty... */
+- error = do_brk(N_TXTADDR(ex), ex.a_text);
++ error = do_brk_locked(N_TXTADDR(ex), ex.a_text);
+ bprm->file->f_op->read(bprm->file, (char __user *)N_TXTADDR(ex),
+ ex.a_text, &pos);
+- error = do_brk(N_DATADDR(ex), ex.a_data);
++ error = do_brk_locked(N_DATADDR(ex), ex.a_data);
+ bprm->file->f_op->read(bprm->file, (char __user *)N_DATADDR(ex),
+ ex.a_data, &pos);
+ goto beyond_if;
+@@ -257,7 +257,7 @@
+
+ if (N_MAGIC(ex) == OMAGIC) {
+ loff_t pos = fd_offset;
+- do_brk(N_TXTADDR(ex) & PAGE_MASK,
++ do_brk_locked(N_TXTADDR(ex) & PAGE_MASK,
+ ex.a_text+ex.a_data + PAGE_SIZE - 1);
+ bprm->file->f_op->read(bprm->file, (char __user *)N_TXTADDR(ex),
+ ex.a_text+ex.a_data, &pos);
+@@ -272,7 +272,7 @@
+
+ if (!bprm->file->f_op->mmap) {
+ loff_t pos = fd_offset;
+- do_brk(0, ex.a_text+ex.a_data);
++ do_brk_locked(0, ex.a_text+ex.a_data);
+ bprm->file->f_op->read(bprm->file,
+ (char __user *)N_TXTADDR(ex),
+ ex.a_text+ex.a_data, &pos);
+@@ -389,7 +389,7 @@
+ len = PAGE_ALIGN(ex.a_text + ex.a_data);
+ bss = ex.a_text + ex.a_data + ex.a_bss;
+ if (bss > len) {
+- error = do_brk(start_addr + len, bss - len);
++ error = do_brk_locked(start_addr + len, bss - len);
+ retval = error;
+ if (error != start_addr + len)
+ goto out;
+diff -Nur linux-2.6.10/arch/x86_64/ia32/ia32_aout.c linux-2.6.10.plasmaroo/arch/x86_64/ia32/ia32_aout.c
+--- linux-2.6.10/arch/x86_64/ia32/ia32_aout.c 2005-01-03 16:17:04.000000000 -0200
++++ linux-2.6.10.plasmaroo/arch/x86_64/ia32/ia32_aout.c 2005-01-03 16:46:53.846823360 -0200
+@@ -115,7 +115,7 @@
+ end = PAGE_ALIGN(end);
+ if (end <= start)
+ return;
+- do_brk(start, end - start);
++ do_brk_locked(start, end - start);
+ }
+
+ #if CORE_DUMP
+@@ -325,7 +325,7 @@
+ pos = 32;
+ map_size = ex.a_text+ex.a_data;
+
+- error = do_brk(text_addr & PAGE_MASK, map_size);
++ error = do_brk_locked(text_addr & PAGE_MASK, map_size);
+ if (error != (text_addr & PAGE_MASK)) {
+ send_sig(SIGKILL, current, 0);
+ return error;
+@@ -361,7 +361,7 @@
+
+ if (!bprm->file->f_op->mmap||((fd_offset & ~PAGE_MASK) != 0)) {
+ loff_t pos = fd_offset;
+- do_brk(N_TXTADDR(ex), ex.a_text+ex.a_data);
++ do_brk_locked(N_TXTADDR(ex), ex.a_text+ex.a_data);
+ bprm->file->f_op->read(bprm->file,(char *)N_TXTADDR(ex),
+ ex.a_text+ex.a_data, &pos);
+ flush_icache_range((unsigned long) N_TXTADDR(ex),
+@@ -470,7 +470,7 @@
+ }
+ #endif
+
+- do_brk(start_addr, ex.a_text + ex.a_data + ex.a_bss);
++ do_brk_locked(start_addr, ex.a_text + ex.a_data + ex.a_bss);
+
+ file->f_op->read(file, (char *)start_addr,
+ ex.a_text + ex.a_data, &pos);
+@@ -494,7 +494,7 @@
+ len = PAGE_ALIGN(ex.a_text + ex.a_data);
+ bss = ex.a_text + ex.a_data + ex.a_bss;
+ if (bss > len) {
+- error = do_brk(start_addr + len, bss - len);
++ error = do_brk_locked(start_addr + len, bss - len);
+ retval = error;
+ if (error != start_addr + len)
+ goto out;
+diff -ur linux-2.6.10/fs/binfmt_aout.c linux-2.6.10.plasmaroo/fs/binfmt_aout.c
+--- linux-2.6.10/fs/binfmt_aout.c 2004-12-24 21:35:50.000000000 +0000
++++ linux-2.6.10.plasmaroo/fs/binfmt_aout.c 2005-01-07 15:36:00.000000000 +0000
+@@ -50,7 +50,7 @@
+ start = PAGE_ALIGN(start);
+ end = PAGE_ALIGN(end);
+ if (end > start) {
+- unsigned long addr = do_brk(start, end - start);
++ unsigned long addr = do_brk_locked(start, end - start);
+ if (BAD_ADDR(addr))
+ return addr;
+ }
+@@ -323,10 +323,10 @@
+ loff_t pos = fd_offset;
+ /* Fuck me plenty... */
+ /* <AOL></AOL> */
+- error = do_brk(N_TXTADDR(ex), ex.a_text);
++ error = do_brk_locked(N_TXTADDR(ex), ex.a_text);
+ bprm->file->f_op->read(bprm->file, (char *) N_TXTADDR(ex),
+ ex.a_text, &pos);
+- error = do_brk(N_DATADDR(ex), ex.a_data);
++ error = do_brk_locked(N_DATADDR(ex), ex.a_data);
+ bprm->file->f_op->read(bprm->file, (char *) N_DATADDR(ex),
+ ex.a_data, &pos);
+ goto beyond_if;
+@@ -347,7 +347,7 @@
+ map_size = ex.a_text+ex.a_data;
+ #endif
+
+- error = do_brk(text_addr & PAGE_MASK, map_size);
++ error = do_brk_locked(text_addr & PAGE_MASK, map_size);
+ if (error != (text_addr & PAGE_MASK)) {
+ send_sig(SIGKILL, current, 0);
+ return error;
+@@ -382,7 +382,7 @@
+
+ if (!bprm->file->f_op->mmap||((fd_offset & ~PAGE_MASK) != 0)) {
+ loff_t pos = fd_offset;
+- do_brk(N_TXTADDR(ex), ex.a_text+ex.a_data);
++ do_brk_locked(N_TXTADDR(ex), ex.a_text+ex.a_data);
+ bprm->file->f_op->read(bprm->file,
+ (char __user *)N_TXTADDR(ex),
+ ex.a_text+ex.a_data, &pos);
+@@ -488,7 +488,7 @@
+ error_time = jiffies;
+ }
+
+- do_brk(start_addr, ex.a_text + ex.a_data + ex.a_bss);
++ do_brk_locked(start_addr, ex.a_text + ex.a_data + ex.a_bss);
+
+ file->f_op->read(file, (char __user *)start_addr,
+ ex.a_text + ex.a_data, &pos);
+@@ -512,7 +512,7 @@
+ len = PAGE_ALIGN(ex.a_text + ex.a_data);
+ bss = ex.a_text + ex.a_data + ex.a_bss;
+ if (bss > len) {
+- error = do_brk(start_addr + len, bss - len);
++ error = do_brk_locked(start_addr + len, bss - len);
+ retval = error;
+ if (error != start_addr + len)
+ goto out;
+diff -ur linux-2.6.10/fs/binfmt_elf.c linux-2.6.10.plasmaroo/fs/binfmt_elf.c
+--- linux-2.6.10/fs/binfmt_elf.c 2004-12-24 21:34:33.000000000 +0000
++++ linux-2.6.10.plasmaroo/fs/binfmt_elf.c 2005-01-07 15:36:00.000000000 +0000
+@@ -88,7 +88,7 @@
+ start = ELF_PAGEALIGN(start);
+ end = ELF_PAGEALIGN(end);
+ if (end > start) {
+- unsigned long addr = do_brk(start, end - start);
++ unsigned long addr = do_brk_locked(start, end - start);
+ if (BAD_ADDR(addr))
+ return addr;
+ }
+@@ -408,7 +408,7 @@
+
+ /* Map the last of the bss segment */
+ if (last_bss > elf_bss) {
+- error = do_brk(elf_bss, last_bss - elf_bss);
++ error = do_brk_locked(elf_bss, last_bss - elf_bss);
+ if (BAD_ADDR(error))
+ goto out_close;
+ }
+@@ -448,7 +448,7 @@
+ goto out;
+ }
+
+- do_brk(0, text_data);
++ do_brk_locked(0, text_data);
+ if (!interpreter->f_op || !interpreter->f_op->read)
+ goto out;
+ if (interpreter->f_op->read(interpreter, addr, text_data, &offset) < 0)
+@@ -456,7 +456,7 @@
+ flush_icache_range((unsigned long)addr,
+ (unsigned long)addr + text_data);
+
+- do_brk(ELF_PAGESTART(text_data + ELF_MIN_ALIGN - 1),
++ do_brk_locked(ELF_PAGESTART(text_data + ELF_MIN_ALIGN - 1),
+ interp_ex->a_bss);
+ elf_entry = interp_ex->a_entry;
+
+@@ -1025,7 +1025,7 @@
+ len = ELF_PAGESTART(elf_phdata->p_filesz + elf_phdata->p_vaddr + ELF_MIN_ALIGN - 1);
+ bss = elf_phdata->p_memsz + elf_phdata->p_vaddr;
+ if (bss > len)
+- do_brk(len, bss - len);
++ do_brk_locked(len, bss - len);
+ error = 0;
+
+ out_free_ph:
+diff -ur linux-2.6.10/include/linux/mm.h linux-2.6.10.plasmaroo/include/linux/mm.h
+--- linux-2.6.10/include/linux/mm.h 2004-12-24 21:33:50.000000000 +0000
++++ linux-2.6.10.plasmaroo/include/linux/mm.h 2005-01-07 15:36:00.000000000 +0000
+@@ -704,6 +704,7 @@
+ extern int do_munmap(struct mm_struct *, unsigned long, size_t);
+
+ extern unsigned long do_brk(unsigned long, unsigned long);
++extern unsigned long do_brk_locked(unsigned long, unsigned long);
+
+ /* filemap.c */
+ extern unsigned long page_unuse(struct page *);
+diff -ur linux-2.6.10/mm/mmap.c linux-2.6.10.plasmaroo/mm/mmap.c
+--- linux-2.6.10/mm/mmap.c 2004-12-24 21:35:00.000000000 +0000
++++ linux-2.6.10.plasmaroo/mm/mmap.c 2005-01-07 15:36:04.000000000 +0000
+@@ -1826,6 +1826,20 @@
+
+ EXPORT_SYMBOL(do_brk);
+
++/* locking version of do_brk. */
++unsigned long do_brk_locked(unsigned long addr, unsigned long len)
++{
++ unsigned long ret;
++
++ down_write(&current->mm->mmap_sem);
++ ret = do_brk(addr, len);
++ up_write(&current->mm->mmap_sem);
++
++ return ret;
++}
++
++EXPORT_SYMBOL(do_brk_locked);
++
+ /* Release all mmaps. */
+ void exit_mmap(struct mm_struct *mm)
+ {
+@@ -1952,3 +1966,4 @@
+ }
+ return new_vma;
+ }
++
+diff -ur linux-2.6.10/mm/nommu.c linux-2.6.10.plasmaroo/mm/nommu.c
+--- linux-2.6.10/mm/nommu.c 2004-12-24 21:35:25.000000000 +0000
++++ linux-2.6.10.plasmaroo/mm/nommu.c 2005-01-07 15:30:24.000000000 +0000
+@@ -557,6 +557,11 @@
+ return -ENOMEM;
+ }
+
++unsigned long do_brk_locked(unsigned long addr, unsigned long len)
++{
++ return -ENOMEM;
++}
++
+ struct vm_area_struct * find_vma(struct mm_struct * mm, unsigned long addr)
+ {
+ return NULL;
diff --git a/sys-kernel/hppa-sources/files/CAN-2004-685.patch b/sys-kernel/hppa-sources/files/CAN-2004-685.patch
deleted file mode 100644
index d1be834cc8a5..000000000000
--- a/sys-kernel/hppa-sources/files/CAN-2004-685.patch
+++ /dev/null
@@ -1,83 +0,0 @@
-# This is a BitKeeper generated diff -Nru style patch.
-#
-# ChangeSet
-# 2004/07/26 19:14:16-03:00 mjc@redhat.com
-# [PATCH] USB: more sparse fixes
-#
-# Back in October 2003 Arnaldo commited some fixes prior to 2.6 for some leaking info to userspace in the
-# usb drivers:
-# http://linux.bkbits.net:8080/linux-2.6/cset@3f986b35LyBKc-OxB8G6k22oOjgYTQ
-#
-# The corresponding changes have not been commited to 2.4, or included in
-# the previous sparse fixes.
-#
-# drivers/usb/audio.c
-# 2004/07/15 08:46:52-03:00 mjc@redhat.com +4 -0
-# USB: more sparse fixes
-#
-# drivers/usb/brlvger.c
-# 2004/07/15 08:47:27-03:00 mjc@redhat.com +1 -0
-# USB: more sparse fixes
-#
-# drivers/usb/serial/io_edgeport.c
-# 2004/07/15 08:48:06-03:00 mjc@redhat.com +1 -0
-# USB: more sparse fixes
-#
-# drivers/usb/vicam.c
-# 2004/07/15 08:47:13-03:00 mjc@redhat.com +1 -0
-# USB: more sparse fixes
-#
-diff -Nru a/drivers/usb/audio.c b/drivers/usb/audio.c
---- a/drivers/usb/audio.c 2004-08-08 07:41:30 -07:00
-+++ b/drivers/usb/audio.c 2004-08-08 07:41:30 -07:00
-@@ -2141,6 +2141,8 @@
-
- if (cmd == SOUND_MIXER_INFO) {
- mixer_info info;
-+
-+ memset(&info, 0, sizeof(info));
- strncpy(info.id, "USB_AUDIO", sizeof(info.id));
- strncpy(info.name, "USB Audio Class Driver", sizeof(info.name));
- info.modify_counter = ms->modcnt;
-@@ -2150,6 +2152,8 @@
- }
- if (cmd == SOUND_OLD_MIXER_INFO) {
- _old_mixer_info info;
-+
-+ memset(&info, 0, sizeof(info));
- strncpy(info.id, "USB_AUDIO", sizeof(info.id));
- strncpy(info.name, "USB Audio Class Driver", sizeof(info.name));
- if (copy_to_user((void *)arg, &info, sizeof(info)))
-diff -Nru a/drivers/usb/brlvger.c b/drivers/usb/brlvger.c
---- a/drivers/usb/brlvger.c 2004-08-08 07:41:30 -07:00
-+++ b/drivers/usb/brlvger.c 2004-08-08 07:41:30 -07:00
-@@ -743,6 +743,7 @@
- case BRLVGER_GET_INFO: {
- struct brlvger_info vi;
-
-+ memset(&vi, 0, sizeof(vi));
- strncpy(vi.driver_version, DRIVER_VERSION,
- sizeof(vi.driver_version));
- vi.driver_version[sizeof(vi.driver_version)-1] = 0;
-diff -Nru a/drivers/usb/serial/io_edgeport.c b/drivers/usb/serial/io_edgeport.c
---- a/drivers/usb/serial/io_edgeport.c 2004-08-08 07:41:30 -07:00
-+++ b/drivers/usb/serial/io_edgeport.c 2004-08-08 07:41:30 -07:00
-@@ -1913,6 +1913,7 @@
-
- case TIOCGICOUNT:
- cnow = edge_port->icount;
-+ memset(&icount, 0, sizeof(icount));
- icount.cts = cnow.cts;
- icount.dsr = cnow.dsr;
- icount.rng = cnow.rng;
-diff -Nru a/drivers/usb/vicam.c b/drivers/usb/vicam.c
---- a/drivers/usb/vicam.c 2004-08-08 07:41:30 -07:00
-+++ b/drivers/usb/vicam.c 2004-08-08 07:41:30 -07:00
-@@ -481,6 +481,7 @@
- struct video_capability b;
-
- DBG("VIDIOCGCAP\n");
-+ memset(&b, 0, sizeof(b));
- strcpy(b.name, "ViCam-based Camera");
- b.type = VID_TYPE_CAPTURE;
- b.channels = 1;
diff --git a/sys-kernel/hppa-sources/files/LKA-20050107.patch b/sys-kernel/hppa-sources/files/LKA-20050107.patch
new file mode 100644
index 000000000000..bc4ba1a9a207
--- /dev/null
+++ b/sys-kernel/hppa-sources/files/LKA-20050107.patch
@@ -0,0 +1,163 @@
+diff -urNp linux-2.6.10/drivers/char/moxa.c linux-2.6.10-new/drivers/char/moxa.c
+--- linux-2.6.10/drivers/char/moxa.c 2005-01-07 10:51:23 -0500
++++ linux-2.6.10-new/drivers/char/moxa.c 2005-01-07 10:51:33 -0500
+@@ -1668,6 +1668,8 @@ int MoxaDriverIoctl(unsigned int cmd, un
+ return -EFAULT;
+ if(dltmp.cardno < 0 || dltmp.cardno >= MAX_BOARDS)
+ return -EINVAL;
++ if(dltmp.len < 0 || dltmp.len > sizeof(moxaBuff))
++ return -EINVAL;
+
+ switch(cmd)
+ {
+@@ -2822,8 +2824,6 @@ static int moxaload320b(int cardno, unsi
+ void __iomem *baseAddr;
+ int i;
+
+- if(len > sizeof(moxaBuff))
+- return -EINVAL;
+ if(copy_from_user(moxaBuff, tmp, len))
+ return -EFAULT;
+ baseAddr = moxaBaseAddr[cardno];
+diff -urNp linux-2.6.10/drivers/block/scsi_ioctl.c linux-2.6.10-new/drivers/block/scsi_ioctl.c
+--- linux-2.6.10/drivers/block/scsi_ioctl.c 2005-01-07 10:51:24 -0500
++++ linux-2.6.10-new/drivers/block/scsi_ioctl.c 2005-01-07 10:51:33 -0500
+@@ -339,7 +339,8 @@ static int sg_scsi_ioctl(struct file *fi
+ struct gendisk *bd_disk, Scsi_Ioctl_Command __user *sic)
+ {
+ struct request *rq;
+- int err, in_len, out_len, bytes, opcode, cmdlen;
++ unsigned int in_len, out_len, bytes, opcode, cmdlen;
++ int err;
+ char *buffer = NULL, sense[SCSI_SENSE_BUFFERSIZE];
+
+ /*
+diff -urNp linux-2.6.10/include/linux/writeback.h linux-2.6.10-new/include/linux/writeback.h
+--- linux-2.6.10/include/linux/writeback.h 2005-01-07 10:51:22 -0500
++++ linux-2.6.10-new/include/linux/writeback.h 2005-01-07 10:51:33 -0500
+@@ -86,6 +86,7 @@ static inline void wait_on_inode(struct
+ int wakeup_bdflush(long nr_pages);
+ void laptop_io_completion(void);
+ void laptop_sync_completion(void);
++void throttle_vm_writeout(void);
+
+ /* These are exported to sysctl. */
+ extern int dirty_background_ratio;
+diff -urNp linux-2.6.10/drivers/char/random.c linux-2.6.10-new/drivers/char/random.c
+--- linux-2.6.10/drivers/char/random.c 2005-01-07 10:51:23 -0500
++++ linux-2.6.10-new/drivers/char/random.c 2005-01-07 10:51:33 -0500
+@@ -1912,7 +1912,7 @@ static int poolsize_strategy(ctl_table *
+ void __user *oldval, size_t __user *oldlenp,
+ void __user *newval, size_t newlen, void **context)
+ {
+- int len;
++ size_t len;
+
+ sysctl_poolsize = random_state->poolinfo.POOLBYTES;
+
+diff -urNp linux-2.6.10/mm/mmap.c linux-2.6.10-new/mm/mmap.c
+--- linux-2.6.10/mm/mmap.c 2004-12-24 22:35:00.000000000 +0100
++++ linux-2.6.10-new/mm/mmap.c 2004-12-27 16:37:47.000000000 +0100
+@@ -1360,6 +1360,13 @@ int expand_stack(struct vm_area_struct *
+ vm_unacct_memory(grow);
+ return -ENOMEM;
+ }
++ if ((vma->vm_flags & VM_LOCKED) && !capable(CAP_IPC_LOCK) &&
++ ((vma->vm_mm->locked_vm + grow) << PAGE_SHIFT) >
++ current->signal->rlim[RLIMIT_MEMLOCK].rlim_cur) {
++ anon_vma_unlock(vma);
++ vm_unacct_memory(grow);
++ return -ENOMEM;
++ }
+ vma->vm_end = address;
+ vma->vm_mm->total_vm += grow;
+ if (vma->vm_flags & VM_LOCKED)
+@@ -1422,6 +1429,13 @@ int expand_stack(struct vm_area_struct *
+ vm_unacct_memory(grow);
+ return -ENOMEM;
+ }
++ if ((vma->vm_flags & VM_LOCKED) && !capable(CAP_IPC_LOCK) &&
++ ((vma->vm_mm->locked_vm + grow) << PAGE_SHIFT) >
++ current->signal->rlim[RLIMIT_MEMLOCK].rlim_cur) {
++ anon_vma_unlock(vma);
++ vm_unacct_memory(grow);
++ return -ENOMEM;
++ }
+ vma->vm_start = address;
+ vma->vm_pgoff -= grow;
+ vma->vm_mm->total_vm += grow;
+diff -urNp linux-2.6.10/mm/page-writeback.c linux-2.6.10-new/mm/page-writeback.c
+--- linux-2.6.10/mm/page-writeback.c 2005-01-07 10:51:24 -0500
++++ linux-2.6.10-new/mm/page-writeback.c 2005-01-07 10:51:33 -0500
+@@ -276,6 +276,28 @@ void balance_dirty_pages_ratelimited(str
+ }
+ EXPORT_SYMBOL(balance_dirty_pages_ratelimited);
+
++void throttle_vm_writeout(void)
++{
++ struct writeback_state wbs;
++ long background_thresh;
++ long dirty_thresh;
++
++ for ( ; ; ) {
++ get_dirty_limits(&wbs, &background_thresh, &dirty_thresh);
++
++ /*
++ * Boost the allowable dirty threshold a bit for page
++ * allocators so they don't get DoS'ed by heavy writers
++ */
++ dirty_thresh += dirty_thresh / 10; /* wheeee... */
++
++ if (wbs.nr_unstable + wbs.nr_writeback <= dirty_thresh)
++ break;
++ blk_congestion_wait(WRITE, HZ/10);
++ }
++}
++
++
+ /*
+ * writeback at least _min_pages, and keep writing until the amount of dirty
+ * memory is less than the background threshold, or until we're all clean.
+diff -urNp linux-2.6.10/mm/vmscan.c linux-2.6.10-new/mm/vmscan.c
+--- linux-2.6.10/mm/vmscan.c 2005-01-07 10:51:24 -0500
++++ linux-2.6.10-new/mm/vmscan.c 2005-01-07 10:51:33 -0500
+@@ -369,14 +369,14 @@ static int shrink_list(struct list_head
+
+ BUG_ON(PageActive(page));
+
+- if (PageWriteback(page))
+- goto keep_locked;
+-
+ sc->nr_scanned++;
+ /* Double the slab pressure for mapped and swapcache pages */
+ if (page_mapped(page) || PageSwapCache(page))
+ sc->nr_scanned++;
+
++ if (PageWriteback(page))
++ goto keep_locked;
++
+ referenced = page_referenced(page, 1, sc->priority <= 0);
+ /* In active use or really unfreeable? Activate it. */
+ if (referenced && page_mapping_inuse(page))
+@@ -825,6 +825,8 @@ shrink_zone(struct zone *zone, struct sc
+ break;
+ }
+ }
++
++ throttle_vm_writeout();
+ }
+
+ /*
+diff -urNp linux-2.6.10/net/ipv4/netfilter/ip_conntrack_proto_tcp.c linux-2.6.10-new/net/ipv4/netfilter/ip_conntrack_proto_tcp.c
+--- linux-2.6.10/net/ipv4/netfilter/ip_conntrack_proto_tcp.c 2005-01-07 10:51:24 -0500
++++ linux-2.6.10-new/net/ipv4/netfilter/ip_conntrack_proto_tcp.c 2005-01-07 10:51:33 -0500
+@@ -906,7 +906,8 @@ static int tcp_packet(struct ip_conntrac
+ if (index == TCP_RST_SET
+ && ((test_bit(IPS_SEEN_REPLY_BIT, &conntrack->status)
+ && conntrack->proto.tcp.last_index <= TCP_SYNACK_SET)
+- || conntrack->proto.tcp.last_index == TCP_ACK_SET)
++ || (!test_bit(IPS_ASSURED_BIT, &conntrack->status)
++ && conntrack->proto.tcp.last_index == TCP_ACK_SET))
+ && after(ntohl(th->ack_seq),
+ conntrack->proto.tcp.last_seq)) {
+ /* Ignore RST closing down invalid SYN or ACK
diff --git a/sys-kernel/hppa-sources/files/NFS-XDR-security.patch b/sys-kernel/hppa-sources/files/NFS-XDR-security.patch
deleted file mode 100644
index 9a336ab7876a..000000000000
--- a/sys-kernel/hppa-sources/files/NFS-XDR-security.patch
+++ /dev/null
@@ -1,48 +0,0 @@
-# This is a BitKeeper generated diff -Nru style patch.
-#
-# ChangeSet
-# 2004/08/16 14:50:04-03:00 neilb@cse.unsw.edu.au
-# [PATCH] Fixed possibly xdr parsing error if write size exceed 2^31
-#
-# xdr_argsize_check needs to cope with the possibility that the
-# pointer has wrapped and could be below buf->base.
-#
-# Signed-off-by: Neil Brown <neilb@cse.unsw.edu.au>
-#
-# ### Diffstat output
-# ./fs/nfsd/nfs3xdr.c | 2 +-
-# ./include/linux/nfsd/xdr3.h | 2 +-
-# 2 files changed, 2 insertions(+), 2 deletions(-)
-#
-# fs/nfsd/nfs3xdr.c
-# 2004/08/14 00:23:06-03:00 neilb@cse.unsw.edu.au +1 -1
-# Fixed possibly xdr parsing error if write size exceed 2^31
-#
-# include/linux/nfsd/xdr3.h
-# 2004/08/15 20:48:43-03:00 neilb@cse.unsw.edu.au +1 -1
-# Fixed possibly xdr parsing error if write size exceed 2^31
-#
-diff -Nru a/fs/nfsd/nfs3xdr.c b/fs/nfsd/nfs3xdr.c
---- a/fs/nfsd/nfs3xdr.c 2004-09-06 11:20:28 -07:00
-+++ b/fs/nfsd/nfs3xdr.c 2004-09-06 11:20:28 -07:00
-@@ -273,7 +273,7 @@
- {
- struct svc_buf *buf = &rqstp->rq_argbuf;
-
-- return p - buf->base <= buf->buflen;
-+ return p >= buf->base && p <= buf->base + buf->buflen ;
- }
-
- static inline int
-diff -Nru a/include/linux/nfsd/xdr3.h b/include/linux/nfsd/xdr3.h
---- a/include/linux/nfsd/xdr3.h 2004-09-06 11:20:28 -07:00
-+++ b/include/linux/nfsd/xdr3.h 2004-09-06 11:20:28 -07:00
-@@ -41,7 +41,7 @@
- __u32 count;
- int stable;
- __u8 * data;
-- int len;
-+ __u32 len;
- };
-
- struct nfsd3_createargs {
diff --git a/sys-kernel/hppa-sources/files/binfmt_elf-loader-security.patch b/sys-kernel/hppa-sources/files/binfmt_elf-loader-security.patch
deleted file mode 100644
index 534e4c064a52..000000000000
--- a/sys-kernel/hppa-sources/files/binfmt_elf-loader-security.patch
+++ /dev/null
@@ -1,72 +0,0 @@
---- linux-2.4.27/fs/binfmt_elf.c 2004-11-10 12:25:16 -08:00
-+++ linux-2.4.27-plasmaroo/fs/binfmt_elf.c 2004-11-10 12:25:16 -08:00
-@@ -335,9 +335,12 @@
- goto out;
-
- retval = kernel_read(interpreter,interp_elf_ex->e_phoff,(char *)elf_phdata,size);
-- error = retval;
-- if (retval < 0)
-+ error = -EIO;
-+ if (retval != size) {
-+ if (retval < 0)
-+ error = retval;
- goto out_close;
-+ }
-
- eppnt = elf_phdata;
- for (i=0; i<interp_elf_ex->e_phnum; i++, eppnt++) {
-@@ -532,8 +535,11 @@
- goto out;
-
- retval = kernel_read(bprm->file, elf_ex.e_phoff, (char *) elf_phdata, size);
-- if (retval < 0)
-+ if (retval != size) {
-+ if (retval >= 0)
-+ retval = -EIO;
- goto out_free_ph;
-+ }
-
- files = current->files; /* Refcounted so ok */
- retval = unshare_files();
-@@ -580,8 +586,14 @@
- retval = kernel_read(bprm->file, elf_ppnt->p_offset,
- elf_interpreter,
- elf_ppnt->p_filesz);
-- if (retval < 0)
-+ if (retval != elf_ppnt->p_filesz) {
-+ if (retval >= 0)
-+ retval = -EIO;
- goto out_free_interp;
-+ }
-+ /* make sure path is NULL terminated */
-+ elf_interpreter[elf_ppnt->p_filesz - 1] = '\0';
-+
- /* If the program interpreter is one of these two,
- * then assume an iBCS2 image. Otherwise assume
- * a native linux image.
-@@ -616,8 +628,11 @@
- if (IS_ERR(interpreter))
- goto out_free_interp;
- retval = kernel_read(interpreter, 0, bprm->buf, BINPRM_BUF_SIZE);
-- if (retval < 0)
-+ if (retval != BINPRM_BUF_SIZE) {
-+ if (retval >= 0)
-+ retval = -EIO;
- goto out_free_dentry;
-+ }
-
- /* Get the exec headers */
- loc->interp_ex = *((struct exec *) bprm->buf);
-@@ -776,8 +791,10 @@
- }
-
- error = elf_map(bprm->file, load_bias + vaddr, elf_ppnt, elf_prot, elf_flags);
-- if (BAD_ADDR(error))
-- continue;
-+ if (BAD_ADDR(error)) {
-+ send_sig(SIGKILL, current, 0);
-+ goto out_free_dentry;
-+ }
-
- if (!load_addr_set) {
- load_addr_set = 1;
diff --git a/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.26_p6-r1 b/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.26_p6-r1
deleted file mode 100644
index 1783d6ae9683..000000000000
--- a/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.26_p6-r1
+++ /dev/null
@@ -1,3 +0,0 @@
-MD5 88d7aefa03c92739cb70298a0b486e2c linux-2.4.26.tar.bz2 30772389
-MD5 889e7590ba57391259d832f5ef7fef8c patch-2.4.26-pa6.gz 724962
-MD5 010fe6b49e97365f12ce3f70376d5eb0 parisc-2.4.23-pa4-missing-ioctl-translations.diff 18091
diff --git a/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.26_p7 b/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.26_p7
deleted file mode 100644
index 9e79b49b2488..000000000000
--- a/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.26_p7
+++ /dev/null
@@ -1,4 +0,0 @@
-MD5 88d7aefa03c92739cb70298a0b486e2c linux-2.4.26.tar.bz2 30772389
-MD5 993a9ea8c553f198ef62747bb7c9a7c4 patch-2.4.26-pa7.gz 725125
-MD5 010fe6b49e97365f12ce3f70376d5eb0 parisc-2.4.23-pa4-missing-ioctl-translations.diff 18091
-MD5 2758cec1dc37d4069a42fc7544599860 lasi-config-max-tag-queue-dep.patch 1455
diff --git a/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.26_p7-r1 b/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.26_p7-r1
deleted file mode 100644
index 1be356f1f4e4..000000000000
--- a/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.26_p7-r1
+++ /dev/null
@@ -1,5 +0,0 @@
-MD5 88d7aefa03c92739cb70298a0b486e2c linux-2.4.26.tar.bz2 30772389
-MD5 993a9ea8c553f198ef62747bb7c9a7c4 patch-2.4.26-pa7.gz 725125
-MD5 010fe6b49e97365f12ce3f70376d5eb0 parisc-2.4.23-pa4-missing-ioctl-translations.diff 18091
-MD5 2758cec1dc37d4069a42fc7544599860 lasi-config-max-tag-queue-dep.patch 1455
-MD5 8f8f2412aacf9a01b5549bf2a9a3bff8 linux-2.4.26-CAN-2004-0415.patch 90145
diff --git a/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.27_p4 b/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.27_p4
deleted file mode 100644
index ed0632124e01..000000000000
--- a/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.27_p4
+++ /dev/null
@@ -1,4 +0,0 @@
-MD5 59a2e6fde1d110e2ffa20351ac8b4d9e linux-2.4.27.tar.bz2 30898453
-MD5 e6ee93aafa687932abd2c09fca43d4c3 patch-2.4.27-pa4.gz 727846
-MD5 010fe6b49e97365f12ce3f70376d5eb0 parisc-2.4.23-pa4-missing-ioctl-translations.diff 18091
-MD5 2758cec1dc37d4069a42fc7544599860 lasi-config-max-tag-queue-dep.patch 1455
diff --git a/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.27_p4-r1 b/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.27_p4-r1
deleted file mode 100644
index ed0632124e01..000000000000
--- a/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.27_p4-r1
+++ /dev/null
@@ -1,4 +0,0 @@
-MD5 59a2e6fde1d110e2ffa20351ac8b4d9e linux-2.4.27.tar.bz2 30898453
-MD5 e6ee93aafa687932abd2c09fca43d4c3 patch-2.4.27-pa4.gz 727846
-MD5 010fe6b49e97365f12ce3f70376d5eb0 parisc-2.4.23-pa4-missing-ioctl-translations.diff 18091
-MD5 2758cec1dc37d4069a42fc7544599860 lasi-config-max-tag-queue-dep.patch 1455
diff --git a/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.27_p4-r2 b/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.27_p4-r2
deleted file mode 100644
index ed0632124e01..000000000000
--- a/sys-kernel/hppa-sources/files/digest-hppa-sources-2.4.27_p4-r2
+++ /dev/null
@@ -1,4 +0,0 @@
-MD5 59a2e6fde1d110e2ffa20351ac8b4d9e linux-2.4.27.tar.bz2 30898453
-MD5 e6ee93aafa687932abd2c09fca43d4c3 patch-2.4.27-pa4.gz 727846
-MD5 010fe6b49e97365f12ce3f70376d5eb0 parisc-2.4.23-pa4-missing-ioctl-translations.diff 18091
-MD5 2758cec1dc37d4069a42fc7544599860 lasi-config-max-tag-queue-dep.patch 1455
diff --git a/sys-kernel/hppa-sources/files/digest-hppa-sources-2.6.10_p10 b/sys-kernel/hppa-sources/files/digest-hppa-sources-2.6.10_p10
new file mode 100644
index 000000000000..b1567b9fb7e1
--- /dev/null
+++ b/sys-kernel/hppa-sources/files/digest-hppa-sources-2.6.10_p10
@@ -0,0 +1,2 @@
+MD5 cffcd2919d9c8ef793ce1ac07a440eda linux-2.6.10.tar.bz2 36533484
+MD5 ac56c33ed522d0d3f7ed72faaaf19e34 patch-2.6.10-pa10.gz 189423
diff --git a/sys-kernel/hppa-sources/files/security-proc-cmdline.patch b/sys-kernel/hppa-sources/files/security-proc-cmdline.patch
deleted file mode 100644
index bb80884c394e..000000000000
--- a/sys-kernel/hppa-sources/files/security-proc-cmdline.patch
+++ /dev/null
@@ -1,24 +0,0 @@
-
-From: Roger Luethi <rl@hellgate.ch>
-
-If you win the race with a starting process, you can read its environment.
-
-Signed-off-by: Andrew Morton <akpm@osdl.org>
----
-
- 25-akpm/fs/proc/base.c | 2 ++
- 1 files changed, 2 insertions(+)
-
-diff -puN fs/proc/base.c~proc_pid_cmdline-race-fix fs/proc/base.c
---- 25/fs/proc/base.c~proc_pid_cmdline-race-fix 2004-08-05 11:28:21.915442360 -0700
-+++ 25-akpm/fs/proc/base.c 2004-08-05 11:28:21.919441752 -0700
-@@ -340,6 +340,8 @@ static int proc_pid_cmdline(struct task_
- struct mm_struct *mm = get_task_mm(task);
- if (!mm)
- goto out;
-+ if (!mm->arg_end)
-+ goto out; /* Shh! No looking before we're done */
-
- len = mm->arg_end - mm->arg_start;
-
-_
diff --git a/sys-kernel/hppa-sources/hppa-sources-2.6.10_p10.ebuild b/sys-kernel/hppa-sources/hppa-sources-2.6.10_p10.ebuild
new file mode 100644
index 000000000000..99f55c1a5902
--- /dev/null
+++ b/sys-kernel/hppa-sources/hppa-sources-2.6.10_p10.ebuild
@@ -0,0 +1,17 @@
+# Copyright 1999-2005 Gentoo Foundation
+# Distributed under the terms of the GNU General Public License v2
+# $Header: /var/cvsroot/gentoo-x86/sys-kernel/hppa-sources/hppa-sources-2.6.10_p10.ebuild,v 1.1 2005/01/10 17:44:18 gmsoft Exp $
+
+ETYPE="sources"
+inherit kernel-2
+K_NOUSENAME=true
+K_NOSETEXTRAVERSION=true
+
+detect_version
+
+DESCRIPTION="Full sources for the Linux kernel with patch for hppa"
+PATCH_LEVEL="${PV/${OKV}_p/}"
+SRC_URI="${KERNEL_URI} http://ftp.parisc-linux.org/cvs/linux-2.6/patch-${OKV}-pa${PATCH_LEVEL}.gz"
+UNIPATCH_LIST="${DISTDIR}/patch-${OKV}-pa${PATCH_LEVEL}.gz ${FILESDIR}/CAN-2004-1056.patch ${FILESDIR}/CAN-2004-1235.patch ${FILESDIR}/LKA-20050107.patch"
+HOMEPAGE="http://www.kernel.org/ http://www.gentoo.org/ http://parisc-linux.org"
+KEYWORDS="hppa -*"