Merge git://git.kernel.org/pub/scm/linux/kernel/git/rusty/linux-2.6-for-linus
[safe/jmp/linux-2.6] / drivers / char / cs5535_gpio.c
index 46d6603..04ba906 100644 (file)
@@ -17,6 +17,7 @@
 #include <linux/cdev.h>
 #include <linux/ioport.h>
 #include <linux/pci.h>
+#include <linux/smp_lock.h>
 #include <asm/uaccess.h>
 #include <asm/io.h>
 
@@ -44,6 +45,7 @@ static struct pci_device_id divil_pci[] = {
        { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_CS5536_ISA) },
        { } /* NULL entry */
 };
+MODULE_DEVICE_TABLE(pci, divil_pci);
 
 static struct cdev cs5535_gpio_cdev;
 
@@ -82,7 +84,7 @@ static inline u32 cs5535_lowhigh_base(int reg)
 static ssize_t cs5535_gpio_write(struct file *file, const char __user *data,
                                 size_t len, loff_t *ppos)
 {
-       u32     m = iminor(file->f_dentry->d_inode);
+       u32     m = iminor(file->f_path.dentry->d_inode);
        int     i, j;
        u32     base = gpio_base + cs5535_lowhigh_base(m);
        u32     m0, m1;
@@ -103,6 +105,11 @@ static ssize_t cs5535_gpio_write(struct file *file, const char __user *data,
                for (j = 0; j < ARRAY_SIZE(rm); j++) {
                        if (c == rm[j].on) {
                                outl(m1, base + rm[j].wr_offset);
+                               /* If enabling output, turn off AUX 1 and AUX 2 */
+                               if (c == 'O') {
+                                       outl(m0, base + 0x10);
+                                       outl(m0, base + 0x14);
+                               }
                                break;
                        } else if (c == rm[j].off) {
                                outl(m0, base + rm[j].wr_offset);
@@ -117,7 +124,7 @@ static ssize_t cs5535_gpio_write(struct file *file, const char __user *data,
 static ssize_t cs5535_gpio_read(struct file *file, char __user *buf,
                                size_t len, loff_t *ppos)
 {
-       u32     m = iminor(file->f_dentry->d_inode);
+       u32     m = iminor(file->f_path.dentry->d_inode);
        u32     base = gpio_base + cs5535_lowhigh_base(m);
        int     rd_bit = 1 << (m & 0x0f);
        int     i;
@@ -151,6 +158,7 @@ static int cs5535_gpio_open(struct inode *inode, struct file *file)
 {
        u32 m = iminor(inode);
 
+       cycle_kernel_lock();
        /* the mask says which pins are usable by this driver */
        if ((mask & (1 << m)) == 0)
                return -EINVAL;
@@ -158,7 +166,7 @@ static int cs5535_gpio_open(struct inode *inode, struct file *file)
        return nonseekable_open(inode, file);
 }
 
-static struct file_operations cs5535_gpio_fops = {
+static const struct file_operations cs5535_gpio_fops = {
        .owner  = THIS_MODULE,
        .write  = cs5535_gpio_write,
        .read   = cs5535_gpio_read,
@@ -209,7 +217,7 @@ static int __init cs5535_gpio_init(void)
        else
                mask = 0x0b003c66;
 
-       if (request_region(gpio_base, CS5535_GPIO_SIZE, NAME) == 0) {
+       if (!request_region(gpio_base, CS5535_GPIO_SIZE, NAME)) {
                printk(KERN_ERR NAME ": can't allocate I/O for GPIO\n");
                return -ENODEV;
        }