1/* 2 * sata_sis.c - Silicon Integrated Systems SATA 3 * 4 * Maintained by: Uwe Koziolek 5 * Please ALWAYS copy linux-ide@vger.kernel.org 6 * on emails. 7 * 8 * Copyright 2004 Uwe Koziolek 9 * 10 * 11 * This program is free software; you can redistribute it and/or modify 12 * it under the terms of the GNU General Public License as published by 13 * the Free Software Foundation; either version 2, or (at your option) 14 * any later version. 15 * 16 * This program is distributed in the hope that it will be useful, 17 * but WITHOUT ANY WARRANTY; without even the implied warranty of 18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 19 * GNU General Public License for more details. 20 * 21 * You should have received a copy of the GNU General Public License 22 * along with this program; see the file COPYING. If not, write to 23 * the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. 24 * 25 * 26 * libata documentation is available via 'make {ps|pdf}docs', 27 * as Documentation/DocBook/libata.* 28 * 29 * Hardware documentation available under NDA. 30 * 31 */ 32 33#include <linux/kernel.h> 34#include <linux/module.h> 35#include <linux/pci.h> 36#include <linux/blkdev.h> 37#include <linux/delay.h> 38#include <linux/interrupt.h> 39#include <linux/device.h> 40#include <scsi/scsi_host.h> 41#include <linux/libata.h> 42#include "sis.h" 43 44#define DRV_NAME "sata_sis" 45#define DRV_VERSION "1.0" 46 47enum { 48 sis_180 = 0, 49 SIS_SCR_PCI_BAR = 5, 50 51 /* PCI configuration registers */ 52 SIS_GENCTL = 0x54, /* IDE General Control register */ 53 SIS_SCR_BASE = 0xc0, /* sata0 phy SCR registers */ 54 SIS180_SATA1_OFS = 0x10, /* offset from sata0->sata1 phy regs */ 55 SIS182_SATA1_OFS = 0x20, /* offset from sata0->sata1 phy regs */ 56 SIS_PMR = 0x90, /* port mapping register */ 57 SIS_PMR_COMBINED = 0x30, 58 59 /* random bits */ 60 SIS_FLAG_CFGSCR = (1 << 30), /* host flag: SCRs via PCI cfg */ 61 62 GENCTL_IOMAPPED_SCR = (1 << 26), /* if set, SCRs are in IO space */ 63}; 64 65static int sis_init_one(struct pci_dev *pdev, const struct pci_device_id *ent); 66static int sis_scr_read(struct ata_link *link, unsigned int sc_reg, u32 *val); 67static int sis_scr_write(struct ata_link *link, unsigned int sc_reg, u32 val); 68 69static const struct pci_device_id sis_pci_tbl[] = { 70 { PCI_VDEVICE(SI, 0x0180), sis_180 }, /* SiS 964/180 */ 71 { PCI_VDEVICE(SI, 0x0181), sis_180 }, /* SiS 964/180 */ 72 { PCI_VDEVICE(SI, 0x0182), sis_180 }, /* SiS 965/965L */ 73 { PCI_VDEVICE(SI, 0x0183), sis_180 }, /* SiS 965/965L */ 74 { PCI_VDEVICE(SI, 0x1182), sis_180 }, /* SiS 966/680 */ 75 { PCI_VDEVICE(SI, 0x1183), sis_180 }, /* SiS 966/966L/968/680 */ 76 77 { } /* terminate list */ 78}; 79 80static struct pci_driver sis_pci_driver = { 81 .name = DRV_NAME, 82 .id_table = sis_pci_tbl, 83 .probe = sis_init_one, 84 .remove = ata_pci_remove_one, 85#ifdef CONFIG_PM_SLEEP 86 .suspend = ata_pci_device_suspend, 87 .resume = ata_pci_device_resume, 88#endif 89}; 90 91static struct scsi_host_template sis_sht = { 92 ATA_BMDMA_SHT(DRV_NAME), 93}; 94 95static struct ata_port_operations sis_ops = { 96 .inherits = &ata_bmdma_port_ops, 97 .scr_read = sis_scr_read, 98 .scr_write = sis_scr_write, 99}; 100 101static const struct ata_port_info sis_port_info = { 102 .flags = ATA_FLAG_SATA, 103 .pio_mask = ATA_PIO4, 104 .mwdma_mask = ATA_MWDMA2, 105 .udma_mask = ATA_UDMA6, 106 .port_ops = &sis_ops, 107}; 108 109MODULE_AUTHOR("Uwe Koziolek"); 110MODULE_DESCRIPTION("low-level driver for Silicon Integrated Systems SATA controller"); 111MODULE_LICENSE("GPL"); 112MODULE_DEVICE_TABLE(pci, sis_pci_tbl); 113MODULE_VERSION(DRV_VERSION); 114 115static unsigned int get_scr_cfg_addr(struct ata_link *link, unsigned int sc_reg) 116{ 117 struct ata_port *ap = link->ap; 118 struct pci_dev *pdev = to_pci_dev(ap->host->dev); 119 unsigned int addr = SIS_SCR_BASE + (4 * sc_reg); 120 u8 pmr; 121 122 if (ap->port_no) { 123 switch (pdev->device) { 124 case 0x0180: 125 case 0x0181: 126 pci_read_config_byte(pdev, SIS_PMR, &pmr); 127 if ((pmr & SIS_PMR_COMBINED) == 0) 128 addr += SIS180_SATA1_OFS; 129 break; 130 131 case 0x0182: 132 case 0x0183: 133 case 0x1182: 134 addr += SIS182_SATA1_OFS; 135 break; 136 } 137 } 138 if (link->pmp) 139 addr += 0x10; 140 141 return addr; 142} 143 144static u32 sis_scr_cfg_read(struct ata_link *link, 145 unsigned int sc_reg, u32 *val) 146{ 147 struct pci_dev *pdev = to_pci_dev(link->ap->host->dev); 148 unsigned int cfg_addr = get_scr_cfg_addr(link, sc_reg); 149 150 if (sc_reg == SCR_ERROR) /* doesn't exist in PCI cfg space */ 151 return -EINVAL; 152 153 pci_read_config_dword(pdev, cfg_addr, val); 154 return 0; 155} 156 157static int sis_scr_cfg_write(struct ata_link *link, 158 unsigned int sc_reg, u32 val) 159{ 160 struct pci_dev *pdev = to_pci_dev(link->ap->host->dev); 161 unsigned int cfg_addr = get_scr_cfg_addr(link, sc_reg); 162 163 pci_write_config_dword(pdev, cfg_addr, val); 164 return 0; 165} 166 167static int sis_scr_read(struct ata_link *link, unsigned int sc_reg, u32 *val) 168{ 169 struct ata_port *ap = link->ap; 170 void __iomem *base = ap->ioaddr.scr_addr + link->pmp * 0x10; 171 172 if (sc_reg > SCR_CONTROL) 173 return -EINVAL; 174 175 if (ap->flags & SIS_FLAG_CFGSCR) 176 return sis_scr_cfg_read(link, sc_reg, val); 177 178 *val = ioread32(base + sc_reg * 4); 179 return 0; 180} 181 182static int sis_scr_write(struct ata_link *link, unsigned int sc_reg, u32 val) 183{ 184 struct ata_port *ap = link->ap; 185 void __iomem *base = ap->ioaddr.scr_addr + link->pmp * 0x10; 186 187 if (sc_reg > SCR_CONTROL) 188 return -EINVAL; 189 190 if (ap->flags & SIS_FLAG_CFGSCR) 191 return sis_scr_cfg_write(link, sc_reg, val); 192 193 iowrite32(val, base + (sc_reg * 4)); 194 return 0; 195} 196 197static int sis_init_one(struct pci_dev *pdev, const struct pci_device_id *ent) 198{ 199 struct ata_port_info pi = sis_port_info; 200 const struct ata_port_info *ppi[] = { &pi, &pi }; 201 struct ata_host *host; 202 u32 genctl, val; 203 u8 pmr; 204 u8 port2_start = 0x20; 205 int i, rc; 206 207 ata_print_version_once(&pdev->dev, DRV_VERSION); 208 209 rc = pcim_enable_device(pdev); 210 if (rc) 211 return rc; 212 213 /* check and see if the SCRs are in IO space or PCI cfg space */ 214 pci_read_config_dword(pdev, SIS_GENCTL, &genctl); 215 if ((genctl & GENCTL_IOMAPPED_SCR) == 0) 216 pi.flags |= SIS_FLAG_CFGSCR; 217 218 /* if hardware thinks SCRs are in IO space, but there are 219 * no IO resources assigned, change to PCI cfg space. 220 */ 221 if ((!(pi.flags & SIS_FLAG_CFGSCR)) && 222 ((pci_resource_start(pdev, SIS_SCR_PCI_BAR) == 0) || 223 (pci_resource_len(pdev, SIS_SCR_PCI_BAR) < 128))) { 224 genctl &= ~GENCTL_IOMAPPED_SCR; 225 pci_write_config_dword(pdev, SIS_GENCTL, genctl); 226 pi.flags |= SIS_FLAG_CFGSCR; 227 } 228 229 pci_read_config_byte(pdev, SIS_PMR, &pmr); 230 switch (ent->device) { 231 case 0x0180: 232 case 0x0181: 233 234 /* The PATA-handling is provided by pata_sis */ 235 switch (pmr & 0x30) { 236 case 0x10: 237 ppi[1] = &sis_info133_for_sata; 238 break; 239 240 case 0x30: 241 ppi[0] = &sis_info133_for_sata; 242 break; 243 } 244 if ((pmr & SIS_PMR_COMBINED) == 0) { 245 dev_info(&pdev->dev, 246 "Detected SiS 180/181/964 chipset in SATA mode\n"); 247 port2_start = 64; 248 } else { 249 dev_info(&pdev->dev, 250 "Detected SiS 180/181 chipset in combined mode\n"); 251 port2_start = 0; 252 pi.flags |= ATA_FLAG_SLAVE_POSS; 253 } 254 break; 255 256 case 0x0182: 257 case 0x0183: 258 pci_read_config_dword(pdev, 0x6C, &val); 259 if (val & (1L << 31)) { 260 dev_info(&pdev->dev, "Detected SiS 182/965 chipset\n"); 261 pi.flags |= ATA_FLAG_SLAVE_POSS; 262 } else { 263 dev_info(&pdev->dev, "Detected SiS 182/965L chipset\n"); 264 } 265 break; 266 267 case 0x1182: 268 dev_info(&pdev->dev, 269 "Detected SiS 1182/966/680 SATA controller\n"); 270 pi.flags |= ATA_FLAG_SLAVE_POSS; 271 break; 272 273 case 0x1183: 274 dev_info(&pdev->dev, 275 "Detected SiS 1183/966/966L/968/680 controller in PATA mode\n"); 276 ppi[0] = &sis_info133_for_sata; 277 ppi[1] = &sis_info133_for_sata; 278 break; 279 } 280 281 rc = ata_pci_bmdma_prepare_host(pdev, ppi, &host); 282 if (rc) 283 return rc; 284 285 for (i = 0; i < 2; i++) { 286 struct ata_port *ap = host->ports[i]; 287 288 if (ap->flags & ATA_FLAG_SATA && 289 ap->flags & ATA_FLAG_SLAVE_POSS) { 290 rc = ata_slave_link_init(ap); 291 if (rc) 292 return rc; 293 } 294 } 295 296 if (!(pi.flags & SIS_FLAG_CFGSCR)) { 297 void __iomem *mmio; 298 299 rc = pcim_iomap_regions(pdev, 1 << SIS_SCR_PCI_BAR, DRV_NAME); 300 if (rc) 301 return rc; 302 mmio = host->iomap[SIS_SCR_PCI_BAR]; 303 304 host->ports[0]->ioaddr.scr_addr = mmio; 305 host->ports[1]->ioaddr.scr_addr = mmio + port2_start; 306 } 307 308 pci_set_master(pdev); 309 pci_intx(pdev, 1); 310 return ata_host_activate(host, pdev->irq, ata_bmdma_interrupt, 311 IRQF_SHARED, &sis_sht); 312} 313 314module_pci_driver(sis_pci_driver); 315