ata-via.c (874108aed99d76099ff9eb6c8d830479a504c1ad) ata-via.c (066f913a94b134b6d5e32b6af88f297c7da9c031)
1/*-
2 * Copyright (c) 1998 - 2008 S�ren Schmidt <sos@FreeBSD.org>
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 * 1. Redistributions of source code must retain the above copyright

--- 42 unchanged lines hidden (view full) ---

51#include <dev/ata/ata-pci.h>
52#include <ata_if.h>
53
54/* local prototypes */
55static int ata_via_chipinit(device_t dev);
56static int ata_via_ch_attach(device_t dev);
57static int ata_via_ch_detach(device_t dev);
58static void ata_via_reset(device_t dev);
1/*-
2 * Copyright (c) 1998 - 2008 S�ren Schmidt <sos@FreeBSD.org>
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 * 1. Redistributions of source code must retain the above copyright

--- 42 unchanged lines hidden (view full) ---

51#include <dev/ata/ata-pci.h>
52#include <ata_if.h>
53
54/* local prototypes */
55static int ata_via_chipinit(device_t dev);
56static int ata_via_ch_attach(device_t dev);
57static int ata_via_ch_detach(device_t dev);
58static void ata_via_reset(device_t dev);
59static void ata_via_old_setmode(device_t dev, int mode);
59static int ata_via_old_setmode(device_t dev, int target, int mode);
60static void ata_via_southbridge_fixup(device_t dev);
60static void ata_via_southbridge_fixup(device_t dev);
61static void ata_via_new_setmode(device_t dev, int mode);
61static int ata_via_new_setmode(device_t dev, int target, int mode);
62
63/* misc defines */
64#define VIA33 0
65#define VIA66 1
66#define VIA100 2
67#define VIA133 3
68
69#define VIACLK 0x01

--- 77 unchanged lines hidden (view full) ---

147 ctlr->ch_attach = ata_via_ch_attach;
148 ctlr->ch_detach = ata_via_ch_detach;
149 ctlr->reset = ata_via_reset;
150 }
151
152 if (ctlr->chip->cfg2 & VIABAR) {
153 ctlr->channels = 3;
154 ctlr->setmode = ata_via_new_setmode;
62
63/* misc defines */
64#define VIA33 0
65#define VIA66 1
66#define VIA100 2
67#define VIA133 3
68
69#define VIACLK 0x01

--- 77 unchanged lines hidden (view full) ---

147 ctlr->ch_attach = ata_via_ch_attach;
148 ctlr->ch_detach = ata_via_ch_detach;
149 ctlr->reset = ata_via_reset;
150 }
151
152 if (ctlr->chip->cfg2 & VIABAR) {
153 ctlr->channels = 3;
154 ctlr->setmode = ata_via_new_setmode;
155 }
156 else
155 } else
157 ctlr->setmode = ata_sata_setmode;
156 ctlr->setmode = ata_sata_setmode;
157 ctlr->getrev = ata_sata_getrev;
158 return 0;
159 }
160
161 /* prepare for ATA-66 on the 82C686a and 82C596b */
162 if (ctlr->chip->cfg2 & VIACLK)
163 pci_write_config(dev, 0x50, 0x030b030b, 4);
164
165 /* the southbridge might need the data corruption fix */

--- 62 unchanged lines hidden (view full) ---

228
229 ch->r_io[ATA_SSTATUS].res = ctlr->r_res2;
230 ch->r_io[ATA_SSTATUS].offset = (ch->unit << ctlr->chip->cfg1);
231 ch->r_io[ATA_SERROR].res = ctlr->r_res2;
232 ch->r_io[ATA_SERROR].offset = 0x04 + (ch->unit << ctlr->chip->cfg1);
233 ch->r_io[ATA_SCONTROL].res = ctlr->r_res2;
234 ch->r_io[ATA_SCONTROL].offset = 0x08 + (ch->unit << ctlr->chip->cfg1);
235 ch->flags |= ATA_NO_SLAVE;
158 return 0;
159 }
160
161 /* prepare for ATA-66 on the 82C686a and 82C596b */
162 if (ctlr->chip->cfg2 & VIACLK)
163 pci_write_config(dev, 0x50, 0x030b030b, 4);
164
165 /* the southbridge might need the data corruption fix */

--- 62 unchanged lines hidden (view full) ---

