aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/char
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/char')
-rw-r--r--drivers/char/Kconfig19
-rw-r--r--drivers/char/Makefile4
-rw-r--r--drivers/char/agp/nvidia-agp.c3
-rw-r--r--drivers/char/drm/drm_fops.c2
-rw-r--r--drivers/char/drm/i810_dma.c2
-rw-r--r--drivers/char/drm/i830_dma.c2
-rw-r--r--drivers/char/generic_nvram.c5
-rw-r--r--drivers/char/hvc_console.c101
-rw-r--r--drivers/char/hvc_console.h63
-rw-r--r--drivers/char/hvc_rtas.c138
-rw-r--r--drivers/char/hvc_vio.c11
-rw-r--r--drivers/char/hvcs.c1
-rw-r--r--drivers/char/ipmi/ipmi_msghandler.c4
-rw-r--r--drivers/char/ipmi/ipmi_si_intf.c7
-rw-r--r--drivers/char/ipmi/ipmi_watchdog.c6
-rw-r--r--drivers/char/mem.c2
-rw-r--r--drivers/char/misc.c2
-rw-r--r--drivers/char/mxser.h2
-rw-r--r--drivers/char/synclink.c33
-rw-r--r--drivers/char/synclink_gt.c250
-rw-r--r--drivers/char/tty_io.c20
21 files changed, 561 insertions, 116 deletions
diff --git a/drivers/char/Kconfig b/drivers/char/Kconfig
index facc3f1d9e37..889cad07774e 100644
--- a/drivers/char/Kconfig
+++ b/drivers/char/Kconfig
@@ -561,14 +561,31 @@ config TIPAR
561 561
562 If unsure, say N. 562 If unsure, say N.
563 563
564config HVC_DRIVER
565 bool
566 help
567 Users of pSeries machines that want to utilize the hvc console front-end
568 module for their backend console driver should select this option.
569 It will automatically be selected if one of the back-end console drivers
570 is selected.
571
572
564config HVC_CONSOLE 573config HVC_CONSOLE
565 bool "pSeries Hypervisor Virtual Console support" 574 bool "pSeries Hypervisor Virtual Console support"
566 depends on PPC_PSERIES 575 depends on PPC_PSERIES
576 select HVC_DRIVER
567 help 577 help
568 pSeries machines when partitioned support a hypervisor virtual 578 pSeries machines when partitioned support a hypervisor virtual
569 console. This driver allows each pSeries partition to have a console 579 console. This driver allows each pSeries partition to have a console
570 which is accessed via the HMC. 580 which is accessed via the HMC.
571 581
582config HVC_RTAS
583 bool "IBM RTAS Console support"
584 depends on PPC_RTAS
585 select HVC_DRIVER
586 help
587 IBM Console device driver which makes use of RTAS
588
572config HVCS 589config HVCS
573 tristate "IBM Hypervisor Virtual Console Server support" 590 tristate "IBM Hypervisor Virtual Console Server support"
574 depends on PPC_PSERIES 591 depends on PPC_PSERIES
@@ -696,7 +713,7 @@ config NVRAM
696 713
697config RTC 714config RTC
698 tristate "Enhanced Real Time Clock Support" 715 tristate "Enhanced Real Time Clock Support"
699 depends on !PPC && !PARISC && !IA64 && !M68K && (!SPARC || PCI) && !FRV 716 depends on !PPC && !PARISC && !IA64 && !M68K && (!SPARC || PCI) && !FRV && !ARM
700 ---help--- 717 ---help---
701 If you say Y here and create a character special file /dev/rtc with 718 If you say Y here and create a character special file /dev/rtc with
702 major number 10 and minor number 135 using mknod ("man mknod"), you 719 major number 10 and minor number 135 using mknod ("man mknod"), you
diff --git a/drivers/char/Makefile b/drivers/char/Makefile
index b2a11245fa95..a73cb4956928 100644
--- a/drivers/char/Makefile
+++ b/drivers/char/Makefile
@@ -41,7 +41,9 @@ obj-$(CONFIG_N_HDLC) += n_hdlc.o
41obj-$(CONFIG_AMIGA_BUILTIN_SERIAL) += amiserial.o 41obj-$(CONFIG_AMIGA_BUILTIN_SERIAL) += amiserial.o
42obj-$(CONFIG_SX) += sx.o generic_serial.o 42obj-$(CONFIG_SX) += sx.o generic_serial.o
43obj-$(CONFIG_RIO) += rio/ generic_serial.o 43obj-$(CONFIG_RIO) += rio/ generic_serial.o
44obj-$(CONFIG_HVC_CONSOLE) += hvc_console.o hvc_vio.o hvsi.o 44obj-$(CONFIG_HVC_DRIVER) += hvc_console.o
45obj-$(CONFIG_HVC_CONSOLE) += hvc_vio.o hvsi.o
46obj-$(CONFIG_HVC_RTAS) += hvc_rtas.o
45obj-$(CONFIG_RAW_DRIVER) += raw.o 47obj-$(CONFIG_RAW_DRIVER) += raw.o
46obj-$(CONFIG_SGI_SNSC) += snsc.o snsc_event.o 48obj-$(CONFIG_SGI_SNSC) += snsc.o snsc_event.o
47obj-$(CONFIG_MMTIMER) += mmtimer.o 49obj-$(CONFIG_MMTIMER) += mmtimer.o
diff --git a/drivers/char/agp/nvidia-agp.c b/drivers/char/agp/nvidia-agp.c
index 70b8ed9cd172..4c67135c12d8 100644
--- a/drivers/char/agp/nvidia-agp.c
+++ b/drivers/char/agp/nvidia-agp.c
@@ -11,6 +11,7 @@
11#include <linux/gfp.h> 11#include <linux/gfp.h>
12#include <linux/page-flags.h> 12#include <linux/page-flags.h>
13#include <linux/mm.h> 13#include <linux/mm.h>
14#include <linux/jiffies.h>
14#include "agp.h" 15#include "agp.h"
15 16
16/* NVIDIA registers */ 17/* NVIDIA registers */
@@ -256,7 +257,7 @@ static void nvidia_tlbflush(struct agp_memory *mem)
256 do { 257 do {
257 pci_read_config_dword(nvidia_private.dev_1, 258 pci_read_config_dword(nvidia_private.dev_1,
258 NVIDIA_1_WBC, &wbc_reg); 259 NVIDIA_1_WBC, &wbc_reg);
259 if ((signed)(end - jiffies) <= 0) { 260 if (time_before_eq(end, jiffies)) {
260 printk(KERN_ERR PFX 261 printk(KERN_ERR PFX
261 "TLB flush took more than 3 seconds.\n"); 262 "TLB flush took more than 3 seconds.\n");
262 } 263 }
diff --git a/drivers/char/drm/drm_fops.c b/drivers/char/drm/drm_fops.c
index 641f7633878c..b7f7951c4587 100644
--- a/drivers/char/drm/drm_fops.c
+++ b/drivers/char/drm/drm_fops.c
@@ -175,7 +175,7 @@ int drm_stub_open(struct inode *inode, struct file *filp)
175 drm_device_t *dev = NULL; 175 drm_device_t *dev = NULL;
176 int minor = iminor(inode); 176 int minor = iminor(inode);
177 int err = -ENODEV; 177 int err = -ENODEV;
178 struct file_operations *old_fops; 178 const struct file_operations *old_fops;
179 179
180 DRM_DEBUG("\n"); 180 DRM_DEBUG("\n");
181 181
diff --git a/drivers/char/drm/i810_dma.c b/drivers/char/drm/i810_dma.c
index ae0aa6d7e0bb..c658dde3633b 100644
--- a/drivers/char/drm/i810_dma.c
+++ b/drivers/char/drm/i810_dma.c
@@ -126,7 +126,7 @@ static int i810_map_buffer(drm_buf_t * buf, struct file *filp)
126 drm_device_t *dev = priv->head->dev; 126 drm_device_t *dev = priv->head->dev;
127 drm_i810_buf_priv_t *buf_priv = buf->dev_private; 127 drm_i810_buf_priv_t *buf_priv = buf->dev_private;
128 drm_i810_private_t *dev_priv = dev->dev_private; 128 drm_i810_private_t *dev_priv = dev->dev_private;
129 struct file_operations *old_fops; 129 const struct file_operations *old_fops;
130 int retcode = 0; 130 int retcode = 0;
131 131
132 if (buf_priv->currently_mapped == I810_BUF_MAPPED) 132 if (buf_priv->currently_mapped == I810_BUF_MAPPED)
diff --git a/drivers/char/drm/i830_dma.c b/drivers/char/drm/i830_dma.c
index 163f2cbfe60d..b0f815d8cea8 100644
--- a/drivers/char/drm/i830_dma.c
+++ b/drivers/char/drm/i830_dma.c
@@ -128,7 +128,7 @@ static int i830_map_buffer(drm_buf_t * buf, struct file *filp)
128 drm_device_t *dev = priv->head->dev; 128 drm_device_t *dev = priv->head->dev;
129 drm_i830_buf_priv_t *buf_priv = buf->dev_private; 129 drm_i830_buf_priv_t *buf_priv = buf->dev_private;
130 drm_i830_private_t *dev_priv = dev->dev_private; 130 drm_i830_private_t *dev_priv = dev->dev_private;
131 struct file_operations *old_fops; 131 const struct file_operations *old_fops;
132 unsigned long virtual; 132 unsigned long virtual;
133 int retcode = 0; 133 int retcode = 0;
134 134
diff --git a/drivers/char/generic_nvram.c b/drivers/char/generic_nvram.c
index 1b5e01e6e129..43ff59816511 100644
--- a/drivers/char/generic_nvram.c
+++ b/drivers/char/generic_nvram.c
@@ -22,6 +22,9 @@
22#include <linux/smp_lock.h> 22#include <linux/smp_lock.h>
23#include <asm/uaccess.h> 23#include <asm/uaccess.h>
24#include <asm/nvram.h> 24#include <asm/nvram.h>
25#ifdef CONFIG_PPC_PMAC
26#include <asm/machdep.h>
27#endif
25 28
26#define NVRAM_SIZE 8192 29#define NVRAM_SIZE 8192
27 30
@@ -92,7 +95,7 @@ static int nvram_ioctl(struct inode *inode, struct file *file,
92 case IOC_NVRAM_GET_OFFSET: { 95 case IOC_NVRAM_GET_OFFSET: {
93 int part, offset; 96 int part, offset;
94 97
95 if (_machine != _MACH_Pmac) 98 if (!machine_is(powermac))
96 return -EINVAL; 99 return -EINVAL;
97 if (copy_from_user(&part, (void __user*)arg, sizeof(part)) != 0) 100 if (copy_from_user(&part, (void __user*)arg, sizeof(part)) != 0)
98 return -EFAULT; 101 return -EFAULT;
diff --git a/drivers/char/hvc_console.c b/drivers/char/hvc_console.c
index f65b2e14a485..2b6a56b2bf35 100644
--- a/drivers/char/hvc_console.c
+++ b/drivers/char/hvc_console.c
@@ -39,8 +39,10 @@
39#include <linux/sched.h> 39#include <linux/sched.h>
40#include <linux/spinlock.h> 40#include <linux/spinlock.h>
41#include <linux/delay.h> 41#include <linux/delay.h>
42
42#include <asm/uaccess.h> 43#include <asm/uaccess.h>
43#include <asm/hvconsole.h> 44
45#include "hvc_console.h"
44 46
45#define HVC_MAJOR 229 47#define HVC_MAJOR 229
46#define HVC_MINOR 0 48#define HVC_MINOR 0
@@ -54,17 +56,14 @@
54#define HVC_CLOSE_WAIT (HZ/100) /* 1/10 of a second */ 56#define HVC_CLOSE_WAIT (HZ/100) /* 1/10 of a second */
55 57
56/* 58/*
57 * The Linux TTY code does not support dynamic addition of tty derived devices 59 * These sizes are most efficient for vio, because they are the
58 * so we need to know how many tty devices we might need when space is allocated 60 * native transfer size. We could make them selectable in the
59 * for the tty device. Since this driver supports hotplug of vty adapters we 61 * future to better deal with backends that want other buffer sizes.
60 * need to make sure we have enough allocated.
61 */ 62 */
62#define HVC_ALLOC_TTY_ADAPTERS 8
63
64#define N_OUTBUF 16 63#define N_OUTBUF 16
65#define N_INBUF 16 64#define N_INBUF 16
66 65
67#define __ALIGNED__ __attribute__((__aligned__(8))) 66#define __ALIGNED__ __attribute__((__aligned__(sizeof(long))))
68 67
69static struct tty_driver *hvc_driver; 68static struct tty_driver *hvc_driver;
70static struct task_struct *hvc_task; 69static struct task_struct *hvc_task;
@@ -154,7 +153,7 @@ static uint32_t vtermnos[MAX_NR_HVC_CONSOLES] =
154 153
155void hvc_console_print(struct console *co, const char *b, unsigned count) 154void hvc_console_print(struct console *co, const char *b, unsigned count)
156{ 155{
157 char c[16] __ALIGNED__; 156 char c[N_OUTBUF] __ALIGNED__;
158 unsigned i = 0, n = 0; 157 unsigned i = 0, n = 0;
159 int r, donecr = 0, index = co->index; 158 int r, donecr = 0, index = co->index;
160 159
@@ -473,8 +472,10 @@ static void hvc_push(struct hvc_struct *hp)
473 472
474 n = hp->ops->put_chars(hp->vtermno, hp->outbuf, hp->n_outbuf); 473 n = hp->ops->put_chars(hp->vtermno, hp->outbuf, hp->n_outbuf);
475 if (n <= 0) { 474 if (n <= 0) {
476 if (n == 0) 475 if (n == 0) {
476 hp->do_wakeup = 1;
477 return; 477 return;
478 }
478 /* throw away output on error; this happens when 479 /* throw away output on error; this happens when
479 there is no session connected to the vterm. */ 480 there is no session connected to the vterm. */
480 hp->n_outbuf = 0; 481 hp->n_outbuf = 0;
@@ -486,12 +487,19 @@ static void hvc_push(struct hvc_struct *hp)
486 hp->do_wakeup = 1; 487 hp->do_wakeup = 1;
487} 488}
488 489
489static inline int __hvc_write_kernel(struct hvc_struct *hp, 490static int hvc_write(struct tty_struct *tty, const unsigned char *buf, int count)
490 const unsigned char *buf, int count)
491{ 491{
492 struct hvc_struct *hp = tty->driver_data;
492 unsigned long flags; 493 unsigned long flags;
493 int rsize, written = 0; 494 int rsize, written = 0;
494 495
496 /* This write was probably executed during a tty close. */
497 if (!hp)
498 return -EPIPE;
499
500 if (hp->count <= 0)
501 return -EIO;
502
495 spin_lock_irqsave(&hp->lock, flags); 503 spin_lock_irqsave(&hp->lock, flags);
496 504
497 /* Push pending writes */ 505 /* Push pending writes */
@@ -510,26 +518,8 @@ static inline int __hvc_write_kernel(struct hvc_struct *hp,
510 } 518 }
511 spin_unlock_irqrestore(&hp->lock, flags); 519 spin_unlock_irqrestore(&hp->lock, flags);
512 520
513 return written;
514}
515static int hvc_write(struct tty_struct *tty, const unsigned char *buf, int count)
516{
517 struct hvc_struct *hp = tty->driver_data;
518 int written;
519
520 /* This write was probably executed during a tty close. */
521 if (!hp)
522 return -EPIPE;
523
524 if (hp->count <= 0)
525 return -EIO;
526
527 written = __hvc_write_kernel(hp, buf, count);
528
529 /* 521 /*
530 * Racy, but harmless, kick thread if there is still pending data. 522 * Racy, but harmless, kick thread if there is still pending data.
531 * There really is nothing wrong with kicking the thread, even if there
532 * is no buffered data.
533 */ 523 */
534 if (hp->n_outbuf) 524 if (hp->n_outbuf)
535 hvc_kick(); 525 hvc_kick();
@@ -614,6 +604,13 @@ static int hvc_poll(struct hvc_struct *hp)
614 spin_unlock_irqrestore(&hp->lock, flags); 604 spin_unlock_irqrestore(&hp->lock, flags);
615 tty_hangup(tty); 605 tty_hangup(tty);
616 spin_lock_irqsave(&hp->lock, flags); 606 spin_lock_irqsave(&hp->lock, flags);
607 } else if ( n == -EAGAIN ) {
608 /*
609 * Some back-ends can only ensure a certain min
610 * num of bytes read, which may be > 'count'.
611 * Let the tty clear the flip buff to make room.
612 */
613 poll_mask |= HVC_POLL_READ;
617 } 614 }
618 break; 615 break;
619 } 616 }
@@ -635,16 +632,7 @@ static int hvc_poll(struct hvc_struct *hp)
635 tty_insert_flip_char(tty, buf[i], 0); 632 tty_insert_flip_char(tty, buf[i], 0);
636 } 633 }
637 634
638 /*
639 * Account for the total amount read in one loop, and if above
640 * 64 bytes, we do a quick schedule loop to let the tty grok
641 * the data and eventually throttle us.
642 */
643 read_total += n; 635 read_total += n;
644 if (read_total >= 64) {
645 poll_mask |= HVC_POLL_QUICK;
646 break;
647 }
648 } 636 }
649 throttled: 637 throttled:
650 /* Wakeup write queue if necessary */ 638 /* Wakeup write queue if necessary */
@@ -767,7 +755,8 @@ struct hvc_struct __devinit *hvc_alloc(uint32_t vtermno, int irq,
767 * see if this vterm id matches one registered for console. 755 * see if this vterm id matches one registered for console.
768 */ 756 */
769 for (i=0; i < MAX_NR_HVC_CONSOLES; i++) 757 for (i=0; i < MAX_NR_HVC_CONSOLES; i++)
770 if (vtermnos[i] == hp->vtermno) 758 if (vtermnos[i] == hp->vtermno &&
759 cons_ops[i] == hp->ops)
771 break; 760 break;
772 761
773 /* no matching slot, just use a counter */ 762 /* no matching slot, just use a counter */
@@ -823,34 +812,38 @@ EXPORT_SYMBOL(hvc_remove);
823 * interfaces start to become available. */ 812 * interfaces start to become available. */
824int __init hvc_init(void) 813int __init hvc_init(void)
825{ 814{
815 struct tty_driver *drv;
816
826 /* We need more than hvc_count adapters due to hotplug additions. */ 817 /* We need more than hvc_count adapters due to hotplug additions. */
827 hvc_driver = alloc_tty_driver(HVC_ALLOC_TTY_ADAPTERS); 818 drv = alloc_tty_driver(HVC_ALLOC_TTY_ADAPTERS);
828 if (!hvc_driver) 819 if (!drv)
829 return -ENOMEM; 820 return -ENOMEM;
830 821
831 hvc_driver->owner = THIS_MODULE; 822 drv->owner = THIS_MODULE;
832 hvc_driver->devfs_name = "hvc/"; 823 drv->devfs_name = "hvc/";
833 hvc_driver->driver_name = "hvc"; 824 drv->driver_name = "hvc";
834 hvc_driver->name = "hvc"; 825 drv->name = "hvc";
835 hvc_driver->major = HVC_MAJOR; 826 drv->major = HVC_MAJOR;
836 hvc_driver->minor_start = HVC_MINOR; 827 drv->minor_start = HVC_MINOR;
837 hvc_driver->type = TTY_DRIVER_TYPE_SYSTEM; 828 drv->type = TTY_DRIVER_TYPE_SYSTEM;
838 hvc_driver->init_termios = tty_std_termios; 829 drv->init_termios = tty_std_termios;
839 hvc_driver->flags = TTY_DRIVER_REAL_RAW; 830 drv->flags = TTY_DRIVER_REAL_RAW;
840 tty_set_operations(hvc_driver, &hvc_ops); 831 tty_set_operations(drv, &hvc_ops);
841 832
842 /* Always start the kthread because there can be hotplug vty adapters 833 /* Always start the kthread because there can be hotplug vty adapters
843 * added later. */ 834 * added later. */
844 hvc_task = kthread_run(khvcd, NULL, "khvcd"); 835 hvc_task = kthread_run(khvcd, NULL, "khvcd");
845 if (IS_ERR(hvc_task)) { 836 if (IS_ERR(hvc_task)) {
846 panic("Couldn't create kthread for console.\n"); 837 panic("Couldn't create kthread for console.\n");
847 put_tty_driver(hvc_driver); 838 put_tty_driver(drv);
848 return -EIO; 839 return -EIO;
849 } 840 }
850 841
851 if (tty_register_driver(hvc_driver)) 842 if (tty_register_driver(drv))
852 panic("Couldn't register hvc console driver\n"); 843 panic("Couldn't register hvc console driver\n");
853 844
845 mb();
846 hvc_driver = drv;
854 return 0; 847 return 0;
855} 848}
856module_init(hvc_init); 849module_init(hvc_init);
diff --git a/drivers/char/hvc_console.h b/drivers/char/hvc_console.h
new file mode 100644
index 000000000000..96b7401319c1
--- /dev/null
+++ b/drivers/char/hvc_console.h
@@ -0,0 +1,63 @@
1/*
2 * hvc_console.h
3 * Copyright (C) 2005 IBM Corporation
4 *
5 * Author(s):
6 * Ryan S. Arnold <rsa@us.ibm.com>
7 *
8 * hvc_console header information:
9 * moved here from include/asm-powerpc/hvconsole.h
10 * and drivers/char/hvc_console.c
11 *
12 * This program is free software; you can redistribute it and/or modify
13 * it under the terms of the GNU General Public License as published by
14 * the Free Software Foundation; either version 2 of the License, or
15 * (at your option) any later version.
16 *
17 * This program is distributed in the hope that it will be useful,
18 * but WITHOUT ANY WARRANTY; without even the implied warranty of
19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 * GNU General Public License for more details.
21 *
22 * You should have received a copy of the GNU General Public License
23 * along with this program; if not, write to the Free Software
24 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
25 */
26
27#ifndef HVC_CONSOLE_H
28#define HVC_CONSOLE_H
29
30/*
31 * This is the max number of console adapters that can/will be found as
32 * console devices on first stage console init. Any number beyond this range
33 * can't be used as a console device but is still a valid tty device.
34 */
35#define MAX_NR_HVC_CONSOLES 16
36
37/*
38 * The Linux TTY code does not support dynamic addition of tty derived devices
39 * so we need to know how many tty devices we might need when space is allocated
40 * for the tty device. Since this driver supports hotplug of vty adapters we
41 * need to make sure we have enough allocated.
42 */
43#define HVC_ALLOC_TTY_ADAPTERS 8
44
45
46/* implemented by a low level driver */
47struct hv_ops {
48 int (*get_chars)(uint32_t vtermno, char *buf, int count);
49 int (*put_chars)(uint32_t vtermno, const char *buf, int count);
50};
51
52struct hvc_struct;
53
54/* Register a vterm and a slot index for use as a console (console_init) */
55extern int hvc_instantiate(uint32_t vtermno, int index, struct hv_ops *ops);
56
57/* register a vterm for hvc tty operation (module_init or hotplug add) */
58extern struct hvc_struct * __devinit hvc_alloc(uint32_t vtermno, int irq,
59 struct hv_ops *ops);
60/* remove a vterm from hvc tty operation (modele_exit or hotplug remove) */
61extern int __devexit hvc_remove(struct hvc_struct *hp);
62
63#endif // HVC_CONSOLE_H
diff --git a/drivers/char/hvc_rtas.c b/drivers/char/hvc_rtas.c
new file mode 100644
index 000000000000..83364ea63cba
--- /dev/null
+++ b/drivers/char/hvc_rtas.c
@@ -0,0 +1,138 @@
1/*
2 * IBM RTAS driver interface to hvc_console.c
3 *
4 * (C) Copyright IBM Corporation 2001-2005
5 * (C) Copyright Red Hat, Inc. 2005
6 *
7 * Author(s): Maximino Augilar <IBM STI Design Center>
8 * : Ryan S. Arnold <rsa@us.ibm.com>
9 * : Utz Bacher <utz.bacher@de.ibm.com>
10 * : David Woodhouse <dwmw2@infradead.org>
11 *
12 * inspired by drivers/char/hvc_console.c
13 * written by Anton Blanchard and Paul Mackerras
14 *
15 * This program is free software; you can redistribute it and/or modify
16 * it under the terms of the GNU General Public License as published by
17 * the Free Software Foundation; either version 2 of the License, or
18 * (at your option) any later version.
19 *
20 * This program is distributed in the hope that it will be useful,
21 * but WITHOUT ANY WARRANTY; without even the implied warranty of
22 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
23 * GNU General Public License for more details.
24 *
25 * You should have received a copy of the GNU General Public License
26 * along with this program; if not, write to the Free Software
27 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
28 */
29
30#include <linux/console.h>
31#include <linux/delay.h>
32#include <linux/err.h>
33#include <linux/init.h>
34#include <linux/moduleparam.h>
35#include <linux/types.h>
36
37#include <asm/irq.h>
38#include <asm/rtas.h>
39#include "hvc_console.h"
40
41#define hvc_rtas_cookie 0x67781e15
42struct hvc_struct *hvc_rtas_dev;
43
44#define RTASCONS_PUT_ATTEMPTS 16
45
46static int rtascons_put_char_token = RTAS_UNKNOWN_SERVICE;
47static int rtascons_get_char_token = RTAS_UNKNOWN_SERVICE;
48static int rtascons_put_delay = 100;
49module_param_named(put_delay, rtascons_put_delay, int, 0644);
50
51static inline int hvc_rtas_write_console(uint32_t vtermno, const char *buf, int count)
52{
53 int done;
54
55 /* if there is more than one character to be displayed, wait a bit */
56 for (done = 0; done < count; done++) {
57 int result;
58 result = rtas_call(rtascons_put_char_token, 1, 1, NULL, buf[done]);
59 if (result)
60 break;
61 }
62 /* the calling routine expects to receive the number of bytes sent */
63 return done;
64}
65
66static int hvc_rtas_read_console(uint32_t vtermno, char *buf, int count)
67{
68 int i;
69
70 for (i = 0; i < count; i++) {
71 int c, err;
72
73 err = rtas_call(rtascons_get_char_token, 0, 2, &c);
74 if (err)
75 break;
76
77 buf[i] = c;
78 }
79
80 return i;
81}
82
83static struct hv_ops hvc_rtas_get_put_ops = {
84 .get_chars = hvc_rtas_read_console,
85 .put_chars = hvc_rtas_write_console,
86};
87
88static int hvc_rtas_init(void)
89{
90 struct hvc_struct *hp;
91
92 if (rtascons_put_char_token == RTAS_UNKNOWN_SERVICE)
93 rtascons_put_char_token = rtas_token("put-term-char");
94 if (rtascons_put_char_token == RTAS_UNKNOWN_SERVICE)
95 return -EIO;
96
97 if (rtascons_get_char_token == RTAS_UNKNOWN_SERVICE)
98 rtascons_get_char_token = rtas_token("get-term-char");
99 if (rtascons_get_char_token == RTAS_UNKNOWN_SERVICE)
100 return -EIO;
101
102 BUG_ON(hvc_rtas_dev);
103
104 /* Allocate an hvc_struct for the console device we instantiated
105 * earlier. Save off hp so that we can return it on exit */
106 hp = hvc_alloc(hvc_rtas_cookie, NO_IRQ, &hvc_rtas_get_put_ops);
107 if (IS_ERR(hp))
108 return PTR_ERR(hp);
109 hvc_rtas_dev = hp;
110 return 0;
111}
112module_init(hvc_rtas_init);
113
114/* This will tear down the tty portion of the driver */
115static void __exit hvc_rtas_exit(void)
116{
117 /* Really the fun isn't over until the worker thread breaks down and the
118 * tty cleans up */
119 if (hvc_rtas_dev)
120 hvc_remove(hvc_rtas_dev);
121}
122module_exit(hvc_rtas_exit);
123
124/* This will happen prior to module init. There is no tty at this time? */
125static int hvc_rtas_console_init(void)
126{
127 rtascons_put_char_token = rtas_token("put-term-char");
128 if (rtascons_put_char_token == RTAS_UNKNOWN_SERVICE)
129 return -EIO;
130 rtascons_get_char_token = rtas_token("get-term-char");
131 if (rtascons_get_char_token == RTAS_UNKNOWN_SERVICE)
132 return -EIO;
133
134 hvc_instantiate(hvc_rtas_cookie, 0, &hvc_rtas_get_put_ops );
135 add_preferred_console("hvc", 0, NULL);
136 return 0;
137}
138console_initcall(hvc_rtas_console_init);
diff --git a/drivers/char/hvc_vio.c b/drivers/char/hvc_vio.c
index f5212eb2b41d..9add81ceb440 100644
--- a/drivers/char/hvc_vio.c
+++ b/drivers/char/hvc_vio.c
@@ -31,10 +31,13 @@
31 31
32#include <linux/types.h> 32#include <linux/types.h>
33#include <linux/init.h> 33#include <linux/init.h>
34
34#include <asm/hvconsole.h> 35#include <asm/hvconsole.h>
35#include <asm/vio.h> 36#include <asm/vio.h>
36#include <asm/prom.h> 37#include <asm/prom.h>
37 38
39#include "hvc_console.h"
40
38char hvc_driver_name[] = "hvc_console"; 41char hvc_driver_name[] = "hvc_console";
39 42
40static struct vio_device_id hvc_driver_table[] __devinitdata = { 43static struct vio_device_id hvc_driver_table[] __devinitdata = {
@@ -48,6 +51,14 @@ static int filtered_get_chars(uint32_t vtermno, char *buf, int count)
48 unsigned long got; 51 unsigned long got;
49 int i; 52 int i;
50 53
54 /*
55 * Vio firmware will read up to SIZE_VIO_GET_CHARS at its own discretion
56 * so we play safe and avoid the situation where got > count which could
57 * overload the flip buffer.
58 */
59 if (count < SIZE_VIO_GET_CHARS)
60 return -EAGAIN;
61
51 got = hvc_get_chars(vtermno, buf, count); 62 got = hvc_get_chars(vtermno, buf, count);
52 63
53 /* 64 /*
diff --git a/drivers/char/hvcs.c b/drivers/char/hvcs.c
index f7ac31856572..327b00c3c45e 100644
--- a/drivers/char/hvcs.c
+++ b/drivers/char/hvcs.c
@@ -439,7 +439,6 @@ static int hvcs_io(struct hvcs_struct *hvcsd)
439 char buf[HVCS_BUFF_LEN] __ALIGNED__; 439 char buf[HVCS_BUFF_LEN] __ALIGNED__;
440 unsigned long flags; 440 unsigned long flags;
441 int got = 0; 441 int got = 0;
442 int i;
443 442
444 spin_lock_irqsave(&hvcsd->lock, flags); 443 spin_lock_irqsave(&hvcsd->lock, flags);
445 444
diff --git a/drivers/char/ipmi/ipmi_msghandler.c b/drivers/char/ipmi/ipmi_msghandler.c
index b8fb87c6c29f..40eb005b9d77 100644
--- a/drivers/char/ipmi/ipmi_msghandler.c
+++ b/drivers/char/ipmi/ipmi_msghandler.c
@@ -3744,7 +3744,7 @@ static int ipmi_init_msghandler(void)
3744 ipmi_timer.expires = jiffies + IPMI_TIMEOUT_JIFFIES; 3744 ipmi_timer.expires = jiffies + IPMI_TIMEOUT_JIFFIES;
3745 add_timer(&ipmi_timer); 3745 add_timer(&ipmi_timer);
3746 3746
3747 notifier_chain_register(&panic_notifier_list, &panic_block); 3747 atomic_notifier_chain_register(&panic_notifier_list, &panic_block);
3748 3748
3749 initialized = 1; 3749 initialized = 1;
3750 3750
@@ -3764,7 +3764,7 @@ static __exit void cleanup_ipmi(void)
3764 if (!initialized) 3764 if (!initialized)
3765 return; 3765 return;
3766 3766
3767 notifier_chain_unregister(&panic_notifier_list, &panic_block); 3767 atomic_notifier_chain_unregister(&panic_notifier_list, &panic_block);
3768 3768
3769 /* This can't be called if any interfaces exist, so no worry about 3769 /* This can't be called if any interfaces exist, so no worry about
3770 shutting down the interfaces. */ 3770 shutting down the interfaces. */
diff --git a/drivers/char/ipmi/ipmi_si_intf.c b/drivers/char/ipmi/ipmi_si_intf.c
index 12f858dc9994..35fbd4d8ed4b 100644
--- a/drivers/char/ipmi/ipmi_si_intf.c
+++ b/drivers/char/ipmi/ipmi_si_intf.c
@@ -237,10 +237,10 @@ struct smi_info
237 237
238static int try_smi_init(struct smi_info *smi); 238static int try_smi_init(struct smi_info *smi);
239 239
240static struct notifier_block *xaction_notifier_list; 240static ATOMIC_NOTIFIER_HEAD(xaction_notifier_list);
241static int register_xaction_notifier(struct notifier_block * nb) 241static int register_xaction_notifier(struct notifier_block * nb)
242{ 242{
243 return notifier_chain_register(&xaction_notifier_list, nb); 243 return atomic_notifier_chain_register(&xaction_notifier_list, nb);
244} 244}
245 245
246static void si_restart_short_timer(struct smi_info *smi_info); 246static void si_restart_short_timer(struct smi_info *smi_info);
@@ -302,7 +302,8 @@ static enum si_sm_result start_next_msg(struct smi_info *smi_info)
302 do_gettimeofday(&t); 302 do_gettimeofday(&t);
303 printk("**Start2: %d.%9.9d\n", t.tv_sec, t.tv_usec); 303 printk("**Start2: %d.%9.9d\n", t.tv_sec, t.tv_usec);
304#endif 304#endif
305 err = notifier_call_chain(&xaction_notifier_list, 0, smi_info); 305 err = atomic_notifier_call_chain(&xaction_notifier_list,
306 0, smi_info);
306 if (err & NOTIFY_STOP_MASK) { 307 if (err & NOTIFY_STOP_MASK) {
307 rv = SI_SM_CALL_WITHOUT_DELAY; 308 rv = SI_SM_CALL_WITHOUT_DELAY;
308 goto out; 309 goto out;
diff --git a/drivers/char/ipmi/ipmi_watchdog.c b/drivers/char/ipmi/ipmi_watchdog.c
index 616539310d9a..7ece9f3c8f70 100644
--- a/drivers/char/ipmi/ipmi_watchdog.c
+++ b/drivers/char/ipmi/ipmi_watchdog.c
@@ -1158,7 +1158,8 @@ static int __init ipmi_wdog_init(void)
1158 } 1158 }
1159 1159
1160 register_reboot_notifier(&wdog_reboot_notifier); 1160 register_reboot_notifier(&wdog_reboot_notifier);
1161 notifier_chain_register(&panic_notifier_list, &wdog_panic_notifier); 1161 atomic_notifier_chain_register(&panic_notifier_list,
1162 &wdog_panic_notifier);
1162 1163
1163 printk(KERN_INFO PFX "driver initialized\n"); 1164 printk(KERN_INFO PFX "driver initialized\n");
1164 1165
@@ -1176,7 +1177,8 @@ static __exit void ipmi_unregister_watchdog(void)
1176 release_nmi(&ipmi_nmi_handler); 1177 release_nmi(&ipmi_nmi_handler);
1177#endif 1178#endif
1178 1179
1179 notifier_chain_unregister(&panic_notifier_list, &wdog_panic_notifier); 1180 atomic_notifier_chain_unregister(&panic_notifier_list,
1181 &wdog_panic_notifier);
1180 unregister_reboot_notifier(&wdog_reboot_notifier); 1182 unregister_reboot_notifier(&wdog_reboot_notifier);
1181 1183
1182 if (! watchdog_user) 1184 if (! watchdog_user)
diff --git a/drivers/char/mem.c b/drivers/char/mem.c
index 5245ba1649ed..66719f9d294c 100644
--- a/drivers/char/mem.c
+++ b/drivers/char/mem.c
@@ -899,7 +899,7 @@ static const struct {
899 unsigned int minor; 899 unsigned int minor;
900 char *name; 900 char *name;
901 umode_t mode; 901 umode_t mode;
902 struct file_operations *fops; 902 const struct file_operations *fops;
903} devlist[] = { /* list of minor devices */ 903} devlist[] = { /* list of minor devices */
904 {1, "mem", S_IRUSR | S_IWUSR | S_IRGRP, &mem_fops}, 904 {1, "mem", S_IRUSR | S_IWUSR | S_IRGRP, &mem_fops},
905 {2, "kmem", S_IRUSR | S_IWUSR | S_IRGRP, &kmem_fops}, 905 {2, "kmem", S_IRUSR | S_IWUSR | S_IRGRP, &kmem_fops},
diff --git a/drivers/char/misc.c b/drivers/char/misc.c
index 3e4c0414a01a..96eb2a709e21 100644
--- a/drivers/char/misc.c
+++ b/drivers/char/misc.c
@@ -129,7 +129,7 @@ static int misc_open(struct inode * inode, struct file * file)
129 int minor = iminor(inode); 129 int minor = iminor(inode);
130 struct miscdevice *c; 130 struct miscdevice *c;
131 int err = -ENODEV; 131 int err = -ENODEV;
132 struct file_operations *old_fops, *new_fops = NULL; 132 const struct file_operations *old_fops, *new_fops = NULL;
133 133
134 down(&misc_sem); 134 down(&misc_sem);
135 135
diff --git a/drivers/char/mxser.h b/drivers/char/mxser.h
index e7fd0b08e0b7..7e188a4d602a 100644
--- a/drivers/char/mxser.h
+++ b/drivers/char/mxser.h
@@ -118,7 +118,7 @@
118 118
119// enable CTS interrupt 119// enable CTS interrupt
120#define MOXA_MUST_IER_ECTSI 0x80 120#define MOXA_MUST_IER_ECTSI 0x80
121// eanble RTS interrupt 121// enable RTS interrupt
122#define MOXA_MUST_IER_ERTSI 0x40 122#define MOXA_MUST_IER_ERTSI 0x40
123// enable Xon/Xoff interrupt 123// enable Xon/Xoff interrupt
124#define MOXA_MUST_IER_XINT 0x20 124#define MOXA_MUST_IER_XINT 0x20
diff --git a/drivers/char/synclink.c b/drivers/char/synclink.c
index d68be61f0a49..fee2aca3f6a5 100644
--- a/drivers/char/synclink.c
+++ b/drivers/char/synclink.c
@@ -941,17 +941,6 @@ static void* mgsl_get_text_ptr(void)
941 return mgsl_get_text_ptr; 941 return mgsl_get_text_ptr;
942} 942}
943 943
944/*
945 * tmp_buf is used as a temporary buffer by mgsl_write. We need to
946 * lock it in case the COPY_FROM_USER blocks while swapping in a page,
947 * and some other program tries to do a serial write at the same time.
948 * Since the lock will only come under contention when the system is
949 * swapping and available memory is low, it makes sense to share one
950 * buffer across all the serial ioports, since it significantly saves
951 * memory if large numbers of serial ports are open.
952 */
953static unsigned char *tmp_buf;
954
955static inline int mgsl_paranoia_check(struct mgsl_struct *info, 944static inline int mgsl_paranoia_check(struct mgsl_struct *info,
956 char *name, const char *routine) 945 char *name, const char *routine)
957{ 946{
@@ -2150,7 +2139,7 @@ static int mgsl_write(struct tty_struct * tty,
2150 if (mgsl_paranoia_check(info, tty->name, "mgsl_write")) 2139 if (mgsl_paranoia_check(info, tty->name, "mgsl_write"))
2151 goto cleanup; 2140 goto cleanup;
2152 2141
2153 if (!tty || !info->xmit_buf || !tmp_buf) 2142 if (!tty || !info->xmit_buf)
2154 goto cleanup; 2143 goto cleanup;
2155 2144
2156 if ( info->params.mode == MGSL_MODE_HDLC || 2145 if ( info->params.mode == MGSL_MODE_HDLC ||
@@ -3438,7 +3427,6 @@ static int mgsl_open(struct tty_struct *tty, struct file * filp)
3438{ 3427{
3439 struct mgsl_struct *info; 3428 struct mgsl_struct *info;
3440 int retval, line; 3429 int retval, line;
3441 unsigned long page;
3442 unsigned long flags; 3430 unsigned long flags;
3443 3431
3444 /* verify range of specified line number */ 3432 /* verify range of specified line number */
@@ -3472,18 +3460,6 @@ static int mgsl_open(struct tty_struct *tty, struct file * filp)
3472 goto cleanup; 3460 goto cleanup;
3473 } 3461 }
3474 3462
3475 if (!tmp_buf) {
3476 page = get_zeroed_page(GFP_KERNEL);
3477 if (!page) {
3478 retval = -ENOMEM;
3479 goto cleanup;
3480 }
3481 if (tmp_buf)
3482 free_page(page);
3483 else
3484 tmp_buf = (unsigned char *) page;
3485 }
3486
3487 info->tty->low_latency = (info->flags & ASYNC_LOW_LATENCY) ? 1 : 0; 3463 info->tty->low_latency = (info->flags & ASYNC_LOW_LATENCY) ? 1 : 0;
3488 3464
3489 spin_lock_irqsave(&info->netlock, flags); 3465 spin_lock_irqsave(&info->netlock, flags);
@@ -4502,11 +4478,6 @@ static void synclink_cleanup(void)
4502 kfree(tmp); 4478 kfree(tmp);
4503 } 4479 }
4504 4480
4505 if (tmp_buf) {
4506 free_page((unsigned long) tmp_buf);
4507 tmp_buf = NULL;
4508 }
4509
4510 if (pci_registered) 4481 if (pci_registered)
4511 pci_unregister_driver(&synclink_pci_driver); 4482 pci_unregister_driver(&synclink_pci_driver);
4512} 4483}
@@ -6025,7 +5996,7 @@ static void usc_set_async_mode( struct mgsl_struct *info )
6025 * <15..8> ? RxFIFO IRQ Request Level 5996 * <15..8> ? RxFIFO IRQ Request Level
6026 * 5997 *
6027 * Note: For async mode the receive FIFO level must be set 5998 * Note: For async mode the receive FIFO level must be set
6028 * to 0 to aviod the situation where the FIFO contains fewer bytes 5999 * to 0 to avoid the situation where the FIFO contains fewer bytes
6029 * than the trigger level and no more data is expected. 6000 * than the trigger level and no more data is expected.
6030 * 6001 *
6031 * <7> 0 Exited Hunt IA (Interrupt Arm) 6002 * <7> 0 Exited Hunt IA (Interrupt Arm)
diff --git a/drivers/char/synclink_gt.c b/drivers/char/synclink_gt.c
index 738ec2f4e563..b4d1f4eea435 100644
--- a/drivers/char/synclink_gt.c
+++ b/drivers/char/synclink_gt.c
@@ -1,5 +1,5 @@
1/* 1/*
2 * $Id: synclink_gt.c,v 4.22 2006/01/09 20:16:06 paulkf Exp $ 2 * $Id: synclink_gt.c,v 4.25 2006/02/06 21:20:33 paulkf Exp $
3 * 3 *
4 * Device driver for Microgate SyncLink GT serial adapters. 4 * Device driver for Microgate SyncLink GT serial adapters.
5 * 5 *
@@ -92,7 +92,7 @@
92 * module identification 92 * module identification
93 */ 93 */
94static char *driver_name = "SyncLink GT"; 94static char *driver_name = "SyncLink GT";
95static char *driver_version = "$Revision: 4.22 $"; 95static char *driver_version = "$Revision: 4.25 $";
96static char *tty_driver_name = "synclink_gt"; 96static char *tty_driver_name = "synclink_gt";
97static char *tty_dev_prefix = "ttySLG"; 97static char *tty_dev_prefix = "ttySLG";
98MODULE_LICENSE("GPL"); 98MODULE_LICENSE("GPL");
@@ -188,6 +188,20 @@ static void hdlcdev_exit(struct slgt_info *info);
188#define SLGT_REG_SIZE 256 188#define SLGT_REG_SIZE 256
189 189
190/* 190/*
191 * conditional wait facility
192 */
193struct cond_wait {
194 struct cond_wait *next;
195 wait_queue_head_t q;
196 wait_queue_t wait;
197 unsigned int data;
198};
199static void init_cond_wait(struct cond_wait *w, unsigned int data);
200static void add_cond_wait(struct cond_wait **head, struct cond_wait *w);
201static void remove_cond_wait(struct cond_wait **head, struct cond_wait *w);
202static void flush_cond_wait(struct cond_wait **head);
203
204/*
191 * DMA buffer descriptor and access macros 205 * DMA buffer descriptor and access macros
192 */ 206 */
193struct slgt_desc 207struct slgt_desc
@@ -269,6 +283,9 @@ struct slgt_info {
269 struct timer_list tx_timer; 283 struct timer_list tx_timer;
270 struct timer_list rx_timer; 284 struct timer_list rx_timer;
271 285
286 unsigned int gpio_present;
287 struct cond_wait *gpio_wait_q;
288
272 spinlock_t lock; /* spinlock for synchronizing with ISR */ 289 spinlock_t lock; /* spinlock for synchronizing with ISR */
273 290
274 struct work_struct task; 291 struct work_struct task;
@@ -379,6 +396,11 @@ static MGSL_PARAMS default_params = {
379#define MASK_OVERRUN BIT4 396#define MASK_OVERRUN BIT4
380 397
381#define GSR 0x00 /* global status */ 398#define GSR 0x00 /* global status */
399#define JCR 0x04 /* JTAG control */
400#define IODR 0x08 /* GPIO direction */
401#define IOER 0x0c /* GPIO interrupt enable */
402#define IOVR 0x10 /* GPIO value */
403#define IOSR 0x14 /* GPIO interrupt status */
382#define TDR 0x80 /* tx data */ 404#define TDR 0x80 /* tx data */
383#define RDR 0x80 /* rx data */ 405#define RDR 0x80 /* rx data */
384#define TCR 0x82 /* tx control */ 406#define TCR 0x82 /* tx control */
@@ -503,6 +525,9 @@ static int tiocmset(struct tty_struct *tty, struct file *file,
503static void set_break(struct tty_struct *tty, int break_state); 525static void set_break(struct tty_struct *tty, int break_state);
504static int get_interface(struct slgt_info *info, int __user *if_mode); 526static int get_interface(struct slgt_info *info, int __user *if_mode);
505static int set_interface(struct slgt_info *info, int if_mode); 527static int set_interface(struct slgt_info *info, int if_mode);
528static int set_gpio(struct slgt_info *info, struct gpio_desc __user *gpio);
529static int get_gpio(struct slgt_info *info, struct gpio_desc __user *gpio);
530static int wait_gpio(struct slgt_info *info, struct gpio_desc __user *gpio);
506 531
507/* 532/*
508 * driver functions 533 * driver functions
@@ -1112,6 +1137,12 @@ static int ioctl(struct tty_struct *tty, struct file *file,
1112 return get_interface(info, argp); 1137 return get_interface(info, argp);
1113 case MGSL_IOCSIF: 1138 case MGSL_IOCSIF:
1114 return set_interface(info,(int)arg); 1139 return set_interface(info,(int)arg);
1140 case MGSL_IOCSGPIO:
1141 return set_gpio(info, argp);
1142 case MGSL_IOCGGPIO:
1143 return get_gpio(info, argp);
1144 case MGSL_IOCWAITGPIO:
1145 return wait_gpio(info, argp);
1115 case TIOCGICOUNT: 1146 case TIOCGICOUNT:
1116 spin_lock_irqsave(&info->lock,flags); 1147 spin_lock_irqsave(&info->lock,flags);
1117 cnow = info->icount; 1148 cnow = info->icount;
@@ -1762,10 +1793,6 @@ static void rx_async(struct slgt_info *info)
1762 DBGDATA(info, p, count, "rx"); 1793 DBGDATA(info, p, count, "rx");
1763 1794
1764 for(i=0 ; i < count; i+=2, p+=2) { 1795 for(i=0 ; i < count; i+=2, p+=2) {
1765 if (tty && chars) {
1766 tty_flip_buffer_push(tty);
1767 chars = 0;
1768 }
1769 ch = *p; 1796 ch = *p;
1770 icount->rx++; 1797 icount->rx++;
1771 1798
@@ -2158,6 +2185,24 @@ static void isr_txeom(struct slgt_info *info, unsigned short status)
2158 } 2185 }
2159} 2186}
2160 2187
2188static void isr_gpio(struct slgt_info *info, unsigned int changed, unsigned int state)
2189{
2190 struct cond_wait *w, *prev;
2191
2192 /* wake processes waiting for specific transitions */
2193 for (w = info->gpio_wait_q, prev = NULL ; w != NULL ; w = w->next) {
2194 if (w->data & changed) {
2195 w->data = state;
2196 wake_up_interruptible(&w->q);
2197 if (prev != NULL)
2198 prev->next = w->next;
2199 else
2200 info->gpio_wait_q = w->next;
2201 } else
2202 prev = w;
2203 }
2204}
2205
2161/* interrupt service routine 2206/* interrupt service routine
2162 * 2207 *
2163 * irq interrupt number 2208 * irq interrupt number
@@ -2193,6 +2238,22 @@ static irqreturn_t slgt_interrupt(int irq, void *dev_id, struct pt_regs * regs)
2193 } 2238 }
2194 } 2239 }
2195 2240
2241 if (info->gpio_present) {
2242 unsigned int state;
2243 unsigned int changed;
2244 while ((changed = rd_reg32(info, IOSR)) != 0) {
2245 DBGISR(("%s iosr=%08x\n", info->device_name, changed));
2246 /* read latched state of GPIO signals */
2247 state = rd_reg32(info, IOVR);
2248 /* clear pending GPIO interrupt bits */
2249 wr_reg32(info, IOSR, changed);
2250 for (i=0 ; i < info->port_count ; i++) {
2251 if (info->port_array[i] != NULL)
2252 isr_gpio(info->port_array[i], changed, state);
2253 }
2254 }
2255 }
2256
2196 for(i=0; i < info->port_count ; i++) { 2257 for(i=0; i < info->port_count ; i++) {
2197 struct slgt_info *port = info->port_array[i]; 2258 struct slgt_info *port = info->port_array[i];
2198 2259
@@ -2276,6 +2337,8 @@ static void shutdown(struct slgt_info *info)
2276 set_signals(info); 2337 set_signals(info);
2277 } 2338 }
2278 2339
2340 flush_cond_wait(&info->gpio_wait_q);
2341
2279 spin_unlock_irqrestore(&info->lock,flags); 2342 spin_unlock_irqrestore(&info->lock,flags);
2280 2343
2281 if (info->tty) 2344 if (info->tty)
@@ -2650,6 +2713,175 @@ static int set_interface(struct slgt_info *info, int if_mode)
2650 return 0; 2713 return 0;
2651} 2714}
2652 2715
2716/*
2717 * set general purpose IO pin state and direction
2718 *
2719 * user_gpio fields:
2720 * state each bit indicates a pin state
2721 * smask set bit indicates pin state to set
2722 * dir each bit indicates a pin direction (0=input, 1=output)
2723 * dmask set bit indicates pin direction to set
2724 */
2725static int set_gpio(struct slgt_info *info, struct gpio_desc __user *user_gpio)
2726{
2727 unsigned long flags;
2728 struct gpio_desc gpio;
2729 __u32 data;
2730
2731 if (!info->gpio_present)
2732 return -EINVAL;
2733 if (copy_from_user(&gpio, user_gpio, sizeof(gpio)))
2734 return -EFAULT;
2735 DBGINFO(("%s set_gpio state=%08x smask=%08x dir=%08x dmask=%08x\n",
2736 info->device_name, gpio.state, gpio.smask,
2737 gpio.dir, gpio.dmask));
2738
2739 spin_lock_irqsave(&info->lock,flags);
2740 if (gpio.dmask) {
2741 data = rd_reg32(info, IODR);
2742 data |= gpio.dmask & gpio.dir;
2743 data &= ~(gpio.dmask & ~gpio.dir);
2744 wr_reg32(info, IODR, data);
2745 }
2746 if (gpio.smask) {
2747 data = rd_reg32(info, IOVR);
2748 data |= gpio.smask & gpio.state;
2749 data &= ~(gpio.smask & ~gpio.state);
2750 wr_reg32(info, IOVR, data);
2751 }
2752 spin_unlock_irqrestore(&info->lock,flags);
2753
2754 return 0;
2755}
2756
2757/*
2758 * get general purpose IO pin state and direction
2759 */
2760static int get_gpio(struct slgt_info *info, struct gpio_desc __user *user_gpio)
2761{
2762 struct gpio_desc gpio;
2763 if (!info->gpio_present)
2764 return -EINVAL;
2765 gpio.state = rd_reg32(info, IOVR);
2766 gpio.smask = 0xffffffff;
2767 gpio.dir = rd_reg32(info, IODR);
2768 gpio.dmask = 0xffffffff;
2769 if (copy_to_user(user_gpio, &gpio, sizeof(gpio)))
2770 return -EFAULT;
2771 DBGINFO(("%s get_gpio state=%08x dir=%08x\n",
2772 info->device_name, gpio.state, gpio.dir));
2773 return 0;
2774}
2775
2776/*
2777 * conditional wait facility
2778 */
2779static void init_cond_wait(struct cond_wait *w, unsigned int data)
2780{
2781 init_waitqueue_head(&w->q);
2782 init_waitqueue_entry(&w->wait, current);
2783 w->data = data;
2784}
2785
2786static void add_cond_wait(struct cond_wait **head, struct cond_wait *w)
2787{
2788 set_current_state(TASK_INTERRUPTIBLE);
2789 add_wait_queue(&w->q, &w->wait);
2790 w->next = *head;
2791 *head = w;
2792}
2793
2794static void remove_cond_wait(struct cond_wait **head, struct cond_wait *cw)
2795{
2796 struct cond_wait *w, *prev;
2797 remove_wait_queue(&cw->q, &cw->wait);
2798 set_current_state(TASK_RUNNING);
2799 for (w = *head, prev = NULL ; w != NULL ; prev = w, w = w->next) {
2800 if (w == cw) {
2801 if (prev != NULL)
2802 prev->next = w->next;
2803 else
2804 *head = w->next;
2805 break;
2806 }
2807 }
2808}
2809
2810static void flush_cond_wait(struct cond_wait **head)
2811{
2812 while (*head != NULL) {
2813 wake_up_interruptible(&(*head)->q);
2814 *head = (*head)->next;
2815 }
2816}
2817
2818/*
2819 * wait for general purpose I/O pin(s) to enter specified state
2820 *
2821 * user_gpio fields:
2822 * state - bit indicates target pin state
2823 * smask - set bit indicates watched pin
2824 *
2825 * The wait ends when at least one watched pin enters the specified
2826 * state. When 0 (no error) is returned, user_gpio->state is set to the
2827 * state of all GPIO pins when the wait ends.
2828 *
2829 * Note: Each pin may be a dedicated input, dedicated output, or
2830 * configurable input/output. The number and configuration of pins
2831 * varies with the specific adapter model. Only input pins (dedicated
2832 * or configured) can be monitored with this function.
2833 */
2834static int wait_gpio(struct slgt_info *info, struct gpio_desc __user *user_gpio)
2835{
2836 unsigned long flags;
2837 int rc = 0;
2838 struct gpio_desc gpio;
2839 struct cond_wait wait;
2840 u32 state;
2841
2842 if (!info->gpio_present)
2843 return -EINVAL;
2844 if (copy_from_user(&gpio, user_gpio, sizeof(gpio)))
2845 return -EFAULT;
2846 DBGINFO(("%s wait_gpio() state=%08x smask=%08x\n",
2847 info->device_name, gpio.state, gpio.smask));
2848 /* ignore output pins identified by set IODR bit */
2849 if ((gpio.smask &= ~rd_reg32(info, IODR)) == 0)
2850 return -EINVAL;
2851 init_cond_wait(&wait, gpio.smask);
2852
2853 spin_lock_irqsave(&info->lock, flags);
2854 /* enable interrupts for watched pins */
2855 wr_reg32(info, IOER, rd_reg32(info, IOER) | gpio.smask);
2856 /* get current pin states */
2857 state = rd_reg32(info, IOVR);
2858
2859 if (gpio.smask & ~(state ^ gpio.state)) {
2860 /* already in target state */
2861 gpio.state = state;
2862 } else {
2863 /* wait for target state */
2864 add_cond_wait(&info->gpio_wait_q, &wait);
2865 spin_unlock_irqrestore(&info->lock, flags);
2866 schedule();
2867 if (signal_pending(current))
2868 rc = -ERESTARTSYS;
2869 else
2870 gpio.state = wait.data;
2871 spin_lock_irqsave(&info->lock, flags);
2872 remove_cond_wait(&info->gpio_wait_q, &wait);
2873 }
2874
2875 /* disable all GPIO interrupts if no waiting processes */
2876 if (info->gpio_wait_q == NULL)
2877 wr_reg32(info, IOER, 0);
2878 spin_unlock_irqrestore(&info->lock,flags);
2879
2880 if ((rc == 0) && copy_to_user(user_gpio, &gpio, sizeof(gpio)))
2881 rc = -EFAULT;
2882 return rc;
2883}
2884
2653static int modem_input_wait(struct slgt_info *info,int arg) 2885static int modem_input_wait(struct slgt_info *info,int arg)
2654{ 2886{
2655 unsigned long flags; 2887 unsigned long flags;
@@ -3166,8 +3398,10 @@ static void device_init(int adapter_num, struct pci_dev *pdev)
3166 } else { 3398 } else {
3167 port_array[0]->irq_requested = 1; 3399 port_array[0]->irq_requested = 1;
3168 adapter_test(port_array[0]); 3400 adapter_test(port_array[0]);
3169 for (i=1 ; i < port_count ; i++) 3401 for (i=1 ; i < port_count ; i++) {
3170 port_array[i]->init_error = port_array[0]->init_error; 3402 port_array[i]->init_error = port_array[0]->init_error;
3403 port_array[i]->gpio_present = port_array[0]->gpio_present;
3404 }
3171 } 3405 }
3172 } 3406 }
3173} 3407}
@@ -4301,7 +4535,7 @@ static int register_test(struct slgt_info *info)
4301 break; 4535 break;
4302 } 4536 }
4303 } 4537 }
4304 4538 info->gpio_present = (rd_reg32(info, JCR) & BIT5) ? 1 : 0;
4305 info->init_error = rc ? 0 : DiagStatus_AddressFailure; 4539 info->init_error = rc ? 0 : DiagStatus_AddressFailure;
4306 return rc; 4540 return rc;
4307} 4541}
diff --git a/drivers/char/tty_io.c b/drivers/char/tty_io.c
index 811dadb9ce3e..0bfd1b63662e 100644
--- a/drivers/char/tty_io.c
+++ b/drivers/char/tty_io.c
@@ -1094,8 +1094,8 @@ static void do_tty_hangup(void *data)
1094 p->signal->tty = NULL; 1094 p->signal->tty = NULL;
1095 if (!p->signal->leader) 1095 if (!p->signal->leader)
1096 continue; 1096 continue;
1097 send_group_sig_info(SIGHUP, SEND_SIG_PRIV, p); 1097 group_send_sig_info(SIGHUP, SEND_SIG_PRIV, p);
1098 send_group_sig_info(SIGCONT, SEND_SIG_PRIV, p); 1098 group_send_sig_info(SIGCONT, SEND_SIG_PRIV, p);
1099 if (tty->pgrp > 0) 1099 if (tty->pgrp > 0)
1100 p->signal->tty_old_pgrp = tty->pgrp; 1100 p->signal->tty_old_pgrp = tty->pgrp;
1101 } while_each_task_pid(tty->session, PIDTYPE_SID, p); 1101 } while_each_task_pid(tty->session, PIDTYPE_SID, p);
@@ -2672,7 +2672,7 @@ static void __do_SAK(void *arg)
2672 tty_hangup(tty); 2672 tty_hangup(tty);
2673#else 2673#else
2674 struct tty_struct *tty = arg; 2674 struct tty_struct *tty = arg;
2675 struct task_struct *p; 2675 struct task_struct *g, *p;
2676 int session; 2676 int session;
2677 int i; 2677 int i;
2678 struct file *filp; 2678 struct file *filp;
@@ -2693,8 +2693,18 @@ static void __do_SAK(void *arg)
2693 tty->driver->flush_buffer(tty); 2693 tty->driver->flush_buffer(tty);
2694 2694
2695 read_lock(&tasklist_lock); 2695 read_lock(&tasklist_lock);
2696 /* Kill the entire session */
2696 do_each_task_pid(session, PIDTYPE_SID, p) { 2697 do_each_task_pid(session, PIDTYPE_SID, p) {
2697 if (p->signal->tty == tty || session > 0) { 2698 printk(KERN_NOTICE "SAK: killed process %d"
2699 " (%s): p->signal->session==tty->session\n",
2700 p->pid, p->comm);
2701 send_sig(SIGKILL, p, 1);
2702 } while_each_task_pid(session, PIDTYPE_SID, p);
2703 /* Now kill any processes that happen to have the
2704 * tty open.
2705 */
2706 do_each_thread(g, p) {
2707 if (p->signal->tty == tty) {
2698 printk(KERN_NOTICE "SAK: killed process %d" 2708 printk(KERN_NOTICE "SAK: killed process %d"
2699 " (%s): p->signal->session==tty->session\n", 2709 " (%s): p->signal->session==tty->session\n",
2700 p->pid, p->comm); 2710 p->pid, p->comm);
@@ -2721,7 +2731,7 @@ static void __do_SAK(void *arg)
2721 rcu_read_unlock(); 2731 rcu_read_unlock();
2722 } 2732 }
2723 task_unlock(p); 2733 task_unlock(p);
2724 } while_each_task_pid(session, PIDTYPE_SID, p); 2734 } while_each_thread(g, p);
2725 read_unlock(&tasklist_lock); 2735 read_unlock(&tasklist_lock);
2726#endif 2736#endif
2727} 2737}