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 | ||