228
229 ch->r_io[ATA_SSTATUS].res = ctlr->r_res2;
230 ch->r_io[ATA_SSTATUS].offset = (ch->unit << ctlr->chip->cfg1);
231 ch->r_io[ATA_SERROR].res = ctlr->r_res2;
232 ch->r_io[ATA_SERROR].offset = 0x04 + (ch->unit << ctlr->chip->cfg1);
233 ch->r_io[ATA_SCONTROL].res = ctlr->r_res2;
234 ch->r_io[ATA_SCONTROL].offset = 0x08 + (ch->unit << ctlr->chip->cfg1);
235 ch->flags |= ATA_NO_SLAVE;
236 ch->flags |= ATA_SATA;
236
237 /* XXX SOS PHY hotplug handling missing in VIA chip ?? */
238 /* XXX SOS unknown how to enable PHY state change interrupt */
239 return 0;
240}
241
242static int
243ata_via_ch_detach(device_t dev)

--- 28 unchanged lines hidden (view full) ---

272
273 if ((ctlr->chip->cfg2 & VIABAR) && (ch->unit > 1))
274 ata_generic_reset(dev);
275 else
276 if (ata_sata_phy_reset(dev, -1, 1))
277 ata_generic_reset(dev);
278}
279
237
238 /* XXX SOS PHY hotplug handling missing in VIA chip ?? */
239 /* XXX SOS unknown how to enable PHY state change interrupt */
240 return 0;
241}
242
243static int
244ata_via_ch_detach(device_t dev)

--- 28 unchanged lines hidden (view full) ---

