diff options
| author | Tejun Heo <htejun@gmail.com> | 2006-07-03 03:07:27 -0400 |
|---|---|---|
| committer | Jeff Garzik <jeff@garzik.org> | 2006-07-05 22:16:28 -0400 |
| commit | 2a41a6108d93a62910d1c36913d83a79b550b40a (patch) | |
| tree | cebc87c478fd968503bdfec6c7bd3fddc9a66fdb | |
| parent | afb5a7cb84b1ea8b6045945e3d288303e6b71336 (diff) | |
[PATCH] sata_sil24: separate out sil24_init_controller()
Separate out controller initialization from sil24_init_one() into
sil24_init_controller(). This will be used by resume.
Signed-off-by: Tejun Heo <htejun@gmail.com>
Signed-off-by: Jeff Garzik <jeff@garzik.org>
| -rw-r--r-- | drivers/scsi/sata_sil24.c | 107 |
1 files changed, 62 insertions, 45 deletions
diff --git a/drivers/scsi/sata_sil24.c b/drivers/scsi/sata_sil24.c index 04ae1ef25484..1850c2e3aa21 100644 --- a/drivers/scsi/sata_sil24.c +++ b/drivers/scsi/sata_sil24.c | |||
| @@ -988,6 +988,64 @@ static void sil24_host_stop(struct ata_host_set *host_set) | |||
| 988 | kfree(hpriv); | 988 | kfree(hpriv); |
| 989 | } | 989 | } |
| 990 | 990 | ||
| 991 | static void sil24_init_controller(struct pci_dev *pdev, int n_ports, | ||
| 992 | unsigned long host_flags, | ||
| 993 | void __iomem *host_base, | ||
| 994 | void __iomem *port_base) | ||
| 995 | { | ||
| 996 | u32 tmp; | ||
| 997 | int i; | ||
| 998 | |||
| 999 | /* GPIO off */ | ||
| 1000 | writel(0, host_base + HOST_FLASH_CMD); | ||
| 1001 | |||
| 1002 | /* clear global reset & mask interrupts during initialization */ | ||
| 1003 | writel(0, host_base + HOST_CTRL); | ||
| 1004 | |||
| 1005 | /* init ports */ | ||
| 1006 | for (i = 0; i < n_ports; i++) { | ||
| 1007 | void __iomem *port = port_base + i * PORT_REGS_SIZE; | ||
| 1008 | |||
| 1009 | /* Initial PHY setting */ | ||
| 1010 | writel(0x20c, port + PORT_PHY_CFG); | ||
| 1011 | |||
| 1012 | /* Clear port RST */ | ||
| 1013 | tmp = readl(port + PORT_CTRL_STAT); | ||
| 1014 | if (tmp & PORT_CS_PORT_RST) { | ||
| 1015 | writel(PORT_CS_PORT_RST, port + PORT_CTRL_CLR); | ||
| 1016 | tmp = ata_wait_register(port + PORT_CTRL_STAT, | ||
| 1017 | PORT_CS_PORT_RST, | ||
| 1018 | PORT_CS_PORT_RST, 10, 100); | ||
| 1019 | if (tmp & PORT_CS_PORT_RST) | ||
| 1020 | dev_printk(KERN_ERR, &pdev->dev, | ||
| 1021 | "failed to clear port RST\n"); | ||
| 1022 | } | ||
| 1023 | |||
| 1024 | /* Configure IRQ WoC */ | ||
| 1025 | if (host_flags & SIL24_FLAG_PCIX_IRQ_WOC) | ||
| 1026 | writel(PORT_CS_IRQ_WOC, port + PORT_CTRL_STAT); | ||
| 1027 | else | ||
| 1028 | writel(PORT_CS_IRQ_WOC, port + PORT_CTRL_CLR); | ||
| 1029 | |||
| 1030 | /* Zero error counters. */ | ||
| 1031 | writel(0x8000, port + PORT_DECODE_ERR_THRESH); | ||
| 1032 | writel(0x8000, port + PORT_CRC_ERR_THRESH); | ||
| 1033 | writel(0x8000, port + PORT_HSHK_ERR_THRESH); | ||
| 1034 | writel(0x0000, port + PORT_DECODE_ERR_CNT); | ||
| 1035 | writel(0x0000, port + PORT_CRC_ERR_CNT); | ||
| 1036 | writel(0x0000, port + PORT_HSHK_ERR_CNT); | ||
| 1037 | |||
| 1038 | /* Always use 64bit activation */ | ||
| 1039 | writel(PORT_CS_32BIT_ACTV, port + PORT_CTRL_CLR); | ||
| 1040 | |||
| 1041 | /* Clear port multiplier enable and resume bits */ | ||
| 1042 | writel(PORT_CS_PM_EN | PORT_CS_RESUME, port + PORT_CTRL_CLR); | ||
| 1043 | } | ||
| 1044 | |||
| 1045 | /* Turn on interrupts */ | ||
| 1046 | writel(IRQ_STAT_4PORTS, host_base + HOST_CTRL); | ||
| 1047 | } | ||
| 1048 | |||
| 991 | static int sil24_init_one(struct pci_dev *pdev, const struct pci_device_id *ent) | 1049 | static int sil24_init_one(struct pci_dev *pdev, const struct pci_device_id *ent) |
| 992 | { | 1050 | { |
| 993 | static int printed_version = 0; | 1051 | static int printed_version = 0; |
| @@ -1076,9 +1134,6 @@ static int sil24_init_one(struct pci_dev *pdev, const struct pci_device_id *ent) | |||
| 1076 | } | 1134 | } |
| 1077 | } | 1135 | } |
| 1078 | 1136 | ||
| 1079 | /* GPIO off */ | ||
| 1080 | writel(0, host_base + HOST_FLASH_CMD); | ||
| 1081 | |||
| 1082 | /* Apply workaround for completion IRQ loss on PCI-X errata */ | 1137 | /* Apply workaround for completion IRQ loss on PCI-X errata */ |
| 1083 | if (probe_ent->host_flags & SIL24_FLAG_PCIX_IRQ_WOC) { | 1138 | if (probe_ent->host_flags & SIL24_FLAG_PCIX_IRQ_WOC) { |
| 1084 | tmp = readl(host_base + HOST_CTRL); | 1139 | tmp = readl(host_base + HOST_CTRL); |
| @@ -1090,56 +1145,18 @@ static int sil24_init_one(struct pci_dev *pdev, const struct pci_device_id *ent) | |||
| 1090 | probe_ent->host_flags &= ~SIL24_FLAG_PCIX_IRQ_WOC; | 1145 | probe_ent->host_flags &= ~SIL24_FLAG_PCIX_IRQ_WOC; |
| 1091 | } | 1146 | } |
| 1092 | 1147 | ||
| 1093 | /* clear global reset & mask interrupts during initialization */ | ||
| 1094 | writel(0, host_base + HOST_CTRL); | ||
| 1095 | |||
| 1096 | for (i = 0; i < probe_ent->n_ports; i++) { | 1148 | for (i = 0; i < probe_ent->n_ports; i++) { |
| 1097 | void __iomem *port = port_base + i * PORT_REGS_SIZE; | 1149 | unsigned long portu = |
| 1098 | unsigned long portu = (unsigned long)port; | 1150 | (unsigned long)port_base + i * PORT_REGS_SIZE; |
| 1099 | 1151 | ||
| 1100 | probe_ent->port[i].cmd_addr = portu; | 1152 | probe_ent->port[i].cmd_addr = portu; |
| 1101 | probe_ent->port[i].scr_addr = portu + PORT_SCONTROL; | 1153 | probe_ent->port[i].scr_addr = portu + PORT_SCONTROL; |
| 1102 | 1154 | ||
| 1103 | ata_std_ports(&probe_ent->port[i]); | 1155 | ata_std_ports(&probe_ent->port[i]); |
| 1104 | |||
| 1105 | /* Initial PHY setting */ | ||
| 1106 | writel(0x20c, port + PORT_PHY_CFG); | ||
| 1107 | |||
| 1108 | /* Clear port RST */ | ||
| 1109 | tmp = readl(port + PORT_CTRL_STAT); | ||
| 1110 | if (tmp & PORT_CS_PORT_RST) { | ||
| 1111 | writel(PORT_CS_PORT_RST, port + PORT_CTRL_CLR); | ||
| 1112 | tmp = ata_wait_register(port + PORT_CTRL_STAT, | ||
| 1113 | PORT_CS_PORT_RST, | ||
| 1114 | PORT_CS_PORT_RST, 10, 100); | ||
| 1115 | if (tmp & PORT_CS_PORT_RST) | ||
| 1116 | dev_printk(KERN_ERR, &pdev->dev, | ||
| 1117 | "failed to clear port RST\n"); | ||
| 1118 | } | ||
| 1119 | |||
| 1120 | /* Configure IRQ WoC */ | ||
| 1121 | if (probe_ent->host_flags & SIL24_FLAG_PCIX_IRQ_WOC) | ||
| 1122 | writel(PORT_CS_IRQ_WOC, port + PORT_CTRL_STAT); | ||
| 1123 | else | ||
| 1124 | writel(PORT_CS_IRQ_WOC, port + PORT_CTRL_CLR); | ||
| 1125 | |||
| 1126 | /* Zero error counters. */ | ||
| 1127 | writel(0x8000, port + PORT_DECODE_ERR_THRESH); | ||
| 1128 | writel(0x8000, port + PORT_CRC_ERR_THRESH); | ||
| 1129 | writel(0x8000, port + PORT_HSHK_ERR_THRESH); | ||
| 1130 | writel(0x0000, port + PORT_DECODE_ERR_CNT); | ||
| 1131 | writel(0x0000, port + PORT_CRC_ERR_CNT); | ||
| 1132 | writel(0x0000, port + PORT_HSHK_ERR_CNT); | ||
| 1133 | |||
| 1134 | /* Always use 64bit activation */ | ||
| 1135 | writel(PORT_CS_32BIT_ACTV, port + PORT_CTRL_CLR); | ||
| 1136 | |||
| 1137 | /* Clear port multiplier enable and resume bits */ | ||
| 1138 | writel(PORT_CS_PM_EN | PORT_CS_RESUME, port + PORT_CTRL_CLR); | ||
| 1139 | } | 1156 | } |
| 1140 | 1157 | ||
| 1141 | /* Turn on interrupts */ | 1158 | sil24_init_controller(pdev, probe_ent->n_ports, probe_ent->host_flags, |
| 1142 | writel(IRQ_STAT_4PORTS, host_base + HOST_CTRL); | 1159 | host_base, port_base); |
| 1143 | 1160 | ||
| 1144 | pci_set_master(pdev); | 1161 | pci_set_master(pdev); |
| 1145 | 1162 | ||
