598 |
598 |
599 if (NULL == (priv = kmalloc(sizeof(*priv), GFP_KERNEL))) { |
599 if (NULL == (priv = kmalloc(sizeof(*priv), GFP_KERNEL))) { |
600 printk(KERN_ERR "ME8100: me8100_open(): kmalloc() failed\n"); |
600 printk(KERN_ERR "ME8100: me8100_open(): kmalloc() failed\n"); |
601 return -EIO; |
601 return -EIO; |
602 } |
602 } |
|
603 |
603 file_ptr->private_data = priv; |
604 file_ptr->private_data = priv; |
604 |
|
605 memset(priv, 0, sizeof(*priv)); |
605 memset(priv, 0, sizeof(*priv)); |
606 |
606 |
607 info = &info_vec[device]; |
607 priv->info = info = &info_vec[device]; |
608 subinfo = &info->subinfo[subdevice]; |
608 priv->subinfo = subinfo = &info->subinfo[subdevice]; |
609 priv->info = info; |
|
610 priv->subinfo = subinfo; |
|
611 |
609 |
612 MOD_INC_USE_COUNT; |
610 MOD_INC_USE_COUNT; |
613 |
611 |
614 if (file_ptr->f_mode & FMODE_WRITE) { |
612 if (file_ptr->f_mode & FMODE_WRITE) { |
615 /* If we're the first writer, the control register has to be |
613 /* If we're the first writer, the control register has to be |
631 if (file_ptr->f_mode & FMODE_READ) { |
629 if (file_ptr->f_mode & FMODE_READ) { |
632 /* If we're a reader, the IRQ should be setup -- if not done already |
630 /* If we're a reader, the IRQ should be setup -- if not done already |
633 * (might be done by some ioctl()s. The file_ptr get a private data |
631 * (might be done by some ioctl()s. The file_ptr get a private data |
634 * pointer passed. We need this to keep track of timestamps for |
632 * pointer passed. We need this to keep track of timestamps for |
635 * read data. */ |
633 * read data. */ |
|
634 unsigned short icsr; |
636 |
635 |
637 PDEBUG("*** open for reading\n"); |
636 PDEBUG("*** open for reading\n"); |
638 |
637 |
639 /* The first reader should setup the IRQs (enabling IRQ handling |
638 /* The first reader on the board will enable IRQs at all. |
640 * with the full bit mask. It might be modified later. */ |
639 * Every next reader shouldn't care. */ |
|
640 if (0 == info->num_reader++) icsr = PCI_INT_EN; |
|
641 else icsr = inw(info->plx_regbase + PLX_ICSR); |
|
642 |
|
643 /* The first reader per subdevice should enable IRQs for |
|
644 * this subdevice, but not change the settings found already |
|
645 * in the ICSR. */ |
641 if (0 == subinfo->num_reader++) { |
646 if (0 == subinfo->num_reader++) { |
642 int mask; |
647 int mask = 0xffff; |
643 unsigned short icsr; |
|
644 |
|
645 mask = 0xffff; |
|
646 icsr = PCI_INT_EN | ((LOCAL_INT_EN | LOCAL_INT_POL) << (3 * subdevice)); |
|
647 |
648 |
648 PDEBUG("*** first reader on subdevice %d\n", subdevice); |
649 PDEBUG("*** first reader on subdevice %d\n", subdevice); |
649 |
650 |
650 /* 1) setup the PLX register */ |
651 subinfo->icsr_flags = (LOCAL_INT_EN | LOCAL_INT_POL) << (3 * subdevice); |
|
652 icsr |= subinfo->icsr_flags; |
|
653 |
|
654 /* Setup the interrupt mask */ |
|
655 PDEBUG("*** irqmask = 0x%04x\n", mask); |
|
656 outw(mask, subinfo->regbase + ME8100_MASK_REG); |
|
657 |
|
658 /* Setup the PLX register */ |
651 PDEBUG("*** plx = 0x%0x\n", icsr); |
659 PDEBUG("*** plx = 0x%0x\n", icsr); |
652 outb(icsr, info->plx_regbase + PLX_ICSR); |
660 outb(icsr, info->plx_regbase + PLX_ICSR); |
653 |
661 |
654 /* 2) setup the interrupt mask */ |
662 /* Setup the irq flags in regbase */ |
655 PDEBUG("*** irqmask = 0x%04x\n", mask); |
|
656 outw(mask, subinfo->regbase + ME8100_MASK_REG); |
|
657 |
|
658 /* 3) setup the irq flags in regbase */ |
|
659 subinfo->ctrl_rflags = ME8100_CTRL_IRQ_MASK; |
663 subinfo->ctrl_rflags = ME8100_CTRL_IRQ_MASK; |
660 subinfo->ctrl_reg |= subinfo->ctrl_rflags; |
664 subinfo->ctrl_reg |= subinfo->ctrl_rflags; |
661 PDEBUG("*** adding 0x%0x to ctrl => 0x%04x\n", |
665 PDEBUG("*** adding 0x%0x to ctrl => 0x%04x\n", |
662 subinfo->ctrl_rflags, subinfo->ctrl_reg); |
666 subinfo->ctrl_rflags, subinfo->ctrl_reg); |
663 outw(subinfo->ctrl_reg, subinfo->regbase + ME8100_CTRL_REG); |
667 outw(subinfo->ctrl_reg, subinfo->regbase + ME8100_CTRL_REG); |
664 |
|
665 } /* first reader */ |
668 } /* first reader */ |
666 } /* reader */ |
669 } /* reader */ |
667 |
670 |
668 |
671 |
669 return 0; |
672 return 0; |
728 subinfo->ctrl_reg &= ~subinfo->ctrl_rflags; |
731 subinfo->ctrl_reg &= ~subinfo->ctrl_rflags; |
729 subinfo->ctrl_rflags = 0; |
732 subinfo->ctrl_rflags = 0; |
730 PDEBUG("*** resetting IRQ mode ctrl: 0x%x\n", subinfo->ctrl_reg); |
733 PDEBUG("*** resetting IRQ mode ctrl: 0x%x\n", subinfo->ctrl_reg); |
731 outw(subinfo->ctrl_reg, subinfo->regbase + ME8100_CTRL_REG); |
734 outw(subinfo->ctrl_reg, subinfo->regbase + ME8100_CTRL_REG); |
732 } |
735 } |
|
736 |
|
737 if (0 == --info->num_reader) { |
|
738 unsigned short icsr; |
|
739 icsr = inw(info->plx_regbase + PLX_ICSR); |
|
740 icsr &= ~(PCI_INT_EN | SOFT_INT); |
|
741 outw(icsr, info->plx_regbase + PLX_ICSR); |
|
742 PDEBUG("** reset icsr to 0x%0X\n", icsr); |
|
743 } |
733 } |
744 } |
734 |
745 |
735 |
746 |
736 /* resetting the board on last close */ |
747 /* resetting the board on last close */ |
737 |
748 |
2079 * |
2090 * |
2080 * Parameter list: |
2091 * Parameter list: |
2081 * Name Type Access Description |
2092 * Name Type Access Description |
2082 *-------------------------------------------------------------------------- |
2093 *-------------------------------------------------------------------------- |
2083 * irq int read number of interrupt occured |
2094 * irq int read number of interrupt occured |
2084 * dev_id void* read pointer to board specific |
2095 * dev void* read pointer to board specific |
2085 * informations |
2096 * informations |
2086 * regs struct pt_regs * read pointer to cpu register |
2097 * regs struct pt_regs * read pointer to cpu register |
2087 * |
2098 * |
2088 * Result: |
2099 * Result: |
2089 *-------------------------------------------------------------------------- |
2100 *-------------------------------------------------------------------------- |
2090 * Author: GG |
2101 * Author: GG |
2091 * Modification: |
2102 * Modification: |
2092 */ |
2103 */ |
2093 static void me8100_isr(int irq, void *dev_id, struct pt_regs *regs){ |
2104 static void me8100_isr(int irq, void *dev, struct pt_regs *regs){ |
2094 int i; |
2105 int i; |
2095 unsigned char icsr; |
2106 unsigned char icsr; |
2096 me8100_info_t *info; |
2107 me8100_info_t *info; |
2097 |
2108 |
2098 /* A: 0x04 & 0x40 & 0x01 for irq at port A */ |
2109 /* A: 0x04 & 0x40 & 0x01 for irq at port A */ |
2099 /* B: 0x20 & 0x40 & 0x08 for irq at port B */ |
2110 /* B: 0x20 & 0x40 & 0x08 for irq at port B */ |
2100 unsigned short icsr_mask[] = { 0x45, 0x68 }; |
2111 unsigned short icsr_mask[] = { 0x45, 0x68 }; |
2101 |
2112 |
2102 info = (me8100_info_t *) dev_id; |
2113 info = dev; |
2103 |
2114 |
2104 PDEBUG("INT: me8100_isr()\n"); |
2115 PDEBUG("==> me8100_isr()\n"); |
2105 |
2116 |
2106 if(irq != info->int_line){ |
2117 if(irq != info->int_line){ |
2107 PDEBUG("me8100_isr():incorrect interrupt num: %d\n", irq); |
2118 PDEBUG("me8100_isr():incorrect interrupt num: %d\n", irq); |
2108 return; |
2119 return; |
2109 } |
2120 } |
2110 |
2121 |
2111 |
2122 |
2112 icsr = inb(info->plx_regbase + PLX_ICSR); |
2123 icsr = inb(info->plx_regbase + PLX_ICSR); |
2113 PDEBUG("ICSR: 0x%04x\n", icsr); |
2124 PDEBUG("==> ICSR: 0x%04x\n", icsr); |
2114 |
2125 |
2115 /* We got an interrupt. Now try each possible subdevice in turn. |
2126 /* We got an interrupt. Now try each possible subdevice in turn. |
2116 * (There is the possibility that all subdevices raised an interupt |
2127 * (There is the possibility that all subdevices raised an interupt |
2117 * at the same time. I don't know how this is resolved by the board. |
2128 * at the same time. I don't know how this is resolved by the board. |
2118 * So we've to try each subdevice in turn.) */ |
2129 * So we've to try each subdevice in turn.) */ |
2119 for (i = 0; i < MAX_SUBDEVICES; ++i) { |
2130 for (i = 0; i < MAX_SUBDEVICES; ++i) { |
2120 if ((icsr & icsr_mask[i]) == icsr_mask[i]) { |
2131 if ((icsr & icsr_mask[i]) == icsr_mask[i]) { |
2121 |
|
2122 me8100_subinfo_t *subinfo = &info->subinfo[i]; |
2132 me8100_subinfo_t *subinfo = &info->subinfo[i]; |
|
2133 |
|
2134 PDEBUG("==> Interrupt for subdevice %d\n", i); |
|
2135 |
2123 subinfo->int_seen = jiffies; |
2136 subinfo->int_seen = jiffies; |
2124 ++subinfo->int_count; |
2137 ++subinfo->int_count; |
2125 |
2138 |
2126 subinfo->int_di = inw(subinfo->regbase + ME8100_INT_DI_REG); |
2139 subinfo->int_di = inw(subinfo->regbase + ME8100_INT_DI_REG); |
2127 inw(subinfo->regbase + ME8100_RES_INT_REG); // dummy read |
2140 inw(subinfo->regbase + ME8100_RES_INT_REG); // dummy read |
2128 |
2141 |
2129 PDEBUG("===> read: 0x%04x\n", subinfo->int_di); |
2142 PDEBUG("==> read: 0x%04x\n", subinfo->int_di); |
2130 wake_up_interruptible(&subinfo->readq); |
2143 wake_up_interruptible(&subinfo->readq); |
2131 if (subinfo->fasync_ptr) kill_fasync(&subinfo->fasync_ptr, SIGIO, POLL_IN); |
2144 if (subinfo->fasync_ptr) kill_fasync(&subinfo->fasync_ptr, SIGIO, POLL_IN); |
2132 } |
2145 } |
2133 } |
2146 } |
2134 |
2147 |
2135 |
2148 |
2136 return; |
2149 return; |
2137 |
|
2138 } |
2150 } |
2139 |
2151 |
2140 |
2152 |
2141 |
2153 |
2142 |
2154 |