diff options
Diffstat (limited to 'drivers/char/cyclades.c')
-rw-r--r-- | drivers/char/cyclades.c | 2581 |
1 files changed, 1119 insertions, 1462 deletions
diff --git a/drivers/char/cyclades.c b/drivers/char/cyclades.c index 16dc5d1d3cb4..c72ee97d3892 100644 --- a/drivers/char/cyclades.c +++ b/drivers/char/cyclades.c | |||
@@ -10,15 +10,14 @@ | |||
10 | * | 10 | * |
11 | * Initially written by Randolph Bentson <bentson@grieg.seaslug.org>. | 11 | * Initially written by Randolph Bentson <bentson@grieg.seaslug.org>. |
12 | * Modified and maintained by Marcio Saito <marcio@cyclades.com>. | 12 | * Modified and maintained by Marcio Saito <marcio@cyclades.com>. |
13 | * Currently maintained by Cyclades team <async@cyclades.com>. | ||
14 | * | 13 | * |
15 | * For Technical support and installation problems, please send e-mail | 14 | * Copyright (C) 2007 Jiri Slaby <jirislaby@gmail.com> |
16 | * to support@cyclades.com. | ||
17 | * | 15 | * |
18 | * Much of the design and some of the code came from serial.c | 16 | * Much of the design and some of the code came from serial.c |
19 | * which was copyright (C) 1991, 1992 Linus Torvalds. It was | 17 | * which was copyright (C) 1991, 1992 Linus Torvalds. It was |
20 | * extensively rewritten by Theodore Ts'o, 8/16/92 -- 9/14/92, | 18 | * extensively rewritten by Theodore Ts'o, 8/16/92 -- 9/14/92, |
21 | * and then fixed as suggested by Michael K. Johnson 12/12/92. | 19 | * and then fixed as suggested by Michael K. Johnson 12/12/92. |
20 | * Converted to pci probing and cleaned up by Jiri Slaby. | ||
22 | * | 21 | * |
23 | * This version supports shared IRQ's (only for PCI boards). | 22 | * This version supports shared IRQ's (only for PCI boards). |
24 | * | 23 | * |
@@ -591,7 +590,7 @@ | |||
591 | * | 590 | * |
592 | */ | 591 | */ |
593 | 592 | ||
594 | #define CY_VERSION "2.4" | 593 | #define CY_VERSION "2.5" |
595 | 594 | ||
596 | /* If you need to install more boards than NR_CARDS, change the constant | 595 | /* If you need to install more boards than NR_CARDS, change the constant |
597 | in the definition below. No other change is necessary to support up to | 596 | in the definition below. No other change is necessary to support up to |
@@ -624,12 +623,6 @@ | |||
624 | #undef CY_ENABLE_MONITORING | 623 | #undef CY_ENABLE_MONITORING |
625 | #undef CY_PCI_DEBUG | 624 | #undef CY_PCI_DEBUG |
626 | 625 | ||
627 | #if 0 | ||
628 | #define PAUSE __asm__("nop") | ||
629 | #else | ||
630 | #define PAUSE do {} while (0) | ||
631 | #endif | ||
632 | |||
633 | /* | 626 | /* |
634 | * Include section | 627 | * Include section |
635 | */ | 628 | */ |
@@ -659,17 +652,6 @@ | |||
659 | #include <asm/irq.h> | 652 | #include <asm/irq.h> |
660 | #include <asm/uaccess.h> | 653 | #include <asm/uaccess.h> |
661 | 654 | ||
662 | #define CY_LOCK(info,flags) \ | ||
663 | do { \ | ||
664 | spin_lock_irqsave(&cy_card[info->card].card_lock, flags); \ | ||
665 | } while (0) | ||
666 | |||
667 | #define CY_UNLOCK(info,flags) \ | ||
668 | do { \ | ||
669 | spin_unlock_irqrestore(&cy_card[info->card].card_lock, flags); \ | ||
670 | } while (0) | ||
671 | |||
672 | #include <linux/types.h> | ||
673 | #include <linux/kernel.h> | 655 | #include <linux/kernel.h> |
674 | #include <linux/pci.h> | 656 | #include <linux/pci.h> |
675 | 657 | ||
@@ -682,13 +664,13 @@ static void cy_send_xchar(struct tty_struct *tty, char ch); | |||
682 | #define IS_CYC_Z(card) ((card).num_chips == -1) | 664 | #define IS_CYC_Z(card) ((card).num_chips == -1) |
683 | 665 | ||
684 | #define Z_FPGA_CHECK(card) \ | 666 | #define Z_FPGA_CHECK(card) \ |
685 | ((cy_readl(&((struct RUNTIME_9060 __iomem *) \ | 667 | ((readl(&((struct RUNTIME_9060 __iomem *) \ |
686 | ((card).ctl_addr))->init_ctrl) & (1<<17)) != 0) | 668 | ((card).ctl_addr))->init_ctrl) & (1<<17)) != 0) |
687 | 669 | ||
688 | #define ISZLOADED(card) (((ZO_V1==cy_readl(&((struct RUNTIME_9060 __iomem *) \ | 670 | #define ISZLOADED(card) (((ZO_V1==readl(&((struct RUNTIME_9060 __iomem *) \ |
689 | ((card).ctl_addr))->mail_box_0)) || \ | 671 | ((card).ctl_addr))->mail_box_0)) || \ |
690 | Z_FPGA_CHECK(card)) && \ | 672 | Z_FPGA_CHECK(card)) && \ |
691 | (ZFIRM_ID==cy_readl(&((struct FIRM_ID __iomem *) \ | 673 | (ZFIRM_ID==readl(&((struct FIRM_ID __iomem *) \ |
692 | ((card).base_addr+ID_ADDRESS))->signature))) | 674 | ((card).base_addr+ID_ADDRESS))->signature))) |
693 | 675 | ||
694 | #ifndef SERIAL_XMIT_SIZE | 676 | #ifndef SERIAL_XMIT_SIZE |
@@ -725,8 +707,8 @@ static unsigned int cy_isa_addresses[] = { | |||
725 | #define NR_ISA_ADDRS ARRAY_SIZE(cy_isa_addresses) | 707 | #define NR_ISA_ADDRS ARRAY_SIZE(cy_isa_addresses) |
726 | 708 | ||
727 | #ifdef MODULE | 709 | #ifdef MODULE |
728 | static long maddr[NR_CARDS] = { 0, }; | 710 | static long maddr[NR_CARDS]; |
729 | static int irq[NR_CARDS] = { 0, }; | 711 | static int irq[NR_CARDS]; |
730 | 712 | ||
731 | module_param_array(maddr, long, NULL, 0); | 713 | module_param_array(maddr, long, NULL, 0); |
732 | module_param_array(irq, int, NULL, 0); | 714 | module_param_array(irq, int, NULL, 0); |
@@ -739,11 +721,6 @@ module_param_array(irq, int, NULL, 0); | |||
739 | */ | 721 | */ |
740 | static struct cyclades_card cy_card[NR_CARDS]; | 722 | static struct cyclades_card cy_card[NR_CARDS]; |
741 | 723 | ||
742 | /* This is the per-channel data structure containing pointers, flags | ||
743 | and variables for the port. This driver supports a maximum of NR_PORTS. | ||
744 | */ | ||
745 | static struct cyclades_port cy_port[NR_PORTS]; | ||
746 | |||
747 | static int cy_next_channel; /* next minor available */ | 724 | static int cy_next_channel; /* next minor available */ |
748 | 725 | ||
749 | /* | 726 | /* |
@@ -825,9 +802,6 @@ static int cy_chip_offset[] = { 0x0000, | |||
825 | 802 | ||
826 | /* PCI related definitions */ | 803 | /* PCI related definitions */ |
827 | 804 | ||
828 | static unsigned short cy_pci_nboard; | ||
829 | static unsigned short cy_isa_nboard; | ||
830 | static unsigned short cy_nboard; | ||
831 | #ifdef CONFIG_PCI | 805 | #ifdef CONFIG_PCI |
832 | static struct pci_device_id cy_pci_dev_id[] __devinitdata = { | 806 | static struct pci_device_id cy_pci_dev_id[] __devinitdata = { |
833 | { PCI_DEVICE(PCI_VENDOR_ID_CYCLADES, PCI_DEVICE_ID_CYCLOM_Y_Lo) }, /* PCI < 1Mb */ | 807 | { PCI_DEVICE(PCI_VENDOR_ID_CYCLADES, PCI_DEVICE_ID_CYCLOM_Y_Lo) }, /* PCI < 1Mb */ |
@@ -845,7 +819,7 @@ MODULE_DEVICE_TABLE(pci, cy_pci_dev_id); | |||
845 | 819 | ||
846 | static void cy_start(struct tty_struct *); | 820 | static void cy_start(struct tty_struct *); |
847 | static void set_line_char(struct cyclades_port *); | 821 | static void set_line_char(struct cyclades_port *); |
848 | static int cyz_issue_cmd(struct cyclades_card *, uclong, ucchar, uclong); | 822 | static int cyz_issue_cmd(struct cyclades_card *, __u32, __u8, __u32); |
849 | #ifdef CONFIG_ISA | 823 | #ifdef CONFIG_ISA |
850 | static unsigned detect_isa_irq(void __iomem *); | 824 | static unsigned detect_isa_irq(void __iomem *); |
851 | #endif /* CONFIG_ISA */ | 825 | #endif /* CONFIG_ISA */ |
@@ -858,7 +832,6 @@ static void cyz_poll(unsigned long); | |||
858 | /* The Cyclades-Z polling cycle is defined by this variable */ | 832 | /* The Cyclades-Z polling cycle is defined by this variable */ |
859 | static long cyz_polling_cycle = CZ_DEF_POLL; | 833 | static long cyz_polling_cycle = CZ_DEF_POLL; |
860 | 834 | ||
861 | static int cyz_timeron = 0; | ||
862 | static DEFINE_TIMER(cyz_timerlist, cyz_poll, 0, 0); | 835 | static DEFINE_TIMER(cyz_timerlist, cyz_poll, 0, 0); |
863 | 836 | ||
864 | #else /* CONFIG_CYZ_INTR */ | 837 | #else /* CONFIG_CYZ_INTR */ |
@@ -871,21 +844,14 @@ static inline int serial_paranoia_check(struct cyclades_port *info, | |||
871 | { | 844 | { |
872 | #ifdef SERIAL_PARANOIA_CHECK | 845 | #ifdef SERIAL_PARANOIA_CHECK |
873 | if (!info) { | 846 | if (!info) { |
874 | printk("cyc Warning: null cyclades_port for (%s) in %s\n", | 847 | printk(KERN_WARNING "cyc Warning: null cyclades_port for (%s) " |
875 | name, routine); | 848 | "in %s\n", name, routine); |
876 | return 1; | ||
877 | } | ||
878 | |||
879 | if ((long)info < (long)(&cy_port[0]) || | ||
880 | (long)(&cy_port[NR_PORTS]) < (long)info) { | ||
881 | printk("cyc Warning: cyclades_port out of range for (%s) in " | ||
882 | "%s\n", name, routine); | ||
883 | return 1; | 849 | return 1; |
884 | } | 850 | } |
885 | 851 | ||
886 | if (info->magic != CYCLADES_MAGIC) { | 852 | if (info->magic != CYCLADES_MAGIC) { |
887 | printk("cyc Warning: bad magic number for serial struct (%s) " | 853 | printk(KERN_WARNING "cyc Warning: bad magic number for serial " |
888 | "in %s\n", name, routine); | 854 | "struct (%s) in %s\n", name, routine); |
889 | return 1; | 855 | return 1; |
890 | } | 856 | } |
891 | #endif | 857 | #endif |
@@ -943,22 +909,16 @@ do_softint(struct work_struct *work) | |||
943 | if (test_and_clear_bit(Cy_EVENT_OPEN_WAKEUP, &info->event)) | 909 | if (test_and_clear_bit(Cy_EVENT_OPEN_WAKEUP, &info->event)) |
944 | wake_up_interruptible(&info->open_wait); | 910 | wake_up_interruptible(&info->open_wait); |
945 | #ifdef CONFIG_CYZ_INTR | 911 | #ifdef CONFIG_CYZ_INTR |
946 | if (test_and_clear_bit(Cy_EVENT_Z_RX_FULL, &info->event)) { | 912 | if (test_and_clear_bit(Cy_EVENT_Z_RX_FULL, &info->event) && |
947 | if (cyz_rx_full_timer[info->line].function == NULL) { | 913 | !timer_pending(&cyz_rx_full_timer[info->line])) |
948 | cyz_rx_full_timer[info->line].expires = jiffies + 1; | 914 | mod_timer(&cyz_rx_full_timer[info->line], jiffies + 1); |
949 | cyz_rx_full_timer[info->line].function = cyz_rx_restart; | ||
950 | cyz_rx_full_timer[info->line].data = | ||
951 | (unsigned long)info; | ||
952 | add_timer(&cyz_rx_full_timer[info->line]); | ||
953 | } | ||
954 | } | ||
955 | #endif | 915 | #endif |
956 | if (test_and_clear_bit(Cy_EVENT_DELTA_WAKEUP, &info->event)) | 916 | if (test_and_clear_bit(Cy_EVENT_DELTA_WAKEUP, &info->event)) |
957 | wake_up_interruptible(&info->delta_msr_wait); | 917 | wake_up_interruptible(&info->delta_msr_wait); |
958 | tty_wakeup(tty); | 918 | tty_wakeup(tty); |
959 | #ifdef Z_WAKE | 919 | #ifdef Z_WAKE |
960 | if (test_and_clear_bit(Cy_EVENT_SHUTDOWN_WAKEUP, &info->event)) | 920 | if (test_and_clear_bit(Cy_EVENT_SHUTDOWN_WAKEUP, &info->event)) |
961 | wake_up_interruptible(&info->shutdown_wait); | 921 | complete(&info->shutdown_wait); |
962 | #endif | 922 | #endif |
963 | } /* do_softint */ | 923 | } /* do_softint */ |
964 | 924 | ||
@@ -975,11 +935,11 @@ do_softint(struct work_struct *work) | |||
975 | */ | 935 | */ |
976 | static int cyy_issue_cmd(void __iomem * base_addr, u_char cmd, int index) | 936 | static int cyy_issue_cmd(void __iomem * base_addr, u_char cmd, int index) |
977 | { | 937 | { |
978 | volatile int i; | 938 | unsigned int i; |
979 | 939 | ||
980 | /* Check to see that the previous command has completed */ | 940 | /* Check to see that the previous command has completed */ |
981 | for (i = 0; i < 100; i++) { | 941 | for (i = 0; i < 100; i++) { |
982 | if (cy_readb(base_addr + (CyCCR << index)) == 0) { | 942 | if (readb(base_addr + (CyCCR << index)) == 0) { |
983 | break; | 943 | break; |
984 | } | 944 | } |
985 | udelay(10L); | 945 | udelay(10L); |
@@ -1022,7 +982,7 @@ static unsigned detect_isa_irq(void __iomem * address) | |||
1022 | 982 | ||
1023 | cy_writeb(address + (CyCAR << index), 0); | 983 | cy_writeb(address + (CyCAR << index), 0); |
1024 | cy_writeb(address + (CySRER << index), | 984 | cy_writeb(address + (CySRER << index), |
1025 | cy_readb(address + (CySRER << index)) | CyTxRdy); | 985 | readb(address + (CySRER << index)) | CyTxRdy); |
1026 | local_irq_restore(flags); | 986 | local_irq_restore(flags); |
1027 | 987 | ||
1028 | /* Wait ... */ | 988 | /* Wait ... */ |
@@ -1032,11 +992,11 @@ static unsigned detect_isa_irq(void __iomem * address) | |||
1032 | irq = probe_irq_off(irqs); | 992 | irq = probe_irq_off(irqs); |
1033 | 993 | ||
1034 | /* Clean up */ | 994 | /* Clean up */ |
1035 | save_xir = (u_char) cy_readb(address + (CyTIR << index)); | 995 | save_xir = (u_char) readb(address + (CyTIR << index)); |
1036 | save_car = cy_readb(address + (CyCAR << index)); | 996 | save_car = readb(address + (CyCAR << index)); |
1037 | cy_writeb(address + (CyCAR << index), (save_xir & 0x3)); | 997 | cy_writeb(address + (CyCAR << index), (save_xir & 0x3)); |
1038 | cy_writeb(address + (CySRER << index), | 998 | cy_writeb(address + (CySRER << index), |
1039 | cy_readb(address + (CySRER << index)) & ~CyTxRdy); | 999 | readb(address + (CySRER << index)) & ~CyTxRdy); |
1040 | cy_writeb(address + (CyTIR << index), (save_xir & 0x3f)); | 1000 | cy_writeb(address + (CyTIR << index), (save_xir & 0x3f)); |
1041 | cy_writeb(address + (CyCAR << index), (save_car)); | 1001 | cy_writeb(address + (CyCAR << index), (save_car)); |
1042 | cy_writeb(address + (Cy_ClrIntr << index), 0); | 1002 | cy_writeb(address + (Cy_ClrIntr << index), 0); |
@@ -1051,45 +1011,43 @@ static void cyy_intr_chip(struct cyclades_card *cinfo, int chip, | |||
1051 | { | 1011 | { |
1052 | struct cyclades_port *info; | 1012 | struct cyclades_port *info; |
1053 | struct tty_struct *tty; | 1013 | struct tty_struct *tty; |
1054 | volatile int char_count; | 1014 | int char_count; |
1055 | int i, j, len, mdm_change, mdm_status, outch; | 1015 | int j, len, mdm_change, mdm_status, outch; |
1056 | int save_xir, channel, save_car; | 1016 | int save_xir, channel, save_car; |
1057 | char data; | 1017 | char data; |
1058 | 1018 | ||
1059 | if (status & CySRReceive) { /* reception interrupt */ | 1019 | if (status & CySRReceive) { /* reception interrupt */ |
1060 | #ifdef CY_DEBUG_INTERRUPTS | 1020 | #ifdef CY_DEBUG_INTERRUPTS |
1061 | printk("cyy_interrupt: rcvd intr, chip %d\n\r", chip); | 1021 | printk(KERN_DEBUG "cyy_interrupt: rcvd intr, chip %d\n", chip); |
1062 | #endif | 1022 | #endif |
1063 | /* determine the channel & change to that context */ | 1023 | /* determine the channel & change to that context */ |
1064 | spin_lock(&cinfo->card_lock); | 1024 | spin_lock(&cinfo->card_lock); |
1065 | save_xir = (u_char) cy_readb(base_addr + (CyRIR << index)); | 1025 | save_xir = (u_char) readb(base_addr + (CyRIR << index)); |
1066 | channel = (u_short) (save_xir & CyIRChannel); | 1026 | channel = (u_short) (save_xir & CyIRChannel); |
1067 | i = channel + chip * 4 + cinfo->first_line; | 1027 | info = &cinfo->ports[channel + chip * 4]; |
1068 | info = &cy_port[i]; | 1028 | save_car = readb(base_addr + (CyCAR << index)); |
1069 | info->last_active = jiffies; | ||
1070 | save_car = cy_readb(base_addr + (CyCAR << index)); | ||
1071 | cy_writeb(base_addr + (CyCAR << index), save_xir); | 1029 | cy_writeb(base_addr + (CyCAR << index), save_xir); |
1072 | 1030 | ||
1073 | /* if there is nowhere to put the data, discard it */ | 1031 | /* if there is nowhere to put the data, discard it */ |
1074 | if (info->tty == 0) { | 1032 | if (info->tty == NULL) { |
1075 | j = (cy_readb(base_addr + (CyRIVR << index)) & | 1033 | j = (readb(base_addr + (CyRIVR << index)) & |
1076 | CyIVRMask); | 1034 | CyIVRMask); |
1077 | if (j == CyIVRRxEx) { /* exception */ | 1035 | if (j == CyIVRRxEx) { /* exception */ |
1078 | data = cy_readb(base_addr + (CyRDSR << index)); | 1036 | data = readb(base_addr + (CyRDSR << index)); |
1079 | } else { /* normal character reception */ | 1037 | } else { /* normal character reception */ |
1080 | char_count = cy_readb(base_addr + | 1038 | char_count = readb(base_addr + |
1081 | (CyRDCR << index)); | 1039 | (CyRDCR << index)); |
1082 | while (char_count--) { | 1040 | while (char_count--) { |
1083 | data = cy_readb(base_addr + | 1041 | data = readb(base_addr + |
1084 | (CyRDSR << index)); | 1042 | (CyRDSR << index)); |
1085 | } | 1043 | } |
1086 | } | 1044 | } |
1087 | } else { /* there is an open port for this data */ | 1045 | } else { /* there is an open port for this data */ |
1088 | tty = info->tty; | 1046 | tty = info->tty; |
1089 | j = (cy_readb(base_addr + (CyRIVR << index)) & | 1047 | j = (readb(base_addr + (CyRIVR << index)) & |
1090 | CyIVRMask); | 1048 | CyIVRMask); |
1091 | if (j == CyIVRRxEx) { /* exception */ | 1049 | if (j == CyIVRRxEx) { /* exception */ |
1092 | data = cy_readb(base_addr + (CyRDSR << index)); | 1050 | data = readb(base_addr + (CyRDSR << index)); |
1093 | 1051 | ||
1094 | /* For statistics only */ | 1052 | /* For statistics only */ |
1095 | if (data & CyBREAK) | 1053 | if (data & CyBREAK) |
@@ -1110,7 +1068,7 @@ static void cyy_intr_chip(struct cyclades_card *cinfo, int chip, | |||
1110 | if (data & CyBREAK) { | 1068 | if (data & CyBREAK) { |
1111 | tty_insert_flip_char( | 1069 | tty_insert_flip_char( |
1112 | tty, | 1070 | tty, |
1113 | cy_readb( | 1071 | readb( |
1114 | base_addr + | 1072 | base_addr + |
1115 | (CyRDSR << | 1073 | (CyRDSR << |
1116 | index)), | 1074 | index)), |
@@ -1123,7 +1081,7 @@ static void cyy_intr_chip(struct cyclades_card *cinfo, int chip, | |||
1123 | } else if (data & CyFRAME) { | 1081 | } else if (data & CyFRAME) { |
1124 | tty_insert_flip_char( | 1082 | tty_insert_flip_char( |
1125 | tty, | 1083 | tty, |
1126 | cy_readb( | 1084 | readb( |
1127 | base_addr + | 1085 | base_addr + |
1128 | (CyRDSR << | 1086 | (CyRDSR << |
1129 | index)), | 1087 | index)), |
@@ -1135,7 +1093,7 @@ static void cyy_intr_chip(struct cyclades_card *cinfo, int chip, | |||
1135 | /* Pieces of seven... */ | 1093 | /* Pieces of seven... */ |
1136 | tty_insert_flip_char( | 1094 | tty_insert_flip_char( |
1137 | tty, | 1095 | tty, |
1138 | cy_readb( | 1096 | readb( |
1139 | base_addr + | 1097 | base_addr + |
1140 | (CyRDSR << | 1098 | (CyRDSR << |
1141 | index)), | 1099 | index)), |
@@ -1154,7 +1112,7 @@ static void cyy_intr_chip(struct cyclades_card *cinfo, int chip, | |||
1154 | */ | 1112 | */ |
1155 | tty_insert_flip_char( | 1113 | tty_insert_flip_char( |
1156 | tty, | 1114 | tty, |
1157 | cy_readb( | 1115 | readb( |
1158 | base_addr + | 1116 | base_addr + |
1159 | (CyRDSR << | 1117 | (CyRDSR << |
1160 | index)), | 1118 | index)), |
@@ -1186,7 +1144,7 @@ static void cyy_intr_chip(struct cyclades_card *cinfo, int chip, | |||
1186 | } | 1144 | } |
1187 | } else { /* normal character reception */ | 1145 | } else { /* normal character reception */ |
1188 | /* load # chars available from the chip */ | 1146 | /* load # chars available from the chip */ |
1189 | char_count = cy_readb(base_addr + | 1147 | char_count = readb(base_addr + |
1190 | (CyRDCR << index)); | 1148 | (CyRDCR << index)); |
1191 | 1149 | ||
1192 | #ifdef CY_ENABLE_MONITORING | 1150 | #ifdef CY_ENABLE_MONITORING |
@@ -1198,7 +1156,7 @@ static void cyy_intr_chip(struct cyclades_card *cinfo, int chip, | |||
1198 | #endif | 1156 | #endif |
1199 | len = tty_buffer_request_room(tty, char_count); | 1157 | len = tty_buffer_request_room(tty, char_count); |
1200 | while (len--) { | 1158 | while (len--) { |
1201 | data = cy_readb(base_addr + | 1159 | data = readb(base_addr + |
1202 | (CyRDSR << index)); | 1160 | (CyRDSR << index)); |
1203 | tty_insert_flip_char(tty, data, | 1161 | tty_insert_flip_char(tty, data, |
1204 | TTY_NORMAL); | 1162 | TTY_NORMAL); |
@@ -1223,29 +1181,27 @@ static void cyy_intr_chip(struct cyclades_card *cinfo, int chip, | |||
1223 | is empty, we know we can always stuff a dozen | 1181 | is empty, we know we can always stuff a dozen |
1224 | characters. */ | 1182 | characters. */ |
1225 | #ifdef CY_DEBUG_INTERRUPTS | 1183 | #ifdef CY_DEBUG_INTERRUPTS |
1226 | printk("cyy_interrupt: xmit intr, chip %d\n\r", chip); | 1184 | printk(KERN_DEBUG "cyy_interrupt: xmit intr, chip %d\n", chip); |
1227 | #endif | 1185 | #endif |
1228 | 1186 | ||
1229 | /* determine the channel & change to that context */ | 1187 | /* determine the channel & change to that context */ |
1230 | spin_lock(&cinfo->card_lock); | 1188 | spin_lock(&cinfo->card_lock); |
1231 | save_xir = (u_char) cy_readb(base_addr + (CyTIR << index)); | 1189 | save_xir = (u_char) readb(base_addr + (CyTIR << index)); |
1232 | channel = (u_short) (save_xir & CyIRChannel); | 1190 | channel = (u_short) (save_xir & CyIRChannel); |
1233 | i = channel + chip * 4 + cinfo->first_line; | 1191 | save_car = readb(base_addr + (CyCAR << index)); |
1234 | save_car = cy_readb(base_addr + (CyCAR << index)); | ||
1235 | cy_writeb(base_addr + (CyCAR << index), save_xir); | 1192 | cy_writeb(base_addr + (CyCAR << index), save_xir); |
1236 | 1193 | ||
1237 | /* validate the port# (as configured and open) */ | 1194 | /* validate the port# (as configured and open) */ |
1238 | if ((i < 0) || (NR_PORTS <= i)) { | 1195 | if (channel + chip * 4 >= cinfo->nports) { |
1239 | cy_writeb(base_addr + (CySRER << index), | 1196 | cy_writeb(base_addr + (CySRER << index), |
1240 | cy_readb(base_addr + (CySRER << index)) & | 1197 | readb(base_addr + (CySRER << index)) & |
1241 | ~CyTxRdy); | 1198 | ~CyTxRdy); |
1242 | goto txend; | 1199 | goto txend; |
1243 | } | 1200 | } |
1244 | info = &cy_port[i]; | 1201 | info = &cinfo->ports[channel + chip * 4]; |
1245 | info->last_active = jiffies; | 1202 | if (info->tty == NULL) { |
1246 | if (info->tty == 0) { | ||
1247 | cy_writeb(base_addr + (CySRER << index), | 1203 | cy_writeb(base_addr + (CySRER << index), |
1248 | cy_readb(base_addr + (CySRER << index)) & | 1204 | readb(base_addr + (CySRER << index)) & |
1249 | ~CyTxRdy); | 1205 | ~CyTxRdy); |
1250 | goto txdone; | 1206 | goto txdone; |
1251 | } | 1207 | } |
@@ -1278,29 +1234,29 @@ static void cyy_intr_chip(struct cyclades_card *cinfo, int chip, | |||
1278 | 1234 | ||
1279 | while (char_count-- > 0) { | 1235 | while (char_count-- > 0) { |
1280 | if (!info->xmit_cnt) { | 1236 | if (!info->xmit_cnt) { |
1281 | if (cy_readb(base_addr + (CySRER << index)) & | 1237 | if (readb(base_addr + (CySRER << index)) & |
1282 | CyTxMpty) { | 1238 | CyTxMpty) { |
1283 | cy_writeb(base_addr + (CySRER << index), | 1239 | cy_writeb(base_addr + (CySRER << index), |
1284 | cy_readb(base_addr + | 1240 | readb(base_addr + |
1285 | (CySRER << index)) & | 1241 | (CySRER << index)) & |
1286 | ~CyTxMpty); | 1242 | ~CyTxMpty); |
1287 | } else { | 1243 | } else { |
1288 | cy_writeb(base_addr + (CySRER << index), | 1244 | cy_writeb(base_addr + (CySRER << index), |
1289 | (cy_readb(base_addr + | 1245 | (readb(base_addr + |
1290 | (CySRER << index)) & | 1246 | (CySRER << index)) & |
1291 | ~CyTxRdy) | CyTxMpty); | 1247 | ~CyTxRdy) | CyTxMpty); |
1292 | } | 1248 | } |
1293 | goto txdone; | 1249 | goto txdone; |
1294 | } | 1250 | } |
1295 | if (info->xmit_buf == 0) { | 1251 | if (info->xmit_buf == NULL) { |
1296 | cy_writeb(base_addr + (CySRER << index), | 1252 | cy_writeb(base_addr + (CySRER << index), |
1297 | cy_readb(base_addr + (CySRER << index))& | 1253 | readb(base_addr + (CySRER << index)) & |
1298 | ~CyTxRdy); | 1254 | ~CyTxRdy); |
1299 | goto txdone; | 1255 | goto txdone; |
1300 | } | 1256 | } |
1301 | if (info->tty->stopped || info->tty->hw_stopped) { | 1257 | if (info->tty->stopped || info->tty->hw_stopped) { |
1302 | cy_writeb(base_addr + (CySRER << index), | 1258 | cy_writeb(base_addr + (CySRER << index), |
1303 | cy_readb(base_addr + (CySRER << index))& | 1259 | readb(base_addr + (CySRER << index)) & |
1304 | ~CyTxRdy); | 1260 | ~CyTxRdy); |
1305 | goto txdone; | 1261 | goto txdone; |
1306 | } | 1262 | } |
@@ -1333,7 +1289,6 @@ static void cyy_intr_chip(struct cyclades_card *cinfo, int chip, | |||
1333 | 0); | 1289 | 0); |
1334 | info->icount.tx++; | 1290 | info->icount.tx++; |
1335 | char_count--; | 1291 | char_count--; |
1336 | } else { | ||
1337 | } | 1292 | } |
1338 | } | 1293 | } |
1339 | } | 1294 | } |
@@ -1353,19 +1308,16 @@ txend: | |||
1353 | 1308 | ||
1354 | /* determine the channel & change to that context */ | 1309 | /* determine the channel & change to that context */ |
1355 | spin_lock(&cinfo->card_lock); | 1310 | spin_lock(&cinfo->card_lock); |
1356 | save_xir = (u_char) cy_readb(base_addr + (CyMIR << index)); | 1311 | save_xir = (u_char) readb(base_addr + (CyMIR << index)); |
1357 | channel = (u_short) (save_xir & CyIRChannel); | 1312 | channel = (u_short) (save_xir & CyIRChannel); |
1358 | info = &cy_port[channel + chip * 4 + cinfo->first_line]; | 1313 | info = &cinfo->ports[channel + chip * 4]; |
1359 | info->last_active = jiffies; | 1314 | save_car = readb(base_addr + (CyCAR << index)); |
1360 | save_car = cy_readb(base_addr + (CyCAR << index)); | ||
1361 | cy_writeb(base_addr + (CyCAR << index), save_xir); | 1315 | cy_writeb(base_addr + (CyCAR << index), save_xir); |
1362 | 1316 | ||
1363 | mdm_change = cy_readb(base_addr + (CyMISR << index)); | 1317 | mdm_change = readb(base_addr + (CyMISR << index)); |
1364 | mdm_status = cy_readb(base_addr + (CyMSVR1 << index)); | 1318 | mdm_status = readb(base_addr + (CyMSVR1 << index)); |
1365 | 1319 | ||
1366 | if (info->tty == 0) { /* no place for data, ignore it */ | 1320 | if (info->tty) { |
1367 | ; | ||
1368 | } else { | ||
1369 | if (mdm_change & CyANY_DELTA) { | 1321 | if (mdm_change & CyANY_DELTA) { |
1370 | /* For statistics only */ | 1322 | /* For statistics only */ |
1371 | if (mdm_change & CyDCD) | 1323 | if (mdm_change & CyDCD) |
@@ -1398,7 +1350,7 @@ txend: | |||
1398 | info->tty->hw_stopped = 0; | 1350 | info->tty->hw_stopped = 0; |
1399 | cy_writeb(base_addr + | 1351 | cy_writeb(base_addr + |
1400 | (CySRER << index), | 1352 | (CySRER << index), |
1401 | cy_readb(base_addr + | 1353 | readb(base_addr + |
1402 | (CySRER << | 1354 | (CySRER << |
1403 | index))| | 1355 | index))| |
1404 | CyTxRdy); | 1356 | CyTxRdy); |
@@ -1412,17 +1364,17 @@ txend: | |||
1412 | info->tty->hw_stopped = 1; | 1364 | info->tty->hw_stopped = 1; |
1413 | cy_writeb(base_addr + | 1365 | cy_writeb(base_addr + |
1414 | (CySRER << index), | 1366 | (CySRER << index), |
1415 | cy_readb(base_addr + | 1367 | readb(base_addr + |
1416 | (CySRER << | 1368 | (CySRER << |
1417 | index)) & | 1369 | index)) & |
1418 | ~CyTxRdy); | 1370 | ~CyTxRdy); |
1419 | } | 1371 | } |
1420 | } | 1372 | } |
1421 | } | 1373 | } |
1422 | if (mdm_change & CyDSR) { | 1374 | /* if (mdm_change & CyDSR) { |
1423 | } | 1375 | } |
1424 | if (mdm_change & CyRI) { | 1376 | if (mdm_change & CyRI) { |
1425 | } | 1377 | }*/ |
1426 | } | 1378 | } |
1427 | /* end of service */ | 1379 | /* end of service */ |
1428 | cy_writeb(base_addr + (CyMIR << index), (save_xir & 0x3f)); | 1380 | cy_writeb(base_addr + (CyMIR << index), (save_xir & 0x3f)); |
@@ -1438,16 +1390,16 @@ txend: | |||
1438 | static irqreturn_t cyy_interrupt(int irq, void *dev_id) | 1390 | static irqreturn_t cyy_interrupt(int irq, void *dev_id) |
1439 | { | 1391 | { |
1440 | int status; | 1392 | int status; |
1441 | struct cyclades_card *cinfo; | 1393 | struct cyclades_card *cinfo = dev_id; |
1442 | void __iomem *base_addr, *card_base_addr; | 1394 | void __iomem *base_addr, *card_base_addr; |
1443 | int chip; | 1395 | int chip; |
1444 | int index; | 1396 | int index; |
1445 | int too_many; | 1397 | int too_many; |
1446 | int had_work; | 1398 | int had_work; |
1447 | 1399 | ||
1448 | if ((cinfo = (struct cyclades_card *)dev_id) == 0) { | 1400 | if (unlikely(cinfo == NULL)) { |
1449 | #ifdef CY_DEBUG_INTERRUPTS | 1401 | #ifdef CY_DEBUG_INTERRUPTS |
1450 | printk("cyy_interrupt: spurious interrupt %d\n\r", irq); | 1402 | printk(KERN_DEBUG "cyy_interrupt: spurious interrupt %d\n",irq); |
1451 | #endif | 1403 | #endif |
1452 | return IRQ_NONE; /* spurious interrupt */ | 1404 | return IRQ_NONE; /* spurious interrupt */ |
1453 | } | 1405 | } |
@@ -1455,6 +1407,10 @@ static irqreturn_t cyy_interrupt(int irq, void *dev_id) | |||
1455 | card_base_addr = cinfo->base_addr; | 1407 | card_base_addr = cinfo->base_addr; |
1456 | index = cinfo->bus_index; | 1408 | index = cinfo->bus_index; |
1457 | 1409 | ||
1410 | /* card was not initialized yet (e.g. DEBUG_SHIRQ) */ | ||
1411 | if (unlikely(card_base_addr == NULL)) | ||
1412 | return IRQ_HANDLED; | ||
1413 | |||
1458 | /* This loop checks all chips in the card. Make a note whenever | 1414 | /* This loop checks all chips in the card. Make a note whenever |
1459 | _any_ chip had some work to do, as this is considered an | 1415 | _any_ chip had some work to do, as this is considered an |
1460 | indication that there will be more to do. Only when no chip | 1416 | indication that there will be more to do. Only when no chip |
@@ -1466,7 +1422,7 @@ static irqreturn_t cyy_interrupt(int irq, void *dev_id) | |||
1466 | base_addr = cinfo->base_addr + | 1422 | base_addr = cinfo->base_addr + |
1467 | (cy_chip_offset[chip] << index); | 1423 | (cy_chip_offset[chip] << index); |
1468 | too_many = 0; | 1424 | too_many = 0; |
1469 | while ((status = cy_readb(base_addr + | 1425 | while ((status = readb(base_addr + |
1470 | (CySVRR << index))) != 0x00) { | 1426 | (CySVRR << index))) != 0x00) { |
1471 | had_work++; | 1427 | had_work++; |
1472 | /* The purpose of the following test is to ensure that | 1428 | /* The purpose of the following test is to ensure that |
@@ -1498,7 +1454,7 @@ static irqreturn_t cyy_interrupt(int irq, void *dev_id) | |||
1498 | 1454 | ||
1499 | static int | 1455 | static int |
1500 | cyz_fetch_msg(struct cyclades_card *cinfo, | 1456 | cyz_fetch_msg(struct cyclades_card *cinfo, |
1501 | uclong * channel, ucchar * cmd, uclong * param) | 1457 | __u32 * channel, __u8 * cmd, __u32 * param) |
1502 | { | 1458 | { |
1503 | struct FIRM_ID __iomem *firm_id; | 1459 | struct FIRM_ID __iomem *firm_id; |
1504 | struct ZFW_CTRL __iomem *zfw_ctrl; | 1460 | struct ZFW_CTRL __iomem *zfw_ctrl; |
@@ -1509,16 +1465,15 @@ cyz_fetch_msg(struct cyclades_card *cinfo, | |||
1509 | if (!ISZLOADED(*cinfo)) { | 1465 | if (!ISZLOADED(*cinfo)) { |
1510 | return -1; | 1466 | return -1; |
1511 | } | 1467 | } |
1512 | zfw_ctrl = cinfo->base_addr + (cy_readl(&firm_id->zfwctrl_addr) & | 1468 | zfw_ctrl = cinfo->base_addr + (readl(&firm_id->zfwctrl_addr) & 0xfffff); |
1513 | 0xfffff); | ||
1514 | board_ctrl = &zfw_ctrl->board_ctrl; | 1469 | board_ctrl = &zfw_ctrl->board_ctrl; |
1515 | 1470 | ||
1516 | loc_doorbell = cy_readl(&((struct RUNTIME_9060 __iomem *) | 1471 | loc_doorbell = readl(&((struct RUNTIME_9060 __iomem *) |
1517 | (cinfo->ctl_addr))->loc_doorbell); | 1472 | (cinfo->ctl_addr))->loc_doorbell); |
1518 | if (loc_doorbell) { | 1473 | if (loc_doorbell) { |
1519 | *cmd = (char)(0xff & loc_doorbell); | 1474 | *cmd = (char)(0xff & loc_doorbell); |
1520 | *channel = cy_readl(&board_ctrl->fwcmd_channel); | 1475 | *channel = readl(&board_ctrl->fwcmd_channel); |
1521 | *param = (uclong) cy_readl(&board_ctrl->fwcmd_param); | 1476 | *param = (__u32) readl(&board_ctrl->fwcmd_param); |
1522 | cy_writel(&((struct RUNTIME_9060 __iomem *)(cinfo->ctl_addr))-> | 1477 | cy_writel(&((struct RUNTIME_9060 __iomem *)(cinfo->ctl_addr))-> |
1523 | loc_doorbell, 0xffffffff); | 1478 | loc_doorbell, 0xffffffff); |
1524 | return 1; | 1479 | return 1; |
@@ -1528,28 +1483,27 @@ cyz_fetch_msg(struct cyclades_card *cinfo, | |||
1528 | 1483 | ||
1529 | static int | 1484 | static int |
1530 | cyz_issue_cmd(struct cyclades_card *cinfo, | 1485 | cyz_issue_cmd(struct cyclades_card *cinfo, |
1531 | uclong channel, ucchar cmd, uclong param) | 1486 | __u32 channel, __u8 cmd, __u32 param) |
1532 | { | 1487 | { |
1533 | struct FIRM_ID __iomem *firm_id; | 1488 | struct FIRM_ID __iomem *firm_id; |
1534 | struct ZFW_CTRL __iomem *zfw_ctrl; | 1489 | struct ZFW_CTRL __iomem *zfw_ctrl; |
1535 | struct BOARD_CTRL __iomem *board_ctrl; | 1490 | struct BOARD_CTRL __iomem *board_ctrl; |
1536 | unsigned long __iomem *pci_doorbell; | 1491 | __u32 __iomem *pci_doorbell; |
1537 | int index; | 1492 | int index; |
1538 | 1493 | ||
1539 | firm_id = cinfo->base_addr + ID_ADDRESS; | 1494 | firm_id = cinfo->base_addr + ID_ADDRESS; |
1540 | if (!ISZLOADED(*cinfo)) { | 1495 | if (!ISZLOADED(*cinfo)) { |
1541 | return -1; | 1496 | return -1; |
1542 | } | 1497 | } |
1543 | zfw_ctrl = cinfo->base_addr + (cy_readl(&firm_id->zfwctrl_addr) & | 1498 | zfw_ctrl = cinfo->base_addr + (readl(&firm_id->zfwctrl_addr) & 0xfffff); |
1544 | 0xfffff); | ||
1545 | board_ctrl = &zfw_ctrl->board_ctrl; | 1499 | board_ctrl = &zfw_ctrl->board_ctrl; |
1546 | 1500 | ||
1547 | index = 0; | 1501 | index = 0; |
1548 | pci_doorbell = | 1502 | pci_doorbell = |
1549 | &((struct RUNTIME_9060 __iomem *)(cinfo->ctl_addr))->pci_doorbell; | 1503 | &((struct RUNTIME_9060 __iomem *)(cinfo->ctl_addr))->pci_doorbell; |
1550 | while ((cy_readl(pci_doorbell) & 0xff) != 0) { | 1504 | while ((readl(pci_doorbell) & 0xff) != 0) { |
1551 | if (index++ == 1000) { | 1505 | if (index++ == 1000) { |
1552 | return (int)(cy_readl(pci_doorbell) & 0xff); | 1506 | return (int)(readl(pci_doorbell) & 0xff); |
1553 | } | 1507 | } |
1554 | udelay(50L); | 1508 | udelay(50L); |
1555 | } | 1509 | } |
@@ -1561,34 +1515,30 @@ cyz_issue_cmd(struct cyclades_card *cinfo, | |||
1561 | } /* cyz_issue_cmd */ | 1515 | } /* cyz_issue_cmd */ |
1562 | 1516 | ||
1563 | static void | 1517 | static void |
1564 | cyz_handle_rx(struct cyclades_port *info, | 1518 | cyz_handle_rx(struct cyclades_port *info, struct CH_CTRL __iomem *ch_ctrl, |
1565 | volatile struct CH_CTRL __iomem * ch_ctrl, | 1519 | struct BUF_CTRL __iomem *buf_ctrl) |
1566 | volatile struct BUF_CTRL __iomem * buf_ctrl) | ||
1567 | { | 1520 | { |
1568 | struct cyclades_card *cinfo = &cy_card[info->card]; | 1521 | struct cyclades_card *cinfo = info->card; |
1569 | struct tty_struct *tty = info->tty; | 1522 | struct tty_struct *tty = info->tty; |
1570 | volatile int char_count; | 1523 | int char_count; |
1571 | int len; | 1524 | int len; |
1572 | #ifdef BLOCKMOVE | 1525 | #ifdef BLOCKMOVE |
1573 | int small_count; | 1526 | unsigned char *buf; |
1574 | #else | 1527 | #else |
1575 | char data; | 1528 | char data; |
1576 | #endif | 1529 | #endif |
1577 | volatile uclong rx_put, rx_get, new_rx_get, rx_bufsize, rx_bufaddr; | 1530 | __u32 rx_put, rx_get, new_rx_get, rx_bufsize, rx_bufaddr; |
1578 | 1531 | ||
1579 | rx_get = new_rx_get = cy_readl(&buf_ctrl->rx_get); | 1532 | rx_get = new_rx_get = readl(&buf_ctrl->rx_get); |
1580 | rx_put = cy_readl(&buf_ctrl->rx_put); | 1533 | rx_put = readl(&buf_ctrl->rx_put); |
1581 | rx_bufsize = cy_readl(&buf_ctrl->rx_bufsize); | 1534 | rx_bufsize = readl(&buf_ctrl->rx_bufsize); |
1582 | rx_bufaddr = cy_readl(&buf_ctrl->rx_bufaddr); | 1535 | rx_bufaddr = readl(&buf_ctrl->rx_bufaddr); |
1583 | if (rx_put >= rx_get) | 1536 | if (rx_put >= rx_get) |
1584 | char_count = rx_put - rx_get; | 1537 | char_count = rx_put - rx_get; |
1585 | else | 1538 | else |
1586 | char_count = rx_put - rx_get + rx_bufsize; | 1539 | char_count = rx_put - rx_get + rx_bufsize; |
1587 | 1540 | ||
1588 | if (char_count) { | 1541 | if (char_count) { |
1589 | info->last_active = jiffies; | ||
1590 | info->jiffies[1] = jiffies; | ||
1591 | |||
1592 | #ifdef CY_ENABLE_MONITORING | 1542 | #ifdef CY_ENABLE_MONITORING |
1593 | info->mon.int_count++; | 1543 | info->mon.int_count++; |
1594 | info->mon.char_count += char_count; | 1544 | info->mon.char_count += char_count; |
@@ -1596,7 +1546,7 @@ cyz_handle_rx(struct cyclades_port *info, | |||
1596 | info->mon.char_max = char_count; | 1546 | info->mon.char_max = char_count; |
1597 | info->mon.char_last = char_count; | 1547 | info->mon.char_last = char_count; |
1598 | #endif | 1548 | #endif |
1599 | if (tty == 0) { | 1549 | if (tty == NULL) { |
1600 | /* flush received characters */ | 1550 | /* flush received characters */ |
1601 | new_rx_get = (new_rx_get + char_count) & | 1551 | new_rx_get = (new_rx_get + char_count) & |
1602 | (rx_bufsize - 1); | 1552 | (rx_bufsize - 1); |
@@ -1606,30 +1556,28 @@ cyz_handle_rx(struct cyclades_port *info, | |||
1606 | /* we'd like to use memcpy(t, f, n) and memset(s, c, count) | 1556 | /* we'd like to use memcpy(t, f, n) and memset(s, c, count) |
1607 | for performance, but because of buffer boundaries, there | 1557 | for performance, but because of buffer boundaries, there |
1608 | may be several steps to the operation */ | 1558 | may be several steps to the operation */ |
1609 | while (0 < (small_count = min_t(unsigned int, | 1559 | while (1) { |
1610 | rx_bufsize - new_rx_get, | 1560 | len = tty_prepare_flip_string(tty, &buf, |
1611 | min_t(unsigned int, TTY_FLIPBUF_SIZE - | 1561 | char_count); |
1612 | tty->flip.count, char_count)))){ | 1562 | if (!len) |
1613 | memcpy_fromio(tty->flip.char_buf_ptr, | 1563 | break; |
1614 | (char *)(cinfo->base_addr + rx_bufaddr + | ||
1615 | new_rx_get), | ||
1616 | small_count); | ||
1617 | 1564 | ||
1618 | tty->flip.char_buf_ptr += small_count; | 1565 | len = min_t(unsigned int, min(len, char_count), |
1619 | memset(tty->flip.flag_buf_ptr, TTY_NORMAL, | 1566 | rx_bufsize - new_rx_get); |
1620 | small_count); | 1567 | |
1621 | tty->flip.flag_buf_ptr += small_count; | 1568 | memcpy_fromio(buf, cinfo->base_addr + |
1622 | new_rx_get = (new_rx_get + small_count) & | 1569 | rx_bufaddr + new_rx_get, len); |
1570 | |||
1571 | new_rx_get = (new_rx_get + len) & | ||
1623 | (rx_bufsize - 1); | 1572 | (rx_bufsize - 1); |
1624 | char_count -= small_count; | 1573 | char_count -= len; |
1625 | info->icount.rx += small_count; | 1574 | info->icount.rx += len; |
1626 | info->idle_stats.recv_bytes += small_count; | 1575 | info->idle_stats.recv_bytes += len; |
1627 | tty->flip.count += small_count; | ||
1628 | } | 1576 | } |
1629 | #else | 1577 | #else |
1630 | len = tty_buffer_request_room(tty, char_count); | 1578 | len = tty_buffer_request_room(tty, char_count); |
1631 | while (len--) { | 1579 | while (len--) { |
1632 | data = cy_readb(cinfo->base_addr + rx_bufaddr + | 1580 | data = readb(cinfo->base_addr + rx_bufaddr + |
1633 | new_rx_get); | 1581 | new_rx_get); |
1634 | new_rx_get = (new_rx_get + 1)& (rx_bufsize - 1); | 1582 | new_rx_get = (new_rx_get + 1)& (rx_bufsize - 1); |
1635 | tty_insert_flip_char(tty, data, TTY_NORMAL); | 1583 | tty_insert_flip_char(tty, data, TTY_NORMAL); |
@@ -1640,13 +1588,12 @@ cyz_handle_rx(struct cyclades_port *info, | |||
1640 | #ifdef CONFIG_CYZ_INTR | 1588 | #ifdef CONFIG_CYZ_INTR |
1641 | /* Recalculate the number of chars in the RX buffer and issue | 1589 | /* Recalculate the number of chars in the RX buffer and issue |
1642 | a cmd in case it's higher than the RX high water mark */ | 1590 | a cmd in case it's higher than the RX high water mark */ |
1643 | rx_put = cy_readl(&buf_ctrl->rx_put); | 1591 | rx_put = readl(&buf_ctrl->rx_put); |
1644 | if (rx_put >= rx_get) | 1592 | if (rx_put >= rx_get) |
1645 | char_count = rx_put - rx_get; | 1593 | char_count = rx_put - rx_get; |
1646 | else | 1594 | else |
1647 | char_count = rx_put - rx_get + rx_bufsize; | 1595 | char_count = rx_put - rx_get + rx_bufsize; |
1648 | if (char_count >= (int)cy_readl(&buf_ctrl-> | 1596 | if (char_count >= (int)readl(&buf_ctrl->rx_threshold)) { |
1649 | rx_threshold)) { | ||
1650 | cy_sched_event(info, Cy_EVENT_Z_RX_FULL); | 1597 | cy_sched_event(info, Cy_EVENT_Z_RX_FULL); |
1651 | } | 1598 | } |
1652 | #endif | 1599 | #endif |
@@ -1659,26 +1606,25 @@ cyz_handle_rx(struct cyclades_port *info, | |||
1659 | } | 1606 | } |
1660 | 1607 | ||
1661 | static void | 1608 | static void |
1662 | cyz_handle_tx(struct cyclades_port *info, | 1609 | cyz_handle_tx(struct cyclades_port *info, struct CH_CTRL __iomem *ch_ctrl, |
1663 | volatile struct CH_CTRL __iomem * ch_ctrl, | 1610 | struct BUF_CTRL __iomem *buf_ctrl) |
1664 | volatile struct BUF_CTRL __iomem * buf_ctrl) | ||
1665 | { | 1611 | { |
1666 | struct cyclades_card *cinfo = &cy_card[info->card]; | 1612 | struct cyclades_card *cinfo = info->card; |
1667 | struct tty_struct *tty = info->tty; | 1613 | struct tty_struct *tty = info->tty; |
1668 | char data; | 1614 | char data; |
1669 | volatile int char_count; | 1615 | int char_count; |
1670 | #ifdef BLOCKMOVE | 1616 | #ifdef BLOCKMOVE |
1671 | int small_count; | 1617 | int small_count; |
1672 | #endif | 1618 | #endif |
1673 | volatile uclong tx_put, tx_get, tx_bufsize, tx_bufaddr; | 1619 | __u32 tx_put, tx_get, tx_bufsize, tx_bufaddr; |
1674 | 1620 | ||
1675 | if (info->xmit_cnt <= 0) /* Nothing to transmit */ | 1621 | if (info->xmit_cnt <= 0) /* Nothing to transmit */ |
1676 | return; | 1622 | return; |
1677 | 1623 | ||
1678 | tx_get = cy_readl(&buf_ctrl->tx_get); | 1624 | tx_get = readl(&buf_ctrl->tx_get); |
1679 | tx_put = cy_readl(&buf_ctrl->tx_put); | 1625 | tx_put = readl(&buf_ctrl->tx_put); |
1680 | tx_bufsize = cy_readl(&buf_ctrl->tx_bufsize); | 1626 | tx_bufsize = readl(&buf_ctrl->tx_bufsize); |
1681 | tx_bufaddr = cy_readl(&buf_ctrl->tx_bufaddr); | 1627 | tx_bufaddr = readl(&buf_ctrl->tx_bufaddr); |
1682 | if (tx_put >= tx_get) | 1628 | if (tx_put >= tx_get) |
1683 | char_count = tx_get - tx_put - 1 + tx_bufsize; | 1629 | char_count = tx_get - tx_put - 1 + tx_bufsize; |
1684 | else | 1630 | else |
@@ -1686,9 +1632,8 @@ cyz_handle_tx(struct cyclades_port *info, | |||
1686 | 1632 | ||
1687 | if (char_count) { | 1633 | if (char_count) { |
1688 | 1634 | ||
1689 | if (tty == 0) { | 1635 | if (tty == NULL) |
1690 | goto ztxdone; | 1636 | goto ztxdone; |
1691 | } | ||
1692 | 1637 | ||
1693 | if (info->x_char) { /* send special char */ | 1638 | if (info->x_char) { /* send special char */ |
1694 | data = info->x_char; | 1639 | data = info->x_char; |
@@ -1698,8 +1643,6 @@ cyz_handle_tx(struct cyclades_port *info, | |||
1698 | info->x_char = 0; | 1643 | info->x_char = 0; |
1699 | char_count--; | 1644 | char_count--; |
1700 | info->icount.tx++; | 1645 | info->icount.tx++; |
1701 | info->last_active = jiffies; | ||
1702 | info->jiffies[2] = jiffies; | ||
1703 | } | 1646 | } |
1704 | #ifdef BLOCKMOVE | 1647 | #ifdef BLOCKMOVE |
1705 | while (0 < (small_count = min_t(unsigned int, | 1648 | while (0 < (small_count = min_t(unsigned int, |
@@ -1719,8 +1662,6 @@ cyz_handle_tx(struct cyclades_port *info, | |||
1719 | info->xmit_cnt -= small_count; | 1662 | info->xmit_cnt -= small_count; |
1720 | info->xmit_tail = (info->xmit_tail + small_count) & | 1663 | info->xmit_tail = (info->xmit_tail + small_count) & |
1721 | (SERIAL_XMIT_SIZE - 1); | 1664 | (SERIAL_XMIT_SIZE - 1); |
1722 | info->last_active = jiffies; | ||
1723 | info->jiffies[2] = jiffies; | ||
1724 | } | 1665 | } |
1725 | #else | 1666 | #else |
1726 | while (info->xmit_cnt && char_count) { | 1667 | while (info->xmit_cnt && char_count) { |
@@ -1733,8 +1674,6 @@ cyz_handle_tx(struct cyclades_port *info, | |||
1733 | tx_put = (tx_put + 1) & (tx_bufsize - 1); | 1674 | tx_put = (tx_put + 1) & (tx_bufsize - 1); |
1734 | char_count--; | 1675 | char_count--; |
1735 | info->icount.tx++; | 1676 | info->icount.tx++; |
1736 | info->last_active = jiffies; | ||
1737 | info->jiffies[2] = jiffies; | ||
1738 | } | 1677 | } |
1739 | #endif | 1678 | #endif |
1740 | ztxdone: | 1679 | ztxdone: |
@@ -1750,33 +1689,32 @@ static void cyz_handle_cmd(struct cyclades_card *cinfo) | |||
1750 | { | 1689 | { |
1751 | struct tty_struct *tty; | 1690 | struct tty_struct *tty; |
1752 | struct cyclades_port *info; | 1691 | struct cyclades_port *info; |
1753 | static volatile struct FIRM_ID __iomem *firm_id; | 1692 | static struct FIRM_ID __iomem *firm_id; |
1754 | static volatile struct ZFW_CTRL __iomem *zfw_ctrl; | 1693 | static struct ZFW_CTRL __iomem *zfw_ctrl; |
1755 | static volatile struct BOARD_CTRL __iomem *board_ctrl; | 1694 | static struct BOARD_CTRL __iomem *board_ctrl; |
1756 | static volatile struct CH_CTRL __iomem *ch_ctrl; | 1695 | static struct CH_CTRL __iomem *ch_ctrl; |
1757 | static volatile struct BUF_CTRL __iomem *buf_ctrl; | 1696 | static struct BUF_CTRL __iomem *buf_ctrl; |
1758 | uclong channel; | 1697 | __u32 channel; |
1759 | ucchar cmd; | 1698 | __u8 cmd; |
1760 | uclong param; | 1699 | __u32 param; |
1761 | uclong hw_ver, fw_ver; | 1700 | __u32 hw_ver, fw_ver; |
1762 | int special_count; | 1701 | int special_count; |
1763 | int delta_count; | 1702 | int delta_count; |
1764 | 1703 | ||
1765 | firm_id = cinfo->base_addr + ID_ADDRESS; | 1704 | firm_id = cinfo->base_addr + ID_ADDRESS; |
1766 | zfw_ctrl = cinfo->base_addr + (cy_readl(&firm_id->zfwctrl_addr) & | 1705 | zfw_ctrl = cinfo->base_addr + (readl(&firm_id->zfwctrl_addr) & 0xfffff); |
1767 | 0xfffff); | ||
1768 | board_ctrl = &zfw_ctrl->board_ctrl; | 1706 | board_ctrl = &zfw_ctrl->board_ctrl; |
1769 | fw_ver = cy_readl(&board_ctrl->fw_version); | 1707 | fw_ver = readl(&board_ctrl->fw_version); |
1770 | hw_ver = cy_readl(&((struct RUNTIME_9060 __iomem *)(cinfo->ctl_addr))-> | 1708 | hw_ver = readl(&((struct RUNTIME_9060 __iomem *)(cinfo->ctl_addr))-> |
1771 | mail_box_0); | 1709 | mail_box_0); |
1772 | 1710 | ||
1773 | while (cyz_fetch_msg(cinfo, &channel, &cmd, ¶m) == 1) { | 1711 | while (cyz_fetch_msg(cinfo, &channel, &cmd, ¶m) == 1) { |
1774 | special_count = 0; | 1712 | special_count = 0; |
1775 | delta_count = 0; | 1713 | delta_count = 0; |
1776 | info = &cy_port[channel + cinfo->first_line]; | 1714 | info = &cinfo->ports[channel]; |
1777 | if ((tty = info->tty) == 0) { | 1715 | if ((tty = info->tty) == NULL) |
1778 | continue; | 1716 | continue; |
1779 | } | 1717 | |
1780 | ch_ctrl = &(zfw_ctrl->ch_ctrl[channel]); | 1718 | ch_ctrl = &(zfw_ctrl->ch_ctrl[channel]); |
1781 | buf_ctrl = &(zfw_ctrl->buf_ctrl[channel]); | 1719 | buf_ctrl = &(zfw_ctrl->buf_ctrl[channel]); |
1782 | 1720 | ||
@@ -1801,7 +1739,7 @@ static void cyz_handle_cmd(struct cyclades_card *cinfo) | |||
1801 | delta_count++; | 1739 | delta_count++; |
1802 | if (info->flags & ASYNC_CHECK_CD) { | 1740 | if (info->flags & ASYNC_CHECK_CD) { |
1803 | if ((fw_ver > 241 ? ((u_long) param) : | 1741 | if ((fw_ver > 241 ? ((u_long) param) : |
1804 | cy_readl(&ch_ctrl->rs_status)) & | 1742 | readl(&ch_ctrl->rs_status)) & |
1805 | C_RS_DCD) { | 1743 | C_RS_DCD) { |
1806 | cy_sched_event(info, | 1744 | cy_sched_event(info, |
1807 | Cy_EVENT_OPEN_WAKEUP); | 1745 | Cy_EVENT_OPEN_WAKEUP); |
@@ -1833,8 +1771,8 @@ static void cyz_handle_cmd(struct cyclades_card *cinfo) | |||
1833 | case C_CM_INTBACK2: | 1771 | case C_CM_INTBACK2: |
1834 | /* Reception Interrupt */ | 1772 | /* Reception Interrupt */ |
1835 | #ifdef CY_DEBUG_INTERRUPTS | 1773 | #ifdef CY_DEBUG_INTERRUPTS |
1836 | printk("cyz_interrupt: rcvd intr, card %d, " | 1774 | printk(KERN_DEBUG "cyz_interrupt: rcvd intr, card %d, " |
1837 | "port %ld\n\r", info->card, channel); | 1775 | "port %ld\n", info->card, channel); |
1838 | #endif | 1776 | #endif |
1839 | cyz_handle_rx(info, ch_ctrl, buf_ctrl); | 1777 | cyz_handle_rx(info, ch_ctrl, buf_ctrl); |
1840 | break; | 1778 | break; |
@@ -1843,8 +1781,8 @@ static void cyz_handle_cmd(struct cyclades_card *cinfo) | |||
1843 | case C_CM_INTBACK: | 1781 | case C_CM_INTBACK: |
1844 | /* Transmission Interrupt */ | 1782 | /* Transmission Interrupt */ |
1845 | #ifdef CY_DEBUG_INTERRUPTS | 1783 | #ifdef CY_DEBUG_INTERRUPTS |
1846 | printk("cyz_interrupt: xmit intr, card %d, " | 1784 | printk(KERN_DEBUG "cyz_interrupt: xmit intr, card %d, " |
1847 | "port %ld\n\r", info->card, channel); | 1785 | "port %ld\n", info->card, channel); |
1848 | #endif | 1786 | #endif |
1849 | cyz_handle_tx(info, ch_ctrl, buf_ctrl); | 1787 | cyz_handle_tx(info, ch_ctrl, buf_ctrl); |
1850 | break; | 1788 | break; |
@@ -1865,18 +1803,19 @@ static void cyz_handle_cmd(struct cyclades_card *cinfo) | |||
1865 | #ifdef CONFIG_CYZ_INTR | 1803 | #ifdef CONFIG_CYZ_INTR |
1866 | static irqreturn_t cyz_interrupt(int irq, void *dev_id) | 1804 | static irqreturn_t cyz_interrupt(int irq, void *dev_id) |
1867 | { | 1805 | { |
1868 | struct cyclades_card *cinfo; | 1806 | struct cyclades_card *cinfo = dev_id; |
1869 | 1807 | ||
1870 | if ((cinfo = (struct cyclades_card *)dev_id) == 0) { | 1808 | if (unlikely(cinfo == NULL)) { |
1871 | #ifdef CY_DEBUG_INTERRUPTS | 1809 | #ifdef CY_DEBUG_INTERRUPTS |
1872 | printk("cyz_interrupt: spurious interrupt %d\n\r", irq); | 1810 | printk(KERN_DEBUG "cyz_interrupt: spurious interrupt %d\n",irq); |
1873 | #endif | 1811 | #endif |
1874 | return IRQ_NONE; /* spurious interrupt */ | 1812 | return IRQ_NONE; /* spurious interrupt */ |
1875 | } | 1813 | } |
1876 | 1814 | ||
1877 | if (!ISZLOADED(*cinfo)) { | 1815 | if (unlikely(!ISZLOADED(*cinfo))) { |
1878 | #ifdef CY_DEBUG_INTERRUPTS | 1816 | #ifdef CY_DEBUG_INTERRUPTS |
1879 | printk("cyz_interrupt: board not yet loaded (IRQ%d).\n\r", irq); | 1817 | printk(KERN_DEBUG "cyz_interrupt: board not yet loaded " |
1818 | "(IRQ%d).\n", irq); | ||
1880 | #endif | 1819 | #endif |
1881 | return IRQ_NONE; | 1820 | return IRQ_NONE; |
1882 | } | 1821 | } |
@@ -1890,19 +1829,18 @@ static irqreturn_t cyz_interrupt(int irq, void *dev_id) | |||
1890 | static void cyz_rx_restart(unsigned long arg) | 1829 | static void cyz_rx_restart(unsigned long arg) |
1891 | { | 1830 | { |
1892 | struct cyclades_port *info = (struct cyclades_port *)arg; | 1831 | struct cyclades_port *info = (struct cyclades_port *)arg; |
1832 | struct cyclades_card *card = info->card; | ||
1893 | int retval; | 1833 | int retval; |
1894 | int card = info->card; | 1834 | __u32 channel = info->line - card->first_line; |
1895 | uclong channel = (info->line) - (cy_card[card].first_line); | ||
1896 | unsigned long flags; | 1835 | unsigned long flags; |
1897 | 1836 | ||
1898 | CY_LOCK(info, flags); | 1837 | spin_lock_irqsave(&card->card_lock, flags); |
1899 | retval = cyz_issue_cmd(&cy_card[card], channel, C_CM_INTBACK2, 0L); | 1838 | retval = cyz_issue_cmd(card, channel, C_CM_INTBACK2, 0L); |
1900 | if (retval != 0) { | 1839 | if (retval != 0) { |
1901 | printk("cyc:cyz_rx_restart retval on ttyC%d was %x\n", | 1840 | printk(KERN_ERR "cyc:cyz_rx_restart retval on ttyC%d was %x\n", |
1902 | info->line, retval); | 1841 | info->line, retval); |
1903 | } | 1842 | } |
1904 | cyz_rx_full_timer[info->line].function = NULL; | 1843 | spin_unlock_irqrestore(&card->card_lock, flags); |
1905 | CY_UNLOCK(info, flags); | ||
1906 | } | 1844 | } |
1907 | 1845 | ||
1908 | #else /* CONFIG_CYZ_INTR */ | 1846 | #else /* CONFIG_CYZ_INTR */ |
@@ -1912,14 +1850,14 @@ static void cyz_poll(unsigned long arg) | |||
1912 | struct cyclades_card *cinfo; | 1850 | struct cyclades_card *cinfo; |
1913 | struct cyclades_port *info; | 1851 | struct cyclades_port *info; |
1914 | struct tty_struct *tty; | 1852 | struct tty_struct *tty; |
1915 | static volatile struct FIRM_ID *firm_id; | 1853 | static struct FIRM_ID *firm_id; |
1916 | static volatile struct ZFW_CTRL *zfw_ctrl; | 1854 | static struct ZFW_CTRL *zfw_ctrl; |
1917 | static volatile struct BOARD_CTRL *board_ctrl; | 1855 | static struct BOARD_CTRL *board_ctrl; |
1918 | static volatile struct CH_CTRL *ch_ctrl; | 1856 | static struct CH_CTRL *ch_ctrl; |
1919 | static volatile struct BUF_CTRL *buf_ctrl; | 1857 | static struct BUF_CTRL *buf_ctrl; |
1858 | unsigned long expires = jiffies + HZ; | ||
1920 | int card, port; | 1859 | int card, port; |
1921 | 1860 | ||
1922 | cyz_timerlist.expires = jiffies + (HZ); | ||
1923 | for (card = 0; card < NR_CARDS; card++) { | 1861 | for (card = 0; card < NR_CARDS; card++) { |
1924 | cinfo = &cy_card[card]; | 1862 | cinfo = &cy_card[card]; |
1925 | 1863 | ||
@@ -1930,12 +1868,12 @@ static void cyz_poll(unsigned long arg) | |||
1930 | 1868 | ||
1931 | firm_id = cinfo->base_addr + ID_ADDRESS; | 1869 | firm_id = cinfo->base_addr + ID_ADDRESS; |
1932 | zfw_ctrl = cinfo->base_addr + | 1870 | zfw_ctrl = cinfo->base_addr + |
1933 | (cy_readl(&firm_id->zfwctrl_addr) & 0xfffff); | 1871 | (readl(&firm_id->zfwctrl_addr) & 0xfffff); |
1934 | board_ctrl = &(zfw_ctrl->board_ctrl); | 1872 | board_ctrl = &(zfw_ctrl->board_ctrl); |
1935 | 1873 | ||
1936 | /* Skip first polling cycle to avoid racing conditions with the FW */ | 1874 | /* Skip first polling cycle to avoid racing conditions with the FW */ |
1937 | if (!cinfo->intr_enabled) { | 1875 | if (!cinfo->intr_enabled) { |
1938 | cinfo->nports = (int)cy_readl(&board_ctrl->n_channel); | 1876 | cinfo->nports = (int)readl(&board_ctrl->n_channel); |
1939 | cinfo->intr_enabled = 1; | 1877 | cinfo->intr_enabled = 1; |
1940 | continue; | 1878 | continue; |
1941 | } | 1879 | } |
@@ -1943,7 +1881,7 @@ static void cyz_poll(unsigned long arg) | |||
1943 | cyz_handle_cmd(cinfo); | 1881 | cyz_handle_cmd(cinfo); |
1944 | 1882 | ||
1945 | for (port = 0; port < cinfo->nports; port++) { | 1883 | for (port = 0; port < cinfo->nports; port++) { |
1946 | info = &cy_port[port + cinfo->first_line]; | 1884 | info = &cinfo->ports[port]; |
1947 | tty = info->tty; | 1885 | tty = info->tty; |
1948 | ch_ctrl = &(zfw_ctrl->ch_ctrl[port]); | 1886 | ch_ctrl = &(zfw_ctrl->ch_ctrl[port]); |
1949 | buf_ctrl = &(zfw_ctrl->buf_ctrl[port]); | 1887 | buf_ctrl = &(zfw_ctrl->buf_ctrl[port]); |
@@ -1953,9 +1891,9 @@ static void cyz_poll(unsigned long arg) | |||
1953 | cyz_handle_tx(info, ch_ctrl, buf_ctrl); | 1891 | cyz_handle_tx(info, ch_ctrl, buf_ctrl); |
1954 | } | 1892 | } |
1955 | /* poll every 'cyz_polling_cycle' period */ | 1893 | /* poll every 'cyz_polling_cycle' period */ |
1956 | cyz_timerlist.expires = jiffies + cyz_polling_cycle; | 1894 | expires = jiffies + cyz_polling_cycle; |
1957 | } | 1895 | } |
1958 | add_timer(&cyz_timerlist); | 1896 | mod_timer(&cyz_timerlist, expires); |
1959 | } /* cyz_poll */ | 1897 | } /* cyz_poll */ |
1960 | 1898 | ||
1961 | #endif /* CONFIG_CYZ_INTR */ | 1899 | #endif /* CONFIG_CYZ_INTR */ |
@@ -1968,20 +1906,21 @@ static void cyz_poll(unsigned long arg) | |||
1968 | */ | 1906 | */ |
1969 | static int startup(struct cyclades_port *info) | 1907 | static int startup(struct cyclades_port *info) |
1970 | { | 1908 | { |
1909 | struct cyclades_card *card; | ||
1971 | unsigned long flags; | 1910 | unsigned long flags; |
1972 | int retval = 0; | 1911 | int retval = 0; |
1973 | void __iomem *base_addr; | 1912 | void __iomem *base_addr; |
1974 | int card, chip, channel, index; | 1913 | int chip, channel, index; |
1975 | unsigned long page; | 1914 | unsigned long page; |
1976 | 1915 | ||
1977 | card = info->card; | 1916 | card = info->card; |
1978 | channel = (info->line) - (cy_card[card].first_line); | 1917 | channel = info->line - card->first_line; |
1979 | 1918 | ||
1980 | page = get_zeroed_page(GFP_KERNEL); | 1919 | page = get_zeroed_page(GFP_KERNEL); |
1981 | if (!page) | 1920 | if (!page) |
1982 | return -ENOMEM; | 1921 | return -ENOMEM; |
1983 | 1922 | ||
1984 | CY_LOCK(info, flags); | 1923 | spin_lock_irqsave(&card->card_lock, flags); |
1985 | 1924 | ||
1986 | if (info->flags & ASYNC_INITIALIZED) { | 1925 | if (info->flags & ASYNC_INITIALIZED) { |
1987 | free_page(page); | 1926 | free_page(page); |
@@ -2001,24 +1940,22 @@ static int startup(struct cyclades_port *info) | |||
2001 | else | 1940 | else |
2002 | info->xmit_buf = (unsigned char *)page; | 1941 | info->xmit_buf = (unsigned char *)page; |
2003 | 1942 | ||
2004 | CY_UNLOCK(info, flags); | 1943 | spin_unlock_irqrestore(&card->card_lock, flags); |
2005 | 1944 | ||
2006 | set_line_char(info); | 1945 | set_line_char(info); |
2007 | 1946 | ||
2008 | if (!IS_CYC_Z(cy_card[card])) { | 1947 | if (!IS_CYC_Z(*card)) { |
2009 | chip = channel >> 2; | 1948 | chip = channel >> 2; |
2010 | channel &= 0x03; | 1949 | channel &= 0x03; |
2011 | index = cy_card[card].bus_index; | 1950 | index = card->bus_index; |
2012 | base_addr = cy_card[card].base_addr + | 1951 | base_addr = card->base_addr + (cy_chip_offset[chip] << index); |
2013 | (cy_chip_offset[chip] << index); | ||
2014 | 1952 | ||
2015 | #ifdef CY_DEBUG_OPEN | 1953 | #ifdef CY_DEBUG_OPEN |
2016 | printk("cyc startup card %d, chip %d, channel %d, " | 1954 | printk(KERN_DEBUG "cyc startup card %d, chip %d, channel %d, " |
2017 | "base_addr %lx\n", | 1955 | "base_addr %p\n", |
2018 | card, chip, channel, (long)base_addr); | 1956 | card, chip, channel, base_addr); |
2019 | /**/ | ||
2020 | #endif | 1957 | #endif |
2021 | CY_LOCK(info, flags); | 1958 | spin_lock_irqsave(&card->card_lock, flags); |
2022 | 1959 | ||
2023 | cy_writeb(base_addr + (CyCAR << index), (u_char) channel); | 1960 | cy_writeb(base_addr + (CyCAR << index), (u_char) channel); |
2024 | 1961 | ||
@@ -2034,14 +1971,14 @@ static int startup(struct cyclades_port *info) | |||
2034 | cy_writeb(base_addr + (CyMSVR2 << index), CyDTR); | 1971 | cy_writeb(base_addr + (CyMSVR2 << index), CyDTR); |
2035 | 1972 | ||
2036 | #ifdef CY_DEBUG_DTR | 1973 | #ifdef CY_DEBUG_DTR |
2037 | printk("cyc:startup raising DTR\n"); | 1974 | printk(KERN_DEBUG "cyc:startup raising DTR\n"); |
2038 | printk(" status: 0x%x, 0x%x\n", | 1975 | printk(KERN_DEBUG " status: 0x%x, 0x%x\n", |
2039 | cy_readb(base_addr + (CyMSVR1 << index)), | 1976 | readb(base_addr + (CyMSVR1 << index)), |
2040 | cy_readb(base_addr + (CyMSVR2 << index))); | 1977 | readb(base_addr + (CyMSVR2 << index))); |
2041 | #endif | 1978 | #endif |
2042 | 1979 | ||
2043 | cy_writeb(base_addr + (CySRER << index), | 1980 | cy_writeb(base_addr + (CySRER << index), |
2044 | cy_readb(base_addr + (CySRER << index)) | CyRxData); | 1981 | readb(base_addr + (CySRER << index)) | CyRxData); |
2045 | info->flags |= ASYNC_INITIALIZED; | 1982 | info->flags |= ASYNC_INITIALIZED; |
2046 | 1983 | ||
2047 | if (info->tty) { | 1984 | if (info->tty) { |
@@ -2054,7 +1991,7 @@ static int startup(struct cyclades_port *info) | |||
2054 | info->idle_stats.recv_idle = | 1991 | info->idle_stats.recv_idle = |
2055 | info->idle_stats.xmit_idle = jiffies; | 1992 | info->idle_stats.xmit_idle = jiffies; |
2056 | 1993 | ||
2057 | CY_UNLOCK(info, flags); | 1994 | spin_unlock_irqrestore(&card->card_lock, flags); |
2058 | 1995 | ||
2059 | } else { | 1996 | } else { |
2060 | struct FIRM_ID __iomem *firm_id; | 1997 | struct FIRM_ID __iomem *firm_id; |
@@ -2063,24 +2000,23 @@ static int startup(struct cyclades_port *info) | |||
2063 | struct CH_CTRL __iomem *ch_ctrl; | 2000 | struct CH_CTRL __iomem *ch_ctrl; |
2064 | int retval; | 2001 | int retval; |
2065 | 2002 | ||
2066 | base_addr = cy_card[card].base_addr; | 2003 | base_addr = card->base_addr; |
2067 | 2004 | ||
2068 | firm_id = base_addr + ID_ADDRESS; | 2005 | firm_id = base_addr + ID_ADDRESS; |
2069 | if (!ISZLOADED(cy_card[card])) { | 2006 | if (!ISZLOADED(*card)) { |
2070 | return -ENODEV; | 2007 | return -ENODEV; |
2071 | } | 2008 | } |
2072 | 2009 | ||
2073 | zfw_ctrl = cy_card[card].base_addr + | 2010 | zfw_ctrl = card->base_addr + |
2074 | (cy_readl(&firm_id->zfwctrl_addr) & 0xfffff); | 2011 | (readl(&firm_id->zfwctrl_addr) & 0xfffff); |
2075 | board_ctrl = &zfw_ctrl->board_ctrl; | 2012 | board_ctrl = &zfw_ctrl->board_ctrl; |
2076 | ch_ctrl = zfw_ctrl->ch_ctrl; | 2013 | ch_ctrl = zfw_ctrl->ch_ctrl; |
2077 | 2014 | ||
2078 | #ifdef CY_DEBUG_OPEN | 2015 | #ifdef CY_DEBUG_OPEN |
2079 | printk("cyc startup Z card %d, channel %d, base_addr %lx\n", | 2016 | printk(KERN_DEBUG "cyc startup Z card %d, channel %d, " |
2080 | card, channel, (long)base_addr); | 2017 | "base_addr %p\n", card, channel, base_addr); |
2081 | /**/ | ||
2082 | #endif | 2018 | #endif |
2083 | CY_LOCK(info, flags); | 2019 | spin_lock_irqsave(&card->card_lock, flags); |
2084 | 2020 | ||
2085 | cy_writel(&ch_ctrl[channel].op_mode, C_CH_ENABLE); | 2021 | cy_writel(&ch_ctrl[channel].op_mode, C_CH_ENABLE); |
2086 | #ifdef Z_WAKE | 2022 | #ifdef Z_WAKE |
@@ -2102,33 +2038,31 @@ static int startup(struct cyclades_port *info) | |||
2102 | #endif /* CONFIG_CYZ_INTR */ | 2038 | #endif /* CONFIG_CYZ_INTR */ |
2103 | #endif /* Z_WAKE */ | 2039 | #endif /* Z_WAKE */ |
2104 | 2040 | ||
2105 | retval = cyz_issue_cmd(&cy_card[card], channel, C_CM_IOCTL, 0L); | 2041 | retval = cyz_issue_cmd(card, channel, C_CM_IOCTL, 0L); |
2106 | if (retval != 0) { | 2042 | if (retval != 0) { |
2107 | printk("cyc:startup(1) retval on ttyC%d was %x\n", | 2043 | printk(KERN_ERR "cyc:startup(1) retval on ttyC%d was " |
2108 | info->line, retval); | 2044 | "%x\n", info->line, retval); |
2109 | } | 2045 | } |
2110 | 2046 | ||
2111 | /* Flush RX buffers before raising DTR and RTS */ | 2047 | /* Flush RX buffers before raising DTR and RTS */ |
2112 | retval = cyz_issue_cmd(&cy_card[card], channel, C_CM_FLUSH_RX, | 2048 | retval = cyz_issue_cmd(card, channel, C_CM_FLUSH_RX, 0L); |
2113 | 0L); | ||
2114 | if (retval != 0) { | 2049 | if (retval != 0) { |
2115 | printk("cyc:startup(2) retval on ttyC%d was %x\n", | 2050 | printk(KERN_ERR "cyc:startup(2) retval on ttyC%d was " |
2116 | info->line, retval); | 2051 | "%x\n", info->line, retval); |
2117 | } | 2052 | } |
2118 | 2053 | ||
2119 | /* set timeout !!! */ | 2054 | /* set timeout !!! */ |
2120 | /* set RTS and DTR !!! */ | 2055 | /* set RTS and DTR !!! */ |
2121 | cy_writel(&ch_ctrl[channel].rs_control, | 2056 | cy_writel(&ch_ctrl[channel].rs_control, |
2122 | cy_readl(&ch_ctrl[channel].rs_control) | C_RS_RTS | | 2057 | readl(&ch_ctrl[channel].rs_control) | C_RS_RTS | |
2123 | C_RS_DTR); | 2058 | C_RS_DTR); |
2124 | retval = cyz_issue_cmd(&cy_card[info->card], channel, | 2059 | retval = cyz_issue_cmd(card, channel, C_CM_IOCTLM, 0L); |
2125 | C_CM_IOCTLM, 0L); | ||
2126 | if (retval != 0) { | 2060 | if (retval != 0) { |
2127 | printk("cyc:startup(3) retval on ttyC%d was %x\n", | 2061 | printk(KERN_ERR "cyc:startup(3) retval on ttyC%d was " |
2128 | info->line, retval); | 2062 | "%x\n", info->line, retval); |
2129 | } | 2063 | } |
2130 | #ifdef CY_DEBUG_DTR | 2064 | #ifdef CY_DEBUG_DTR |
2131 | printk("cyc:startup raising Z DTR\n"); | 2065 | printk(KERN_DEBUG "cyc:startup raising Z DTR\n"); |
2132 | #endif | 2066 | #endif |
2133 | 2067 | ||
2134 | /* enable send, recv, modem !!! */ | 2068 | /* enable send, recv, modem !!! */ |
@@ -2144,51 +2078,50 @@ static int startup(struct cyclades_port *info) | |||
2144 | info->idle_stats.recv_idle = | 2078 | info->idle_stats.recv_idle = |
2145 | info->idle_stats.xmit_idle = jiffies; | 2079 | info->idle_stats.xmit_idle = jiffies; |
2146 | 2080 | ||
2147 | CY_UNLOCK(info, flags); | 2081 | spin_unlock_irqrestore(&card->card_lock, flags); |
2148 | } | 2082 | } |
2149 | 2083 | ||
2150 | #ifdef CY_DEBUG_OPEN | 2084 | #ifdef CY_DEBUG_OPEN |
2151 | printk(" cyc startup done\n"); | 2085 | printk(KERN_DEBUG "cyc startup done\n"); |
2152 | #endif | 2086 | #endif |
2153 | return 0; | 2087 | return 0; |
2154 | 2088 | ||
2155 | errout: | 2089 | errout: |
2156 | CY_UNLOCK(info, flags); | 2090 | spin_unlock_irqrestore(&card->card_lock, flags); |
2157 | return retval; | 2091 | return retval; |
2158 | } /* startup */ | 2092 | } /* startup */ |
2159 | 2093 | ||
2160 | static void start_xmit(struct cyclades_port *info) | 2094 | static void start_xmit(struct cyclades_port *info) |
2161 | { | 2095 | { |
2096 | struct cyclades_card *card; | ||
2162 | unsigned long flags; | 2097 | unsigned long flags; |
2163 | void __iomem *base_addr; | 2098 | void __iomem *base_addr; |
2164 | int card, chip, channel, index; | 2099 | int chip, channel, index; |
2165 | 2100 | ||
2166 | card = info->card; | 2101 | card = info->card; |
2167 | channel = (info->line) - (cy_card[card].first_line); | 2102 | channel = info->line - card->first_line; |
2168 | if (!IS_CYC_Z(cy_card[card])) { | 2103 | if (!IS_CYC_Z(*card)) { |
2169 | chip = channel >> 2; | 2104 | chip = channel >> 2; |
2170 | channel &= 0x03; | 2105 | channel &= 0x03; |
2171 | index = cy_card[card].bus_index; | 2106 | index = card->bus_index; |
2172 | base_addr = cy_card[card].base_addr + | 2107 | base_addr = card->base_addr + (cy_chip_offset[chip] << index); |
2173 | (cy_chip_offset[chip] << index); | ||
2174 | 2108 | ||
2175 | CY_LOCK(info, flags); | 2109 | spin_lock_irqsave(&card->card_lock, flags); |
2176 | cy_writeb(base_addr + (CyCAR << index), channel); | 2110 | cy_writeb(base_addr + (CyCAR << index), channel); |
2177 | cy_writeb(base_addr + (CySRER << index), | 2111 | cy_writeb(base_addr + (CySRER << index), |
2178 | cy_readb(base_addr + (CySRER << index)) | CyTxRdy); | 2112 | readb(base_addr + (CySRER << index)) | CyTxRdy); |
2179 | CY_UNLOCK(info, flags); | 2113 | spin_unlock_irqrestore(&card->card_lock, flags); |
2180 | } else { | 2114 | } else { |
2181 | #ifdef CONFIG_CYZ_INTR | 2115 | #ifdef CONFIG_CYZ_INTR |
2182 | int retval; | 2116 | int retval; |
2183 | 2117 | ||
2184 | CY_LOCK(info, flags); | 2118 | spin_lock_irqsave(&card->card_lock, flags); |
2185 | retval = cyz_issue_cmd(&cy_card[card], channel, C_CM_INTBACK, | 2119 | retval = cyz_issue_cmd(card, channel, C_CM_INTBACK, 0L); |
2186 | 0L); | ||
2187 | if (retval != 0) { | 2120 | if (retval != 0) { |
2188 | printk("cyc:start_xmit retval on ttyC%d was %x\n", | 2121 | printk(KERN_ERR "cyc:start_xmit retval on ttyC%d was " |
2189 | info->line, retval); | 2122 | "%x\n", info->line, retval); |
2190 | } | 2123 | } |
2191 | CY_UNLOCK(info, flags); | 2124 | spin_unlock_irqrestore(&card->card_lock, flags); |
2192 | #else /* CONFIG_CYZ_INTR */ | 2125 | #else /* CONFIG_CYZ_INTR */ |
2193 | /* Don't have to do anything at this time */ | 2126 | /* Don't have to do anything at this time */ |
2194 | #endif /* CONFIG_CYZ_INTR */ | 2127 | #endif /* CONFIG_CYZ_INTR */ |
@@ -2201,30 +2134,30 @@ static void start_xmit(struct cyclades_port *info) | |||
2201 | */ | 2134 | */ |
2202 | static void shutdown(struct cyclades_port *info) | 2135 | static void shutdown(struct cyclades_port *info) |
2203 | { | 2136 | { |
2137 | struct cyclades_card *card; | ||
2204 | unsigned long flags; | 2138 | unsigned long flags; |
2205 | void __iomem *base_addr; | 2139 | void __iomem *base_addr; |
2206 | int card, chip, channel, index; | 2140 | int chip, channel, index; |
2207 | 2141 | ||
2208 | if (!(info->flags & ASYNC_INITIALIZED)) { | 2142 | if (!(info->flags & ASYNC_INITIALIZED)) { |
2209 | return; | 2143 | return; |
2210 | } | 2144 | } |
2211 | 2145 | ||
2212 | card = info->card; | 2146 | card = info->card; |
2213 | channel = info->line - cy_card[card].first_line; | 2147 | channel = info->line - card->first_line; |
2214 | if (!IS_CYC_Z(cy_card[card])) { | 2148 | if (!IS_CYC_Z(*card)) { |
2215 | chip = channel >> 2; | 2149 | chip = channel >> 2; |
2216 | channel &= 0x03; | 2150 | channel &= 0x03; |
2217 | index = cy_card[card].bus_index; | 2151 | index = card->bus_index; |
2218 | base_addr = cy_card[card].base_addr + | 2152 | base_addr = card->base_addr + (cy_chip_offset[chip] << index); |
2219 | (cy_chip_offset[chip] << index); | ||
2220 | 2153 | ||
2221 | #ifdef CY_DEBUG_OPEN | 2154 | #ifdef CY_DEBUG_OPEN |
2222 | printk("cyc shutdown Y card %d, chip %d, channel %d, " | 2155 | printk(KERN_DEBUG "cyc shutdown Y card %d, chip %d, " |
2223 | "base_addr %lx\n", | 2156 | "channel %d, base_addr %p\n", |
2224 | card, chip, channel, (long)base_addr); | 2157 | card, chip, channel, base_addr); |
2225 | #endif | 2158 | #endif |
2226 | 2159 | ||
2227 | CY_LOCK(info, flags); | 2160 | spin_lock_irqsave(&card->card_lock, flags); |
2228 | 2161 | ||
2229 | /* Clear delta_msr_wait queue to avoid mem leaks. */ | 2162 | /* Clear delta_msr_wait queue to avoid mem leaks. */ |
2230 | wake_up_interruptible(&info->delta_msr_wait); | 2163 | wake_up_interruptible(&info->delta_msr_wait); |
@@ -2240,10 +2173,10 @@ static void shutdown(struct cyclades_port *info) | |||
2240 | cy_writeb(base_addr + (CyMSVR1 << index), ~CyRTS); | 2173 | cy_writeb(base_addr + (CyMSVR1 << index), ~CyRTS); |
2241 | cy_writeb(base_addr + (CyMSVR2 << index), ~CyDTR); | 2174 | cy_writeb(base_addr + (CyMSVR2 << index), ~CyDTR); |
2242 | #ifdef CY_DEBUG_DTR | 2175 | #ifdef CY_DEBUG_DTR |
2243 | printk("cyc shutdown dropping DTR\n"); | 2176 | printk(KERN_DEBUG "cyc shutdown dropping DTR\n"); |
2244 | printk(" status: 0x%x, 0x%x\n", | 2177 | printk(KERN_DEBUG " status: 0x%x, 0x%x\n", |
2245 | cy_readb(base_addr + (CyMSVR1 << index)), | 2178 | readb(base_addr + (CyMSVR1 << index)), |
2246 | cy_readb(base_addr + (CyMSVR2 << index))); | 2179 | readb(base_addr + (CyMSVR2 << index))); |
2247 | #endif | 2180 | #endif |
2248 | } | 2181 | } |
2249 | cyy_issue_cmd(base_addr, CyCHAN_CTL | CyDIS_RCVR, index); | 2182 | cyy_issue_cmd(base_addr, CyCHAN_CTL | CyDIS_RCVR, index); |
@@ -2254,7 +2187,7 @@ static void shutdown(struct cyclades_port *info) | |||
2254 | set_bit(TTY_IO_ERROR, &info->tty->flags); | 2187 | set_bit(TTY_IO_ERROR, &info->tty->flags); |
2255 | } | 2188 | } |
2256 | info->flags &= ~ASYNC_INITIALIZED; | 2189 | info->flags &= ~ASYNC_INITIALIZED; |
2257 | CY_UNLOCK(info, flags); | 2190 | spin_unlock_irqrestore(&card->card_lock, flags); |
2258 | } else { | 2191 | } else { |
2259 | struct FIRM_ID __iomem *firm_id; | 2192 | struct FIRM_ID __iomem *firm_id; |
2260 | struct ZFW_CTRL __iomem *zfw_ctrl; | 2193 | struct ZFW_CTRL __iomem *zfw_ctrl; |
@@ -2262,23 +2195,23 @@ static void shutdown(struct cyclades_port *info) | |||
2262 | struct CH_CTRL __iomem *ch_ctrl; | 2195 | struct CH_CTRL __iomem *ch_ctrl; |
2263 | int retval; | 2196 | int retval; |
2264 | 2197 | ||
2265 | base_addr = cy_card[card].base_addr; | 2198 | base_addr = card->base_addr; |
2266 | #ifdef CY_DEBUG_OPEN | 2199 | #ifdef CY_DEBUG_OPEN |
2267 | printk("cyc shutdown Z card %d, channel %d, base_addr %lx\n", | 2200 | printk(KERN_DEBUG "cyc shutdown Z card %d, channel %d, " |
2268 | card, channel, (long)base_addr); | 2201 | "base_addr %p\n", card, channel, base_addr); |
2269 | #endif | 2202 | #endif |
2270 | 2203 | ||
2271 | firm_id = base_addr + ID_ADDRESS; | 2204 | firm_id = base_addr + ID_ADDRESS; |
2272 | if (!ISZLOADED(cy_card[card])) { | 2205 | if (!ISZLOADED(*card)) { |
2273 | return; | 2206 | return; |
2274 | } | 2207 | } |
2275 | 2208 | ||
2276 | zfw_ctrl = cy_card[card].base_addr + | 2209 | zfw_ctrl = card->base_addr + |
2277 | (cy_readl(&firm_id->zfwctrl_addr) & 0xfffff); | 2210 | (readl(&firm_id->zfwctrl_addr) & 0xfffff); |
2278 | board_ctrl = &zfw_ctrl->board_ctrl; | 2211 | board_ctrl = &zfw_ctrl->board_ctrl; |
2279 | ch_ctrl = zfw_ctrl->ch_ctrl; | 2212 | ch_ctrl = zfw_ctrl->ch_ctrl; |
2280 | 2213 | ||
2281 | CY_LOCK(info, flags); | 2214 | spin_lock_irqsave(&card->card_lock, flags); |
2282 | 2215 | ||
2283 | if (info->xmit_buf) { | 2216 | if (info->xmit_buf) { |
2284 | unsigned char *temp; | 2217 | unsigned char *temp; |
@@ -2289,16 +2222,16 @@ static void shutdown(struct cyclades_port *info) | |||
2289 | 2222 | ||
2290 | if (!info->tty || (info->tty->termios->c_cflag & HUPCL)) { | 2223 | if (!info->tty || (info->tty->termios->c_cflag & HUPCL)) { |
2291 | cy_writel(&ch_ctrl[channel].rs_control, | 2224 | cy_writel(&ch_ctrl[channel].rs_control, |
2292 | (uclong)(cy_readl(&ch_ctrl[channel].rs_control)& | 2225 | (__u32)(readl(&ch_ctrl[channel].rs_control) & |
2293 | ~(C_RS_RTS | C_RS_DTR))); | 2226 | ~(C_RS_RTS | C_RS_DTR))); |
2294 | retval = cyz_issue_cmd(&cy_card[info->card], channel, | 2227 | retval = cyz_issue_cmd(info->card, channel, |
2295 | C_CM_IOCTLM, 0L); | 2228 | C_CM_IOCTLM, 0L); |
2296 | if (retval != 0) { | 2229 | if (retval != 0) { |
2297 | printk("cyc:shutdown retval on ttyC%d was %x\n", | 2230 | printk(KERN_ERR"cyc:shutdown retval on ttyC%d " |
2298 | info->line, retval); | 2231 | "was %x\n", info->line, retval); |
2299 | } | 2232 | } |
2300 | #ifdef CY_DEBUG_DTR | 2233 | #ifdef CY_DEBUG_DTR |
2301 | printk("cyc:shutdown dropping Z DTR\n"); | 2234 | printk(KERN_DEBUG "cyc:shutdown dropping Z DTR\n"); |
2302 | #endif | 2235 | #endif |
2303 | } | 2236 | } |
2304 | 2237 | ||
@@ -2307,11 +2240,11 @@ static void shutdown(struct cyclades_port *info) | |||
2307 | } | 2240 | } |
2308 | info->flags &= ~ASYNC_INITIALIZED; | 2241 | info->flags &= ~ASYNC_INITIALIZED; |
2309 | 2242 | ||
2310 | CY_UNLOCK(info, flags); | 2243 | spin_unlock_irqrestore(&card->card_lock, flags); |
2311 | } | 2244 | } |
2312 | 2245 | ||
2313 | #ifdef CY_DEBUG_OPEN | 2246 | #ifdef CY_DEBUG_OPEN |
2314 | printk(" cyc shutdown done\n"); | 2247 | printk(KERN_DEBUG "cyc shutdown done\n"); |
2315 | #endif | 2248 | #endif |
2316 | } /* shutdown */ | 2249 | } /* shutdown */ |
2317 | 2250 | ||
@@ -2332,7 +2265,7 @@ block_til_ready(struct tty_struct *tty, struct file *filp, | |||
2332 | int retval; | 2265 | int retval; |
2333 | void __iomem *base_addr; | 2266 | void __iomem *base_addr; |
2334 | 2267 | ||
2335 | cinfo = &cy_card[info->card]; | 2268 | cinfo = info->card; |
2336 | channel = info->line - cinfo->first_line; | 2269 | channel = info->line - cinfo->first_line; |
2337 | 2270 | ||
2338 | /* | 2271 | /* |
@@ -2340,9 +2273,8 @@ block_til_ready(struct tty_struct *tty, struct file *filp, | |||
2340 | * until it's done, and then try again. | 2273 | * until it's done, and then try again. |
2341 | */ | 2274 | */ |
2342 | if (tty_hung_up_p(filp) || (info->flags & ASYNC_CLOSING)) { | 2275 | if (tty_hung_up_p(filp) || (info->flags & ASYNC_CLOSING)) { |
2343 | if (info->flags & ASYNC_CLOSING) { | 2276 | wait_event_interruptible(info->close_wait, |
2344 | interruptible_sleep_on(&info->close_wait); | 2277 | !(info->flags & ASYNC_CLOSING)); |
2345 | } | ||
2346 | return (info->flags & ASYNC_HUP_NOTIFY) ? -EAGAIN: -ERESTARTSYS; | 2278 | return (info->flags & ASYNC_HUP_NOTIFY) ? -EAGAIN: -ERESTARTSYS; |
2347 | } | 2279 | } |
2348 | 2280 | ||
@@ -2365,17 +2297,16 @@ block_til_ready(struct tty_struct *tty, struct file *filp, | |||
2365 | retval = 0; | 2297 | retval = 0; |
2366 | add_wait_queue(&info->open_wait, &wait); | 2298 | add_wait_queue(&info->open_wait, &wait); |
2367 | #ifdef CY_DEBUG_OPEN | 2299 | #ifdef CY_DEBUG_OPEN |
2368 | printk("cyc block_til_ready before block: ttyC%d, count = %d\n", | 2300 | printk(KERN_DEBUG "cyc block_til_ready before block: ttyC%d, " |
2369 | info->line, info->count); | 2301 | "count = %d\n", info->line, info->count); |
2370 | /**/ | ||
2371 | #endif | 2302 | #endif |
2372 | CY_LOCK(info, flags); | 2303 | spin_lock_irqsave(&cinfo->card_lock, flags); |
2373 | if (!tty_hung_up_p(filp)) | 2304 | if (!tty_hung_up_p(filp)) |
2374 | info->count--; | 2305 | info->count--; |
2375 | CY_UNLOCK(info, flags); | 2306 | spin_unlock_irqrestore(&cinfo->card_lock, flags); |
2376 | #ifdef CY_DEBUG_COUNT | 2307 | #ifdef CY_DEBUG_COUNT |
2377 | printk("cyc block_til_ready: (%d): decrementing count to %d\n", | 2308 | printk(KERN_DEBUG "cyc block_til_ready: (%d): decrementing count to " |
2378 | current->pid, info->count); | 2309 | "%d\n", current->pid, info->count); |
2379 | #endif | 2310 | #endif |
2380 | info->blocked_open++; | 2311 | info->blocked_open++; |
2381 | 2312 | ||
@@ -2386,7 +2317,7 @@ block_til_ready(struct tty_struct *tty, struct file *filp, | |||
2386 | base_addr = cinfo->base_addr + (cy_chip_offset[chip] << index); | 2317 | base_addr = cinfo->base_addr + (cy_chip_offset[chip] << index); |
2387 | 2318 | ||
2388 | while (1) { | 2319 | while (1) { |
2389 | CY_LOCK(info, flags); | 2320 | spin_lock_irqsave(&cinfo->card_lock, flags); |
2390 | if ((tty->termios->c_cflag & CBAUD)) { | 2321 | if ((tty->termios->c_cflag & CBAUD)) { |
2391 | cy_writeb(base_addr + (CyCAR << index), | 2322 | cy_writeb(base_addr + (CyCAR << index), |
2392 | (u_char) channel); | 2323 | (u_char) channel); |
@@ -2395,15 +2326,14 @@ block_til_ready(struct tty_struct *tty, struct file *filp, | |||
2395 | cy_writeb(base_addr + (CyMSVR2 << index), | 2326 | cy_writeb(base_addr + (CyMSVR2 << index), |
2396 | CyDTR); | 2327 | CyDTR); |
2397 | #ifdef CY_DEBUG_DTR | 2328 | #ifdef CY_DEBUG_DTR |
2398 | printk("cyc:block_til_ready raising DTR\n"); | 2329 | printk(KERN_DEBUG "cyc:block_til_ready raising " |
2399 | printk(" status: 0x%x, 0x%x\n", | 2330 | "DTR\n"); |
2400 | cy_readb(base_addr + | 2331 | printk(KERN_DEBUG " status: 0x%x, 0x%x\n", |
2401 | (CyMSVR1 << index)), | 2332 | readb(base_addr + (CyMSVR1 << index)), |
2402 | cy_readb(base_addr + | 2333 | readb(base_addr + (CyMSVR2 << index))); |
2403 | (CyMSVR2 << index))); | ||
2404 | #endif | 2334 | #endif |
2405 | } | 2335 | } |
2406 | CY_UNLOCK(info, flags); | 2336 | spin_unlock_irqrestore(&cinfo->card_lock, flags); |
2407 | 2337 | ||
2408 | set_current_state(TASK_INTERRUPTIBLE); | 2338 | set_current_state(TASK_INTERRUPTIBLE); |
2409 | if (tty_hung_up_p(filp) || | 2339 | if (tty_hung_up_p(filp) || |
@@ -2413,26 +2343,25 @@ block_til_ready(struct tty_struct *tty, struct file *filp, | |||
2413 | break; | 2343 | break; |
2414 | } | 2344 | } |
2415 | 2345 | ||
2416 | CY_LOCK(info, flags); | 2346 | spin_lock_irqsave(&cinfo->card_lock, flags); |
2417 | cy_writeb(base_addr + (CyCAR << index), | 2347 | cy_writeb(base_addr + (CyCAR << index), |
2418 | (u_char) channel); | 2348 | (u_char) channel); |
2419 | if (!(info->flags & ASYNC_CLOSING) && (C_CLOCAL(tty) || | 2349 | if (!(info->flags & ASYNC_CLOSING) && (C_CLOCAL(tty) || |
2420 | (cy_readb(base_addr + | 2350 | (readb(base_addr + |
2421 | (CyMSVR1 << index)) & CyDCD))) { | 2351 | (CyMSVR1 << index)) & CyDCD))) { |
2422 | CY_UNLOCK(info, flags); | 2352 | spin_unlock_irqrestore(&cinfo->card_lock, flags); |
2423 | break; | 2353 | break; |
2424 | } | 2354 | } |
2425 | CY_UNLOCK(info, flags); | 2355 | spin_unlock_irqrestore(&cinfo->card_lock, flags); |
2426 | 2356 | ||
2427 | if (signal_pending(current)) { | 2357 | if (signal_pending(current)) { |
2428 | retval = -ERESTARTSYS; | 2358 | retval = -ERESTARTSYS; |
2429 | break; | 2359 | break; |
2430 | } | 2360 | } |
2431 | #ifdef CY_DEBUG_OPEN | 2361 | #ifdef CY_DEBUG_OPEN |
2432 | printk("cyc block_til_ready blocking: ttyC%d, " | 2362 | printk(KERN_DEBUG "cyc block_til_ready blocking: " |
2433 | "count = %d\n", | 2363 | "ttyC%d, count = %d\n", |
2434 | info->line, info->count); | 2364 | info->line, info->count); |
2435 | /**/ | ||
2436 | #endif | 2365 | #endif |
2437 | schedule(); | 2366 | schedule(); |
2438 | } | 2367 | } |
@@ -2446,31 +2375,30 @@ block_til_ready(struct tty_struct *tty, struct file *filp, | |||
2446 | base_addr = cinfo->base_addr; | 2375 | base_addr = cinfo->base_addr; |
2447 | firm_id = base_addr + ID_ADDRESS; | 2376 | firm_id = base_addr + ID_ADDRESS; |
2448 | if (!ISZLOADED(*cinfo)) { | 2377 | if (!ISZLOADED(*cinfo)) { |
2449 | current->state = TASK_RUNNING; | 2378 | __set_current_state(TASK_RUNNING); |
2450 | remove_wait_queue(&info->open_wait, &wait); | 2379 | remove_wait_queue(&info->open_wait, &wait); |
2451 | return -EINVAL; | 2380 | return -EINVAL; |
2452 | } | 2381 | } |
2453 | 2382 | ||
2454 | zfw_ctrl = base_addr + (cy_readl(&firm_id->zfwctrl_addr) & | 2383 | zfw_ctrl = base_addr + (readl(&firm_id->zfwctrl_addr)& 0xfffff); |
2455 | 0xfffff); | ||
2456 | board_ctrl = &zfw_ctrl->board_ctrl; | 2384 | board_ctrl = &zfw_ctrl->board_ctrl; |
2457 | ch_ctrl = zfw_ctrl->ch_ctrl; | 2385 | ch_ctrl = zfw_ctrl->ch_ctrl; |
2458 | 2386 | ||
2459 | while (1) { | 2387 | while (1) { |
2460 | if ((tty->termios->c_cflag & CBAUD)) { | 2388 | if ((tty->termios->c_cflag & CBAUD)) { |
2461 | cy_writel(&ch_ctrl[channel].rs_control, | 2389 | cy_writel(&ch_ctrl[channel].rs_control, |
2462 | cy_readl(&ch_ctrl[channel]. | 2390 | readl(&ch_ctrl[channel].rs_control) | |
2463 | rs_control) | (C_RS_RTS | | 2391 | C_RS_RTS | C_RS_DTR); |
2464 | C_RS_DTR)); | 2392 | retval = cyz_issue_cmd(cinfo, |
2465 | retval = cyz_issue_cmd(&cy_card[info->card], | 2393 | channel, C_CM_IOCTLM, 0L); |
2466 | channel, C_CM_IOCTLM, 0L); | ||
2467 | if (retval != 0) { | 2394 | if (retval != 0) { |
2468 | printk("cyc:block_til_ready retval on " | 2395 | printk(KERN_ERR "cyc:block_til_ready " |
2469 | "ttyC%d was %x\n", | 2396 | "retval on ttyC%d was %x\n", |
2470 | info->line, retval); | 2397 | info->line, retval); |
2471 | } | 2398 | } |
2472 | #ifdef CY_DEBUG_DTR | 2399 | #ifdef CY_DEBUG_DTR |
2473 | printk("cyc:block_til_ready raising Z DTR\n"); | 2400 | printk(KERN_DEBUG "cyc:block_til_ready raising " |
2401 | "Z DTR\n"); | ||
2474 | #endif | 2402 | #endif |
2475 | } | 2403 | } |
2476 | 2404 | ||
@@ -2482,7 +2410,7 @@ block_til_ready(struct tty_struct *tty, struct file *filp, | |||
2482 | break; | 2410 | break; |
2483 | } | 2411 | } |
2484 | if (!(info->flags & ASYNC_CLOSING) && (C_CLOCAL(tty) || | 2412 | if (!(info->flags & ASYNC_CLOSING) && (C_CLOCAL(tty) || |
2485 | (cy_readl(&ch_ctrl[channel].rs_status) & | 2413 | (readl(&ch_ctrl[channel].rs_status) & |
2486 | C_RS_DCD))) { | 2414 | C_RS_DCD))) { |
2487 | break; | 2415 | break; |
2488 | } | 2416 | } |
@@ -2491,28 +2419,26 @@ block_til_ready(struct tty_struct *tty, struct file *filp, | |||
2491 | break; | 2419 | break; |
2492 | } | 2420 | } |
2493 | #ifdef CY_DEBUG_OPEN | 2421 | #ifdef CY_DEBUG_OPEN |
2494 | printk("cyc block_til_ready blocking: ttyC%d, " | 2422 | printk(KERN_DEBUG "cyc block_til_ready blocking: " |
2495 | "count = %d\n", | 2423 | "ttyC%d, count = %d\n", |
2496 | info->line, info->count); | 2424 | info->line, info->count); |
2497 | /**/ | ||
2498 | #endif | 2425 | #endif |
2499 | schedule(); | 2426 | schedule(); |
2500 | } | 2427 | } |
2501 | } | 2428 | } |
2502 | current->state = TASK_RUNNING; | 2429 | __set_current_state(TASK_RUNNING); |
2503 | remove_wait_queue(&info->open_wait, &wait); | 2430 | remove_wait_queue(&info->open_wait, &wait); |
2504 | if (!tty_hung_up_p(filp)) { | 2431 | if (!tty_hung_up_p(filp)) { |
2505 | info->count++; | 2432 | info->count++; |
2506 | #ifdef CY_DEBUG_COUNT | 2433 | #ifdef CY_DEBUG_COUNT |
2507 | printk("cyc:block_til_ready (%d): incrementing count to %d\n", | 2434 | printk(KERN_DEBUG "cyc:block_til_ready (%d): incrementing " |
2508 | current->pid, info->count); | 2435 | "count to %d\n", current->pid, info->count); |
2509 | #endif | 2436 | #endif |
2510 | } | 2437 | } |
2511 | info->blocked_open--; | 2438 | info->blocked_open--; |
2512 | #ifdef CY_DEBUG_OPEN | 2439 | #ifdef CY_DEBUG_OPEN |
2513 | printk("cyc:block_til_ready after blocking: ttyC%d, count = %d\n", | 2440 | printk(KERN_DEBUG "cyc:block_til_ready after blocking: ttyC%d, " |
2514 | info->line, info->count); | 2441 | "count = %d\n", info->line, info->count); |
2515 | /**/ | ||
2516 | #endif | 2442 | #endif |
2517 | if (retval) | 2443 | if (retval) |
2518 | return retval; | 2444 | return retval; |
@@ -2527,13 +2453,20 @@ block_til_ready(struct tty_struct *tty, struct file *filp, | |||
2527 | static int cy_open(struct tty_struct *tty, struct file *filp) | 2453 | static int cy_open(struct tty_struct *tty, struct file *filp) |
2528 | { | 2454 | { |
2529 | struct cyclades_port *info; | 2455 | struct cyclades_port *info; |
2456 | unsigned int i; | ||
2530 | int retval, line; | 2457 | int retval, line; |
2531 | 2458 | ||
2532 | line = tty->index; | 2459 | line = tty->index; |
2533 | if ((line < 0) || (NR_PORTS <= line)) { | 2460 | if ((line < 0) || (NR_PORTS <= line)) { |
2534 | return -ENODEV; | 2461 | return -ENODEV; |
2535 | } | 2462 | } |
2536 | info = &cy_port[line]; | 2463 | for (i = 0; i < NR_CARDS; i++) |
2464 | if (line < cy_card[i].first_line + cy_card[i].nports && | ||
2465 | line >= cy_card[i].first_line) | ||
2466 | break; | ||
2467 | if (i >= NR_CARDS) | ||
2468 | return -ENODEV; | ||
2469 | info = &cy_card[i].ports[line - cy_card[i].first_line]; | ||
2537 | if (info->line < 0) { | 2470 | if (info->line < 0) { |
2538 | return -ENODEV; | 2471 | return -ENODEV; |
2539 | } | 2472 | } |
@@ -2542,23 +2475,23 @@ static int cy_open(struct tty_struct *tty, struct file *filp) | |||
2542 | treat it as absent from the system. This | 2475 | treat it as absent from the system. This |
2543 | will make the user pay attention. | 2476 | will make the user pay attention. |
2544 | */ | 2477 | */ |
2545 | if (IS_CYC_Z(cy_card[info->card])) { | 2478 | if (IS_CYC_Z(*info->card)) { |
2546 | struct cyclades_card *cinfo = &cy_card[info->card]; | 2479 | struct cyclades_card *cinfo = info->card; |
2547 | struct FIRM_ID __iomem *firm_id = cinfo->base_addr + ID_ADDRESS; | 2480 | struct FIRM_ID __iomem *firm_id = cinfo->base_addr + ID_ADDRESS; |
2548 | 2481 | ||
2549 | if (!ISZLOADED(*cinfo)) { | 2482 | if (!ISZLOADED(*cinfo)) { |
2550 | if (((ZE_V1 == cy_readl( | 2483 | if (((ZE_V1 == readl(&((struct RUNTIME_9060 __iomem *) |
2551 | &((struct RUNTIME_9060 __iomem *) | ||
2552 | (cinfo->ctl_addr))->mail_box_0)) && | 2484 | (cinfo->ctl_addr))->mail_box_0)) && |
2553 | Z_FPGA_CHECK(*cinfo)) && | 2485 | Z_FPGA_CHECK(*cinfo)) && |
2554 | (ZFIRM_HLT == cy_readl( | 2486 | (ZFIRM_HLT == readl( |
2555 | &firm_id->signature))) { | 2487 | &firm_id->signature))) { |
2556 | printk("cyc:Cyclades-Z Error: you need an " | 2488 | printk(KERN_ERR "cyc:Cyclades-Z Error: you " |
2557 | "external power supply for this number " | 2489 | "need an external power supply for " |
2558 | "of ports.\n\rFirmware halted.\r\n"); | 2490 | "this number of ports.\nFirmware " |
2491 | "halted.\n"); | ||
2559 | } else { | 2492 | } else { |
2560 | printk("cyc:Cyclades-Z firmware not yet " | 2493 | printk(KERN_ERR "cyc:Cyclades-Z firmware not " |
2561 | "loaded\n"); | 2494 | "yet loaded\n"); |
2562 | } | 2495 | } |
2563 | return -ENODEV; | 2496 | return -ENODEV; |
2564 | } | 2497 | } |
@@ -2572,24 +2505,23 @@ static int cy_open(struct tty_struct *tty, struct file *filp) | |||
2572 | struct BOARD_CTRL __iomem *board_ctrl; | 2505 | struct BOARD_CTRL __iomem *board_ctrl; |
2573 | 2506 | ||
2574 | zfw_ctrl = cinfo->base_addr + | 2507 | zfw_ctrl = cinfo->base_addr + |
2575 | (cy_readl(&firm_id->zfwctrl_addr) & | 2508 | (readl(&firm_id->zfwctrl_addr) & |
2576 | 0xfffff); | 2509 | 0xfffff); |
2577 | 2510 | ||
2578 | board_ctrl = &zfw_ctrl->board_ctrl; | 2511 | board_ctrl = &zfw_ctrl->board_ctrl; |
2579 | 2512 | ||
2580 | /* Enable interrupts on the PLX chip */ | 2513 | /* Enable interrupts on the PLX chip */ |
2581 | cy_writew(cinfo->ctl_addr + 0x68, | 2514 | cy_writew(cinfo->ctl_addr + 0x68, |
2582 | cy_readw(cinfo->ctl_addr + | 2515 | readw(cinfo->ctl_addr + 0x68) | 0x0900); |
2583 | 0x68) | 0x0900); | ||
2584 | /* Enable interrupts on the FW */ | 2516 | /* Enable interrupts on the FW */ |
2585 | retval = cyz_issue_cmd(cinfo, 0, | 2517 | retval = cyz_issue_cmd(cinfo, 0, |
2586 | C_CM_IRQ_ENBL, 0L); | 2518 | C_CM_IRQ_ENBL, 0L); |
2587 | if (retval != 0) { | 2519 | if (retval != 0) { |
2588 | printk("cyc:IRQ enable retval was %x\n", | 2520 | printk(KERN_ERR "cyc:IRQ enable retval " |
2589 | retval); | 2521 | "was %x\n", retval); |
2590 | } | 2522 | } |
2591 | cinfo->nports = | 2523 | cinfo->nports = |
2592 | (int)cy_readl(&board_ctrl->n_channel); | 2524 | (int)readl(&board_ctrl->n_channel); |
2593 | cinfo->intr_enabled = 1; | 2525 | cinfo->intr_enabled = 1; |
2594 | } | 2526 | } |
2595 | } | 2527 | } |
@@ -2599,7 +2531,7 @@ static int cy_open(struct tty_struct *tty, struct file *filp) | |||
2599 | return -ENODEV; | 2531 | return -ENODEV; |
2600 | } | 2532 | } |
2601 | #ifdef CY_DEBUG_OTHER | 2533 | #ifdef CY_DEBUG_OTHER |
2602 | printk("cyc:cy_open ttyC%d\n", info->line); /* */ | 2534 | printk(KERN_DEBUG "cyc:cy_open ttyC%d\n", info->line); |
2603 | #endif | 2535 | #endif |
2604 | tty->driver_data = info; | 2536 | tty->driver_data = info; |
2605 | info->tty = tty; | 2537 | info->tty = tty; |
@@ -2607,12 +2539,12 @@ static int cy_open(struct tty_struct *tty, struct file *filp) | |||
2607 | return -ENODEV; | 2539 | return -ENODEV; |
2608 | } | 2540 | } |
2609 | #ifdef CY_DEBUG_OPEN | 2541 | #ifdef CY_DEBUG_OPEN |
2610 | printk("cyc:cy_open ttyC%d, count = %d\n", info->line, info->count); | 2542 | printk(KERN_DEBUG "cyc:cy_open ttyC%d, count = %d\n", info->line, |
2611 | /**/ | 2543 | info->count); |
2612 | #endif | 2544 | #endif |
2613 | info->count++; | 2545 | info->count++; |
2614 | #ifdef CY_DEBUG_COUNT | 2546 | #ifdef CY_DEBUG_COUNT |
2615 | printk("cyc:cy_open (%d): incrementing count to %d\n", | 2547 | printk(KERN_DEBUG "cyc:cy_open (%d): incrementing count to %d\n", |
2616 | current->pid, info->count); | 2548 | current->pid, info->count); |
2617 | #endif | 2549 | #endif |
2618 | 2550 | ||
@@ -2620,8 +2552,8 @@ static int cy_open(struct tty_struct *tty, struct file *filp) | |||
2620 | * If the port is the middle of closing, bail out now | 2552 | * If the port is the middle of closing, bail out now |
2621 | */ | 2553 | */ |
2622 | if (tty_hung_up_p(filp) || (info->flags & ASYNC_CLOSING)) { | 2554 | if (tty_hung_up_p(filp) || (info->flags & ASYNC_CLOSING)) { |
2623 | if (info->flags & ASYNC_CLOSING) | 2555 | wait_event_interruptible(info->close_wait, |
2624 | interruptible_sleep_on(&info->close_wait); | 2556 | !(info->flags & ASYNC_CLOSING)); |
2625 | return (info->flags & ASYNC_HUP_NOTIFY) ? -EAGAIN: -ERESTARTSYS; | 2557 | return (info->flags & ASYNC_HUP_NOTIFY) ? -EAGAIN: -ERESTARTSYS; |
2626 | } | 2558 | } |
2627 | 2559 | ||
@@ -2636,8 +2568,8 @@ static int cy_open(struct tty_struct *tty, struct file *filp) | |||
2636 | retval = block_til_ready(tty, filp, info); | 2568 | retval = block_til_ready(tty, filp, info); |
2637 | if (retval) { | 2569 | if (retval) { |
2638 | #ifdef CY_DEBUG_OPEN | 2570 | #ifdef CY_DEBUG_OPEN |
2639 | printk("cyc:cy_open returning after block_til_ready with %d\n", | 2571 | printk(KERN_DEBUG "cyc:cy_open returning after block_til_ready " |
2640 | retval); | 2572 | "with %d\n", retval); |
2641 | #endif | 2573 | #endif |
2642 | return retval; | 2574 | return retval; |
2643 | } | 2575 | } |
@@ -2645,8 +2577,7 @@ static int cy_open(struct tty_struct *tty, struct file *filp) | |||
2645 | info->throttle = 0; | 2577 | info->throttle = 0; |
2646 | 2578 | ||
2647 | #ifdef CY_DEBUG_OPEN | 2579 | #ifdef CY_DEBUG_OPEN |
2648 | printk(" cyc:cy_open done\n"); | 2580 | printk(KERN_DEBUG "cyc:cy_open done\n"); |
2649 | /**/ | ||
2650 | #endif | 2581 | #endif |
2651 | return 0; | 2582 | return 0; |
2652 | } /* cy_open */ | 2583 | } /* cy_open */ |
@@ -2656,9 +2587,10 @@ static int cy_open(struct tty_struct *tty, struct file *filp) | |||
2656 | */ | 2587 | */ |
2657 | static void cy_wait_until_sent(struct tty_struct *tty, int timeout) | 2588 | static void cy_wait_until_sent(struct tty_struct *tty, int timeout) |
2658 | { | 2589 | { |
2659 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 2590 | struct cyclades_card *card; |
2591 | struct cyclades_port *info = tty->driver_data; | ||
2660 | void __iomem *base_addr; | 2592 | void __iomem *base_addr; |
2661 | int card, chip, channel, index; | 2593 | int chip, channel, index; |
2662 | unsigned long orig_jiffies; | 2594 | unsigned long orig_jiffies; |
2663 | int char_time; | 2595 | int char_time; |
2664 | 2596 | ||
@@ -2697,20 +2629,19 @@ static void cy_wait_until_sent(struct tty_struct *tty, int timeout) | |||
2697 | if (!timeout || timeout > 2 * info->timeout) | 2629 | if (!timeout || timeout > 2 * info->timeout) |
2698 | timeout = 2 * info->timeout; | 2630 | timeout = 2 * info->timeout; |
2699 | #ifdef CY_DEBUG_WAIT_UNTIL_SENT | 2631 | #ifdef CY_DEBUG_WAIT_UNTIL_SENT |
2700 | printk("In cy_wait_until_sent(%d) check=%lu...", timeout, char_time); | 2632 | printk(KERN_DEBUG "In cy_wait_until_sent(%d) check=%d, jiff=%lu...", |
2701 | printk("jiff=%lu...", jiffies); | 2633 | timeout, char_time, jiffies); |
2702 | #endif | 2634 | #endif |
2703 | card = info->card; | 2635 | card = info->card; |
2704 | channel = (info->line) - (cy_card[card].first_line); | 2636 | channel = (info->line) - (card->first_line); |
2705 | if (!IS_CYC_Z(cy_card[card])) { | 2637 | if (!IS_CYC_Z(*card)) { |
2706 | chip = channel >> 2; | 2638 | chip = channel >> 2; |
2707 | channel &= 0x03; | 2639 | channel &= 0x03; |
2708 | index = cy_card[card].bus_index; | 2640 | index = card->bus_index; |
2709 | base_addr = | 2641 | base_addr = card->base_addr + (cy_chip_offset[chip] << index); |
2710 | cy_card[card].base_addr + (cy_chip_offset[chip] << index); | 2642 | while (readb(base_addr + (CySRER << index)) & CyTxRdy) { |
2711 | while (cy_readb(base_addr + (CySRER << index)) & CyTxRdy) { | ||
2712 | #ifdef CY_DEBUG_WAIT_UNTIL_SENT | 2643 | #ifdef CY_DEBUG_WAIT_UNTIL_SENT |
2713 | printk("Not clean (jiff=%lu)...", jiffies); | 2644 | printk(KERN_DEBUG "Not clean (jiff=%lu)...", jiffies); |
2714 | #endif | 2645 | #endif |
2715 | if (msleep_interruptible(jiffies_to_msecs(char_time))) | 2646 | if (msleep_interruptible(jiffies_to_msecs(char_time))) |
2716 | break; | 2647 | break; |
@@ -2718,13 +2649,11 @@ static void cy_wait_until_sent(struct tty_struct *tty, int timeout) | |||
2718 | timeout)) | 2649 | timeout)) |
2719 | break; | 2650 | break; |
2720 | } | 2651 | } |
2721 | } else { | ||
2722 | /* Nothing to do! */ | ||
2723 | } | 2652 | } |
2724 | /* Run one more char cycle */ | 2653 | /* Run one more char cycle */ |
2725 | msleep_interruptible(jiffies_to_msecs(char_time * 5)); | 2654 | msleep_interruptible(jiffies_to_msecs(char_time * 5)); |
2726 | #ifdef CY_DEBUG_WAIT_UNTIL_SENT | 2655 | #ifdef CY_DEBUG_WAIT_UNTIL_SENT |
2727 | printk("Clean (jiff=%lu)...done\n", jiffies); | 2656 | printk(KERN_DEBUG "Clean (jiff=%lu)...done\n", jiffies); |
2728 | #endif | 2657 | #endif |
2729 | } | 2658 | } |
2730 | 2659 | ||
@@ -2733,25 +2662,29 @@ static void cy_wait_until_sent(struct tty_struct *tty, int timeout) | |||
2733 | */ | 2662 | */ |
2734 | static void cy_close(struct tty_struct *tty, struct file *filp) | 2663 | static void cy_close(struct tty_struct *tty, struct file *filp) |
2735 | { | 2664 | { |
2736 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 2665 | struct cyclades_port *info = tty->driver_data; |
2666 | struct cyclades_card *card; | ||
2737 | unsigned long flags; | 2667 | unsigned long flags; |
2738 | 2668 | ||
2739 | #ifdef CY_DEBUG_OTHER | 2669 | #ifdef CY_DEBUG_OTHER |
2740 | printk("cyc:cy_close ttyC%d\n", info->line); | 2670 | printk(KERN_DEBUG "cyc:cy_close ttyC%d\n", info->line); |
2741 | #endif | 2671 | #endif |
2742 | 2672 | ||
2743 | if (!info || serial_paranoia_check(info, tty->name, "cy_close")) { | 2673 | if (!info || serial_paranoia_check(info, tty->name, "cy_close")) { |
2744 | return; | 2674 | return; |
2745 | } | 2675 | } |
2746 | 2676 | ||
2747 | CY_LOCK(info, flags); | 2677 | card = info->card; |
2678 | |||
2679 | spin_lock_irqsave(&card->card_lock, flags); | ||
2748 | /* If the TTY is being hung up, nothing to do */ | 2680 | /* If the TTY is being hung up, nothing to do */ |
2749 | if (tty_hung_up_p(filp)) { | 2681 | if (tty_hung_up_p(filp)) { |
2750 | CY_UNLOCK(info, flags); | 2682 | spin_unlock_irqrestore(&card->card_lock, flags); |
2751 | return; | 2683 | return; |
2752 | } | 2684 | } |
2753 | #ifdef CY_DEBUG_OPEN | 2685 | #ifdef CY_DEBUG_OPEN |
2754 | printk("cyc:cy_close ttyC%d, count = %d\n", info->line, info->count); | 2686 | printk(KERN_DEBUG "cyc:cy_close ttyC%d, count = %d\n", info->line, |
2687 | info->count); | ||
2755 | #endif | 2688 | #endif |
2756 | if ((tty->count == 1) && (info->count != 1)) { | 2689 | if ((tty->count == 1) && (info->count != 1)) { |
2757 | /* | 2690 | /* |
@@ -2761,22 +2694,22 @@ static void cy_close(struct tty_struct *tty, struct file *filp) | |||
2761 | * one, we've got real problems, since it means the | 2694 | * one, we've got real problems, since it means the |
2762 | * serial port won't be shutdown. | 2695 | * serial port won't be shutdown. |
2763 | */ | 2696 | */ |
2764 | printk("cyc:cy_close: bad serial port count; tty->count is 1, " | 2697 | printk(KERN_ERR "cyc:cy_close: bad serial port count; " |
2765 | "info->count is %d\n", info->count); | 2698 | "tty->count is 1, info->count is %d\n", info->count); |
2766 | info->count = 1; | 2699 | info->count = 1; |
2767 | } | 2700 | } |
2768 | #ifdef CY_DEBUG_COUNT | 2701 | #ifdef CY_DEBUG_COUNT |
2769 | printk("cyc:cy_close at (%d): decrementing count to %d\n", | 2702 | printk(KERN_DEBUG "cyc:cy_close at (%d): decrementing count to %d\n", |
2770 | current->pid, info->count - 1); | 2703 | current->pid, info->count - 1); |
2771 | #endif | 2704 | #endif |
2772 | if (--info->count < 0) { | 2705 | if (--info->count < 0) { |
2773 | #ifdef CY_DEBUG_COUNT | 2706 | #ifdef CY_DEBUG_COUNT |
2774 | printk("cyc:cyc_close setting count to 0\n"); | 2707 | printk(KERN_DEBUG "cyc:cyc_close setting count to 0\n"); |
2775 | #endif | 2708 | #endif |
2776 | info->count = 0; | 2709 | info->count = 0; |
2777 | } | 2710 | } |
2778 | if (info->count) { | 2711 | if (info->count) { |
2779 | CY_UNLOCK(info, flags); | 2712 | spin_unlock_irqrestore(&card->card_lock, flags); |
2780 | return; | 2713 | return; |
2781 | } | 2714 | } |
2782 | info->flags |= ASYNC_CLOSING; | 2715 | info->flags |= ASYNC_CLOSING; |
@@ -2786,81 +2719,80 @@ static void cy_close(struct tty_struct *tty, struct file *filp) | |||
2786 | * the line discipline to only process XON/XOFF characters. | 2719 | * the line discipline to only process XON/XOFF characters. |
2787 | */ | 2720 | */ |
2788 | tty->closing = 1; | 2721 | tty->closing = 1; |
2789 | CY_UNLOCK(info, flags); | 2722 | spin_unlock_irqrestore(&card->card_lock, flags); |
2790 | if (info->closing_wait != CY_CLOSING_WAIT_NONE) { | 2723 | if (info->closing_wait != CY_CLOSING_WAIT_NONE) { |
2791 | tty_wait_until_sent(tty, info->closing_wait); | 2724 | tty_wait_until_sent(tty, info->closing_wait); |
2792 | } | 2725 | } |
2793 | CY_LOCK(info, flags); | 2726 | spin_lock_irqsave(&card->card_lock, flags); |
2794 | 2727 | ||
2795 | if (!IS_CYC_Z(cy_card[info->card])) { | 2728 | if (!IS_CYC_Z(*card)) { |
2796 | int channel = info->line - cy_card[info->card].first_line; | 2729 | int channel = info->line - card->first_line; |
2797 | int index = cy_card[info->card].bus_index; | 2730 | int index = card->bus_index; |
2798 | void __iomem *base_addr = cy_card[info->card].base_addr + | 2731 | void __iomem *base_addr = card->base_addr + |
2799 | (cy_chip_offset[channel >> 2] << index); | 2732 | (cy_chip_offset[channel >> 2] << index); |
2800 | /* Stop accepting input */ | 2733 | /* Stop accepting input */ |
2801 | channel &= 0x03; | 2734 | channel &= 0x03; |
2802 | cy_writeb(base_addr + (CyCAR << index), (u_char) channel); | 2735 | cy_writeb(base_addr + (CyCAR << index), (u_char) channel); |
2803 | cy_writeb(base_addr + (CySRER << index), | 2736 | cy_writeb(base_addr + (CySRER << index), |
2804 | cy_readb(base_addr + (CySRER << index)) & ~CyRxData); | 2737 | readb(base_addr + (CySRER << index)) & ~CyRxData); |
2805 | if (info->flags & ASYNC_INITIALIZED) { | 2738 | if (info->flags & ASYNC_INITIALIZED) { |
2806 | /* Waiting for on-board buffers to be empty before closing | 2739 | /* Waiting for on-board buffers to be empty before closing |
2807 | the port */ | 2740 | the port */ |
2808 | CY_UNLOCK(info, flags); | 2741 | spin_unlock_irqrestore(&card->card_lock, flags); |
2809 | cy_wait_until_sent(tty, info->timeout); | 2742 | cy_wait_until_sent(tty, info->timeout); |
2810 | CY_LOCK(info, flags); | 2743 | spin_lock_irqsave(&card->card_lock, flags); |
2811 | } | 2744 | } |
2812 | } else { | 2745 | } else { |
2813 | #ifdef Z_WAKE | 2746 | #ifdef Z_WAKE |
2814 | /* Waiting for on-board buffers to be empty before closing the port */ | 2747 | /* Waiting for on-board buffers to be empty before closing the port */ |
2815 | void __iomem *base_addr = cy_card[info->card].base_addr; | 2748 | void __iomem *base_addr = card->base_addr; |
2816 | struct FIRM_ID __iomem *firm_id = base_addr + ID_ADDRESS; | 2749 | struct FIRM_ID __iomem *firm_id = base_addr + ID_ADDRESS; |
2817 | struct ZFW_CTRL __iomem *zfw_ctrl = | 2750 | struct ZFW_CTRL __iomem *zfw_ctrl = |
2818 | base_addr + (cy_readl(&firm_id->zfwctrl_addr) & 0xfffff); | 2751 | base_addr + (readl(&firm_id->zfwctrl_addr) & 0xfffff); |
2819 | struct CH_CTRL __iomem *ch_ctrl = zfw_ctrl->ch_ctrl; | 2752 | struct CH_CTRL __iomem *ch_ctrl = zfw_ctrl->ch_ctrl; |
2820 | int channel = info->line - cy_card[info->card].first_line; | 2753 | int channel = info->line - card->first_line; |
2821 | int retval; | 2754 | int retval; |
2822 | 2755 | ||
2823 | if (cy_readl(&ch_ctrl[channel].flow_status) != C_FS_TXIDLE) { | 2756 | if (readl(&ch_ctrl[channel].flow_status) != C_FS_TXIDLE) { |
2824 | retval = cyz_issue_cmd(&cy_card[info->card], channel, | 2757 | retval = cyz_issue_cmd(card, channel, C_CM_IOCTLW, 0L); |
2825 | C_CM_IOCTLW, 0L); | ||
2826 | if (retval != 0) { | 2758 | if (retval != 0) { |
2827 | printk("cyc:cy_close retval on ttyC%d was %x\n", | 2759 | printk(KERN_DEBUG "cyc:cy_close retval on " |
2828 | info->line, retval); | 2760 | "ttyC%d was %x\n", info->line, retval); |
2829 | } | 2761 | } |
2830 | CY_UNLOCK(info, flags); | 2762 | spin_unlock_irqrestore(&card->card_lock, flags); |
2831 | interruptible_sleep_on(&info->shutdown_wait); | 2763 | wait_for_completion_interruptible(&info->shutdown_wait); |
2832 | CY_LOCK(info, flags); | 2764 | spin_lock_irqsave(&card->card_lock, flags); |
2833 | } | 2765 | } |
2834 | #endif | 2766 | #endif |
2835 | } | 2767 | } |
2836 | 2768 | ||
2837 | CY_UNLOCK(info, flags); | 2769 | spin_unlock_irqrestore(&card->card_lock, flags); |
2838 | shutdown(info); | 2770 | shutdown(info); |
2839 | if (tty->driver->flush_buffer) | 2771 | if (tty->driver->flush_buffer) |
2840 | tty->driver->flush_buffer(tty); | 2772 | tty->driver->flush_buffer(tty); |
2841 | tty_ldisc_flush(tty); | 2773 | tty_ldisc_flush(tty); |
2842 | CY_LOCK(info, flags); | 2774 | spin_lock_irqsave(&card->card_lock, flags); |
2843 | 2775 | ||
2844 | tty->closing = 0; | 2776 | tty->closing = 0; |
2845 | info->event = 0; | 2777 | info->event = 0; |
2846 | info->tty = NULL; | 2778 | info->tty = NULL; |
2847 | if (info->blocked_open) { | 2779 | if (info->blocked_open) { |
2848 | CY_UNLOCK(info, flags); | 2780 | spin_unlock_irqrestore(&card->card_lock, flags); |
2849 | if (info->close_delay) { | 2781 | if (info->close_delay) { |
2850 | msleep_interruptible(jiffies_to_msecs | 2782 | msleep_interruptible(jiffies_to_msecs |
2851 | (info->close_delay)); | 2783 | (info->close_delay)); |
2852 | } | 2784 | } |
2853 | wake_up_interruptible(&info->open_wait); | 2785 | wake_up_interruptible(&info->open_wait); |
2854 | CY_LOCK(info, flags); | 2786 | spin_lock_irqsave(&card->card_lock, flags); |
2855 | } | 2787 | } |
2856 | info->flags &= ~(ASYNC_NORMAL_ACTIVE | ASYNC_CLOSING); | 2788 | info->flags &= ~(ASYNC_NORMAL_ACTIVE | ASYNC_CLOSING); |
2857 | wake_up_interruptible(&info->close_wait); | 2789 | wake_up_interruptible(&info->close_wait); |
2858 | 2790 | ||
2859 | #ifdef CY_DEBUG_OTHER | 2791 | #ifdef CY_DEBUG_OTHER |
2860 | printk(" cyc:cy_close done\n"); | 2792 | printk(KERN_DEBUG "cyc:cy_close done\n"); |
2861 | #endif | 2793 | #endif |
2862 | 2794 | ||
2863 | CY_UNLOCK(info, flags); | 2795 | spin_unlock_irqrestore(&card->card_lock, flags); |
2864 | } /* cy_close */ | 2796 | } /* cy_close */ |
2865 | 2797 | ||
2866 | /* This routine gets called when tty_write has put something into | 2798 | /* This routine gets called when tty_write has put something into |
@@ -2878,12 +2810,12 @@ static void cy_close(struct tty_struct *tty, struct file *filp) | |||
2878 | */ | 2810 | */ |
2879 | static int cy_write(struct tty_struct *tty, const unsigned char *buf, int count) | 2811 | static int cy_write(struct tty_struct *tty, const unsigned char *buf, int count) |
2880 | { | 2812 | { |
2881 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 2813 | struct cyclades_port *info = tty->driver_data; |
2882 | unsigned long flags; | 2814 | unsigned long flags; |
2883 | int c, ret = 0; | 2815 | int c, ret = 0; |
2884 | 2816 | ||
2885 | #ifdef CY_DEBUG_IO | 2817 | #ifdef CY_DEBUG_IO |
2886 | printk("cyc:cy_write ttyC%d\n", info->line); /* */ | 2818 | printk(KERN_DEBUG "cyc:cy_write ttyC%d\n", info->line); |
2887 | #endif | 2819 | #endif |
2888 | 2820 | ||
2889 | if (serial_paranoia_check(info, tty->name, "cy_write")) { | 2821 | if (serial_paranoia_check(info, tty->name, "cy_write")) { |
@@ -2893,7 +2825,7 @@ static int cy_write(struct tty_struct *tty, const unsigned char *buf, int count) | |||
2893 | if (!info->xmit_buf) | 2825 | if (!info->xmit_buf) |
2894 | return 0; | 2826 | return 0; |
2895 | 2827 | ||
2896 | CY_LOCK(info, flags); | 2828 | spin_lock_irqsave(&info->card->card_lock, flags); |
2897 | while (1) { | 2829 | while (1) { |
2898 | c = min(count, min((int)(SERIAL_XMIT_SIZE - info->xmit_cnt - 1), | 2830 | c = min(count, min((int)(SERIAL_XMIT_SIZE - info->xmit_cnt - 1), |
2899 | (int)(SERIAL_XMIT_SIZE - info->xmit_head))); | 2831 | (int)(SERIAL_XMIT_SIZE - info->xmit_head))); |
@@ -2909,7 +2841,7 @@ static int cy_write(struct tty_struct *tty, const unsigned char *buf, int count) | |||
2909 | count -= c; | 2841 | count -= c; |
2910 | ret += c; | 2842 | ret += c; |
2911 | } | 2843 | } |
2912 | CY_UNLOCK(info, flags); | 2844 | spin_unlock_irqrestore(&info->card->card_lock, flags); |
2913 | 2845 | ||
2914 | info->idle_stats.xmit_bytes += ret; | 2846 | info->idle_stats.xmit_bytes += ret; |
2915 | info->idle_stats.xmit_idle = jiffies; | 2847 | info->idle_stats.xmit_idle = jiffies; |
@@ -2929,11 +2861,11 @@ static int cy_write(struct tty_struct *tty, const unsigned char *buf, int count) | |||
2929 | */ | 2861 | */ |
2930 | static void cy_put_char(struct tty_struct *tty, unsigned char ch) | 2862 | static void cy_put_char(struct tty_struct *tty, unsigned char ch) |
2931 | { | 2863 | { |
2932 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 2864 | struct cyclades_port *info = tty->driver_data; |
2933 | unsigned long flags; | 2865 | unsigned long flags; |
2934 | 2866 | ||
2935 | #ifdef CY_DEBUG_IO | 2867 | #ifdef CY_DEBUG_IO |
2936 | printk("cyc:cy_put_char ttyC%d\n", info->line); | 2868 | printk(KERN_DEBUG "cyc:cy_put_char ttyC%d\n", info->line); |
2937 | #endif | 2869 | #endif |
2938 | 2870 | ||
2939 | if (serial_paranoia_check(info, tty->name, "cy_put_char")) | 2871 | if (serial_paranoia_check(info, tty->name, "cy_put_char")) |
@@ -2942,9 +2874,9 @@ static void cy_put_char(struct tty_struct *tty, unsigned char ch) | |||
2942 | if (!info->xmit_buf) | 2874 | if (!info->xmit_buf) |
2943 | return; | 2875 | return; |
2944 | 2876 | ||
2945 | CY_LOCK(info, flags); | 2877 | spin_lock_irqsave(&info->card->card_lock, flags); |
2946 | if (info->xmit_cnt >= (int)(SERIAL_XMIT_SIZE - 1)) { | 2878 | if (info->xmit_cnt >= (int)(SERIAL_XMIT_SIZE - 1)) { |
2947 | CY_UNLOCK(info, flags); | 2879 | spin_unlock_irqrestore(&info->card->card_lock, flags); |
2948 | return; | 2880 | return; |
2949 | } | 2881 | } |
2950 | 2882 | ||
@@ -2953,7 +2885,7 @@ static void cy_put_char(struct tty_struct *tty, unsigned char ch) | |||
2953 | info->xmit_cnt++; | 2885 | info->xmit_cnt++; |
2954 | info->idle_stats.xmit_bytes++; | 2886 | info->idle_stats.xmit_bytes++; |
2955 | info->idle_stats.xmit_idle = jiffies; | 2887 | info->idle_stats.xmit_idle = jiffies; |
2956 | CY_UNLOCK(info, flags); | 2888 | spin_unlock_irqrestore(&info->card->card_lock, flags); |
2957 | } /* cy_put_char */ | 2889 | } /* cy_put_char */ |
2958 | 2890 | ||
2959 | /* | 2891 | /* |
@@ -2962,10 +2894,10 @@ static void cy_put_char(struct tty_struct *tty, unsigned char ch) | |||
2962 | */ | 2894 | */ |
2963 | static void cy_flush_chars(struct tty_struct *tty) | 2895 | static void cy_flush_chars(struct tty_struct *tty) |
2964 | { | 2896 | { |
2965 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 2897 | struct cyclades_port *info = tty->driver_data; |
2966 | 2898 | ||
2967 | #ifdef CY_DEBUG_IO | 2899 | #ifdef CY_DEBUG_IO |
2968 | printk("cyc:cy_flush_chars ttyC%d\n", info->line); /* */ | 2900 | printk(KERN_DEBUG "cyc:cy_flush_chars ttyC%d\n", info->line); |
2969 | #endif | 2901 | #endif |
2970 | 2902 | ||
2971 | if (serial_paranoia_check(info, tty->name, "cy_flush_chars")) | 2903 | if (serial_paranoia_check(info, tty->name, "cy_flush_chars")) |
@@ -2986,11 +2918,11 @@ static void cy_flush_chars(struct tty_struct *tty) | |||
2986 | */ | 2918 | */ |
2987 | static int cy_write_room(struct tty_struct *tty) | 2919 | static int cy_write_room(struct tty_struct *tty) |
2988 | { | 2920 | { |
2989 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 2921 | struct cyclades_port *info = tty->driver_data; |
2990 | int ret; | 2922 | int ret; |
2991 | 2923 | ||
2992 | #ifdef CY_DEBUG_IO | 2924 | #ifdef CY_DEBUG_IO |
2993 | printk("cyc:cy_write_room ttyC%d\n", info->line); /* */ | 2925 | printk(KERN_DEBUG "cyc:cy_write_room ttyC%d\n", info->line); |
2994 | #endif | 2926 | #endif |
2995 | 2927 | ||
2996 | if (serial_paranoia_check(info, tty->name, "cy_write_room")) | 2928 | if (serial_paranoia_check(info, tty->name, "cy_write_room")) |
@@ -3003,46 +2935,49 @@ static int cy_write_room(struct tty_struct *tty) | |||
3003 | 2935 | ||
3004 | static int cy_chars_in_buffer(struct tty_struct *tty) | 2936 | static int cy_chars_in_buffer(struct tty_struct *tty) |
3005 | { | 2937 | { |
3006 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 2938 | struct cyclades_card *card; |
3007 | int card, channel; | 2939 | struct cyclades_port *info = tty->driver_data; |
2940 | int channel; | ||
3008 | 2941 | ||
3009 | if (serial_paranoia_check(info, tty->name, "cy_chars_in_buffer")) | 2942 | if (serial_paranoia_check(info, tty->name, "cy_chars_in_buffer")) |
3010 | return 0; | 2943 | return 0; |
3011 | 2944 | ||
3012 | card = info->card; | 2945 | card = info->card; |
3013 | channel = (info->line) - (cy_card[card].first_line); | 2946 | channel = (info->line) - (card->first_line); |
3014 | 2947 | ||
3015 | #ifdef Z_EXT_CHARS_IN_BUFFER | 2948 | #ifdef Z_EXT_CHARS_IN_BUFFER |
3016 | if (!IS_CYC_Z(cy_card[card])) { | 2949 | if (!IS_CYC_Z(cy_card[card])) { |
3017 | #endif /* Z_EXT_CHARS_IN_BUFFER */ | 2950 | #endif /* Z_EXT_CHARS_IN_BUFFER */ |
3018 | #ifdef CY_DEBUG_IO | 2951 | #ifdef CY_DEBUG_IO |
3019 | printk("cyc:cy_chars_in_buffer ttyC%d %d\n", info->line, info->xmit_cnt); /* */ | 2952 | printk(KERN_DEBUG "cyc:cy_chars_in_buffer ttyC%d %d\n", |
2953 | info->line, info->xmit_cnt); | ||
3020 | #endif | 2954 | #endif |
3021 | return info->xmit_cnt; | 2955 | return info->xmit_cnt; |
3022 | #ifdef Z_EXT_CHARS_IN_BUFFER | 2956 | #ifdef Z_EXT_CHARS_IN_BUFFER |
3023 | } else { | 2957 | } else { |
3024 | static volatile struct FIRM_ID *firm_id; | 2958 | static struct FIRM_ID *firm_id; |
3025 | static volatile struct ZFW_CTRL *zfw_ctrl; | 2959 | static struct ZFW_CTRL *zfw_ctrl; |
3026 | static volatile struct CH_CTRL *ch_ctrl; | 2960 | static struct CH_CTRL *ch_ctrl; |
3027 | static volatile struct BUF_CTRL *buf_ctrl; | 2961 | static struct BUF_CTRL *buf_ctrl; |
3028 | int char_count; | 2962 | int char_count; |
3029 | volatile uclong tx_put, tx_get, tx_bufsize; | 2963 | __u32 tx_put, tx_get, tx_bufsize; |
3030 | 2964 | ||
3031 | firm_id = cy_card[card].base_addr + ID_ADDRESS; | 2965 | firm_id = card->base_addr + ID_ADDRESS; |
3032 | zfw_ctrl = cy_card[card].base_addr + | 2966 | zfw_ctrl = card->base_addr + |
3033 | (cy_readl(&firm_id->zfwctrl_addr) & 0xfffff); | 2967 | (readl(&firm_id->zfwctrl_addr) & 0xfffff); |
3034 | ch_ctrl = &(zfw_ctrl->ch_ctrl[channel]); | 2968 | ch_ctrl = &(zfw_ctrl->ch_ctrl[channel]); |
3035 | buf_ctrl = &(zfw_ctrl->buf_ctrl[channel]); | 2969 | buf_ctrl = &(zfw_ctrl->buf_ctrl[channel]); |
3036 | 2970 | ||
3037 | tx_get = cy_readl(&buf_ctrl->tx_get); | 2971 | tx_get = readl(&buf_ctrl->tx_get); |
3038 | tx_put = cy_readl(&buf_ctrl->tx_put); | 2972 | tx_put = readl(&buf_ctrl->tx_put); |
3039 | tx_bufsize = cy_readl(&buf_ctrl->tx_bufsize); | 2973 | tx_bufsize = readl(&buf_ctrl->tx_bufsize); |
3040 | if (tx_put >= tx_get) | 2974 | if (tx_put >= tx_get) |
3041 | char_count = tx_put - tx_get; | 2975 | char_count = tx_put - tx_get; |
3042 | else | 2976 | else |
3043 | char_count = tx_put - tx_get + tx_bufsize; | 2977 | char_count = tx_put - tx_get + tx_bufsize; |
3044 | #ifdef CY_DEBUG_IO | 2978 | #ifdef CY_DEBUG_IO |
3045 | printk("cyc:cy_chars_in_buffer ttyC%d %d\n", info->line, info->xmit_cnt + char_count); /* */ | 2979 | printk(KERN_DEBUG "cyc:cy_chars_in_buffer ttyC%d %d\n", |
2980 | info->line, info->xmit_cnt + char_count); | ||
3046 | #endif | 2981 | #endif |
3047 | return info->xmit_cnt + char_count; | 2982 | return info->xmit_cnt + char_count; |
3048 | } | 2983 | } |
@@ -3055,10 +2990,10 @@ static int cy_chars_in_buffer(struct tty_struct *tty) | |||
3055 | * ------------------------------------------------------------ | 2990 | * ------------------------------------------------------------ |
3056 | */ | 2991 | */ |
3057 | 2992 | ||
3058 | static void cyy_baud_calc(struct cyclades_port *info, uclong baud) | 2993 | static void cyy_baud_calc(struct cyclades_port *info, __u32 baud) |
3059 | { | 2994 | { |
3060 | int co, co_val, bpr; | 2995 | int co, co_val, bpr; |
3061 | uclong cy_clock = ((info->chip_rev >= CD1400_REV_J) ? 60000000 : | 2996 | __u32 cy_clock = ((info->chip_rev >= CD1400_REV_J) ? 60000000 : |
3062 | 25000000); | 2997 | 25000000); |
3063 | 2998 | ||
3064 | if (baud == 0) { | 2999 | if (baud == 0) { |
@@ -3086,9 +3021,10 @@ static void cyy_baud_calc(struct cyclades_port *info, uclong baud) | |||
3086 | */ | 3021 | */ |
3087 | static void set_line_char(struct cyclades_port *info) | 3022 | static void set_line_char(struct cyclades_port *info) |
3088 | { | 3023 | { |
3024 | struct cyclades_card *card; | ||
3089 | unsigned long flags; | 3025 | unsigned long flags; |
3090 | void __iomem *base_addr; | 3026 | void __iomem *base_addr; |
3091 | int card, chip, channel, index; | 3027 | int chip, channel, index; |
3092 | unsigned cflag, iflag; | 3028 | unsigned cflag, iflag; |
3093 | unsigned short chip_number; | 3029 | unsigned short chip_number; |
3094 | int baud, baud_rate = 0; | 3030 | int baud, baud_rate = 0; |
@@ -3118,12 +3054,12 @@ static void set_line_char(struct cyclades_port *info) | |||
3118 | } | 3054 | } |
3119 | 3055 | ||
3120 | card = info->card; | 3056 | card = info->card; |
3121 | channel = (info->line) - (cy_card[card].first_line); | 3057 | channel = info->line - card->first_line; |
3122 | chip_number = channel / 4; | 3058 | chip_number = channel / 4; |
3123 | 3059 | ||
3124 | if (!IS_CYC_Z(cy_card[card])) { | 3060 | if (!IS_CYC_Z(*card)) { |
3125 | 3061 | ||
3126 | index = cy_card[card].bus_index; | 3062 | index = card->bus_index; |
3127 | 3063 | ||
3128 | /* baud rate */ | 3064 | /* baud rate */ |
3129 | baud = tty_get_baud_rate(info->tty); | 3065 | baud = tty_get_baud_rate(info->tty); |
@@ -3241,10 +3177,9 @@ static void set_line_char(struct cyclades_port *info) | |||
3241 | 3177 | ||
3242 | chip = channel >> 2; | 3178 | chip = channel >> 2; |
3243 | channel &= 0x03; | 3179 | channel &= 0x03; |
3244 | base_addr = cy_card[card].base_addr + | 3180 | base_addr = card->base_addr + (cy_chip_offset[chip] << index); |
3245 | (cy_chip_offset[chip] << index); | ||
3246 | 3181 | ||
3247 | CY_LOCK(info, flags); | 3182 | spin_lock_irqsave(&card->card_lock, flags); |
3248 | cy_writeb(base_addr + (CyCAR << index), (u_char) channel); | 3183 | cy_writeb(base_addr + (CyCAR << index), (u_char) channel); |
3249 | 3184 | ||
3250 | /* tx and rx baud rate */ | 3185 | /* tx and rx baud rate */ |
@@ -3276,8 +3211,7 @@ static void set_line_char(struct cyclades_port *info) | |||
3276 | if (C_CLOCAL(info->tty)) { | 3211 | if (C_CLOCAL(info->tty)) { |
3277 | /* without modem intr */ | 3212 | /* without modem intr */ |
3278 | cy_writeb(base_addr + (CySRER << index), | 3213 | cy_writeb(base_addr + (CySRER << index), |
3279 | cy_readb(base_addr + | 3214 | readb(base_addr + (CySRER << index)) | CyMdmCh); |
3280 | (CySRER << index)) | CyMdmCh); | ||
3281 | /* act on 1->0 modem transitions */ | 3215 | /* act on 1->0 modem transitions */ |
3282 | if ((cflag & CRTSCTS) && info->rflow) { | 3216 | if ((cflag & CRTSCTS) && info->rflow) { |
3283 | cy_writeb(base_addr + (CyMCOR1 << index), | 3217 | cy_writeb(base_addr + (CyMCOR1 << index), |
@@ -3291,7 +3225,7 @@ static void set_line_char(struct cyclades_port *info) | |||
3291 | } else { | 3225 | } else { |
3292 | /* without modem intr */ | 3226 | /* without modem intr */ |
3293 | cy_writeb(base_addr + (CySRER << index), | 3227 | cy_writeb(base_addr + (CySRER << index), |
3294 | cy_readb(base_addr + | 3228 | readb(base_addr + |
3295 | (CySRER << index)) | CyMdmCh); | 3229 | (CySRER << index)) | CyMdmCh); |
3296 | /* act on 1->0 modem transitions */ | 3230 | /* act on 1->0 modem transitions */ |
3297 | if ((cflag & CRTSCTS) && info->rflow) { | 3231 | if ((cflag & CRTSCTS) && info->rflow) { |
@@ -3316,10 +3250,10 @@ static void set_line_char(struct cyclades_port *info) | |||
3316 | ~CyDTR); | 3250 | ~CyDTR); |
3317 | } | 3251 | } |
3318 | #ifdef CY_DEBUG_DTR | 3252 | #ifdef CY_DEBUG_DTR |
3319 | printk("cyc:set_line_char dropping DTR\n"); | 3253 | printk(KERN_DEBUG "cyc:set_line_char dropping DTR\n"); |
3320 | printk(" status: 0x%x, 0x%x\n", | 3254 | printk(KERN_DEBUG " status: 0x%x, 0x%x\n", |
3321 | cy_readb(base_addr + (CyMSVR1 << index)), | 3255 | readb(base_addr + (CyMSVR1 << index)), |
3322 | cy_readb(base_addr + (CyMSVR2 << index))); | 3256 | readb(base_addr + (CyMSVR2 << index))); |
3323 | #endif | 3257 | #endif |
3324 | } else { | 3258 | } else { |
3325 | if (info->rtsdtr_inv) { | 3259 | if (info->rtsdtr_inv) { |
@@ -3330,17 +3264,17 @@ static void set_line_char(struct cyclades_port *info) | |||
3330 | CyDTR); | 3264 | CyDTR); |
3331 | } | 3265 | } |
3332 | #ifdef CY_DEBUG_DTR | 3266 | #ifdef CY_DEBUG_DTR |
3333 | printk("cyc:set_line_char raising DTR\n"); | 3267 | printk(KERN_DEBUG "cyc:set_line_char raising DTR\n"); |
3334 | printk(" status: 0x%x, 0x%x\n", | 3268 | printk(KERN_DEBUG " status: 0x%x, 0x%x\n", |
3335 | cy_readb(base_addr + (CyMSVR1 << index)), | 3269 | readb(base_addr + (CyMSVR1 << index)), |
3336 | cy_readb(base_addr + (CyMSVR2 << index))); | 3270 | readb(base_addr + (CyMSVR2 << index))); |
3337 | #endif | 3271 | #endif |
3338 | } | 3272 | } |
3339 | 3273 | ||
3340 | if (info->tty) { | 3274 | if (info->tty) { |
3341 | clear_bit(TTY_IO_ERROR, &info->tty->flags); | 3275 | clear_bit(TTY_IO_ERROR, &info->tty->flags); |
3342 | } | 3276 | } |
3343 | CY_UNLOCK(info, flags); | 3277 | spin_unlock_irqrestore(&card->card_lock, flags); |
3344 | 3278 | ||
3345 | } else { | 3279 | } else { |
3346 | struct FIRM_ID __iomem *firm_id; | 3280 | struct FIRM_ID __iomem *firm_id; |
@@ -3348,16 +3282,16 @@ static void set_line_char(struct cyclades_port *info) | |||
3348 | struct BOARD_CTRL __iomem *board_ctrl; | 3282 | struct BOARD_CTRL __iomem *board_ctrl; |
3349 | struct CH_CTRL __iomem *ch_ctrl; | 3283 | struct CH_CTRL __iomem *ch_ctrl; |
3350 | struct BUF_CTRL __iomem *buf_ctrl; | 3284 | struct BUF_CTRL __iomem *buf_ctrl; |
3351 | uclong sw_flow; | 3285 | __u32 sw_flow; |
3352 | int retval; | 3286 | int retval; |
3353 | 3287 | ||
3354 | firm_id = cy_card[card].base_addr + ID_ADDRESS; | 3288 | firm_id = card->base_addr + ID_ADDRESS; |
3355 | if (!ISZLOADED(cy_card[card])) { | 3289 | if (!ISZLOADED(*card)) { |
3356 | return; | 3290 | return; |
3357 | } | 3291 | } |
3358 | 3292 | ||
3359 | zfw_ctrl = cy_card[card].base_addr + | 3293 | zfw_ctrl = card->base_addr + |
3360 | (cy_readl(&firm_id->zfwctrl_addr) & 0xfffff); | 3294 | (readl(&firm_id->zfwctrl_addr) & 0xfffff); |
3361 | board_ctrl = &zfw_ctrl->board_ctrl; | 3295 | board_ctrl = &zfw_ctrl->board_ctrl; |
3362 | ch_ctrl = &(zfw_ctrl->ch_ctrl[channel]); | 3296 | ch_ctrl = &(zfw_ctrl->ch_ctrl[channel]); |
3363 | buf_ctrl = &zfw_ctrl->buf_ctrl[channel]; | 3297 | buf_ctrl = &zfw_ctrl->buf_ctrl[channel]; |
@@ -3408,10 +3342,10 @@ static void set_line_char(struct cyclades_port *info) | |||
3408 | } | 3342 | } |
3409 | if (cflag & CSTOPB) { | 3343 | if (cflag & CSTOPB) { |
3410 | cy_writel(&ch_ctrl->comm_data_l, | 3344 | cy_writel(&ch_ctrl->comm_data_l, |
3411 | cy_readl(&ch_ctrl->comm_data_l) | C_DL_2STOP); | 3345 | readl(&ch_ctrl->comm_data_l) | C_DL_2STOP); |
3412 | } else { | 3346 | } else { |
3413 | cy_writel(&ch_ctrl->comm_data_l, | 3347 | cy_writel(&ch_ctrl->comm_data_l, |
3414 | cy_readl(&ch_ctrl->comm_data_l) | C_DL_1STOP); | 3348 | readl(&ch_ctrl->comm_data_l) | C_DL_1STOP); |
3415 | } | 3349 | } |
3416 | if (cflag & PARENB) { | 3350 | if (cflag & PARENB) { |
3417 | if (cflag & PARODD) { | 3351 | if (cflag & PARODD) { |
@@ -3426,12 +3360,10 @@ static void set_line_char(struct cyclades_port *info) | |||
3426 | /* CTS flow control flag */ | 3360 | /* CTS flow control flag */ |
3427 | if (cflag & CRTSCTS) { | 3361 | if (cflag & CRTSCTS) { |
3428 | cy_writel(&ch_ctrl->hw_flow, | 3362 | cy_writel(&ch_ctrl->hw_flow, |
3429 | cy_readl(&ch_ctrl-> | 3363 | readl(&ch_ctrl->hw_flow) | C_RS_CTS | C_RS_RTS); |
3430 | hw_flow) | C_RS_CTS | C_RS_RTS); | ||
3431 | } else { | 3364 | } else { |
3432 | cy_writel(&ch_ctrl->hw_flow, | 3365 | cy_writel(&ch_ctrl->hw_flow, readl(&ch_ctrl->hw_flow) & |
3433 | cy_readl(&ch_ctrl-> | 3366 | ~(C_RS_CTS | C_RS_RTS)); |
3434 | hw_flow) & ~(C_RS_CTS | C_RS_RTS)); | ||
3435 | } | 3367 | } |
3436 | /* As the HW flow control is done in firmware, the driver | 3368 | /* As the HW flow control is done in firmware, the driver |
3437 | doesn't need to care about it */ | 3369 | doesn't need to care about it */ |
@@ -3446,10 +3378,10 @@ static void set_line_char(struct cyclades_port *info) | |||
3446 | } | 3378 | } |
3447 | cy_writel(&ch_ctrl->sw_flow, sw_flow); | 3379 | cy_writel(&ch_ctrl->sw_flow, sw_flow); |
3448 | 3380 | ||
3449 | retval = cyz_issue_cmd(&cy_card[card], channel, C_CM_IOCTL, 0L); | 3381 | retval = cyz_issue_cmd(card, channel, C_CM_IOCTL, 0L); |
3450 | if (retval != 0) { | 3382 | if (retval != 0) { |
3451 | printk("cyc:set_line_char retval on ttyC%d was %x\n", | 3383 | printk(KERN_ERR "cyc:set_line_char retval on ttyC%d " |
3452 | info->line, retval); | 3384 | "was %x\n", info->line, retval); |
3453 | } | 3385 | } |
3454 | 3386 | ||
3455 | /* CD sensitivity */ | 3387 | /* CD sensitivity */ |
@@ -3461,22 +3393,22 @@ static void set_line_char(struct cyclades_port *info) | |||
3461 | 3393 | ||
3462 | if (baud == 0) { /* baud rate is zero, turn off line */ | 3394 | if (baud == 0) { /* baud rate is zero, turn off line */ |
3463 | cy_writel(&ch_ctrl->rs_control, | 3395 | cy_writel(&ch_ctrl->rs_control, |
3464 | cy_readl(&ch_ctrl->rs_control) & ~C_RS_DTR); | 3396 | readl(&ch_ctrl->rs_control) & ~C_RS_DTR); |
3465 | #ifdef CY_DEBUG_DTR | 3397 | #ifdef CY_DEBUG_DTR |
3466 | printk("cyc:set_line_char dropping Z DTR\n"); | 3398 | printk(KERN_DEBUG "cyc:set_line_char dropping Z DTR\n"); |
3467 | #endif | 3399 | #endif |
3468 | } else { | 3400 | } else { |
3469 | cy_writel(&ch_ctrl->rs_control, | 3401 | cy_writel(&ch_ctrl->rs_control, |
3470 | cy_readl(&ch_ctrl->rs_control) | C_RS_DTR); | 3402 | readl(&ch_ctrl->rs_control) | C_RS_DTR); |
3471 | #ifdef CY_DEBUG_DTR | 3403 | #ifdef CY_DEBUG_DTR |
3472 | printk("cyc:set_line_char raising Z DTR\n"); | 3404 | printk(KERN_DEBUG "cyc:set_line_char raising Z DTR\n"); |
3473 | #endif | 3405 | #endif |
3474 | } | 3406 | } |
3475 | 3407 | ||
3476 | retval = cyz_issue_cmd(&cy_card[card], channel, C_CM_IOCTLM,0L); | 3408 | retval = cyz_issue_cmd(card, channel, C_CM_IOCTLM,0L); |
3477 | if (retval != 0) { | 3409 | if (retval != 0) { |
3478 | printk("cyc:set_line_char(2) retval on ttyC%d was %x\n", | 3410 | printk(KERN_ERR "cyc:set_line_char(2) retval on ttyC%d " |
3479 | info->line, retval); | 3411 | "was %x\n", info->line, retval); |
3480 | } | 3412 | } |
3481 | 3413 | ||
3482 | if (info->tty) { | 3414 | if (info->tty) { |
@@ -3490,14 +3422,15 @@ get_serial_info(struct cyclades_port *info, | |||
3490 | struct serial_struct __user * retinfo) | 3422 | struct serial_struct __user * retinfo) |
3491 | { | 3423 | { |
3492 | struct serial_struct tmp; | 3424 | struct serial_struct tmp; |
3493 | struct cyclades_card *cinfo = &cy_card[info->card]; | 3425 | struct cyclades_card *cinfo = info->card; |
3494 | 3426 | ||
3495 | if (!retinfo) | 3427 | if (!retinfo) |
3496 | return -EFAULT; | 3428 | return -EFAULT; |
3497 | memset(&tmp, 0, sizeof(tmp)); | 3429 | memset(&tmp, 0, sizeof(tmp)); |
3498 | tmp.type = info->type; | 3430 | tmp.type = info->type; |
3499 | tmp.line = info->line; | 3431 | tmp.line = info->line; |
3500 | tmp.port = info->card * 0x100 + info->line - cinfo->first_line; | 3432 | tmp.port = (info->card - cy_card) * 0x100 + info->line - |
3433 | cinfo->first_line; | ||
3501 | tmp.irq = cinfo->irq; | 3434 | tmp.irq = cinfo->irq; |
3502 | tmp.flags = info->flags; | 3435 | tmp.flags = info->flags; |
3503 | tmp.close_delay = info->close_delay; | 3436 | tmp.close_delay = info->close_delay; |
@@ -3566,25 +3499,25 @@ check_and_exit: | |||
3566 | */ | 3499 | */ |
3567 | static int get_lsr_info(struct cyclades_port *info, unsigned int __user * value) | 3500 | static int get_lsr_info(struct cyclades_port *info, unsigned int __user * value) |
3568 | { | 3501 | { |
3569 | int card, chip, channel, index; | 3502 | struct cyclades_card *card; |
3503 | int chip, channel, index; | ||
3570 | unsigned char status; | 3504 | unsigned char status; |
3571 | unsigned int result; | 3505 | unsigned int result; |
3572 | unsigned long flags; | 3506 | unsigned long flags; |
3573 | void __iomem *base_addr; | 3507 | void __iomem *base_addr; |
3574 | 3508 | ||
3575 | card = info->card; | 3509 | card = info->card; |
3576 | channel = (info->line) - (cy_card[card].first_line); | 3510 | channel = (info->line) - (card->first_line); |
3577 | if (!IS_CYC_Z(cy_card[card])) { | 3511 | if (!IS_CYC_Z(*card)) { |
3578 | chip = channel >> 2; | 3512 | chip = channel >> 2; |
3579 | channel &= 0x03; | 3513 | channel &= 0x03; |
3580 | index = cy_card[card].bus_index; | 3514 | index = card->bus_index; |
3581 | base_addr = | 3515 | base_addr = card->base_addr + (cy_chip_offset[chip] << index); |
3582 | cy_card[card].base_addr + (cy_chip_offset[chip] << index); | ||
3583 | 3516 | ||
3584 | CY_LOCK(info, flags); | 3517 | spin_lock_irqsave(&card->card_lock, flags); |
3585 | status = cy_readb(base_addr + (CySRER << index)) & | 3518 | status = readb(base_addr + (CySRER << index)) & |
3586 | (CyTxRdy | CyTxMpty); | 3519 | (CyTxRdy | CyTxMpty); |
3587 | CY_UNLOCK(info, flags); | 3520 | spin_unlock_irqrestore(&card->card_lock, flags); |
3588 | result = (status ? 0 : TIOCSER_TEMT); | 3521 | result = (status ? 0 : TIOCSER_TEMT); |
3589 | } else { | 3522 | } else { |
3590 | /* Not supported yet */ | 3523 | /* Not supported yet */ |
@@ -3595,8 +3528,9 @@ static int get_lsr_info(struct cyclades_port *info, unsigned int __user * value) | |||
3595 | 3528 | ||
3596 | static int cy_tiocmget(struct tty_struct *tty, struct file *file) | 3529 | static int cy_tiocmget(struct tty_struct *tty, struct file *file) |
3597 | { | 3530 | { |
3598 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 3531 | struct cyclades_port *info = tty->driver_data; |
3599 | int card, chip, channel, index; | 3532 | struct cyclades_card *card; |
3533 | int chip, channel, index; | ||
3600 | void __iomem *base_addr; | 3534 | void __iomem *base_addr; |
3601 | unsigned long flags; | 3535 | unsigned long flags; |
3602 | unsigned char status; | 3536 | unsigned char status; |
@@ -3611,19 +3545,18 @@ static int cy_tiocmget(struct tty_struct *tty, struct file *file) | |||
3611 | return -ENODEV; | 3545 | return -ENODEV; |
3612 | 3546 | ||
3613 | card = info->card; | 3547 | card = info->card; |
3614 | channel = (info->line) - (cy_card[card].first_line); | 3548 | channel = info->line - card->first_line; |
3615 | if (!IS_CYC_Z(cy_card[card])) { | 3549 | if (!IS_CYC_Z(*card)) { |
3616 | chip = channel >> 2; | 3550 | chip = channel >> 2; |
3617 | channel &= 0x03; | 3551 | channel &= 0x03; |
3618 | index = cy_card[card].bus_index; | 3552 | index = card->bus_index; |
3619 | base_addr = | 3553 | base_addr = card->base_addr + (cy_chip_offset[chip] << index); |
3620 | cy_card[card].base_addr + (cy_chip_offset[chip] << index); | ||
3621 | 3554 | ||
3622 | CY_LOCK(info, flags); | 3555 | spin_lock_irqsave(&card->card_lock, flags); |
3623 | cy_writeb(base_addr + (CyCAR << index), (u_char) channel); | 3556 | cy_writeb(base_addr + (CyCAR << index), (u_char) channel); |
3624 | status = cy_readb(base_addr + (CyMSVR1 << index)); | 3557 | status = readb(base_addr + (CyMSVR1 << index)); |
3625 | status |= cy_readb(base_addr + (CyMSVR2 << index)); | 3558 | status |= readb(base_addr + (CyMSVR2 << index)); |
3626 | CY_UNLOCK(info, flags); | 3559 | spin_unlock_irqrestore(&card->card_lock, flags); |
3627 | 3560 | ||
3628 | if (info->rtsdtr_inv) { | 3561 | if (info->rtsdtr_inv) { |
3629 | result = ((status & CyRTS) ? TIOCM_DTR : 0) | | 3562 | result = ((status & CyRTS) ? TIOCM_DTR : 0) | |
@@ -3637,19 +3570,14 @@ static int cy_tiocmget(struct tty_struct *tty, struct file *file) | |||
3637 | ((status & CyDSR) ? TIOCM_DSR : 0) | | 3570 | ((status & CyDSR) ? TIOCM_DSR : 0) | |
3638 | ((status & CyCTS) ? TIOCM_CTS : 0); | 3571 | ((status & CyCTS) ? TIOCM_CTS : 0); |
3639 | } else { | 3572 | } else { |
3640 | base_addr = cy_card[card].base_addr; | 3573 | base_addr = card->base_addr; |
3641 | 3574 | firm_id = card->base_addr + ID_ADDRESS; | |
3642 | if (cy_card[card].num_chips != -1) { | 3575 | if (ISZLOADED(*card)) { |
3643 | return -EINVAL; | 3576 | zfw_ctrl = card->base_addr + |
3644 | } | 3577 | (readl(&firm_id->zfwctrl_addr) & 0xfffff); |
3645 | |||
3646 | firm_id = cy_card[card].base_addr + ID_ADDRESS; | ||
3647 | if (ISZLOADED(cy_card[card])) { | ||
3648 | zfw_ctrl = cy_card[card].base_addr + | ||
3649 | (cy_readl(&firm_id->zfwctrl_addr) & 0xfffff); | ||
3650 | board_ctrl = &zfw_ctrl->board_ctrl; | 3578 | board_ctrl = &zfw_ctrl->board_ctrl; |
3651 | ch_ctrl = zfw_ctrl->ch_ctrl; | 3579 | ch_ctrl = zfw_ctrl->ch_ctrl; |
3652 | lstatus = cy_readl(&ch_ctrl[channel].rs_status); | 3580 | lstatus = readl(&ch_ctrl[channel].rs_status); |
3653 | result = ((lstatus & C_RS_RTS) ? TIOCM_RTS : 0) | | 3581 | result = ((lstatus & C_RS_RTS) ? TIOCM_RTS : 0) | |
3654 | ((lstatus & C_RS_DTR) ? TIOCM_DTR : 0) | | 3582 | ((lstatus & C_RS_DTR) ? TIOCM_DTR : 0) | |
3655 | ((lstatus & C_RS_DCD) ? TIOCM_CAR : 0) | | 3583 | ((lstatus & C_RS_DCD) ? TIOCM_CAR : 0) | |
@@ -3669,8 +3597,9 @@ static int | |||
3669 | cy_tiocmset(struct tty_struct *tty, struct file *file, | 3597 | cy_tiocmset(struct tty_struct *tty, struct file *file, |
3670 | unsigned int set, unsigned int clear) | 3598 | unsigned int set, unsigned int clear) |
3671 | { | 3599 | { |
3672 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 3600 | struct cyclades_port *info = tty->driver_data; |
3673 | int card, chip, channel, index; | 3601 | struct cyclades_card *card; |
3602 | int chip, channel, index; | ||
3674 | void __iomem *base_addr; | 3603 | void __iomem *base_addr; |
3675 | unsigned long flags; | 3604 | unsigned long flags; |
3676 | struct FIRM_ID __iomem *firm_id; | 3605 | struct FIRM_ID __iomem *firm_id; |
@@ -3683,16 +3612,15 @@ cy_tiocmset(struct tty_struct *tty, struct file *file, | |||
3683 | return -ENODEV; | 3612 | return -ENODEV; |
3684 | 3613 | ||
3685 | card = info->card; | 3614 | card = info->card; |
3686 | channel = (info->line) - (cy_card[card].first_line); | 3615 | channel = (info->line) - (card->first_line); |
3687 | if (!IS_CYC_Z(cy_card[card])) { | 3616 | if (!IS_CYC_Z(*card)) { |
3688 | chip = channel >> 2; | 3617 | chip = channel >> 2; |
3689 | channel &= 0x03; | 3618 | channel &= 0x03; |
3690 | index = cy_card[card].bus_index; | 3619 | index = card->bus_index; |
3691 | base_addr = | 3620 | base_addr = card->base_addr + (cy_chip_offset[chip] << index); |
3692 | cy_card[card].base_addr + (cy_chip_offset[chip] << index); | ||
3693 | 3621 | ||
3694 | if (set & TIOCM_RTS) { | 3622 | if (set & TIOCM_RTS) { |
3695 | CY_LOCK(info, flags); | 3623 | spin_lock_irqsave(&card->card_lock, flags); |
3696 | cy_writeb(base_addr + (CyCAR << index), | 3624 | cy_writeb(base_addr + (CyCAR << index), |
3697 | (u_char) channel); | 3625 | (u_char) channel); |
3698 | if (info->rtsdtr_inv) { | 3626 | if (info->rtsdtr_inv) { |
@@ -3702,10 +3630,10 @@ cy_tiocmset(struct tty_struct *tty, struct file *file, | |||
3702 | cy_writeb(base_addr + (CyMSVR1 << index), | 3630 | cy_writeb(base_addr + (CyMSVR1 << index), |
3703 | CyRTS); | 3631 | CyRTS); |
3704 | } | 3632 | } |
3705 | CY_UNLOCK(info, flags); | 3633 | spin_unlock_irqrestore(&card->card_lock, flags); |
3706 | } | 3634 | } |
3707 | if (clear & TIOCM_RTS) { | 3635 | if (clear & TIOCM_RTS) { |
3708 | CY_LOCK(info, flags); | 3636 | spin_lock_irqsave(&card->card_lock, flags); |
3709 | cy_writeb(base_addr + (CyCAR << index), | 3637 | cy_writeb(base_addr + (CyCAR << index), |
3710 | (u_char) channel); | 3638 | (u_char) channel); |
3711 | if (info->rtsdtr_inv) { | 3639 | if (info->rtsdtr_inv) { |
@@ -3715,10 +3643,10 @@ cy_tiocmset(struct tty_struct *tty, struct file *file, | |||
3715 | cy_writeb(base_addr + (CyMSVR1 << index), | 3643 | cy_writeb(base_addr + (CyMSVR1 << index), |
3716 | ~CyRTS); | 3644 | ~CyRTS); |
3717 | } | 3645 | } |
3718 | CY_UNLOCK(info, flags); | 3646 | spin_unlock_irqrestore(&card->card_lock, flags); |
3719 | } | 3647 | } |
3720 | if (set & TIOCM_DTR) { | 3648 | if (set & TIOCM_DTR) { |
3721 | CY_LOCK(info, flags); | 3649 | spin_lock_irqsave(&card->card_lock, flags); |
3722 | cy_writeb(base_addr + (CyCAR << index), | 3650 | cy_writeb(base_addr + (CyCAR << index), |
3723 | (u_char) channel); | 3651 | (u_char) channel); |
3724 | if (info->rtsdtr_inv) { | 3652 | if (info->rtsdtr_inv) { |
@@ -3729,15 +3657,15 @@ cy_tiocmset(struct tty_struct *tty, struct file *file, | |||
3729 | CyDTR); | 3657 | CyDTR); |
3730 | } | 3658 | } |
3731 | #ifdef CY_DEBUG_DTR | 3659 | #ifdef CY_DEBUG_DTR |
3732 | printk("cyc:set_modem_info raising DTR\n"); | 3660 | printk(KERN_DEBUG "cyc:set_modem_info raising DTR\n"); |
3733 | printk(" status: 0x%x, 0x%x\n", | 3661 | printk(KERN_DEBUG " status: 0x%x, 0x%x\n", |
3734 | cy_readb(base_addr + (CyMSVR1 << index)), | 3662 | readb(base_addr + (CyMSVR1 << index)), |
3735 | cy_readb(base_addr + (CyMSVR2 << index))); | 3663 | readb(base_addr + (CyMSVR2 << index))); |
3736 | #endif | 3664 | #endif |
3737 | CY_UNLOCK(info, flags); | 3665 | spin_unlock_irqrestore(&card->card_lock, flags); |
3738 | } | 3666 | } |
3739 | if (clear & TIOCM_DTR) { | 3667 | if (clear & TIOCM_DTR) { |
3740 | CY_LOCK(info, flags); | 3668 | spin_lock_irqsave(&card->card_lock, flags); |
3741 | cy_writeb(base_addr + (CyCAR << index), | 3669 | cy_writeb(base_addr + (CyCAR << index), |
3742 | (u_char) channel); | 3670 | (u_char) channel); |
3743 | if (info->rtsdtr_inv) { | 3671 | if (info->rtsdtr_inv) { |
@@ -3749,68 +3677,69 @@ cy_tiocmset(struct tty_struct *tty, struct file *file, | |||
3749 | } | 3677 | } |
3750 | 3678 | ||
3751 | #ifdef CY_DEBUG_DTR | 3679 | #ifdef CY_DEBUG_DTR |
3752 | printk("cyc:set_modem_info dropping DTR\n"); | 3680 | printk(KERN_DEBUG "cyc:set_modem_info dropping DTR\n"); |
3753 | printk(" status: 0x%x, 0x%x\n", | 3681 | printk(KERN_DEBUG " status: 0x%x, 0x%x\n", |
3754 | cy_readb(base_addr + (CyMSVR1 << index)), | 3682 | readb(base_addr + (CyMSVR1 << index)), |
3755 | cy_readb(base_addr + (CyMSVR2 << index))); | 3683 | readb(base_addr + (CyMSVR2 << index))); |
3756 | #endif | 3684 | #endif |
3757 | CY_UNLOCK(info, flags); | 3685 | spin_unlock_irqrestore(&card->card_lock, flags); |
3758 | } | 3686 | } |
3759 | } else { | 3687 | } else { |
3760 | base_addr = cy_card[card].base_addr; | 3688 | base_addr = card->base_addr; |
3761 | 3689 | ||
3762 | firm_id = cy_card[card].base_addr + ID_ADDRESS; | 3690 | firm_id = card->base_addr + ID_ADDRESS; |
3763 | if (ISZLOADED(cy_card[card])) { | 3691 | if (ISZLOADED(*card)) { |
3764 | zfw_ctrl = cy_card[card].base_addr + | 3692 | zfw_ctrl = card->base_addr + |
3765 | (cy_readl(&firm_id->zfwctrl_addr) & 0xfffff); | 3693 | (readl(&firm_id->zfwctrl_addr) & 0xfffff); |
3766 | board_ctrl = &zfw_ctrl->board_ctrl; | 3694 | board_ctrl = &zfw_ctrl->board_ctrl; |
3767 | ch_ctrl = zfw_ctrl->ch_ctrl; | 3695 | ch_ctrl = zfw_ctrl->ch_ctrl; |
3768 | 3696 | ||
3769 | if (set & TIOCM_RTS) { | 3697 | if (set & TIOCM_RTS) { |
3770 | CY_LOCK(info, flags); | 3698 | spin_lock_irqsave(&card->card_lock, flags); |
3771 | cy_writel(&ch_ctrl[channel].rs_control, | 3699 | cy_writel(&ch_ctrl[channel].rs_control, |
3772 | cy_readl(&ch_ctrl[channel]. | 3700 | readl(&ch_ctrl[channel].rs_control) | |
3773 | rs_control) | C_RS_RTS); | 3701 | C_RS_RTS); |
3774 | CY_UNLOCK(info, flags); | 3702 | spin_unlock_irqrestore(&card->card_lock, flags); |
3775 | } | 3703 | } |
3776 | if (clear & TIOCM_RTS) { | 3704 | if (clear & TIOCM_RTS) { |
3777 | CY_LOCK(info, flags); | 3705 | spin_lock_irqsave(&card->card_lock, flags); |
3778 | cy_writel(&ch_ctrl[channel].rs_control, | 3706 | cy_writel(&ch_ctrl[channel].rs_control, |
3779 | cy_readl(&ch_ctrl[channel]. | 3707 | readl(&ch_ctrl[channel].rs_control) & |
3780 | rs_control) & ~C_RS_RTS); | 3708 | ~C_RS_RTS); |
3781 | CY_UNLOCK(info, flags); | 3709 | spin_unlock_irqrestore(&card->card_lock, flags); |
3782 | } | 3710 | } |
3783 | if (set & TIOCM_DTR) { | 3711 | if (set & TIOCM_DTR) { |
3784 | CY_LOCK(info, flags); | 3712 | spin_lock_irqsave(&card->card_lock, flags); |
3785 | cy_writel(&ch_ctrl[channel].rs_control, | 3713 | cy_writel(&ch_ctrl[channel].rs_control, |
3786 | cy_readl(&ch_ctrl[channel]. | 3714 | readl(&ch_ctrl[channel].rs_control) | |
3787 | rs_control) | C_RS_DTR); | 3715 | C_RS_DTR); |
3788 | #ifdef CY_DEBUG_DTR | 3716 | #ifdef CY_DEBUG_DTR |
3789 | printk("cyc:set_modem_info raising Z DTR\n"); | 3717 | printk(KERN_DEBUG "cyc:set_modem_info raising " |
3718 | "Z DTR\n"); | ||
3790 | #endif | 3719 | #endif |
3791 | CY_UNLOCK(info, flags); | 3720 | spin_unlock_irqrestore(&card->card_lock, flags); |
3792 | } | 3721 | } |
3793 | if (clear & TIOCM_DTR) { | 3722 | if (clear & TIOCM_DTR) { |
3794 | CY_LOCK(info, flags); | 3723 | spin_lock_irqsave(&card->card_lock, flags); |
3795 | cy_writel(&ch_ctrl[channel].rs_control, | 3724 | cy_writel(&ch_ctrl[channel].rs_control, |
3796 | cy_readl(&ch_ctrl[channel]. | 3725 | readl(&ch_ctrl[channel].rs_control) & |
3797 | rs_control) & ~C_RS_DTR); | 3726 | ~C_RS_DTR); |
3798 | #ifdef CY_DEBUG_DTR | 3727 | #ifdef CY_DEBUG_DTR |
3799 | printk("cyc:set_modem_info clearing Z DTR\n"); | 3728 | printk(KERN_DEBUG "cyc:set_modem_info clearing " |
3729 | "Z DTR\n"); | ||
3800 | #endif | 3730 | #endif |
3801 | CY_UNLOCK(info, flags); | 3731 | spin_unlock_irqrestore(&card->card_lock, flags); |
3802 | } | 3732 | } |
3803 | } else { | 3733 | } else { |
3804 | return -ENODEV; | 3734 | return -ENODEV; |
3805 | } | 3735 | } |
3806 | CY_LOCK(info, flags); | 3736 | spin_lock_irqsave(&card->card_lock, flags); |
3807 | retval = cyz_issue_cmd(&cy_card[info->card], | 3737 | retval = cyz_issue_cmd(card, channel, C_CM_IOCTLM, 0L); |
3808 | channel, C_CM_IOCTLM, 0L); | ||
3809 | if (retval != 0) { | 3738 | if (retval != 0) { |
3810 | printk("cyc:set_modem_info retval on ttyC%d was %x\n", | 3739 | printk(KERN_ERR "cyc:set_modem_info retval on ttyC%d " |
3811 | info->line, retval); | 3740 | "was %x\n", info->line, retval); |
3812 | } | 3741 | } |
3813 | CY_UNLOCK(info, flags); | 3742 | spin_unlock_irqrestore(&card->card_lock, flags); |
3814 | } | 3743 | } |
3815 | return 0; | 3744 | return 0; |
3816 | } /* cy_tiocmset */ | 3745 | } /* cy_tiocmset */ |
@@ -3820,14 +3749,17 @@ cy_tiocmset(struct tty_struct *tty, struct file *file, | |||
3820 | */ | 3749 | */ |
3821 | static void cy_break(struct tty_struct *tty, int break_state) | 3750 | static void cy_break(struct tty_struct *tty, int break_state) |
3822 | { | 3751 | { |
3823 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 3752 | struct cyclades_port *info = tty->driver_data; |
3753 | struct cyclades_card *card; | ||
3824 | unsigned long flags; | 3754 | unsigned long flags; |
3825 | 3755 | ||
3826 | if (serial_paranoia_check(info, tty->name, "cy_break")) | 3756 | if (serial_paranoia_check(info, tty->name, "cy_break")) |
3827 | return; | 3757 | return; |
3828 | 3758 | ||
3829 | CY_LOCK(info, flags); | 3759 | card = info->card; |
3830 | if (!IS_CYC_Z(cy_card[info->card])) { | 3760 | |
3761 | spin_lock_irqsave(&card->card_lock, flags); | ||
3762 | if (!IS_CYC_Z(*card)) { | ||
3831 | /* Let the transmit ISR take care of this (since it | 3763 | /* Let the transmit ISR take care of this (since it |
3832 | requires stuffing characters into the output stream). | 3764 | requires stuffing characters into the output stream). |
3833 | */ | 3765 | */ |
@@ -3835,18 +3767,18 @@ static void cy_break(struct tty_struct *tty, int break_state) | |||
3835 | if (!info->breakon) { | 3767 | if (!info->breakon) { |
3836 | info->breakon = 1; | 3768 | info->breakon = 1; |
3837 | if (!info->xmit_cnt) { | 3769 | if (!info->xmit_cnt) { |
3838 | CY_UNLOCK(info, flags); | 3770 | spin_unlock_irqrestore(&card->card_lock, flags); |
3839 | start_xmit(info); | 3771 | start_xmit(info); |
3840 | CY_LOCK(info, flags); | 3772 | spin_lock_irqsave(&card->card_lock, flags); |
3841 | } | 3773 | } |
3842 | } | 3774 | } |
3843 | } else { | 3775 | } else { |
3844 | if (!info->breakoff) { | 3776 | if (!info->breakoff) { |
3845 | info->breakoff = 1; | 3777 | info->breakoff = 1; |
3846 | if (!info->xmit_cnt) { | 3778 | if (!info->xmit_cnt) { |
3847 | CY_UNLOCK(info, flags); | 3779 | spin_unlock_irqrestore(&card->card_lock, flags); |
3848 | start_xmit(info); | 3780 | start_xmit(info); |
3849 | CY_LOCK(info, flags); | 3781 | spin_lock_irqsave(&card->card_lock, flags); |
3850 | } | 3782 | } |
3851 | } | 3783 | } |
3852 | } | 3784 | } |
@@ -3854,24 +3786,25 @@ static void cy_break(struct tty_struct *tty, int break_state) | |||
3854 | int retval; | 3786 | int retval; |
3855 | 3787 | ||
3856 | if (break_state == -1) { | 3788 | if (break_state == -1) { |
3857 | retval = cyz_issue_cmd(&cy_card[info->card], | 3789 | retval = cyz_issue_cmd(card, |
3858 | info->line - cy_card[info->card].first_line, | 3790 | info->line - card->first_line, |
3859 | C_CM_SET_BREAK, 0L); | 3791 | C_CM_SET_BREAK, 0L); |
3860 | if (retval != 0) { | 3792 | if (retval != 0) { |
3861 | printk("cyc:cy_break (set) retval on ttyC%d " | 3793 | printk(KERN_ERR "cyc:cy_break (set) retval on " |
3862 | "was %x\n", info->line, retval); | 3794 | "ttyC%d was %x\n", info->line, retval); |
3863 | } | 3795 | } |
3864 | } else { | 3796 | } else { |
3865 | retval = cyz_issue_cmd(&cy_card[info->card], | 3797 | retval = cyz_issue_cmd(card, |
3866 | info->line - cy_card[info->card].first_line, | 3798 | info->line - card->first_line, |
3867 | C_CM_CLR_BREAK, 0L); | 3799 | C_CM_CLR_BREAK, 0L); |
3868 | if (retval != 0) { | 3800 | if (retval != 0) { |
3869 | printk("cyc:cy_break (clr) retval on ttyC%d " | 3801 | printk(KERN_DEBUG "cyc:cy_break (clr) retval " |
3870 | "was %x\n", info->line, retval); | 3802 | "on ttyC%d was %x\n", info->line, |
3803 | retval); | ||
3871 | } | 3804 | } |
3872 | } | 3805 | } |
3873 | } | 3806 | } |
3874 | CY_UNLOCK(info, flags); | 3807 | spin_unlock_irqrestore(&card->card_lock, flags); |
3875 | } /* cy_break */ | 3808 | } /* cy_break */ |
3876 | 3809 | ||
3877 | static int | 3810 | static int |
@@ -3889,28 +3822,27 @@ get_mon_info(struct cyclades_port *info, struct cyclades_monitor __user * mon) | |||
3889 | 3822 | ||
3890 | static int set_threshold(struct cyclades_port *info, unsigned long value) | 3823 | static int set_threshold(struct cyclades_port *info, unsigned long value) |
3891 | { | 3824 | { |
3825 | struct cyclades_card *card; | ||
3892 | void __iomem *base_addr; | 3826 | void __iomem *base_addr; |
3893 | int card, channel, chip, index; | 3827 | int channel, chip, index; |
3894 | unsigned long flags; | 3828 | unsigned long flags; |
3895 | 3829 | ||
3896 | card = info->card; | 3830 | card = info->card; |
3897 | channel = info->line - cy_card[card].first_line; | 3831 | channel = info->line - card->first_line; |
3898 | if (!IS_CYC_Z(cy_card[card])) { | 3832 | if (!IS_CYC_Z(*card)) { |
3899 | chip = channel >> 2; | 3833 | chip = channel >> 2; |
3900 | channel &= 0x03; | 3834 | channel &= 0x03; |
3901 | index = cy_card[card].bus_index; | 3835 | index = card->bus_index; |
3902 | base_addr = | 3836 | base_addr = |
3903 | cy_card[card].base_addr + (cy_chip_offset[chip] << index); | 3837 | card->base_addr + (cy_chip_offset[chip] << index); |
3904 | 3838 | ||
3905 | info->cor3 &= ~CyREC_FIFO; | 3839 | info->cor3 &= ~CyREC_FIFO; |
3906 | info->cor3 |= value & CyREC_FIFO; | 3840 | info->cor3 |= value & CyREC_FIFO; |
3907 | 3841 | ||
3908 | CY_LOCK(info, flags); | 3842 | spin_lock_irqsave(&card->card_lock, flags); |
3909 | cy_writeb(base_addr + (CyCOR3 << index), info->cor3); | 3843 | cy_writeb(base_addr + (CyCOR3 << index), info->cor3); |
3910 | cyy_issue_cmd(base_addr, CyCOR_CHANGE | CyCOR3ch, index); | 3844 | cyy_issue_cmd(base_addr, CyCOR_CHANGE | CyCOR3ch, index); |
3911 | CY_UNLOCK(info, flags); | 3845 | spin_unlock_irqrestore(&card->card_lock, flags); |
3912 | } else { | ||
3913 | /* Nothing to do! */ | ||
3914 | } | 3846 | } |
3915 | return 0; | 3847 | return 0; |
3916 | } /* set_threshold */ | 3848 | } /* set_threshold */ |
@@ -3918,25 +3850,23 @@ static int set_threshold(struct cyclades_port *info, unsigned long value) | |||
3918 | static int | 3850 | static int |
3919 | get_threshold(struct cyclades_port *info, unsigned long __user * value) | 3851 | get_threshold(struct cyclades_port *info, unsigned long __user * value) |
3920 | { | 3852 | { |
3853 | struct cyclades_card *card; | ||
3921 | void __iomem *base_addr; | 3854 | void __iomem *base_addr; |
3922 | int card, channel, chip, index; | 3855 | int channel, chip, index; |
3923 | unsigned long tmp; | 3856 | unsigned long tmp; |
3924 | 3857 | ||
3925 | card = info->card; | 3858 | card = info->card; |
3926 | channel = info->line - cy_card[card].first_line; | 3859 | channel = info->line - card->first_line; |
3927 | if (!IS_CYC_Z(cy_card[card])) { | 3860 | if (!IS_CYC_Z(*card)) { |
3928 | chip = channel >> 2; | 3861 | chip = channel >> 2; |
3929 | channel &= 0x03; | 3862 | channel &= 0x03; |
3930 | index = cy_card[card].bus_index; | 3863 | index = card->bus_index; |
3931 | base_addr = | 3864 | base_addr = card->base_addr + (cy_chip_offset[chip] << index); |
3932 | cy_card[card].base_addr + (cy_chip_offset[chip] << index); | ||
3933 | 3865 | ||
3934 | tmp = cy_readb(base_addr + (CyCOR3 << index)) & CyREC_FIFO; | 3866 | tmp = readb(base_addr + (CyCOR3 << index)) & CyREC_FIFO; |
3935 | return put_user(tmp, value); | 3867 | return put_user(tmp, value); |
3936 | } else { | ||
3937 | /* Nothing to do! */ | ||
3938 | return 0; | ||
3939 | } | 3868 | } |
3869 | return 0; | ||
3940 | } /* get_threshold */ | 3870 | } /* get_threshold */ |
3941 | 3871 | ||
3942 | static int | 3872 | static int |
@@ -3954,49 +3884,45 @@ get_default_threshold(struct cyclades_port *info, unsigned long __user * value) | |||
3954 | 3884 | ||
3955 | static int set_timeout(struct cyclades_port *info, unsigned long value) | 3885 | static int set_timeout(struct cyclades_port *info, unsigned long value) |
3956 | { | 3886 | { |
3887 | struct cyclades_card *card; | ||
3957 | void __iomem *base_addr; | 3888 | void __iomem *base_addr; |
3958 | int card, channel, chip, index; | 3889 | int channel, chip, index; |
3959 | unsigned long flags; | 3890 | unsigned long flags; |
3960 | 3891 | ||
3961 | card = info->card; | 3892 | card = info->card; |
3962 | channel = info->line - cy_card[card].first_line; | 3893 | channel = info->line - card->first_line; |
3963 | if (!IS_CYC_Z(cy_card[card])) { | 3894 | if (!IS_CYC_Z(*card)) { |
3964 | chip = channel >> 2; | 3895 | chip = channel >> 2; |
3965 | channel &= 0x03; | 3896 | channel &= 0x03; |
3966 | index = cy_card[card].bus_index; | 3897 | index = card->bus_index; |
3967 | base_addr = | 3898 | base_addr = card->base_addr + (cy_chip_offset[chip] << index); |
3968 | cy_card[card].base_addr + (cy_chip_offset[chip] << index); | ||
3969 | 3899 | ||
3970 | CY_LOCK(info, flags); | 3900 | spin_lock_irqsave(&card->card_lock, flags); |
3971 | cy_writeb(base_addr + (CyRTPR << index), value & 0xff); | 3901 | cy_writeb(base_addr + (CyRTPR << index), value & 0xff); |
3972 | CY_UNLOCK(info, flags); | 3902 | spin_unlock_irqrestore(&card->card_lock, flags); |
3973 | } else { | ||
3974 | /* Nothing to do! */ | ||
3975 | } | 3903 | } |
3976 | return 0; | 3904 | return 0; |
3977 | } /* set_timeout */ | 3905 | } /* set_timeout */ |
3978 | 3906 | ||
3979 | static int get_timeout(struct cyclades_port *info, unsigned long __user * value) | 3907 | static int get_timeout(struct cyclades_port *info, unsigned long __user * value) |
3980 | { | 3908 | { |
3909 | struct cyclades_card *card; | ||
3981 | void __iomem *base_addr; | 3910 | void __iomem *base_addr; |
3982 | int card, channel, chip, index; | 3911 | int channel, chip, index; |
3983 | unsigned long tmp; | 3912 | unsigned long tmp; |
3984 | 3913 | ||
3985 | card = info->card; | 3914 | card = info->card; |
3986 | channel = info->line - cy_card[card].first_line; | 3915 | channel = info->line - card->first_line; |
3987 | if (!IS_CYC_Z(cy_card[card])) { | 3916 | if (!IS_CYC_Z(*card)) { |
3988 | chip = channel >> 2; | 3917 | chip = channel >> 2; |
3989 | channel &= 0x03; | 3918 | channel &= 0x03; |
3990 | index = cy_card[card].bus_index; | 3919 | index = card->bus_index; |
3991 | base_addr = | 3920 | base_addr = card->base_addr + (cy_chip_offset[chip] << index); |
3992 | cy_card[card].base_addr + (cy_chip_offset[chip] << index); | ||
3993 | 3921 | ||
3994 | tmp = cy_readb(base_addr + (CyRTPR << index)); | 3922 | tmp = readb(base_addr + (CyRTPR << index)); |
3995 | return put_user(tmp, value); | 3923 | return put_user(tmp, value); |
3996 | } else { | ||
3997 | /* Nothing to do! */ | ||
3998 | return 0; | ||
3999 | } | 3924 | } |
3925 | return 0; | ||
4000 | } /* get_timeout */ | 3926 | } /* get_timeout */ |
4001 | 3927 | ||
4002 | static int set_default_timeout(struct cyclades_port *info, unsigned long value) | 3928 | static int set_default_timeout(struct cyclades_port *info, unsigned long value) |
@@ -4020,7 +3946,7 @@ static int | |||
4020 | cy_ioctl(struct tty_struct *tty, struct file *file, | 3946 | cy_ioctl(struct tty_struct *tty, struct file *file, |
4021 | unsigned int cmd, unsigned long arg) | 3947 | unsigned int cmd, unsigned long arg) |
4022 | { | 3948 | { |
4023 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 3949 | struct cyclades_port *info = tty->driver_data; |
4024 | struct cyclades_icount cprev, cnow; /* kernel counter temps */ | 3950 | struct cyclades_icount cprev, cnow; /* kernel counter temps */ |
4025 | struct serial_icounter_struct __user *p_cuser; /* user space */ | 3951 | struct serial_icounter_struct __user *p_cuser; /* user space */ |
4026 | int ret_val = 0; | 3952 | int ret_val = 0; |
@@ -4031,7 +3957,8 @@ cy_ioctl(struct tty_struct *tty, struct file *file, | |||
4031 | return -ENODEV; | 3957 | return -ENODEV; |
4032 | 3958 | ||
4033 | #ifdef CY_DEBUG_OTHER | 3959 | #ifdef CY_DEBUG_OTHER |
4034 | printk("cyc:cy_ioctl ttyC%d, cmd = %x arg = %lx\n", info->line, cmd, arg); /* */ | 3960 | printk(KERN_DEBUG "cyc:cy_ioctl ttyC%d, cmd = %x arg = %lx\n", |
3961 | info->line, cmd, arg); | ||
4035 | #endif | 3962 | #endif |
4036 | 3963 | ||
4037 | switch (cmd) { | 3964 | switch (cmd) { |
@@ -4076,14 +4003,6 @@ cy_ioctl(struct tty_struct *tty, struct file *file, | |||
4076 | case CYGETRTSDTR_INV: | 4003 | case CYGETRTSDTR_INV: |
4077 | ret_val = info->rtsdtr_inv; | 4004 | ret_val = info->rtsdtr_inv; |
4078 | break; | 4005 | break; |
4079 | case CYGETCARDINFO: | ||
4080 | if (copy_to_user(argp, &cy_card[info->card], | ||
4081 | sizeof(struct cyclades_card))) { | ||
4082 | ret_val = -EFAULT; | ||
4083 | break; | ||
4084 | } | ||
4085 | ret_val = 0; | ||
4086 | break; | ||
4087 | case CYGETCD1400VER: | 4006 | case CYGETCD1400VER: |
4088 | ret_val = info->chip_rev; | 4007 | ret_val = info->chip_rev; |
4089 | break; | 4008 | break; |
@@ -4119,34 +4038,22 @@ cy_ioctl(struct tty_struct *tty, struct file *file, | |||
4119 | * Caller should use TIOCGICOUNT to see which one it was | 4038 | * Caller should use TIOCGICOUNT to see which one it was |
4120 | */ | 4039 | */ |
4121 | case TIOCMIWAIT: | 4040 | case TIOCMIWAIT: |
4122 | CY_LOCK(info, flags); | 4041 | spin_lock_irqsave(&info->card->card_lock, flags); |
4123 | /* note the counters on entry */ | 4042 | /* note the counters on entry */ |
4124 | cprev = info->icount; | 4043 | cnow = info->icount; |
4125 | CY_UNLOCK(info, flags); | 4044 | spin_unlock_irqrestore(&info->card->card_lock, flags); |
4126 | while (1) { | 4045 | ret_val = wait_event_interruptible(info->delta_msr_wait, ({ |
4127 | interruptible_sleep_on(&info->delta_msr_wait); | 4046 | cprev = cnow; |
4128 | /* see if a signal did it */ | 4047 | spin_lock_irqsave(&info->card->card_lock, flags); |
4129 | if (signal_pending(current)) { | ||
4130 | return -ERESTARTSYS; | ||
4131 | } | ||
4132 | |||
4133 | CY_LOCK(info, flags); | ||
4134 | cnow = info->icount; /* atomic copy */ | 4048 | cnow = info->icount; /* atomic copy */ |
4135 | CY_UNLOCK(info, flags); | 4049 | spin_unlock_irqrestore(&info->card->card_lock, flags); |
4136 | 4050 | ||
4137 | if (cnow.rng == cprev.rng && cnow.dsr == cprev.dsr && | 4051 | ((arg & TIOCM_RNG) && (cnow.rng != cprev.rng)) || |
4138 | cnow.dcd == cprev.dcd && cnow.cts == cprev.cts) { | 4052 | ((arg & TIOCM_DSR) && (cnow.dsr != cprev.dsr)) || |
4139 | return -EIO; /* no change => error */ | 4053 | ((arg & TIOCM_CD) && (cnow.dcd != cprev.dcd)) || |
4140 | } | 4054 | ((arg & TIOCM_CTS) && (cnow.cts != cprev.cts)); |
4141 | if (((arg & TIOCM_RNG) && (cnow.rng != cprev.rng)) || | 4055 | })); |
4142 | ((arg & TIOCM_DSR) && (cnow.dsr != cprev.dsr)) || | 4056 | break; |
4143 | ((arg & TIOCM_CD) && (cnow.dcd != cprev.dcd)) || | ||
4144 | ((arg & TIOCM_CTS) && (cnow.cts != cprev.cts))) { | ||
4145 | return 0; | ||
4146 | } | ||
4147 | cprev = cnow; | ||
4148 | } | ||
4149 | /* NOTREACHED */ | ||
4150 | 4057 | ||
4151 | /* | 4058 | /* |
4152 | * Get counter of input serial line interrupts (DCD,RI,DSR,CTS) | 4059 | * Get counter of input serial line interrupts (DCD,RI,DSR,CTS) |
@@ -4155,9 +4062,9 @@ cy_ioctl(struct tty_struct *tty, struct file *file, | |||
4155 | * RI where only 0->1 is counted. | 4062 | * RI where only 0->1 is counted. |
4156 | */ | 4063 | */ |
4157 | case TIOCGICOUNT: | 4064 | case TIOCGICOUNT: |
4158 | CY_LOCK(info, flags); | 4065 | spin_lock_irqsave(&info->card->card_lock, flags); |
4159 | cnow = info->icount; | 4066 | cnow = info->icount; |
4160 | CY_UNLOCK(info, flags); | 4067 | spin_unlock_irqrestore(&info->card->card_lock, flags); |
4161 | p_cuser = argp; | 4068 | p_cuser = argp; |
4162 | ret_val = put_user(cnow.cts, &p_cuser->cts); | 4069 | ret_val = put_user(cnow.cts, &p_cuser->cts); |
4163 | if (ret_val) | 4070 | if (ret_val) |
@@ -4199,7 +4106,7 @@ cy_ioctl(struct tty_struct *tty, struct file *file, | |||
4199 | } | 4106 | } |
4200 | 4107 | ||
4201 | #ifdef CY_DEBUG_OTHER | 4108 | #ifdef CY_DEBUG_OTHER |
4202 | printk(" cyc:cy_ioctl done\n"); | 4109 | printk(KERN_DEBUG "cyc:cy_ioctl done\n"); |
4203 | #endif | 4110 | #endif |
4204 | 4111 | ||
4205 | return ret_val; | 4112 | return ret_val; |
@@ -4213,10 +4120,10 @@ cy_ioctl(struct tty_struct *tty, struct file *file, | |||
4213 | */ | 4120 | */ |
4214 | static void cy_set_termios(struct tty_struct *tty, struct ktermios *old_termios) | 4121 | static void cy_set_termios(struct tty_struct *tty, struct ktermios *old_termios) |
4215 | { | 4122 | { |
4216 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 4123 | struct cyclades_port *info = tty->driver_data; |
4217 | 4124 | ||
4218 | #ifdef CY_DEBUG_OTHER | 4125 | #ifdef CY_DEBUG_OTHER |
4219 | printk("cyc:cy_set_termios ttyC%d\n", info->line); | 4126 | printk(KERN_DEBUG "cyc:cy_set_termios ttyC%d\n", info->line); |
4220 | #endif | 4127 | #endif |
4221 | 4128 | ||
4222 | if (tty->termios->c_cflag == old_termios->c_cflag && | 4129 | if (tty->termios->c_cflag == old_termios->c_cflag && |
@@ -4248,8 +4155,9 @@ static void cy_set_termios(struct tty_struct *tty, struct ktermios *old_termios) | |||
4248 | */ | 4155 | */ |
4249 | static void cy_send_xchar(struct tty_struct *tty, char ch) | 4156 | static void cy_send_xchar(struct tty_struct *tty, char ch) |
4250 | { | 4157 | { |
4251 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 4158 | struct cyclades_port *info = tty->driver_data; |
4252 | int card, channel; | 4159 | struct cyclades_card *card; |
4160 | int channel; | ||
4253 | 4161 | ||
4254 | if (serial_paranoia_check(info, tty->name, "cy_send_xchar")) | 4162 | if (serial_paranoia_check(info, tty->name, "cy_send_xchar")) |
4255 | return; | 4163 | return; |
@@ -4260,15 +4168,13 @@ static void cy_send_xchar(struct tty_struct *tty, char ch) | |||
4260 | cy_start(tty); | 4168 | cy_start(tty); |
4261 | 4169 | ||
4262 | card = info->card; | 4170 | card = info->card; |
4263 | channel = info->line - cy_card[card].first_line; | 4171 | channel = info->line - card->first_line; |
4264 | 4172 | ||
4265 | if (IS_CYC_Z(cy_card[card])) { | 4173 | if (IS_CYC_Z(*card)) { |
4266 | if (ch == STOP_CHAR(tty)) | 4174 | if (ch == STOP_CHAR(tty)) |
4267 | cyz_issue_cmd(&cy_card[card], channel, C_CM_SENDXOFF, | 4175 | cyz_issue_cmd(card, channel, C_CM_SENDXOFF, 0L); |
4268 | 0L); | ||
4269 | else if (ch == START_CHAR(tty)) | 4176 | else if (ch == START_CHAR(tty)) |
4270 | cyz_issue_cmd(&cy_card[card], channel, C_CM_SENDXON, | 4177 | cyz_issue_cmd(card, channel, C_CM_SENDXON, 0L); |
4271 | 0L); | ||
4272 | } | 4178 | } |
4273 | } | 4179 | } |
4274 | 4180 | ||
@@ -4278,15 +4184,16 @@ static void cy_send_xchar(struct tty_struct *tty, char ch) | |||
4278 | */ | 4184 | */ |
4279 | static void cy_throttle(struct tty_struct *tty) | 4185 | static void cy_throttle(struct tty_struct *tty) |
4280 | { | 4186 | { |
4281 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 4187 | struct cyclades_port *info = tty->driver_data; |
4188 | struct cyclades_card *card; | ||
4282 | unsigned long flags; | 4189 | unsigned long flags; |
4283 | void __iomem *base_addr; | 4190 | void __iomem *base_addr; |
4284 | int card, chip, channel, index; | 4191 | int chip, channel, index; |
4285 | 4192 | ||
4286 | #ifdef CY_DEBUG_THROTTLE | 4193 | #ifdef CY_DEBUG_THROTTLE |
4287 | char buf[64]; | 4194 | char buf[64]; |
4288 | 4195 | ||
4289 | printk("cyc:throttle %s: %d....ttyC%d\n", tty_name(tty, buf), | 4196 | printk(KERN_DEBUG "cyc:throttle %s: %ld...ttyC%d\n", tty_name(tty, buf), |
4290 | tty->ldisc.chars_in_buffer(tty), info->line); | 4197 | tty->ldisc.chars_in_buffer(tty), info->line); |
4291 | #endif | 4198 | #endif |
4292 | 4199 | ||
@@ -4297,22 +4204,22 @@ static void cy_throttle(struct tty_struct *tty) | |||
4297 | card = info->card; | 4204 | card = info->card; |
4298 | 4205 | ||
4299 | if (I_IXOFF(tty)) { | 4206 | if (I_IXOFF(tty)) { |
4300 | if (!IS_CYC_Z(cy_card[card])) | 4207 | if (!IS_CYC_Z(*card)) |
4301 | cy_send_xchar(tty, STOP_CHAR(tty)); | 4208 | cy_send_xchar(tty, STOP_CHAR(tty)); |
4302 | else | 4209 | else |
4303 | info->throttle = 1; | 4210 | info->throttle = 1; |
4304 | } | 4211 | } |
4305 | 4212 | ||
4306 | if (tty->termios->c_cflag & CRTSCTS) { | 4213 | if (tty->termios->c_cflag & CRTSCTS) { |
4307 | channel = info->line - cy_card[card].first_line; | 4214 | channel = info->line - card->first_line; |
4308 | if (!IS_CYC_Z(cy_card[card])) { | 4215 | if (!IS_CYC_Z(*card)) { |
4309 | chip = channel >> 2; | 4216 | chip = channel >> 2; |
4310 | channel &= 0x03; | 4217 | channel &= 0x03; |
4311 | index = cy_card[card].bus_index; | 4218 | index = card->bus_index; |
4312 | base_addr = cy_card[card].base_addr + | 4219 | base_addr = card->base_addr + |
4313 | (cy_chip_offset[chip] << index); | 4220 | (cy_chip_offset[chip] << index); |
4314 | 4221 | ||
4315 | CY_LOCK(info, flags); | 4222 | spin_lock_irqsave(&card->card_lock, flags); |
4316 | cy_writeb(base_addr + (CyCAR << index), | 4223 | cy_writeb(base_addr + (CyCAR << index), |
4317 | (u_char) channel); | 4224 | (u_char) channel); |
4318 | if (info->rtsdtr_inv) { | 4225 | if (info->rtsdtr_inv) { |
@@ -4322,7 +4229,7 @@ static void cy_throttle(struct tty_struct *tty) | |||
4322 | cy_writeb(base_addr + (CyMSVR1 << index), | 4229 | cy_writeb(base_addr + (CyMSVR1 << index), |
4323 | ~CyRTS); | 4230 | ~CyRTS); |
4324 | } | 4231 | } |
4325 | CY_UNLOCK(info, flags); | 4232 | spin_unlock_irqrestore(&card->card_lock, flags); |
4326 | } else { | 4233 | } else { |
4327 | info->throttle = 1; | 4234 | info->throttle = 1; |
4328 | } | 4235 | } |
@@ -4336,16 +4243,17 @@ static void cy_throttle(struct tty_struct *tty) | |||
4336 | */ | 4243 | */ |
4337 | static void cy_unthrottle(struct tty_struct *tty) | 4244 | static void cy_unthrottle(struct tty_struct *tty) |
4338 | { | 4245 | { |
4339 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 4246 | struct cyclades_port *info = tty->driver_data; |
4247 | struct cyclades_card *card; | ||
4340 | unsigned long flags; | 4248 | unsigned long flags; |
4341 | void __iomem *base_addr; | 4249 | void __iomem *base_addr; |
4342 | int card, chip, channel, index; | 4250 | int chip, channel, index; |
4343 | 4251 | ||
4344 | #ifdef CY_DEBUG_THROTTLE | 4252 | #ifdef CY_DEBUG_THROTTLE |
4345 | char buf[64]; | 4253 | char buf[64]; |
4346 | 4254 | ||
4347 | printk("cyc:unthrottle %s: %d....ttyC%d\n", tty_name(tty, buf), | 4255 | printk(KERN_DEBUG "cyc:unthrottle %s: %ld...ttyC%d\n", |
4348 | tty->ldisc.chars_in_buffer(tty), info->line); | 4256 | tty_name(tty, buf), tty->ldisc.chars_in_buffer(tty),info->line); |
4349 | #endif | 4257 | #endif |
4350 | 4258 | ||
4351 | if (serial_paranoia_check(info, tty->name, "cy_unthrottle")) { | 4259 | if (serial_paranoia_check(info, tty->name, "cy_unthrottle")) { |
@@ -4361,15 +4269,15 @@ static void cy_unthrottle(struct tty_struct *tty) | |||
4361 | 4269 | ||
4362 | if (tty->termios->c_cflag & CRTSCTS) { | 4270 | if (tty->termios->c_cflag & CRTSCTS) { |
4363 | card = info->card; | 4271 | card = info->card; |
4364 | channel = info->line - cy_card[card].first_line; | 4272 | channel = info->line - card->first_line; |
4365 | if (!IS_CYC_Z(cy_card[card])) { | 4273 | if (!IS_CYC_Z(*card)) { |
4366 | chip = channel >> 2; | 4274 | chip = channel >> 2; |
4367 | channel &= 0x03; | 4275 | channel &= 0x03; |
4368 | index = cy_card[card].bus_index; | 4276 | index = card->bus_index; |
4369 | base_addr = cy_card[card].base_addr + | 4277 | base_addr = card->base_addr + |
4370 | (cy_chip_offset[chip] << index); | 4278 | (cy_chip_offset[chip] << index); |
4371 | 4279 | ||
4372 | CY_LOCK(info, flags); | 4280 | spin_lock_irqsave(&card->card_lock, flags); |
4373 | cy_writeb(base_addr + (CyCAR << index), | 4281 | cy_writeb(base_addr + (CyCAR << index), |
4374 | (u_char) channel); | 4282 | (u_char) channel); |
4375 | if (info->rtsdtr_inv) { | 4283 | if (info->rtsdtr_inv) { |
@@ -4379,7 +4287,7 @@ static void cy_unthrottle(struct tty_struct *tty) | |||
4379 | cy_writeb(base_addr + (CyMSVR1 << index), | 4287 | cy_writeb(base_addr + (CyMSVR1 << index), |
4380 | CyRTS); | 4288 | CyRTS); |
4381 | } | 4289 | } |
4382 | CY_UNLOCK(info, flags); | 4290 | spin_unlock_irqrestore(&card->card_lock, flags); |
4383 | } else { | 4291 | } else { |
4384 | info->throttle = 0; | 4292 | info->throttle = 0; |
4385 | } | 4293 | } |
@@ -4392,102 +4300,96 @@ static void cy_unthrottle(struct tty_struct *tty) | |||
4392 | static void cy_stop(struct tty_struct *tty) | 4300 | static void cy_stop(struct tty_struct *tty) |
4393 | { | 4301 | { |
4394 | struct cyclades_card *cinfo; | 4302 | struct cyclades_card *cinfo; |
4395 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 4303 | struct cyclades_port *info = tty->driver_data; |
4396 | void __iomem *base_addr; | 4304 | void __iomem *base_addr; |
4397 | int chip, channel, index; | 4305 | int chip, channel, index; |
4398 | unsigned long flags; | 4306 | unsigned long flags; |
4399 | 4307 | ||
4400 | #ifdef CY_DEBUG_OTHER | 4308 | #ifdef CY_DEBUG_OTHER |
4401 | printk("cyc:cy_stop ttyC%d\n", info->line); /* */ | 4309 | printk(KERN_DEBUG "cyc:cy_stop ttyC%d\n", info->line); |
4402 | #endif | 4310 | #endif |
4403 | 4311 | ||
4404 | if (serial_paranoia_check(info, tty->name, "cy_stop")) | 4312 | if (serial_paranoia_check(info, tty->name, "cy_stop")) |
4405 | return; | 4313 | return; |
4406 | 4314 | ||
4407 | cinfo = &cy_card[info->card]; | 4315 | cinfo = info->card; |
4408 | channel = info->line - cinfo->first_line; | 4316 | channel = info->line - cinfo->first_line; |
4409 | if (!IS_CYC_Z(*cinfo)) { | 4317 | if (!IS_CYC_Z(*cinfo)) { |
4410 | index = cinfo->bus_index; | 4318 | index = cinfo->bus_index; |
4411 | chip = channel >> 2; | 4319 | chip = channel >> 2; |
4412 | channel &= 0x03; | 4320 | channel &= 0x03; |
4413 | base_addr = cy_card[info->card].base_addr + | 4321 | base_addr = cinfo->base_addr + (cy_chip_offset[chip] << index); |
4414 | (cy_chip_offset[chip] << index); | ||
4415 | 4322 | ||
4416 | CY_LOCK(info, flags); | 4323 | spin_lock_irqsave(&cinfo->card_lock, flags); |
4417 | cy_writeb(base_addr + (CyCAR << index), | 4324 | cy_writeb(base_addr + (CyCAR << index), |
4418 | (u_char)(channel & 0x0003)); /* index channel */ | 4325 | (u_char)(channel & 0x0003)); /* index channel */ |
4419 | cy_writeb(base_addr + (CySRER << index), | 4326 | cy_writeb(base_addr + (CySRER << index), |
4420 | cy_readb(base_addr + (CySRER << index)) & ~CyTxRdy); | 4327 | readb(base_addr + (CySRER << index)) & ~CyTxRdy); |
4421 | CY_UNLOCK(info, flags); | 4328 | spin_unlock_irqrestore(&cinfo->card_lock, flags); |
4422 | } else { | ||
4423 | /* Nothing to do! */ | ||
4424 | } | 4329 | } |
4425 | } /* cy_stop */ | 4330 | } /* cy_stop */ |
4426 | 4331 | ||
4427 | static void cy_start(struct tty_struct *tty) | 4332 | static void cy_start(struct tty_struct *tty) |
4428 | { | 4333 | { |
4429 | struct cyclades_card *cinfo; | 4334 | struct cyclades_card *cinfo; |
4430 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 4335 | struct cyclades_port *info = tty->driver_data; |
4431 | void __iomem *base_addr; | 4336 | void __iomem *base_addr; |
4432 | int chip, channel, index; | 4337 | int chip, channel, index; |
4433 | unsigned long flags; | 4338 | unsigned long flags; |
4434 | 4339 | ||
4435 | #ifdef CY_DEBUG_OTHER | 4340 | #ifdef CY_DEBUG_OTHER |
4436 | printk("cyc:cy_start ttyC%d\n", info->line); /* */ | 4341 | printk(KERN_DEBUG "cyc:cy_start ttyC%d\n", info->line); |
4437 | #endif | 4342 | #endif |
4438 | 4343 | ||
4439 | if (serial_paranoia_check(info, tty->name, "cy_start")) | 4344 | if (serial_paranoia_check(info, tty->name, "cy_start")) |
4440 | return; | 4345 | return; |
4441 | 4346 | ||
4442 | cinfo = &cy_card[info->card]; | 4347 | cinfo = info->card; |
4443 | channel = info->line - cinfo->first_line; | 4348 | channel = info->line - cinfo->first_line; |
4444 | index = cinfo->bus_index; | 4349 | index = cinfo->bus_index; |
4445 | if (!IS_CYC_Z(*cinfo)) { | 4350 | if (!IS_CYC_Z(*cinfo)) { |
4446 | chip = channel >> 2; | 4351 | chip = channel >> 2; |
4447 | channel &= 0x03; | 4352 | channel &= 0x03; |
4448 | base_addr = cy_card[info->card].base_addr + | 4353 | base_addr = cinfo->base_addr + (cy_chip_offset[chip] << index); |
4449 | (cy_chip_offset[chip] << index); | ||
4450 | 4354 | ||
4451 | CY_LOCK(info, flags); | 4355 | spin_lock_irqsave(&cinfo->card_lock, flags); |
4452 | cy_writeb(base_addr + (CyCAR << index), (u_char) (channel & 0x0003)); /* index channel */ | 4356 | cy_writeb(base_addr + (CyCAR << index), (u_char) (channel & 0x0003)); /* index channel */ |
4453 | cy_writeb(base_addr + (CySRER << index), | 4357 | cy_writeb(base_addr + (CySRER << index), |
4454 | cy_readb(base_addr + (CySRER << index)) | CyTxRdy); | 4358 | readb(base_addr + (CySRER << index)) | CyTxRdy); |
4455 | CY_UNLOCK(info, flags); | 4359 | spin_unlock_irqrestore(&cinfo->card_lock, flags); |
4456 | } else { | ||
4457 | /* Nothing to do! */ | ||
4458 | } | 4360 | } |
4459 | } /* cy_start */ | 4361 | } /* cy_start */ |
4460 | 4362 | ||
4461 | static void cy_flush_buffer(struct tty_struct *tty) | 4363 | static void cy_flush_buffer(struct tty_struct *tty) |
4462 | { | 4364 | { |
4463 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 4365 | struct cyclades_port *info = tty->driver_data; |
4464 | int card, channel, retval; | 4366 | struct cyclades_card *card; |
4367 | int channel, retval; | ||
4465 | unsigned long flags; | 4368 | unsigned long flags; |
4466 | 4369 | ||
4467 | #ifdef CY_DEBUG_IO | 4370 | #ifdef CY_DEBUG_IO |
4468 | printk("cyc:cy_flush_buffer ttyC%d\n", info->line); /* */ | 4371 | printk(KERN_DEBUG "cyc:cy_flush_buffer ttyC%d\n", info->line); |
4469 | #endif | 4372 | #endif |
4470 | 4373 | ||
4471 | if (serial_paranoia_check(info, tty->name, "cy_flush_buffer")) | 4374 | if (serial_paranoia_check(info, tty->name, "cy_flush_buffer")) |
4472 | return; | 4375 | return; |
4473 | 4376 | ||
4474 | card = info->card; | 4377 | card = info->card; |
4475 | channel = (info->line) - (cy_card[card].first_line); | 4378 | channel = info->line - card->first_line; |
4476 | 4379 | ||
4477 | CY_LOCK(info, flags); | 4380 | spin_lock_irqsave(&card->card_lock, flags); |
4478 | info->xmit_cnt = info->xmit_head = info->xmit_tail = 0; | 4381 | info->xmit_cnt = info->xmit_head = info->xmit_tail = 0; |
4479 | CY_UNLOCK(info, flags); | 4382 | spin_unlock_irqrestore(&card->card_lock, flags); |
4480 | 4383 | ||
4481 | if (IS_CYC_Z(cy_card[card])) { /* If it is a Z card, flush the on-board | 4384 | if (IS_CYC_Z(*card)) { /* If it is a Z card, flush the on-board |
4482 | buffers as well */ | 4385 | buffers as well */ |
4483 | CY_LOCK(info, flags); | 4386 | spin_lock_irqsave(&card->card_lock, flags); |
4484 | retval = | 4387 | retval = cyz_issue_cmd(card, channel, C_CM_FLUSH_TX, 0L); |
4485 | cyz_issue_cmd(&cy_card[card], channel, C_CM_FLUSH_TX, 0L); | ||
4486 | if (retval != 0) { | 4388 | if (retval != 0) { |
4487 | printk("cyc: flush_buffer retval on ttyC%d was %x\n", | 4389 | printk(KERN_ERR "cyc: flush_buffer retval on ttyC%d " |
4488 | info->line, retval); | 4390 | "was %x\n", info->line, retval); |
4489 | } | 4391 | } |
4490 | CY_UNLOCK(info, flags); | 4392 | spin_unlock_irqrestore(&card->card_lock, flags); |
4491 | } | 4393 | } |
4492 | tty_wakeup(tty); | 4394 | tty_wakeup(tty); |
4493 | } /* cy_flush_buffer */ | 4395 | } /* cy_flush_buffer */ |
@@ -4497,10 +4399,10 @@ static void cy_flush_buffer(struct tty_struct *tty) | |||
4497 | */ | 4399 | */ |
4498 | static void cy_hangup(struct tty_struct *tty) | 4400 | static void cy_hangup(struct tty_struct *tty) |
4499 | { | 4401 | { |
4500 | struct cyclades_port *info = (struct cyclades_port *)tty->driver_data; | 4402 | struct cyclades_port *info = tty->driver_data; |
4501 | 4403 | ||
4502 | #ifdef CY_DEBUG_OTHER | 4404 | #ifdef CY_DEBUG_OTHER |
4503 | printk("cyc:cy_hangup ttyC%d\n", info->line); /* */ | 4405 | printk(KERN_DEBUG "cyc:cy_hangup ttyC%d\n", info->line); |
4504 | #endif | 4406 | #endif |
4505 | 4407 | ||
4506 | if (serial_paranoia_check(info, tty->name, "cy_hangup")) | 4408 | if (serial_paranoia_check(info, tty->name, "cy_hangup")) |
@@ -4511,7 +4413,8 @@ static void cy_hangup(struct tty_struct *tty) | |||
4511 | info->event = 0; | 4413 | info->event = 0; |
4512 | info->count = 0; | 4414 | info->count = 0; |
4513 | #ifdef CY_DEBUG_COUNT | 4415 | #ifdef CY_DEBUG_COUNT |
4514 | printk("cyc:cy_hangup (%d): setting count to 0\n", current->pid); | 4416 | printk(KERN_DEBUG "cyc:cy_hangup (%d): setting count to 0\n", |
4417 | current->pid); | ||
4515 | #endif | 4418 | #endif |
4516 | info->tty = NULL; | 4419 | info->tty = NULL; |
4517 | info->flags &= ~ASYNC_NORMAL_ACTIVE; | 4420 | info->flags &= ~ASYNC_NORMAL_ACTIVE; |
@@ -4526,10 +4429,107 @@ static void cy_hangup(struct tty_struct *tty) | |||
4526 | * --------------------------------------------------------------------- | 4429 | * --------------------------------------------------------------------- |
4527 | */ | 4430 | */ |
4528 | 4431 | ||
4432 | static int __devinit cy_init_card(struct cyclades_card *cinfo) | ||
4433 | { | ||
4434 | struct cyclades_port *info; | ||
4435 | u32 mailbox; | ||
4436 | unsigned int nports; | ||
4437 | unsigned short chip_number; | ||
4438 | int index, port; | ||
4439 | |||
4440 | spin_lock_init(&cinfo->card_lock); | ||
4441 | |||
4442 | if (IS_CYC_Z(*cinfo)) { /* Cyclades-Z */ | ||
4443 | mailbox = readl(&((struct RUNTIME_9060 __iomem *) | ||
4444 | cinfo->ctl_addr)->mail_box_0); | ||
4445 | nports = (mailbox == ZE_V1) ? ZE_V1_NPORTS : 8; | ||
4446 | cinfo->intr_enabled = 0; | ||
4447 | cinfo->nports = 0; /* Will be correctly set later, after | ||
4448 | Z FW is loaded */ | ||
4449 | } else { | ||
4450 | index = cinfo->bus_index; | ||
4451 | nports = cinfo->nports = CyPORTS_PER_CHIP * cinfo->num_chips; | ||
4452 | } | ||
4453 | |||
4454 | cinfo->ports = kzalloc(sizeof(*cinfo->ports) * nports, GFP_KERNEL); | ||
4455 | if (cinfo->ports == NULL) { | ||
4456 | printk(KERN_ERR "Cyclades: cannot allocate ports\n"); | ||
4457 | cinfo->nports = 0; | ||
4458 | return -ENOMEM; | ||
4459 | } | ||
4460 | |||
4461 | for (port = cinfo->first_line; port < cinfo->first_line + nports; | ||
4462 | port++) { | ||
4463 | info = &cinfo->ports[port - cinfo->first_line]; | ||
4464 | info->magic = CYCLADES_MAGIC; | ||
4465 | info->card = cinfo; | ||
4466 | info->line = port; | ||
4467 | info->flags = STD_COM_FLAGS; | ||
4468 | info->closing_wait = CLOSING_WAIT_DELAY; | ||
4469 | info->close_delay = 5 * HZ / 10; | ||
4470 | |||
4471 | INIT_WORK(&info->tqueue, do_softint); | ||
4472 | init_waitqueue_head(&info->open_wait); | ||
4473 | init_waitqueue_head(&info->close_wait); | ||
4474 | init_completion(&info->shutdown_wait); | ||
4475 | init_waitqueue_head(&info->delta_msr_wait); | ||
4476 | |||
4477 | if (IS_CYC_Z(*cinfo)) { | ||
4478 | info->type = PORT_STARTECH; | ||
4479 | if (mailbox == ZO_V1) | ||
4480 | info->xmit_fifo_size = CYZ_FIFO_SIZE; | ||
4481 | else | ||
4482 | info->xmit_fifo_size = 4 * CYZ_FIFO_SIZE; | ||
4483 | #ifdef CONFIG_CYZ_INTR | ||
4484 | setup_timer(&cyz_rx_full_timer[port], | ||
4485 | cyz_rx_restart, (unsigned long)info); | ||
4486 | #endif | ||
4487 | } else { | ||
4488 | info->type = PORT_CIRRUS; | ||
4489 | info->xmit_fifo_size = CyMAX_CHAR_FIFO; | ||
4490 | info->cor1 = CyPARITY_NONE | Cy_1_STOP | Cy_8_BITS; | ||
4491 | info->cor2 = CyETC; | ||
4492 | info->cor3 = 0x08; /* _very_ small rcv threshold */ | ||
4493 | |||
4494 | chip_number = (port - cinfo->first_line) / 4; | ||
4495 | if ((info->chip_rev = readb(cinfo->base_addr + | ||
4496 | (cy_chip_offset[chip_number] << | ||
4497 | index) + (CyGFRCR << index))) >= | ||
4498 | CD1400_REV_J) { | ||
4499 | /* It is a CD1400 rev. J or later */ | ||
4500 | info->tbpr = baud_bpr_60[13]; /* Tx BPR */ | ||
4501 | info->tco = baud_co_60[13]; /* Tx CO */ | ||
4502 | info->rbpr = baud_bpr_60[13]; /* Rx BPR */ | ||
4503 | info->rco = baud_co_60[13]; /* Rx CO */ | ||
4504 | info->rtsdtr_inv = 1; | ||
4505 | } else { | ||
4506 | info->tbpr = baud_bpr_25[13]; /* Tx BPR */ | ||
4507 | info->tco = baud_co_25[13]; /* Tx CO */ | ||
4508 | info->rbpr = baud_bpr_25[13]; /* Rx BPR */ | ||
4509 | info->rco = baud_co_25[13]; /* Rx CO */ | ||
4510 | info->rtsdtr_inv = 0; | ||
4511 | } | ||
4512 | info->read_status_mask = CyTIMEOUT | CySPECHAR | | ||
4513 | CyBREAK | CyPARITY | CyFRAME | CyOVERRUN; | ||
4514 | } | ||
4515 | |||
4516 | } | ||
4517 | |||
4518 | #ifndef CONFIG_CYZ_INTR | ||
4519 | if (IS_CYC_Z(*cinfo) && !timer_pending(&cyz_timerlist)) { | ||
4520 | mod_timer(&cyz_timerlist, jiffies + 1); | ||
4521 | #ifdef CY_PCI_DEBUG | ||
4522 | printk(KERN_DEBUG "Cyclades-Z polling initialized\n"); | ||
4523 | #endif | ||
4524 | } | ||
4525 | #endif | ||
4526 | return 0; | ||
4527 | } | ||
4528 | |||
4529 | /* initialize chips on Cyclom-Y card -- return number of valid | 4529 | /* initialize chips on Cyclom-Y card -- return number of valid |
4530 | chips (which is number of ports/4) */ | 4530 | chips (which is number of ports/4) */ |
4531 | static unsigned short __init | 4531 | static unsigned short __devinit cyy_init_card(void __iomem *true_base_addr, |
4532 | cyy_init_card(void __iomem * true_base_addr, int index) | 4532 | int index) |
4533 | { | 4533 | { |
4534 | unsigned int chip_number; | 4534 | unsigned int chip_number; |
4535 | void __iomem *base_addr; | 4535 | void __iomem *base_addr; |
@@ -4544,7 +4544,7 @@ cyy_init_card(void __iomem * true_base_addr, int index) | |||
4544 | base_addr = | 4544 | base_addr = |
4545 | true_base_addr + (cy_chip_offset[chip_number] << index); | 4545 | true_base_addr + (cy_chip_offset[chip_number] << index); |
4546 | mdelay(1); | 4546 | mdelay(1); |
4547 | if (cy_readb(base_addr + (CyCCR << index)) != 0x00) { | 4547 | if (readb(base_addr + (CyCCR << index)) != 0x00) { |
4548 | /************* | 4548 | /************* |
4549 | printk(" chip #%d at %#6lx is never idle (CCR != 0)\n", | 4549 | printk(" chip #%d at %#6lx is never idle (CCR != 0)\n", |
4550 | chip_number, (unsigned long)base_addr); | 4550 | chip_number, (unsigned long)base_addr); |
@@ -4561,7 +4561,7 @@ cyy_init_card(void __iomem * true_base_addr, int index) | |||
4561 | chip 4 GFRCR register appears at chip 0, there is no chip 4 | 4561 | chip 4 GFRCR register appears at chip 0, there is no chip 4 |
4562 | and this must be a Cyclom-16Y, not a Cyclom-32Ye. | 4562 | and this must be a Cyclom-16Y, not a Cyclom-32Ye. |
4563 | */ | 4563 | */ |
4564 | if (chip_number == 4 && cy_readb(true_base_addr + | 4564 | if (chip_number == 4 && readb(true_base_addr + |
4565 | (cy_chip_offset[0] << index) + | 4565 | (cy_chip_offset[0] << index) + |
4566 | (CyGFRCR << index)) == 0) { | 4566 | (CyGFRCR << index)) == 0) { |
4567 | return chip_number; | 4567 | return chip_number; |
@@ -4570,7 +4570,7 @@ cyy_init_card(void __iomem * true_base_addr, int index) | |||
4570 | cy_writeb(base_addr + (CyCCR << index), CyCHIP_RESET); | 4570 | cy_writeb(base_addr + (CyCCR << index), CyCHIP_RESET); |
4571 | mdelay(1); | 4571 | mdelay(1); |
4572 | 4572 | ||
4573 | if (cy_readb(base_addr + (CyGFRCR << index)) == 0x00) { | 4573 | if (readb(base_addr + (CyGFRCR << index)) == 0x00) { |
4574 | /* | 4574 | /* |
4575 | printk(" chip #%d at %#6lx is not responding ", | 4575 | printk(" chip #%d at %#6lx is not responding ", |
4576 | chip_number, (unsigned long)base_addr); | 4576 | chip_number, (unsigned long)base_addr); |
@@ -4578,7 +4578,7 @@ cyy_init_card(void __iomem * true_base_addr, int index) | |||
4578 | */ | 4578 | */ |
4579 | return chip_number; | 4579 | return chip_number; |
4580 | } | 4580 | } |
4581 | if ((0xf0 & (cy_readb(base_addr + (CyGFRCR << index)))) != | 4581 | if ((0xf0 & (readb(base_addr + (CyGFRCR << index)))) != |
4582 | 0x40) { | 4582 | 0x40) { |
4583 | /* | 4583 | /* |
4584 | printk(" chip #%d at %#6lx is not valid (GFRCR == " | 4584 | printk(" chip #%d at %#6lx is not valid (GFRCR == " |
@@ -4589,7 +4589,7 @@ cyy_init_card(void __iomem * true_base_addr, int index) | |||
4589 | return chip_number; | 4589 | return chip_number; |
4590 | } | 4590 | } |
4591 | cy_writeb(base_addr + (CyGCR << index), CyCH0_SERIAL); | 4591 | cy_writeb(base_addr + (CyGCR << index), CyCH0_SERIAL); |
4592 | if (cy_readb(base_addr + (CyGFRCR << index)) >= CD1400_REV_J) { | 4592 | if (readb(base_addr + (CyGFRCR << index)) >= CD1400_REV_J) { |
4593 | /* It is a CD1400 rev. J or later */ | 4593 | /* It is a CD1400 rev. J or later */ |
4594 | /* Impossible to reach 5ms with this chip. | 4594 | /* Impossible to reach 5ms with this chip. |
4595 | Changed to 2ms instead (f = 500 Hz). */ | 4595 | Changed to 2ms instead (f = 500 Hz). */ |
@@ -4602,7 +4602,7 @@ cyy_init_card(void __iomem * true_base_addr, int index) | |||
4602 | /* | 4602 | /* |
4603 | printk(" chip #%d at %#6lx is rev 0x%2x\n", | 4603 | printk(" chip #%d at %#6lx is rev 0x%2x\n", |
4604 | chip_number, (unsigned long)base_addr, | 4604 | chip_number, (unsigned long)base_addr, |
4605 | cy_readb(base_addr+(CyGFRCR<<index))); | 4605 | readb(base_addr+(CyGFRCR<<index))); |
4606 | */ | 4606 | */ |
4607 | } | 4607 | } |
4608 | return chip_number; | 4608 | return chip_number; |
@@ -4647,9 +4647,15 @@ static int __init cy_detect_isa(void) | |||
4647 | 4647 | ||
4648 | /* probe for CD1400... */ | 4648 | /* probe for CD1400... */ |
4649 | cy_isa_address = ioremap(isa_address, CyISA_Ywin); | 4649 | cy_isa_address = ioremap(isa_address, CyISA_Ywin); |
4650 | if (cy_isa_address == NULL) { | ||
4651 | printk(KERN_ERR "Cyclom-Y/ISA: can't remap base " | ||
4652 | "address\n"); | ||
4653 | continue; | ||
4654 | } | ||
4650 | cy_isa_nchan = CyPORTS_PER_CHIP * | 4655 | cy_isa_nchan = CyPORTS_PER_CHIP * |
4651 | cyy_init_card(cy_isa_address, 0); | 4656 | cyy_init_card(cy_isa_address, 0); |
4652 | if (cy_isa_nchan == 0) { | 4657 | if (cy_isa_nchan == 0) { |
4658 | iounmap(cy_isa_address); | ||
4653 | continue; | 4659 | continue; |
4654 | } | 4660 | } |
4655 | #ifdef MODULE | 4661 | #ifdef MODULE |
@@ -4660,40 +4666,42 @@ static int __init cy_detect_isa(void) | |||
4660 | /* find out the board's irq by probing */ | 4666 | /* find out the board's irq by probing */ |
4661 | cy_isa_irq = detect_isa_irq(cy_isa_address); | 4667 | cy_isa_irq = detect_isa_irq(cy_isa_address); |
4662 | if (cy_isa_irq == 0) { | 4668 | if (cy_isa_irq == 0) { |
4663 | printk("Cyclom-Y/ISA found at 0x%lx ", | 4669 | printk(KERN_ERR "Cyclom-Y/ISA found at 0x%lx, but the " |
4670 | "IRQ could not be detected.\n", | ||
4664 | (unsigned long)cy_isa_address); | 4671 | (unsigned long)cy_isa_address); |
4665 | printk("but the IRQ could not be detected.\n"); | 4672 | iounmap(cy_isa_address); |
4666 | continue; | 4673 | continue; |
4667 | } | 4674 | } |
4668 | 4675 | ||
4669 | if ((cy_next_channel + cy_isa_nchan) > NR_PORTS) { | 4676 | if ((cy_next_channel + cy_isa_nchan) > NR_PORTS) { |
4670 | printk("Cyclom-Y/ISA found at 0x%lx ", | 4677 | printk(KERN_ERR "Cyclom-Y/ISA found at 0x%lx, but no " |
4678 | "more channels are available. Change NR_PORTS " | ||
4679 | "in cyclades.c and recompile kernel.\n", | ||
4671 | (unsigned long)cy_isa_address); | 4680 | (unsigned long)cy_isa_address); |
4672 | printk("but no more channels are available.\n"); | 4681 | iounmap(cy_isa_address); |
4673 | printk("Change NR_PORTS in cyclades.c and recompile " | ||
4674 | "kernel.\n"); | ||
4675 | return nboard; | 4682 | return nboard; |
4676 | } | 4683 | } |
4677 | /* fill the next cy_card structure available */ | 4684 | /* fill the next cy_card structure available */ |
4678 | for (j = 0; j < NR_CARDS; j++) { | 4685 | for (j = 0; j < NR_CARDS; j++) { |
4679 | if (cy_card[j].base_addr == 0) | 4686 | if (cy_card[j].base_addr == NULL) |
4680 | break; | 4687 | break; |
4681 | } | 4688 | } |
4682 | if (j == NR_CARDS) { /* no more cy_cards available */ | 4689 | if (j == NR_CARDS) { /* no more cy_cards available */ |
4683 | printk("Cyclom-Y/ISA found at 0x%lx ", | 4690 | printk(KERN_ERR "Cyclom-Y/ISA found at 0x%lx, but no " |
4691 | "more cards can be used. Change NR_CARDS in " | ||
4692 | "cyclades.c and recompile kernel.\n", | ||
4684 | (unsigned long)cy_isa_address); | 4693 | (unsigned long)cy_isa_address); |
4685 | printk("but no more cards can be used .\n"); | 4694 | iounmap(cy_isa_address); |
4686 | printk("Change NR_CARDS in cyclades.c and recompile " | ||
4687 | "kernel.\n"); | ||
4688 | return nboard; | 4695 | return nboard; |
4689 | } | 4696 | } |
4690 | 4697 | ||
4691 | /* allocate IRQ */ | 4698 | /* allocate IRQ */ |
4692 | if (request_irq(cy_isa_irq, cyy_interrupt, | 4699 | if (request_irq(cy_isa_irq, cyy_interrupt, |
4693 | IRQF_DISABLED, "Cyclom-Y", &cy_card[j])) { | 4700 | IRQF_DISABLED, "Cyclom-Y", &cy_card[j])) { |
4694 | printk("Cyclom-Y/ISA found at 0x%lx ", | 4701 | printk(KERN_ERR "Cyclom-Y/ISA found at 0x%lx, but " |
4695 | (unsigned long)cy_isa_address); | 4702 | "could not allocate IRQ#%d.\n", |
4696 | printk("but could not allocate IRQ#%d.\n", cy_isa_irq); | 4703 | (unsigned long)cy_isa_address, cy_isa_irq); |
4704 | iounmap(cy_isa_address); | ||
4697 | return nboard; | 4705 | return nboard; |
4698 | } | 4706 | } |
4699 | 4707 | ||
@@ -4704,15 +4712,23 @@ static int __init cy_detect_isa(void) | |||
4704 | cy_card[j].bus_index = 0; | 4712 | cy_card[j].bus_index = 0; |
4705 | cy_card[j].first_line = cy_next_channel; | 4713 | cy_card[j].first_line = cy_next_channel; |
4706 | cy_card[j].num_chips = cy_isa_nchan / 4; | 4714 | cy_card[j].num_chips = cy_isa_nchan / 4; |
4715 | if (cy_init_card(&cy_card[j])) { | ||
4716 | cy_card[j].base_addr = NULL; | ||
4717 | free_irq(cy_isa_irq, &cy_card[j]); | ||
4718 | iounmap(cy_isa_address); | ||
4719 | continue; | ||
4720 | } | ||
4707 | nboard++; | 4721 | nboard++; |
4708 | 4722 | ||
4709 | /* print message */ | 4723 | printk(KERN_INFO "Cyclom-Y/ISA #%d: 0x%lx-0x%lx, IRQ%d found: " |
4710 | printk("Cyclom-Y/ISA #%d: 0x%lx-0x%lx, IRQ%d, ", | 4724 | "%d channels starting from port %d\n", |
4711 | j + 1, (unsigned long)cy_isa_address, | 4725 | j + 1, (unsigned long)cy_isa_address, |
4712 | (unsigned long)(cy_isa_address + (CyISA_Ywin - 1)), | 4726 | (unsigned long)(cy_isa_address + (CyISA_Ywin - 1)), |
4713 | cy_isa_irq); | 4727 | cy_isa_irq, cy_isa_nchan, cy_next_channel); |
4714 | printk("%d channels starting from port %d.\n", | 4728 | |
4715 | cy_isa_nchan, cy_next_channel); | 4729 | for (j = cy_next_channel; |
4730 | j < cy_next_channel + cy_isa_nchan; j++) | ||
4731 | tty_register_device(cy_serial_driver, j, NULL); | ||
4716 | cy_next_channel += cy_isa_nchan; | 4732 | cy_next_channel += cy_isa_nchan; |
4717 | } | 4733 | } |
4718 | return nboard; | 4734 | return nboard; |
@@ -4721,510 +4737,310 @@ static int __init cy_detect_isa(void) | |||
4721 | #endif /* CONFIG_ISA */ | 4737 | #endif /* CONFIG_ISA */ |
4722 | } /* cy_detect_isa */ | 4738 | } /* cy_detect_isa */ |
4723 | 4739 | ||
4724 | static void plx_init(void __iomem * addr, uclong initctl) | 4740 | #ifdef CONFIG_PCI |
4741 | static void __devinit plx_init(void __iomem * addr, __u32 initctl) | ||
4725 | { | 4742 | { |
4726 | /* Reset PLX */ | 4743 | /* Reset PLX */ |
4727 | cy_writel(addr + initctl, cy_readl(addr + initctl) | 0x40000000); | 4744 | cy_writel(addr + initctl, readl(addr + initctl) | 0x40000000); |
4728 | udelay(100L); | 4745 | udelay(100L); |
4729 | cy_writel(addr + initctl, cy_readl(addr + initctl) & ~0x40000000); | 4746 | cy_writel(addr + initctl, readl(addr + initctl) & ~0x40000000); |
4730 | 4747 | ||
4731 | /* Reload Config. Registers from EEPROM */ | 4748 | /* Reload Config. Registers from EEPROM */ |
4732 | cy_writel(addr + initctl, cy_readl(addr + initctl) | 0x20000000); | 4749 | cy_writel(addr + initctl, readl(addr + initctl) | 0x20000000); |
4733 | udelay(100L); | 4750 | udelay(100L); |
4734 | cy_writel(addr + initctl, cy_readl(addr + initctl) & ~0x20000000); | 4751 | cy_writel(addr + initctl, readl(addr + initctl) & ~0x20000000); |
4735 | } | 4752 | } |
4736 | 4753 | ||
4737 | /* | 4754 | static int __devinit cy_pci_probe(struct pci_dev *pdev, |
4738 | * --------------------------------------------------------------------- | 4755 | const struct pci_device_id *ent) |
4739 | * cy_detect_pci() - Test PCI bus presence and Cyclom-Ye/PCI. | ||
4740 | * sets global variables and return the number of PCI boards found. | ||
4741 | * --------------------------------------------------------------------- | ||
4742 | */ | ||
4743 | static int __init cy_detect_pci(void) | ||
4744 | { | 4756 | { |
4745 | #ifdef CONFIG_PCI | 4757 | void __iomem *addr0 = NULL, *addr2 = NULL; |
4746 | 4758 | char *card_name = NULL; | |
4747 | struct pci_dev *pdev = NULL; | 4759 | u32 mailbox; |
4748 | unsigned char cyy_rev_id; | 4760 | unsigned int device_id, nchan = 0, card_no, i; |
4749 | unsigned char cy_pci_irq = 0; | 4761 | unsigned char plx_ver; |
4750 | uclong cy_pci_phys0, cy_pci_phys2; | 4762 | int retval, irq; |
4751 | void __iomem *cy_pci_addr0, *cy_pci_addr2; | 4763 | |
4752 | unsigned short i, j, cy_pci_nchan, plx_ver; | 4764 | retval = pci_enable_device(pdev); |
4753 | unsigned short device_id, dev_index = 0; | 4765 | if (retval) { |
4754 | uclong mailbox; | 4766 | dev_err(&pdev->dev, "cannot enable device\n"); |
4755 | uclong ZeIndex = 0; | 4767 | goto err; |
4756 | void __iomem *Ze_addr0[NR_CARDS], *Ze_addr2[NR_CARDS]; | 4768 | } |
4757 | uclong Ze_phys0[NR_CARDS], Ze_phys2[NR_CARDS]; | ||
4758 | unsigned char Ze_irq[NR_CARDS]; | ||
4759 | struct pci_dev *Ze_pdev[NR_CARDS]; | ||
4760 | |||
4761 | for (i = 0; i < NR_CARDS; i++) { | ||
4762 | /* look for a Cyclades card by vendor and device id */ | ||
4763 | while ((device_id = cy_pci_dev_id[dev_index].device) != 0) { | ||
4764 | if ((pdev = pci_get_device(PCI_VENDOR_ID_CYCLADES, | ||
4765 | device_id, pdev)) == NULL) { | ||
4766 | dev_index++; /* try next device id */ | ||
4767 | } else { | ||
4768 | break; /* found a board */ | ||
4769 | } | ||
4770 | } | ||
4771 | |||
4772 | if (device_id == 0) | ||
4773 | break; | ||
4774 | |||
4775 | if (pci_enable_device(pdev)) | ||
4776 | continue; | ||
4777 | |||
4778 | /* read PCI configuration area */ | ||
4779 | cy_pci_irq = pdev->irq; | ||
4780 | cy_pci_phys0 = pci_resource_start(pdev, 0); | ||
4781 | cy_pci_phys2 = pci_resource_start(pdev, 2); | ||
4782 | pci_read_config_byte(pdev, PCI_REVISION_ID, &cyy_rev_id); | ||
4783 | 4769 | ||
4784 | device_id &= ~PCI_DEVICE_ID_MASK; | 4770 | /* read PCI configuration area */ |
4771 | irq = pdev->irq; | ||
4772 | device_id = pdev->device & ~PCI_DEVICE_ID_MASK; | ||
4785 | 4773 | ||
4786 | if (device_id == PCI_DEVICE_ID_CYCLOM_Y_Lo || | 4774 | #if defined(__alpha__) |
4787 | device_id == PCI_DEVICE_ID_CYCLOM_Y_Hi) { | 4775 | if (device_id == PCI_DEVICE_ID_CYCLOM_Y_Lo) { /* below 1M? */ |
4788 | #ifdef CY_PCI_DEBUG | 4776 | dev_err(&pdev->dev, "Cyclom-Y/PCI not supported for low " |
4789 | printk("Cyclom-Y/PCI (bus=0x0%x, pci_id=0x%x, ", | 4777 | "addresses on Alpha systems.\n"); |
4790 | pdev->bus->number, pdev->devfn); | 4778 | retval = -EIO; |
4791 | printk("rev_id=%d) IRQ%d\n", | 4779 | goto err_dis; |
4792 | cyy_rev_id, (int)cy_pci_irq); | 4780 | } |
4793 | printk("Cyclom-Y/PCI:found winaddr=0x%lx " | ||
4794 | "ctladdr=0x%lx\n", | ||
4795 | (ulong)cy_pci_phys2, (ulong)cy_pci_phys0); | ||
4796 | #endif | 4781 | #endif |
4782 | if (device_id == PCI_DEVICE_ID_CYCLOM_Z_Lo) { | ||
4783 | dev_err(&pdev->dev, "Cyclades-Z/PCI not supported for low " | ||
4784 | "addresses\n"); | ||
4785 | retval = -EIO; | ||
4786 | goto err_dis; | ||
4787 | } | ||
4797 | 4788 | ||
4798 | if (pci_resource_flags(pdev, 2) & IORESOURCE_IO) { | 4789 | if (pci_resource_flags(pdev, 2) & IORESOURCE_IO) { |
4799 | printk(" Warning: PCI I/O bit incorrectly " | 4790 | dev_warn(&pdev->dev, "PCI I/O bit incorrectly set. Ignoring " |
4800 | "set. Ignoring it...\n"); | 4791 | "it...\n"); |
4801 | pdev->resource[2].flags &= ~IORESOURCE_IO; | 4792 | pdev->resource[2].flags &= ~IORESOURCE_IO; |
4802 | } | 4793 | } |
4803 | 4794 | ||
4804 | /* Although we don't use this I/O region, we should | 4795 | retval = pci_request_regions(pdev, "cyclades"); |
4805 | request it from the kernel anyway, to avoid problems | 4796 | if (retval) { |
4806 | with other drivers accessing it. */ | 4797 | dev_err(&pdev->dev, "failed to reserve resources\n"); |
4807 | if (pci_request_regions(pdev, "Cyclom-Y") != 0) { | 4798 | goto err_dis; |
4808 | printk(KERN_ERR "cyclades: failed to reserve " | 4799 | } |
4809 | "PCI resources\n"); | ||
4810 | continue; | ||
4811 | } | ||
4812 | #if defined(__alpha__) | ||
4813 | if (device_id == PCI_DEVICE_ID_CYCLOM_Y_Lo) { /* below 1M? */ | ||
4814 | printk("Cyclom-Y/PCI (bus=0x0%x, pci_id=0x%x, ", | ||
4815 | pdev->bus->number, pdev->devfn); | ||
4816 | printk("rev_id=%d) IRQ%d\n", | ||
4817 | cyy_rev_id, (int)cy_pci_irq); | ||
4818 | printk("Cyclom-Y/PCI:found winaddr=0x%lx " | ||
4819 | "ctladdr=0x%lx\n", | ||
4820 | (ulong)cy_pci_phys2, | ||
4821 | (ulong)cy_pci_phys0); | ||
4822 | printk("Cyclom-Y/PCI not supported for low " | ||
4823 | "addresses in Alpha systems.\n"); | ||
4824 | i--; | ||
4825 | continue; | ||
4826 | } | ||
4827 | #endif | ||
4828 | cy_pci_addr0 = ioremap(cy_pci_phys0, CyPCI_Yctl); | ||
4829 | cy_pci_addr2 = ioremap(cy_pci_phys2, CyPCI_Ywin); | ||
4830 | 4800 | ||
4831 | #ifdef CY_PCI_DEBUG | 4801 | retval = -EIO; |
4832 | printk("Cyclom-Y/PCI: relocate winaddr=0x%lx " | 4802 | if (device_id == PCI_DEVICE_ID_CYCLOM_Y_Lo || |
4833 | "ctladdr=0x%lx\n", | 4803 | device_id == PCI_DEVICE_ID_CYCLOM_Y_Hi) { |
4834 | (u_long)cy_pci_addr2, (u_long)cy_pci_addr0); | 4804 | card_name = "Cyclom-Y"; |
4835 | #endif | ||
4836 | cy_pci_nchan = (unsigned short)(CyPORTS_PER_CHIP * | ||
4837 | cyy_init_card(cy_pci_addr2, 1)); | ||
4838 | if (cy_pci_nchan == 0) { | ||
4839 | printk("Cyclom-Y PCI host card with "); | ||
4840 | printk("no Serial-Modules at 0x%lx.\n", | ||
4841 | (ulong) cy_pci_phys2); | ||
4842 | i--; | ||
4843 | continue; | ||
4844 | } | ||
4845 | if ((cy_next_channel + cy_pci_nchan) > NR_PORTS) { | ||
4846 | printk("Cyclom-Y/PCI found at 0x%lx ", | ||
4847 | (ulong) cy_pci_phys2); | ||
4848 | printk("but no channels are available.\n"); | ||
4849 | printk("Change NR_PORTS in cyclades.c and " | ||
4850 | "recompile kernel.\n"); | ||
4851 | return i; | ||
4852 | } | ||
4853 | /* fill the next cy_card structure available */ | ||
4854 | for (j = 0; j < NR_CARDS; j++) { | ||
4855 | if (cy_card[j].base_addr == 0) | ||
4856 | break; | ||
4857 | } | ||
4858 | if (j == NR_CARDS) { /* no more cy_cards available */ | ||
4859 | printk("Cyclom-Y/PCI found at 0x%lx ", | ||
4860 | (ulong) cy_pci_phys2); | ||
4861 | printk("but no more cards can be used.\n"); | ||
4862 | printk("Change NR_CARDS in cyclades.c and " | ||
4863 | "recompile kernel.\n"); | ||
4864 | return i; | ||
4865 | } | ||
4866 | 4805 | ||
4867 | /* allocate IRQ */ | 4806 | addr0 = pci_iomap(pdev, 0, CyPCI_Yctl); |
4868 | if (request_irq(cy_pci_irq, cyy_interrupt, | 4807 | if (addr0 == NULL) { |
4869 | IRQF_SHARED, "Cyclom-Y", &cy_card[j])) { | 4808 | dev_err(&pdev->dev, "can't remap ctl region\n"); |
4870 | printk("Cyclom-Y/PCI found at 0x%lx ", | 4809 | goto err_reg; |
4871 | (ulong) cy_pci_phys2); | 4810 | } |
4872 | printk("but could not allocate IRQ%d.\n", | 4811 | addr2 = pci_iomap(pdev, 2, CyPCI_Ywin); |
4873 | cy_pci_irq); | 4812 | if (addr2 == NULL) { |
4874 | return i; | 4813 | dev_err(&pdev->dev, "can't remap base region\n"); |
4875 | } | 4814 | goto err_unmap; |
4815 | } | ||
4876 | 4816 | ||
4877 | /* set cy_card */ | 4817 | nchan = CyPORTS_PER_CHIP * cyy_init_card(addr2, 1); |
4878 | cy_card[j].base_phys = (ulong) cy_pci_phys2; | 4818 | if (nchan == 0) { |
4879 | cy_card[j].ctl_phys = (ulong) cy_pci_phys0; | 4819 | dev_err(&pdev->dev, "Cyclom-Y PCI host card with no " |
4880 | cy_card[j].base_addr = cy_pci_addr2; | 4820 | "Serial-Modules\n"); |
4881 | cy_card[j].ctl_addr = cy_pci_addr0; | 4821 | return -EIO; |
4882 | cy_card[j].irq = (int)cy_pci_irq; | 4822 | } |
4883 | cy_card[j].bus_index = 1; | 4823 | } else if (device_id == PCI_DEVICE_ID_CYCLOM_Z_Hi) { |
4884 | cy_card[j].first_line = cy_next_channel; | 4824 | struct RUNTIME_9060 __iomem *ctl_addr; |
4885 | cy_card[j].num_chips = cy_pci_nchan / 4; | ||
4886 | cy_card[j].pdev = pdev; | ||
4887 | |||
4888 | /* enable interrupts in the PCI interface */ | ||
4889 | plx_ver = cy_readb(cy_pci_addr2 + CyPLX_VER) & 0x0f; | ||
4890 | switch (plx_ver) { | ||
4891 | case PLX_9050: | ||
4892 | |||
4893 | cy_writeb(cy_pci_addr0 + 0x4c, 0x43); | ||
4894 | break; | ||
4895 | 4825 | ||
4896 | case PLX_9060: | 4826 | ctl_addr = addr0 = pci_iomap(pdev, 0, CyPCI_Zctl); |
4897 | case PLX_9080: | 4827 | if (addr0 == NULL) { |
4898 | default: /* Old boards, use PLX_9060 */ | 4828 | dev_err(&pdev->dev, "can't remap ctl region\n"); |
4899 | 4829 | goto err_reg; | |
4900 | plx_init(cy_pci_addr0, 0x6c); | 4830 | } |
4901 | /* For some yet unknown reason, once the PLX9060 reloads | ||
4902 | the EEPROM, the IRQ is lost and, thus, we have to | ||
4903 | re-write it to the PCI config. registers. | ||
4904 | This will remain here until we find a permanent | ||
4905 | fix. */ | ||
4906 | pci_write_config_byte(pdev, PCI_INTERRUPT_LINE, | ||
4907 | cy_pci_irq); | ||
4908 | |||
4909 | cy_writew(cy_pci_addr0 + 0x68, | ||
4910 | cy_readw(cy_pci_addr0 + | ||
4911 | 0x68) | 0x0900); | ||
4912 | break; | ||
4913 | } | ||
4914 | 4831 | ||
4915 | /* print message */ | 4832 | /* Disable interrupts on the PLX before resetting it */ |
4916 | printk("Cyclom-Y/PCI #%d: 0x%lx-0x%lx, IRQ%d, ", | 4833 | cy_writew(addr0 + 0x68, |
4917 | j + 1, (ulong)cy_pci_phys2, | 4834 | readw(addr0 + 0x68) & ~0x0900); |
4918 | (ulong) (cy_pci_phys2 + CyPCI_Ywin - 1), | 4835 | |
4919 | (int)cy_pci_irq); | 4836 | plx_init(addr0, 0x6c); |
4920 | printk("%d channels starting from port %d.\n", | 4837 | /* For some yet unknown reason, once the PLX9060 reloads |
4921 | cy_pci_nchan, cy_next_channel); | 4838 | the EEPROM, the IRQ is lost and, thus, we have to |
4922 | 4839 | re-write it to the PCI config. registers. | |
4923 | cy_next_channel += cy_pci_nchan; | 4840 | This will remain here until we find a permanent |
4924 | } else if (device_id == PCI_DEVICE_ID_CYCLOM_Z_Lo) { | 4841 | fix. */ |
4925 | /* print message */ | 4842 | pci_write_config_byte(pdev, PCI_INTERRUPT_LINE, irq); |
4926 | printk("Cyclades-Z/PCI (bus=0x0%x, pci_id=0x%x, ", | 4843 | |
4927 | pdev->bus->number, pdev->devfn); | 4844 | mailbox = (u32)readl(&ctl_addr->mail_box_0); |
4928 | printk("rev_id=%d) IRQ%d\n", | 4845 | |
4929 | cyy_rev_id, (int)cy_pci_irq); | 4846 | addr2 = pci_iomap(pdev, 2, mailbox == ZE_V1 ? |
4930 | printk("Cyclades-Z/PCI: found winaddr=0x%lx " | 4847 | CyPCI_Ze_win : CyPCI_Zwin); |
4931 | "ctladdr=0x%lx\n", | 4848 | if (addr2 == NULL) { |
4932 | (ulong)cy_pci_phys2, (ulong)cy_pci_phys0); | 4849 | dev_err(&pdev->dev, "can't remap base region\n"); |
4933 | printk("Cyclades-Z/PCI not supported for low " | 4850 | goto err_unmap; |
4934 | "addresses\n"); | 4851 | } |
4935 | break; | ||
4936 | } else if (device_id == PCI_DEVICE_ID_CYCLOM_Z_Hi) { | ||
4937 | #ifdef CY_PCI_DEBUG | ||
4938 | printk("Cyclades-Z/PCI (bus=0x0%x, pci_id=0x%x, ", | ||
4939 | pdev->bus->number, pdev->devfn); | ||
4940 | printk("rev_id=%d) IRQ%d\n", | ||
4941 | cyy_rev_id, (int)cy_pci_irq); | ||
4942 | printk("Cyclades-Z/PCI: found winaddr=0x%lx " | ||
4943 | "ctladdr=0x%lx\n", | ||
4944 | (ulong) cy_pci_phys2, (ulong) cy_pci_phys0); | ||
4945 | #endif | ||
4946 | cy_pci_addr0 = ioremap(cy_pci_phys0, CyPCI_Zctl); | ||
4947 | |||
4948 | /* Disable interrupts on the PLX before resetting it */ | ||
4949 | cy_writew(cy_pci_addr0 + 0x68, | ||
4950 | cy_readw(cy_pci_addr0 + 0x68) & ~0x0900); | ||
4951 | |||
4952 | plx_init(cy_pci_addr0, 0x6c); | ||
4953 | /* For some yet unknown reason, once the PLX9060 reloads | ||
4954 | the EEPROM, the IRQ is lost and, thus, we have to | ||
4955 | re-write it to the PCI config. registers. | ||
4956 | This will remain here until we find a permanent | ||
4957 | fix. */ | ||
4958 | pci_write_config_byte(pdev, PCI_INTERRUPT_LINE, | ||
4959 | cy_pci_irq); | ||
4960 | |||
4961 | mailbox = | ||
4962 | (uclong)cy_readl(&((struct RUNTIME_9060 __iomem *) | ||
4963 | cy_pci_addr0)->mail_box_0); | ||
4964 | |||
4965 | if (pci_resource_flags(pdev, 2) & IORESOURCE_IO) { | ||
4966 | printk(" Warning: PCI I/O bit incorrectly " | ||
4967 | "set. Ignoring it...\n"); | ||
4968 | pdev->resource[2].flags &= ~IORESOURCE_IO; | ||
4969 | } | ||
4970 | 4852 | ||
4971 | /* Although we don't use this I/O region, we should | 4853 | if (mailbox == ZE_V1) { |
4972 | request it from the kernel anyway, to avoid problems | 4854 | card_name = "Cyclades-Ze"; |
4973 | with other drivers accessing it. */ | ||
4974 | if (pci_request_regions(pdev, "Cyclades-Z") != 0) { | ||
4975 | printk(KERN_ERR "cyclades: failed to reserve " | ||
4976 | "PCI resources\n"); | ||
4977 | continue; | ||
4978 | } | ||
4979 | 4855 | ||
4980 | if (mailbox == ZE_V1) { | 4856 | readl(&ctl_addr->mail_box_0); |
4981 | cy_pci_addr2 = ioremap(cy_pci_phys2, | 4857 | nchan = ZE_V1_NPORTS; |
4982 | CyPCI_Ze_win); | 4858 | } else { |
4983 | if (ZeIndex == NR_CARDS) { | 4859 | card_name = "Cyclades-8Zo"; |
4984 | printk("Cyclades-Ze/PCI found at " | ||
4985 | "0x%lx but no more cards can " | ||
4986 | "be used.\nChange NR_CARDS in " | ||
4987 | "cyclades.c and recompile " | ||
4988 | "kernel.\n", | ||
4989 | (ulong)cy_pci_phys2); | ||
4990 | } else { | ||
4991 | Ze_phys0[ZeIndex] = cy_pci_phys0; | ||
4992 | Ze_phys2[ZeIndex] = cy_pci_phys2; | ||
4993 | Ze_addr0[ZeIndex] = cy_pci_addr0; | ||
4994 | Ze_addr2[ZeIndex] = cy_pci_addr2; | ||
4995 | Ze_irq[ZeIndex] = cy_pci_irq; | ||
4996 | Ze_pdev[ZeIndex] = pdev; | ||
4997 | ZeIndex++; | ||
4998 | } | ||
4999 | i--; | ||
5000 | continue; | ||
5001 | } else { | ||
5002 | cy_pci_addr2 = ioremap(cy_pci_phys2,CyPCI_Zwin); | ||
5003 | } | ||
5004 | 4860 | ||
5005 | #ifdef CY_PCI_DEBUG | 4861 | #ifdef CY_PCI_DEBUG |
5006 | printk("Cyclades-Z/PCI: relocate winaddr=0x%lx " | ||
5007 | "ctladdr=0x%lx\n", | ||
5008 | (ulong) cy_pci_addr2, (ulong) cy_pci_addr0); | ||
5009 | if (mailbox == ZO_V1) { | 4862 | if (mailbox == ZO_V1) { |
5010 | cy_writel(&((struct RUNTIME_9060 *) | 4863 | cy_writel(&ctl_addr->loc_addr_base, WIN_CREG); |
5011 | (cy_pci_addr0))->loc_addr_base, | 4864 | dev_info(&pdev->dev, "Cyclades-8Zo/PCI: FPGA " |
5012 | WIN_CREG); | 4865 | "id %lx, ver %lx\n", (ulong)(0xff & |
5013 | PAUSE; | 4866 | readl(&((struct CUSTOM_REG *)addr2)-> |
5014 | printk("Cyclades-8Zo/PCI: FPGA id %lx, ver " | 4867 | fpga_id)), (ulong)(0xff & |
5015 | "%lx\n", (ulong) (0xff & | 4868 | readl(&((struct CUSTOM_REG *)addr2)-> |
5016 | cy_readl(&((struct CUSTOM_REG *) | 4869 | fpga_version))); |
5017 | (cy_pci_addr2))->fpga_id)), | 4870 | cy_writel(&ctl_addr->loc_addr_base, WIN_RAM); |
5018 | (ulong)(0xff & | ||
5019 | cy_readl(&((struct CUSTOM_REG *) | ||
5020 | (cy_pci_addr2))-> | ||
5021 | fpga_version))); | ||
5022 | cy_writel(&((struct RUNTIME_9060 *) | ||
5023 | (cy_pci_addr0))->loc_addr_base, | ||
5024 | WIN_RAM); | ||
5025 | } else { | 4871 | } else { |
5026 | printk("Cyclades-Z/PCI: New Cyclades-Z board. " | 4872 | dev_info(&pdev->dev, "Cyclades-Z/PCI: New " |
5027 | "FPGA not loaded\n"); | 4873 | "Cyclades-Z board. FPGA not loaded\n"); |
5028 | } | 4874 | } |
5029 | #endif | 4875 | #endif |
5030 | /* The following clears the firmware id word. This | 4876 | /* The following clears the firmware id word. This |
5031 | ensures that the driver will not attempt to talk to | 4877 | ensures that the driver will not attempt to talk to |
5032 | the board until it has been properly initialized. | 4878 | the board until it has been properly initialized. |
5033 | */ | 4879 | */ |
5034 | PAUSE; | ||
5035 | if ((mailbox == ZO_V1) || (mailbox == ZO_V2)) | 4880 | if ((mailbox == ZO_V1) || (mailbox == ZO_V2)) |
5036 | cy_writel(cy_pci_addr2 + ID_ADDRESS, 0L); | 4881 | cy_writel(addr2 + ID_ADDRESS, 0L); |
5037 | 4882 | ||
5038 | /* This must be a Cyclades-8Zo/PCI. The extendable | 4883 | /* This must be a Cyclades-8Zo/PCI. The extendable |
5039 | version will have a different device_id and will | 4884 | version will have a different device_id and will |
5040 | be allocated its maximum number of ports. */ | 4885 | be allocated its maximum number of ports. */ |
5041 | cy_pci_nchan = 8; | 4886 | nchan = 8; |
5042 | |||
5043 | if ((cy_next_channel + cy_pci_nchan) > NR_PORTS) { | ||
5044 | printk("Cyclades-8Zo/PCI found at 0x%lx but" | ||
5045 | "no channels are available.\nChange " | ||
5046 | "NR_PORTS in cyclades.c and recompile " | ||
5047 | "kernel.\n", (ulong)cy_pci_phys2); | ||
5048 | return i; | ||
5049 | } | ||
5050 | |||
5051 | /* fill the next cy_card structure available */ | ||
5052 | for (j = 0; j < NR_CARDS; j++) { | ||
5053 | if (cy_card[j].base_addr == 0) | ||
5054 | break; | ||
5055 | } | ||
5056 | if (j == NR_CARDS) { /* no more cy_cards available */ | ||
5057 | printk("Cyclades-8Zo/PCI found at 0x%lx but" | ||
5058 | "no more cards can be used.\nChange " | ||
5059 | "NR_CARDS in cyclades.c and recompile " | ||
5060 | "kernel.\n", (ulong)cy_pci_phys2); | ||
5061 | return i; | ||
5062 | } | ||
5063 | #ifdef CONFIG_CYZ_INTR | ||
5064 | /* allocate IRQ only if board has an IRQ */ | ||
5065 | if ((cy_pci_irq != 0) && (cy_pci_irq != 255)) { | ||
5066 | if (request_irq(cy_pci_irq, cyz_interrupt, | ||
5067 | IRQF_SHARED, "Cyclades-Z", | ||
5068 | &cy_card[j])) { | ||
5069 | printk("Cyclom-8Zo/PCI found at 0x%lx " | ||
5070 | "but could not allocate " | ||
5071 | "IRQ%d.\n", (ulong)cy_pci_phys2, | ||
5072 | cy_pci_irq); | ||
5073 | return i; | ||
5074 | } | ||
5075 | } | ||
5076 | #endif /* CONFIG_CYZ_INTR */ | ||
5077 | |||
5078 | /* set cy_card */ | ||
5079 | cy_card[j].base_phys = cy_pci_phys2; | ||
5080 | cy_card[j].ctl_phys = cy_pci_phys0; | ||
5081 | cy_card[j].base_addr = cy_pci_addr2; | ||
5082 | cy_card[j].ctl_addr = cy_pci_addr0; | ||
5083 | cy_card[j].irq = (int)cy_pci_irq; | ||
5084 | cy_card[j].bus_index = 1; | ||
5085 | cy_card[j].first_line = cy_next_channel; | ||
5086 | cy_card[j].num_chips = -1; | ||
5087 | cy_card[j].pdev = pdev; | ||
5088 | |||
5089 | /* print message */ | ||
5090 | #ifdef CONFIG_CYZ_INTR | ||
5091 | /* don't report IRQ if board is no IRQ */ | ||
5092 | if ((cy_pci_irq != 0) && (cy_pci_irq != 255)) | ||
5093 | printk("Cyclades-8Zo/PCI #%d: 0x%lx-0x%lx, " | ||
5094 | "IRQ%d, ", j + 1, (ulong)cy_pci_phys2, | ||
5095 | (ulong) (cy_pci_phys2 + CyPCI_Zwin - 1), | ||
5096 | (int)cy_pci_irq); | ||
5097 | else | ||
5098 | #endif /* CONFIG_CYZ_INTR */ | ||
5099 | printk("Cyclades-8Zo/PCI #%d: 0x%lx-0x%lx, ", | ||
5100 | j + 1, (ulong)cy_pci_phys2, | ||
5101 | (ulong)(cy_pci_phys2 + CyPCI_Zwin - 1)); | ||
5102 | |||
5103 | printk("%d channels starting from port %d.\n", | ||
5104 | cy_pci_nchan, cy_next_channel); | ||
5105 | cy_next_channel += cy_pci_nchan; | ||
5106 | } | 4887 | } |
5107 | } | 4888 | } |
5108 | 4889 | ||
5109 | for (; ZeIndex != 0 && i < NR_CARDS; i++) { | 4890 | if ((cy_next_channel + nchan) > NR_PORTS) { |
5110 | cy_pci_phys0 = Ze_phys0[0]; | 4891 | dev_err(&pdev->dev, "Cyclades-8Zo/PCI found, but no " |
5111 | cy_pci_phys2 = Ze_phys2[0]; | 4892 | "channels are available. Change NR_PORTS in " |
5112 | cy_pci_addr0 = Ze_addr0[0]; | 4893 | "cyclades.c and recompile kernel.\n"); |
5113 | cy_pci_addr2 = Ze_addr2[0]; | 4894 | goto err_unmap; |
5114 | cy_pci_irq = Ze_irq[0]; | 4895 | } |
5115 | pdev = Ze_pdev[0]; | 4896 | /* fill the next cy_card structure available */ |
5116 | for (j = 0; j < ZeIndex - 1; j++) { | 4897 | for (card_no = 0; card_no < NR_CARDS; card_no++) { |
5117 | Ze_phys0[j] = Ze_phys0[j + 1]; | 4898 | if (cy_card[card_no].base_addr == NULL) |
5118 | Ze_phys2[j] = Ze_phys2[j + 1]; | 4899 | break; |
5119 | Ze_addr0[j] = Ze_addr0[j + 1]; | 4900 | } |
5120 | Ze_addr2[j] = Ze_addr2[j + 1]; | 4901 | if (card_no == NR_CARDS) { /* no more cy_cards available */ |
5121 | Ze_irq[j] = Ze_irq[j + 1]; | 4902 | dev_err(&pdev->dev, "Cyclades-8Zo/PCI found, but no " |
5122 | Ze_pdev[j] = Ze_pdev[j + 1]; | 4903 | "more cards can be used. Change NR_CARDS in " |
5123 | } | 4904 | "cyclades.c and recompile kernel.\n"); |
5124 | ZeIndex--; | 4905 | goto err_unmap; |
5125 | mailbox = (uclong)cy_readl(&((struct RUNTIME_9060 __iomem *) | 4906 | } |
5126 | cy_pci_addr0)->mail_box_0); | ||
5127 | #ifdef CY_PCI_DEBUG | ||
5128 | printk("Cyclades-Z/PCI: relocate winaddr=0x%lx ctladdr=0x%lx\n", | ||
5129 | (ulong)cy_pci_addr2, (ulong)cy_pci_addr0); | ||
5130 | printk("Cyclades-Z/PCI: New Cyclades-Z board. FPGA not " | ||
5131 | "loaded\n"); | ||
5132 | #endif | ||
5133 | PAUSE; | ||
5134 | /* This must be the new Cyclades-Ze/PCI. */ | ||
5135 | cy_pci_nchan = ZE_V1_NPORTS; | ||
5136 | |||
5137 | if ((cy_next_channel + cy_pci_nchan) > NR_PORTS) { | ||
5138 | printk("Cyclades-Ze/PCI found at 0x%lx but no channels " | ||
5139 | "are available.\nChange NR_PORTS in cyclades.c " | ||
5140 | "and recompile kernel.\n", | ||
5141 | (ulong) cy_pci_phys2); | ||
5142 | return i; | ||
5143 | } | ||
5144 | 4907 | ||
5145 | /* fill the next cy_card structure available */ | 4908 | if (device_id == PCI_DEVICE_ID_CYCLOM_Y_Lo || |
5146 | for (j = 0; j < NR_CARDS; j++) { | 4909 | device_id == PCI_DEVICE_ID_CYCLOM_Y_Hi) { |
5147 | if (cy_card[j].base_addr == 0) | 4910 | /* allocate IRQ */ |
5148 | break; | 4911 | retval = request_irq(irq, cyy_interrupt, |
5149 | } | 4912 | IRQF_SHARED, "Cyclom-Y", &cy_card[card_no]); |
5150 | if (j == NR_CARDS) { /* no more cy_cards available */ | 4913 | if (retval) { |
5151 | printk("Cyclades-Ze/PCI found at 0x%lx but no more " | 4914 | dev_err(&pdev->dev, "could not allocate IRQ\n"); |
5152 | "cards can be used.\nChange NR_CARDS in " | 4915 | goto err_unmap; |
5153 | "cyclades.c and recompile kernel.\n", | ||
5154 | (ulong) cy_pci_phys2); | ||
5155 | return i; | ||
5156 | } | 4916 | } |
4917 | cy_card[card_no].num_chips = nchan / 4; | ||
4918 | } else { | ||
5157 | #ifdef CONFIG_CYZ_INTR | 4919 | #ifdef CONFIG_CYZ_INTR |
5158 | /* allocate IRQ only if board has an IRQ */ | 4920 | /* allocate IRQ only if board has an IRQ */ |
5159 | if ((cy_pci_irq != 0) && (cy_pci_irq != 255)) { | 4921 | if (irq != 0 && irq != 255) { |
5160 | if (request_irq(cy_pci_irq, cyz_interrupt, | 4922 | retval = request_irq(irq, cyz_interrupt, |
5161 | IRQF_SHARED, "Cyclades-Z", | 4923 | IRQF_SHARED, "Cyclades-Z", |
5162 | &cy_card[j])) { | 4924 | &cy_card[card_no]); |
5163 | printk("Cyclom-Ze/PCI found at 0x%lx ", | 4925 | if (retval) { |
5164 | (ulong) cy_pci_phys2); | 4926 | dev_err(&pdev->dev, "could not allocate IRQ\n"); |
5165 | printk("but could not allocate IRQ%d.\n", | 4927 | goto err_unmap; |
5166 | cy_pci_irq); | ||
5167 | return i; | ||
5168 | } | 4928 | } |
5169 | } | 4929 | } |
5170 | #endif /* CONFIG_CYZ_INTR */ | 4930 | #endif /* CONFIG_CYZ_INTR */ |
4931 | cy_card[card_no].num_chips = -1; | ||
4932 | } | ||
5171 | 4933 | ||
5172 | /* set cy_card */ | 4934 | /* set cy_card */ |
5173 | cy_card[j].base_phys = cy_pci_phys2; | 4935 | cy_card[card_no].base_addr = addr2; |
5174 | cy_card[j].ctl_phys = cy_pci_phys0; | 4936 | cy_card[card_no].ctl_addr = addr0; |
5175 | cy_card[j].base_addr = cy_pci_addr2; | 4937 | cy_card[card_no].irq = irq; |
5176 | cy_card[j].ctl_addr = cy_pci_addr0; | 4938 | cy_card[card_no].bus_index = 1; |
5177 | cy_card[j].irq = (int)cy_pci_irq; | 4939 | cy_card[card_no].first_line = cy_next_channel; |
5178 | cy_card[j].bus_index = 1; | 4940 | retval = cy_init_card(&cy_card[card_no]); |
5179 | cy_card[j].first_line = cy_next_channel; | 4941 | if (retval) |
5180 | cy_card[j].num_chips = -1; | 4942 | goto err_null; |
5181 | cy_card[j].pdev = pdev; | ||
5182 | 4943 | ||
5183 | /* print message */ | 4944 | pci_set_drvdata(pdev, &cy_card[card_no]); |
5184 | #ifdef CONFIG_CYZ_INTR | ||
5185 | /* don't report IRQ if board is no IRQ */ | ||
5186 | if ((cy_pci_irq != 0) && (cy_pci_irq != 255)) | ||
5187 | printk("Cyclades-Ze/PCI #%d: 0x%lx-0x%lx, IRQ%d, ", | ||
5188 | j + 1, (ulong) cy_pci_phys2, | ||
5189 | (ulong) (cy_pci_phys2 + CyPCI_Ze_win - 1), | ||
5190 | (int)cy_pci_irq); | ||
5191 | else | ||
5192 | #endif /* CONFIG_CYZ_INTR */ | ||
5193 | printk("Cyclades-Ze/PCI #%d: 0x%lx-0x%lx, ", | ||
5194 | j + 1, (ulong) cy_pci_phys2, | ||
5195 | (ulong) (cy_pci_phys2 + CyPCI_Ze_win - 1)); | ||
5196 | 4945 | ||
5197 | printk("%d channels starting from port %d.\n", | 4946 | if (device_id == PCI_DEVICE_ID_CYCLOM_Y_Lo || |
5198 | cy_pci_nchan, cy_next_channel); | 4947 | device_id == PCI_DEVICE_ID_CYCLOM_Y_Hi) { |
5199 | cy_next_channel += cy_pci_nchan; | 4948 | /* enable interrupts in the PCI interface */ |
5200 | } | 4949 | plx_ver = readb(addr2 + CyPLX_VER) & 0x0f; |
5201 | if (ZeIndex != 0) { | 4950 | switch (plx_ver) { |
5202 | printk("Cyclades-Ze/PCI found at 0x%x but no more cards can be " | 4951 | case PLX_9050: |
5203 | "used.\nChange NR_CARDS in cyclades.c and recompile " | 4952 | |
5204 | "kernel.\n", (unsigned int)Ze_phys2[0]); | 4953 | cy_writeb(addr0 + 0x4c, 0x43); |
4954 | break; | ||
4955 | |||
4956 | case PLX_9060: | ||
4957 | case PLX_9080: | ||
4958 | default: /* Old boards, use PLX_9060 */ | ||
4959 | |||
4960 | plx_init(addr0, 0x6c); | ||
4961 | /* For some yet unknown reason, once the PLX9060 reloads | ||
4962 | the EEPROM, the IRQ is lost and, thus, we have to | ||
4963 | re-write it to the PCI config. registers. | ||
4964 | This will remain here until we find a permanent | ||
4965 | fix. */ | ||
4966 | pci_write_config_byte(pdev, PCI_INTERRUPT_LINE, irq); | ||
4967 | |||
4968 | cy_writew(addr0 + 0x68, readw(addr0 + 0x68) | 0x0900); | ||
4969 | break; | ||
4970 | } | ||
5205 | } | 4971 | } |
5206 | return i; | 4972 | |
5207 | #else | 4973 | dev_info(&pdev->dev, "%s/PCI #%d found: %d channels starting from " |
4974 | "port %d.\n", card_name, card_no + 1, nchan, cy_next_channel); | ||
4975 | for (i = cy_next_channel; i < cy_next_channel + nchan; i++) | ||
4976 | tty_register_device(cy_serial_driver, i, &pdev->dev); | ||
4977 | cy_next_channel += nchan; | ||
4978 | |||
5208 | return 0; | 4979 | return 0; |
5209 | #endif /* ifdef CONFIG_PCI */ | 4980 | err_null: |
5210 | } /* cy_detect_pci */ | 4981 | cy_card[card_no].base_addr = NULL; |
4982 | free_irq(irq, &cy_card[card_no]); | ||
4983 | err_unmap: | ||
4984 | pci_iounmap(pdev, addr0); | ||
4985 | if (addr2) | ||
4986 | pci_iounmap(pdev, addr2); | ||
4987 | err_reg: | ||
4988 | pci_release_regions(pdev); | ||
4989 | err_dis: | ||
4990 | pci_disable_device(pdev); | ||
4991 | err: | ||
4992 | return retval; | ||
4993 | } | ||
5211 | 4994 | ||
5212 | /* | 4995 | static void __devexit cy_pci_remove(struct pci_dev *pdev) |
5213 | * This routine prints out the appropriate serial driver version number | ||
5214 | * and identifies which options were configured into this driver. | ||
5215 | */ | ||
5216 | static inline void show_version(void) | ||
5217 | { | 4996 | { |
5218 | printk("Cyclades driver " CY_VERSION "\n"); | 4997 | struct cyclades_card *cinfo = pci_get_drvdata(pdev); |
5219 | printk(" built %s %s\n", __DATE__, __TIME__); | 4998 | unsigned int i; |
5220 | } /* show_version */ | 4999 | |
5000 | /* non-Z with old PLX */ | ||
5001 | if (!IS_CYC_Z(*cinfo) && (readb(cinfo->base_addr + CyPLX_VER) & 0x0f) == | ||
5002 | PLX_9050) | ||
5003 | cy_writeb(cinfo->ctl_addr + 0x4c, 0); | ||
5004 | else | ||
5005 | #ifndef CONFIG_CYZ_INTR | ||
5006 | if (!IS_CYC_Z(*cinfo)) | ||
5007 | #endif | ||
5008 | cy_writew(cinfo->ctl_addr + 0x68, | ||
5009 | readw(cinfo->ctl_addr + 0x68) & ~0x0900); | ||
5010 | |||
5011 | pci_iounmap(pdev, cinfo->base_addr); | ||
5012 | if (cinfo->ctl_addr) | ||
5013 | pci_iounmap(pdev, cinfo->ctl_addr); | ||
5014 | if (cinfo->irq | ||
5015 | #ifndef CONFIG_CYZ_INTR | ||
5016 | && !IS_CYC_Z(*cinfo) | ||
5017 | #endif /* CONFIG_CYZ_INTR */ | ||
5018 | ) | ||
5019 | free_irq(cinfo->irq, cinfo); | ||
5020 | pci_release_regions(pdev); | ||
5021 | |||
5022 | cinfo->base_addr = NULL; | ||
5023 | for (i = cinfo->first_line; i < cinfo->first_line + | ||
5024 | cinfo->nports; i++) | ||
5025 | tty_unregister_device(cy_serial_driver, i); | ||
5026 | cinfo->nports = 0; | ||
5027 | kfree(cinfo->ports); | ||
5028 | } | ||
5029 | |||
5030 | static struct pci_driver cy_pci_driver = { | ||
5031 | .name = "cyclades", | ||
5032 | .id_table = cy_pci_dev_id, | ||
5033 | .probe = cy_pci_probe, | ||
5034 | .remove = __devexit_p(cy_pci_remove) | ||
5035 | }; | ||
5036 | #endif | ||
5221 | 5037 | ||
5222 | static int | 5038 | static int |
5223 | cyclades_get_proc_info(char *buf, char **start, off_t offset, int length, | 5039 | cyclades_get_proc_info(char *buf, char **start, off_t offset, int length, |
5224 | int *eof, void *data) | 5040 | int *eof, void *data) |
5225 | { | 5041 | { |
5226 | struct cyclades_port *info; | 5042 | struct cyclades_port *info; |
5227 | int i; | 5043 | unsigned int i, j; |
5228 | int len = 0; | 5044 | int len = 0; |
5229 | off_t begin = 0; | 5045 | off_t begin = 0; |
5230 | off_t pos = 0; | 5046 | off_t pos = 0; |
@@ -5238,33 +5054,34 @@ cyclades_get_proc_info(char *buf, char **start, off_t offset, int length, | |||
5238 | len += size; | 5054 | len += size; |
5239 | 5055 | ||
5240 | /* Output one line for each known port */ | 5056 | /* Output one line for each known port */ |
5241 | for (i = 0; i < NR_PORTS && cy_port[i].line >= 0; i++) { | 5057 | for (i = 0; i < NR_CARDS; i++) |
5242 | info = &cy_port[i]; | 5058 | for (j = 0; j < cy_card[i].nports; j++) { |
5243 | 5059 | info = &cy_card[i].ports[j]; | |
5244 | if (info->count) | 5060 | |
5245 | size = sprintf(buf + len, "%3d %8lu %10lu %8lu %10lu " | 5061 | if (info->count) |
5246 | "%8lu %9lu %6ld\n", info->line, | 5062 | size = sprintf(buf + len, "%3d %8lu %10lu %8lu " |
5247 | (cur_jifs - info->idle_stats.in_use) / HZ, | 5063 | "%10lu %8lu %9lu %6ld\n", info->line, |
5248 | info->idle_stats.xmit_bytes, | 5064 | (cur_jifs - info->idle_stats.in_use) / |
5249 | (cur_jifs - info->idle_stats.xmit_idle) / HZ, | 5065 | HZ, info->idle_stats.xmit_bytes, |
5250 | info->idle_stats.recv_bytes, | 5066 | (cur_jifs - info->idle_stats.xmit_idle)/ |
5251 | (cur_jifs - info->idle_stats.recv_idle) / HZ, | 5067 | HZ, info->idle_stats.recv_bytes, |
5252 | info->idle_stats.overruns, | 5068 | (cur_jifs - info->idle_stats.recv_idle)/ |
5253 | (long)info->tty->ldisc.num); | 5069 | HZ, info->idle_stats.overruns, |
5254 | else | 5070 | (long)info->tty->ldisc.num); |
5255 | size = sprintf(buf + len, "%3d %8lu %10lu %8lu %10lu " | 5071 | else |
5256 | "%8lu %9lu %6ld\n", | 5072 | size = sprintf(buf + len, "%3d %8lu %10lu %8lu " |
5257 | info->line, 0L, 0L, 0L, 0L, 0L, 0L, 0L); | 5073 | "%10lu %8lu %9lu %6ld\n", |
5258 | len += size; | 5074 | info->line, 0L, 0L, 0L, 0L, 0L, 0L, 0L); |
5259 | pos = begin + len; | 5075 | len += size; |
5260 | 5076 | pos = begin + len; | |
5261 | if (pos < offset) { | 5077 | |
5262 | len = 0; | 5078 | if (pos < offset) { |
5263 | begin = pos; | 5079 | len = 0; |
5080 | begin = pos; | ||
5081 | } | ||
5082 | if (pos > offset + length) | ||
5083 | goto done; | ||
5264 | } | 5084 | } |
5265 | if (pos > offset + length) | ||
5266 | goto done; | ||
5267 | } | ||
5268 | *eof = 1; | 5085 | *eof = 1; |
5269 | done: | 5086 | done: |
5270 | *start = buf + (offset - begin); /* Start of wanted data */ | 5087 | *start = buf + (offset - begin); /* Start of wanted data */ |
@@ -5319,18 +5136,15 @@ static const struct tty_operations cy_ops = { | |||
5319 | 5136 | ||
5320 | static int __init cy_init(void) | 5137 | static int __init cy_init(void) |
5321 | { | 5138 | { |
5322 | struct cyclades_port *info; | 5139 | unsigned int nboards; |
5323 | struct cyclades_card *cinfo; | 5140 | int retval = -ENOMEM; |
5324 | int number_z_boards = 0; | ||
5325 | int board, port, i, index; | ||
5326 | unsigned long mailbox; | ||
5327 | unsigned short chip_number; | ||
5328 | int nports; | ||
5329 | 5141 | ||
5330 | cy_serial_driver = alloc_tty_driver(NR_PORTS); | 5142 | cy_serial_driver = alloc_tty_driver(NR_PORTS); |
5331 | if (!cy_serial_driver) | 5143 | if (!cy_serial_driver) |
5332 | return -ENOMEM; | 5144 | goto err; |
5333 | show_version(); | 5145 | |
5146 | printk(KERN_INFO "Cyclades driver " CY_VERSION " (built %s %s)\n", | ||
5147 | __DATE__, __TIME__); | ||
5334 | 5148 | ||
5335 | /* Initialize the tty_driver structure */ | 5149 | /* Initialize the tty_driver structure */ |
5336 | 5150 | ||
@@ -5344,15 +5158,13 @@ static int __init cy_init(void) | |||
5344 | cy_serial_driver->init_termios = tty_std_termios; | 5158 | cy_serial_driver->init_termios = tty_std_termios; |
5345 | cy_serial_driver->init_termios.c_cflag = | 5159 | cy_serial_driver->init_termios.c_cflag = |
5346 | B9600 | CS8 | CREAD | HUPCL | CLOCAL; | 5160 | B9600 | CS8 | CREAD | HUPCL | CLOCAL; |
5347 | cy_serial_driver->flags = TTY_DRIVER_REAL_RAW; | 5161 | cy_serial_driver->flags = TTY_DRIVER_REAL_RAW | TTY_DRIVER_DYNAMIC_DEV; |
5348 | tty_set_operations(cy_serial_driver, &cy_ops); | 5162 | tty_set_operations(cy_serial_driver, &cy_ops); |
5349 | 5163 | ||
5350 | if (tty_register_driver(cy_serial_driver)) | 5164 | retval = tty_register_driver(cy_serial_driver); |
5351 | panic("Couldn't register Cyclades serial driver\n"); | 5165 | if (retval) { |
5352 | 5166 | printk(KERN_ERR "Couldn't register Cyclades serial driver\n"); | |
5353 | for (i = 0; i < NR_CARDS; i++) { | 5167 | goto err_frtty; |
5354 | /* base_addr=0 indicates board not found */ | ||
5355 | cy_card[i].base_addr = NULL; | ||
5356 | } | 5168 | } |
5357 | 5169 | ||
5358 | /* the code below is responsible to find the boards. Each different | 5170 | /* the code below is responsible to find the boards. Each different |
@@ -5363,223 +5175,68 @@ static int __init cy_init(void) | |||
5363 | the cy_next_channel. */ | 5175 | the cy_next_channel. */ |
5364 | 5176 | ||
5365 | /* look for isa boards */ | 5177 | /* look for isa boards */ |
5366 | cy_isa_nboard = cy_detect_isa(); | 5178 | nboards = cy_detect_isa(); |
5367 | 5179 | ||
5180 | #ifdef CONFIG_PCI | ||
5368 | /* look for pci boards */ | 5181 | /* look for pci boards */ |
5369 | cy_pci_nboard = cy_detect_pci(); | 5182 | retval = pci_register_driver(&cy_pci_driver); |
5370 | 5183 | if (retval && !nboards) | |
5371 | cy_nboard = cy_isa_nboard + cy_pci_nboard; | 5184 | goto err_unr; |
5372 | |||
5373 | /* invalidate remaining cy_card structures */ | ||
5374 | for (i = 0; i < NR_CARDS; i++) { | ||
5375 | if (cy_card[i].base_addr == 0) { | ||
5376 | cy_card[i].first_line = -1; | ||
5377 | cy_card[i].ctl_addr = NULL; | ||
5378 | cy_card[i].irq = 0; | ||
5379 | cy_card[i].bus_index = 0; | ||
5380 | cy_card[i].first_line = 0; | ||
5381 | cy_card[i].num_chips = 0; | ||
5382 | } | ||
5383 | } | ||
5384 | /* invalidate remaining cy_port structures */ | ||
5385 | for (i = cy_next_channel; i < NR_PORTS; i++) { | ||
5386 | cy_port[i].line = -1; | ||
5387 | cy_port[i].magic = -1; | ||
5388 | } | ||
5389 | |||
5390 | /* initialize per-port data structures for each valid board found */ | ||
5391 | for (board = 0; board < cy_nboard; board++) { | ||
5392 | cinfo = &cy_card[board]; | ||
5393 | if (cinfo->num_chips == -1) { /* Cyclades-Z */ | ||
5394 | number_z_boards++; | ||
5395 | mailbox = cy_readl(&((struct RUNTIME_9060 __iomem *) | ||
5396 | cy_card[board].ctl_addr)-> | ||
5397 | mail_box_0); | ||
5398 | nports = (mailbox == ZE_V1) ? ZE_V1_NPORTS : 8; | ||
5399 | cinfo->intr_enabled = 0; | ||
5400 | cinfo->nports = 0; /* Will be correctly set later, after | ||
5401 | Z FW is loaded */ | ||
5402 | spin_lock_init(&cinfo->card_lock); | ||
5403 | for (port = cinfo->first_line; | ||
5404 | port < cinfo->first_line + nports; port++) { | ||
5405 | info = &cy_port[port]; | ||
5406 | info->magic = CYCLADES_MAGIC; | ||
5407 | info->type = PORT_STARTECH; | ||
5408 | info->card = board; | ||
5409 | info->line = port; | ||
5410 | info->chip_rev = 0; | ||
5411 | info->flags = STD_COM_FLAGS; | ||
5412 | info->tty = NULL; | ||
5413 | if (mailbox == ZO_V1) | ||
5414 | info->xmit_fifo_size = CYZ_FIFO_SIZE; | ||
5415 | else | ||
5416 | info->xmit_fifo_size = | ||
5417 | 4 * CYZ_FIFO_SIZE; | ||
5418 | info->cor1 = 0; | ||
5419 | info->cor2 = 0; | ||
5420 | info->cor3 = 0; | ||
5421 | info->cor4 = 0; | ||
5422 | info->cor5 = 0; | ||
5423 | info->tbpr = 0; | ||
5424 | info->tco = 0; | ||
5425 | info->rbpr = 0; | ||
5426 | info->rco = 0; | ||
5427 | info->custom_divisor = 0; | ||
5428 | info->close_delay = 5 * HZ / 10; | ||
5429 | info->closing_wait = CLOSING_WAIT_DELAY; | ||
5430 | info->icount.cts = info->icount.dsr = | ||
5431 | info->icount.rng = info->icount.dcd = 0; | ||
5432 | info->icount.rx = info->icount.tx = 0; | ||
5433 | info->icount.frame = info->icount.parity = 0; | ||
5434 | info->icount.overrun = info->icount.brk = 0; | ||
5435 | info->x_char = 0; | ||
5436 | info->event = 0; | ||
5437 | info->count = 0; | ||
5438 | info->blocked_open = 0; | ||
5439 | info->default_threshold = 0; | ||
5440 | info->default_timeout = 0; | ||
5441 | INIT_WORK(&info->tqueue, do_softint); | ||
5442 | init_waitqueue_head(&info->open_wait); | ||
5443 | init_waitqueue_head(&info->close_wait); | ||
5444 | init_waitqueue_head(&info->shutdown_wait); | ||
5445 | init_waitqueue_head(&info->delta_msr_wait); | ||
5446 | /* info->session */ | ||
5447 | /* info->pgrp */ | ||
5448 | info->read_status_mask = 0; | ||
5449 | /* info->timeout */ | ||
5450 | /* Bentson's vars */ | ||
5451 | info->jiffies[0] = 0; | ||
5452 | info->jiffies[1] = 0; | ||
5453 | info->jiffies[2] = 0; | ||
5454 | info->rflush_count = 0; | ||
5455 | #ifdef CONFIG_CYZ_INTR | ||
5456 | init_timer(&cyz_rx_full_timer[port]); | ||
5457 | cyz_rx_full_timer[port].function = NULL; | ||
5458 | #endif | 5185 | #endif |
5459 | } | ||
5460 | continue; | ||
5461 | } else { /* Cyclom-Y of some kind */ | ||
5462 | index = cinfo->bus_index; | ||
5463 | spin_lock_init(&cinfo->card_lock); | ||
5464 | cinfo->nports = CyPORTS_PER_CHIP * cinfo->num_chips; | ||
5465 | for (port = cinfo->first_line; | ||
5466 | port < cinfo->first_line + cinfo->nports; port++) { | ||
5467 | info = &cy_port[port]; | ||
5468 | info->magic = CYCLADES_MAGIC; | ||
5469 | info->type = PORT_CIRRUS; | ||
5470 | info->card = board; | ||
5471 | info->line = port; | ||
5472 | info->flags = STD_COM_FLAGS; | ||
5473 | info->tty = NULL; | ||
5474 | info->xmit_fifo_size = CyMAX_CHAR_FIFO; | ||
5475 | info->cor1 = | ||
5476 | CyPARITY_NONE | Cy_1_STOP | Cy_8_BITS; | ||
5477 | info->cor2 = CyETC; | ||
5478 | info->cor3 = 0x08; /* _very_ small rcv threshold */ | ||
5479 | info->cor4 = 0; | ||
5480 | info->cor5 = 0; | ||
5481 | info->custom_divisor = 0; | ||
5482 | info->close_delay = 5 * HZ / 10; | ||
5483 | info->closing_wait = CLOSING_WAIT_DELAY; | ||
5484 | info->icount.cts = info->icount.dsr = | ||
5485 | info->icount.rng = info->icount.dcd = 0; | ||
5486 | info->icount.rx = info->icount.tx = 0; | ||
5487 | info->icount.frame = info->icount.parity = 0; | ||
5488 | info->icount.overrun = info->icount.brk = 0; | ||
5489 | chip_number = (port - cinfo->first_line) / 4; | ||
5490 | if ((info->chip_rev = | ||
5491 | cy_readb(cinfo->base_addr + | ||
5492 | (cy_chip_offset[chip_number] << | ||
5493 | index) + (CyGFRCR << index))) >= | ||
5494 | CD1400_REV_J) { | ||
5495 | /* It is a CD1400 rev. J or later */ | ||
5496 | info->tbpr = baud_bpr_60[13]; /* Tx BPR */ | ||
5497 | info->tco = baud_co_60[13]; /* Tx CO */ | ||
5498 | info->rbpr = baud_bpr_60[13]; /* Rx BPR */ | ||
5499 | info->rco = baud_co_60[13]; /* Rx CO */ | ||
5500 | info->rflow = 0; | ||
5501 | info->rtsdtr_inv = 1; | ||
5502 | } else { | ||
5503 | info->tbpr = baud_bpr_25[13]; /* Tx BPR */ | ||
5504 | info->tco = baud_co_25[13]; /* Tx CO */ | ||
5505 | info->rbpr = baud_bpr_25[13]; /* Rx BPR */ | ||
5506 | info->rco = baud_co_25[13]; /* Rx CO */ | ||
5507 | info->rflow = 0; | ||
5508 | info->rtsdtr_inv = 0; | ||
5509 | } | ||
5510 | info->x_char = 0; | ||
5511 | info->event = 0; | ||
5512 | info->count = 0; | ||
5513 | info->blocked_open = 0; | ||
5514 | info->default_threshold = 0; | ||
5515 | info->default_timeout = 0; | ||
5516 | INIT_WORK(&info->tqueue, do_softint); | ||
5517 | init_waitqueue_head(&info->open_wait); | ||
5518 | init_waitqueue_head(&info->close_wait); | ||
5519 | init_waitqueue_head(&info->shutdown_wait); | ||
5520 | init_waitqueue_head(&info->delta_msr_wait); | ||
5521 | /* info->session */ | ||
5522 | /* info->pgrp */ | ||
5523 | info->read_status_mask = | ||
5524 | CyTIMEOUT | CySPECHAR | CyBREAK | ||
5525 | | CyPARITY | CyFRAME | CyOVERRUN; | ||
5526 | /* info->timeout */ | ||
5527 | } | ||
5528 | } | ||
5529 | } | ||
5530 | |||
5531 | #ifndef CONFIG_CYZ_INTR | ||
5532 | if (number_z_boards && !cyz_timeron) { | ||
5533 | cyz_timeron++; | ||
5534 | cyz_timerlist.expires = jiffies + 1; | ||
5535 | add_timer(&cyz_timerlist); | ||
5536 | #ifdef CY_PCI_DEBUG | ||
5537 | printk("Cyclades-Z polling initialized\n"); | ||
5538 | #endif | ||
5539 | } | ||
5540 | #endif /* CONFIG_CYZ_INTR */ | ||
5541 | 5186 | ||
5542 | return 0; | 5187 | return 0; |
5543 | 5188 | err_unr: | |
5189 | tty_unregister_driver(cy_serial_driver); | ||
5190 | err_frtty: | ||
5191 | put_tty_driver(cy_serial_driver); | ||
5192 | err: | ||
5193 | return retval; | ||
5544 | } /* cy_init */ | 5194 | } /* cy_init */ |
5545 | 5195 | ||
5546 | static void __exit cy_cleanup_module(void) | 5196 | static void __exit cy_cleanup_module(void) |
5547 | { | 5197 | { |
5198 | struct cyclades_card *card; | ||
5548 | int i, e1; | 5199 | int i, e1; |
5549 | 5200 | ||
5550 | #ifndef CONFIG_CYZ_INTR | 5201 | #ifndef CONFIG_CYZ_INTR |
5551 | if (cyz_timeron){ | 5202 | del_timer_sync(&cyz_timerlist); |
5552 | cyz_timeron = 0; | ||
5553 | del_timer(&cyz_timerlist); | ||
5554 | } | ||
5555 | #endif /* CONFIG_CYZ_INTR */ | 5203 | #endif /* CONFIG_CYZ_INTR */ |
5556 | 5204 | ||
5557 | if ((e1 = tty_unregister_driver(cy_serial_driver))) | 5205 | if ((e1 = tty_unregister_driver(cy_serial_driver))) |
5558 | printk("cyc: failed to unregister Cyclades serial driver(%d)\n", | 5206 | printk(KERN_ERR "failed to unregister Cyclades serial " |
5559 | e1); | 5207 | "driver(%d)\n", e1); |
5560 | 5208 | ||
5561 | put_tty_driver(cy_serial_driver); | 5209 | #ifdef CONFIG_PCI |
5210 | pci_unregister_driver(&cy_pci_driver); | ||
5211 | #endif | ||
5562 | 5212 | ||
5563 | for (i = 0; i < NR_CARDS; i++) { | 5213 | for (i = 0; i < NR_CARDS; i++) { |
5564 | if (cy_card[i].base_addr) { | 5214 | card = &cy_card[i]; |
5565 | iounmap(cy_card[i].base_addr); | 5215 | if (card->base_addr) { |
5566 | if (cy_card[i].ctl_addr) | 5216 | /* clear interrupt */ |
5567 | iounmap(cy_card[i].ctl_addr); | 5217 | cy_writeb(card->base_addr + Cy_ClrIntr, 0); |
5568 | if (cy_card[i].irq | 5218 | iounmap(card->base_addr); |
5219 | if (card->ctl_addr) | ||
5220 | iounmap(card->ctl_addr); | ||
5221 | if (card->irq | ||
5569 | #ifndef CONFIG_CYZ_INTR | 5222 | #ifndef CONFIG_CYZ_INTR |
5570 | && cy_card[i].num_chips != -1 /* not a Z card */ | 5223 | && !IS_CYC_Z(*card) |
5571 | #endif /* CONFIG_CYZ_INTR */ | 5224 | #endif /* CONFIG_CYZ_INTR */ |
5572 | ) | 5225 | ) |
5573 | free_irq(cy_card[i].irq, &cy_card[i]); | 5226 | free_irq(card->irq, card); |
5574 | #ifdef CONFIG_PCI | 5227 | for (e1 = card->first_line; |
5575 | if (cy_card[i].pdev) | 5228 | e1 < card->first_line + |
5576 | pci_release_regions(cy_card[i].pdev); | 5229 | card->nports; e1++) |
5577 | #endif | 5230 | tty_unregister_device(cy_serial_driver, e1); |
5231 | kfree(card->ports); | ||
5578 | } | 5232 | } |
5579 | } | 5233 | } |
5234 | |||
5235 | put_tty_driver(cy_serial_driver); | ||
5580 | } /* cy_cleanup_module */ | 5236 | } /* cy_cleanup_module */ |
5581 | 5237 | ||
5582 | module_init(cy_init); | 5238 | module_init(cy_init); |
5583 | module_exit(cy_cleanup_module); | 5239 | module_exit(cy_cleanup_module); |
5584 | 5240 | ||
5585 | MODULE_LICENSE("GPL"); | 5241 | MODULE_LICENSE("GPL"); |
5242 | MODULE_VERSION(CY_VERSION); | ||