273
274 if ((ctlr->chip->cfg2 & VIABAR) && (ch->unit > 1))
275 ata_generic_reset(dev);
276 else
277 if (ata_sata_phy_reset(dev, -1, 1))
278 ata_generic_reset(dev);
279}
280
280static void
281ata_via_new_setmode(device_t dev, int mode)
281static int
282ata_via_new_setmode(device_t dev, int target, int mode)
282{
283{
283 device_t gparent = GRANDPARENT(dev);
284 struct ata_pci_controller *ctlr = device_get_softc(gparent);
285 struct ata_channel *ch = device_get_softc(device_get_parent(dev));
286 struct ata_device *atadev = device_get_softc(dev);
287 int error;
284 device_t parent = device_get_parent(dev);
285 struct ata_pci_controller *ctlr = device_get_softc(parent);
286 struct ata_channel *ch = device_get_softc(dev);
288
287
289 if ((ctlr->chip->cfg2 & VIABAR) && (ch->unit > 1)) {
290 u_int8_t pio_timings[] = { 0xa8, 0x65, 0x65, 0x32, 0x20,
291 0x65, 0x32, 0x20,
292 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20 };
293 u_int8_t dma_timings[] = { 0xee, 0xe8, 0xe6, 0xe4, 0xe2, 0xe1, 0xe0 };
288 if ((ctlr->chip->cfg2 & VIABAR) && (ch->unit > 1)) {
289 int piomode;
290 u_int8_t pio_timings[] = { 0xa8, 0x65, 0x65, 0x32, 0x20 };
291 u_int8_t dma_timings[] = { 0xee, 0xe8, 0xe6, 0xe4, 0xe2, 0xe1, 0xe0 };
294
292
295 mode = ata_check_80pin(dev, ata_limit_mode(dev, mode, ATA_UDMA6));
296 error = ata_controlcmd(dev, ATA_SETFEATURES, ATA_SF_SETXFER, 0, mode);
297 if (bootverbose)
298 device_printf(dev, "%ssetting %s on %s chip\n",
299 (error) ? "FAILURE " : "", ata_mode2str(mode),
300 ctlr->chip->text);
301 if (!error) {
302 pci_write_config(gparent, 0xab, pio_timings[ata_mode2idx(mode)], 1);
303 if (mode >= ATA_UDMA0)
304 pci_write_config(gparent, 0xb3,
293 /* This chip can't do WDMA. */
294 if (mode >= ATA_WDMA0 && mode < ATA_UDMA0)
295 mode = ATA_PIO4;
296 if (mode >= ATA_UDMA0) {
297 pci_write_config(parent, 0xb3,
305 dma_timings[mode & ATA_MODE_MASK], 1);
298 dma_timings[mode & ATA_MODE_MASK], 1);
306 atadev->mode = mode;
307 }
308 }
309 else
310 ata_sata_setmode(dev, mode);
299 piomode = ATA_PIO4;
300 } else
301 piomode = mode;
302 pci_write_config(parent, 0xab, pio_timings[ata_mode2idx(piomode)], 1);
303 } else
304 mode = ata_sata_setmode(dev, target, mode);
305 return (mode);
311}
312
306}
307
313static void
314ata_via_old_setmode(device_t dev, int mode)
308static int
309ata_via_old_setmode(device_t dev, int target, int mode)
315{
310{
316 device_t gparent = GRANDPARENT(dev);
317 struct ata_pci_controller *ctlr = device_get_softc(gparent);
318 struct ata_channel *ch = device_get_softc(device_get_parent(dev));
319 struct ata_device *atadev = device_get_softc(dev);
320 u_int8_t timings[] = { 0xa8, 0x65, 0x42, 0x22, 0x20, 0x42, 0x22, 0x20,
321 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20 };
322 int modes[][7] = {
323 { 0xc2, 0xc1, 0xc0, 0x00, 0x00, 0x00, 0x00 }, /* VIA ATA33 */
324 { 0xee, 0xec, 0xea, 0xe9, 0xe8, 0x00, 0x00 }, /* VIA ATA66 */
325 { 0xf7, 0xf6, 0xf4, 0xf2, 0xf1, 0xf0, 0x00 }, /* VIA ATA100 */
326 { 0xf7, 0xf7, 0xf6, 0xf4, 0xf2, 0xf1, 0xf0 } }; /* VIA ATA133 */
327 int devno = (ch->unit << 1) + atadev->unit;
328 int reg = 0x53 - devno;
329 int error;
311 device_t parent = device_get_parent(dev);
312 struct ata_pci_controller *ctlr = device_get_softc(parent);
313 struct ata_channel *ch = device_get_softc(dev);
314 int devno = (ch->unit << 1) + target;
315 int reg = 0x53 - devno;
316 int piomode;
317 uint8_t timings[] = { 0xa8, 0x65, 0x42, 0x22, 0x20, 0xa8, 0x22, 0x20 };
318 uint8_t modes[][7] = {
319 { 0xc2, 0xc1, 0xc0, 0x00, 0x00, 0x00, 0x00 }, /* VIA ATA33 */
320 { 0xee, 0xec, 0xea, 0xe9, 0xe8, 0x00, 0x00 }, /* VIA ATA66 */
321 { 0xf7, 0xf6, 0xf4, 0xf2, 0xf1, 0xf0, 0x00 }, /* VIA ATA100 */
322 { 0xf7, 0xf7, 0xf6, 0xf4, 0xf2, 0xf1, 0xf0 } }; /* VIA ATA133 */
330
323
331 mode = ata_limit_mode(dev, mode, ctlr->chip->max_dma);
332 mode = ata_check_80pin(dev, mode);
333
334 error = ata_controlcmd(dev, ATA_SETFEATURES, ATA_SF_SETXFER, 0, mode);
335 if (bootverbose)
336 device_printf(dev, "%ssetting %s on %s chip\n",
337 (error) ? "FAILURE " : "", ata_mode2str(mode),
338 ctlr->chip->text);
339 if (!error) {
340 if (ctlr->chip->cfg1 != VIA133)
341 pci_write_config(gparent, reg - 0x08,timings[ata_mode2idx(mode)],1);
342 if (mode >= ATA_UDMA0)
343 pci_write_config(gparent, reg,
324 mode = min(mode, ctlr->chip->max_dma);
325 /* Set UDMA timings */
326 if (mode >= ATA_UDMA0) {
327 pci_write_config(parent, reg,
344 modes[ctlr->chip->cfg1][mode & ATA_MODE_MASK], 1);
328 modes[ctlr->chip->cfg1][mode & ATA_MODE_MASK], 1);
345 else
346 pci_write_config(gparent, reg, 0x8b, 1);
347 atadev->mode = mode;
348 }
329 piomode = ATA_PIO4;
330 } else {
331 pci_write_config(parent, reg, 0x8b, 1);
332 piomode = mode;
333 }
334 /* Set WDMA/PIO timings */
335 if (ctlr->chip->cfg1 != VIA133)
336 pci_write_config(parent, reg - 0x08,timings[ata_mode2idx(piomode)], 1);
337 return (mode);
349}
350
351static void
352ata_via_southbridge_fixup(device_t dev)
353{
354 device_t *children;
355 int nchildren, i;
356

--- 24 unchanged lines hidden ---
338}
339
340static void
341ata_via_southbridge_fixup(device_t dev)
342{
343 device_t *children;
344 int nchildren, i;
345

--- 24 unchanged lines hidden ---