1*a1917f14Szrj /*-
2*a1917f14Szrj  * Copyright (c) 1998 - 2008 Søren Schmidt <sos@FreeBSD.org>
3*a1917f14Szrj  * All rights reserved.
4*a1917f14Szrj  *
5*a1917f14Szrj  * Redistribution and use in source and binary forms, with or without
6*a1917f14Szrj  * modification, are permitted provided that the following conditions
7*a1917f14Szrj  * are met:
8*a1917f14Szrj  * 1. Redistributions of source code must retain the above copyright
9*a1917f14Szrj  *    notice, this list of conditions and the following disclaimer,
10*a1917f14Szrj  *    without modification, immediately at the beginning of the file.
11*a1917f14Szrj  * 2. Redistributions in binary form must reproduce the above copyright
12*a1917f14Szrj  *    notice, this list of conditions and the following disclaimer in the
13*a1917f14Szrj  *    documentation and/or other materials provided with the distribution.
14*a1917f14Szrj  *
15*a1917f14Szrj  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
16*a1917f14Szrj  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
17*a1917f14Szrj  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
18*a1917f14Szrj  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
19*a1917f14Szrj  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
20*a1917f14Szrj  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
21*a1917f14Szrj  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
22*a1917f14Szrj  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
23*a1917f14Szrj  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
24*a1917f14Szrj  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
25*a1917f14Szrj  */
26*a1917f14Szrj 
27*a1917f14Szrj /* local prototypes */
28*a1917f14Szrj static int ata_marvell_pata_chipinit(device_t dev);
29*a1917f14Szrj static int ata_marvell_pata_allocate(device_t dev);
30*a1917f14Szrj static void ata_marvell_pata_setmode(device_t dev, int mode);
31*a1917f14Szrj static int ata_marvell_edma_chipinit(device_t dev);
32*a1917f14Szrj static int ata_marvell_edma_allocate(device_t dev);
33*a1917f14Szrj static int ata_marvell_edma_status(device_t dev);
34*a1917f14Szrj static int ata_marvell_edma_begin_transaction(struct ata_request *request);
35*a1917f14Szrj static int ata_marvell_edma_end_transaction(struct ata_request *request);
36*a1917f14Szrj static void ata_marvell_edma_reset(device_t dev);
37*a1917f14Szrj static void ata_marvell_edma_dmasetprd(void *xsc, bus_dma_segment_t *segs, int nsegs, int error);
38*a1917f14Szrj static void ata_marvell_edma_dmainit(device_t dev);
39*a1917f14Szrj 
40*a1917f14Szrj #define ATA_MV_HOST_BASE(ch) \
41*a1917f14Szrj 	((ch->unit & 3) * 0x0100) + (ch->unit > 3 ? 0x30000 : 0x20000)
42*a1917f14Szrj #define ATA_MV_EDMA_BASE(ch) \
43*a1917f14Szrj 	((ch->unit & 3) * 0x2000) + (ch->unit > 3 ? 0x30000 : 0x20000)
44*a1917f14Szrj 
45*a1917f14Szrj struct ata_marvell_response {
46*a1917f14Szrj     u_int16_t   tag;
47*a1917f14Szrj     u_int8_t    edma_status;
48*a1917f14Szrj     u_int8_t    dev_status;
49*a1917f14Szrj     u_int32_t   timestamp;
50*a1917f14Szrj };
51*a1917f14Szrj 
52*a1917f14Szrj struct ata_marvell_dma_prdentry {
53*a1917f14Szrj     u_int32_t addrlo;
54*a1917f14Szrj     u_int32_t count;
55*a1917f14Szrj     u_int32_t addrhi;
56*a1917f14Szrj     u_int32_t reserved;
57*a1917f14Szrj };
58*a1917f14Szrj 
59*a1917f14Szrj /*
60*a1917f14Szrj  * Marvell chipset support functions
61*a1917f14Szrj  */
62*a1917f14Szrj int
63*a1917f14Szrj ata_marvell_ident(device_t dev)
64*a1917f14Szrj {
65*a1917f14Szrj     struct ata_pci_controller *ctlr = device_get_softc(dev);
66*a1917f14Szrj     struct ata_chip_id *idx;
67*a1917f14Szrj     static struct ata_chip_id ids[] =
68*a1917f14Szrj     {{ ATA_M88SX5040, 0, 4, MV50XX, ATA_SA150, "88SX5040" },
69*a1917f14Szrj      { ATA_M88SX5041, 0, 4, MV50XX, ATA_SA150, "88SX5041" },
70*a1917f14Szrj      { ATA_M88SX5080, 0, 8, MV50XX, ATA_SA150, "88SX5080" },
71*a1917f14Szrj      { ATA_M88SX5081, 0, 8, MV50XX, ATA_SA150, "88SX5081" },
72*a1917f14Szrj      { ATA_M88SX6041, 0, 4, MV60XX, ATA_SA300, "88SX6041" },
73*a1917f14Szrj      { ATA_M88SX6081, 0, 8, MV60XX, ATA_SA300, "88SX6081" },
74*a1917f14Szrj      { ATA_M88SX6101, 0, 1, MV61XX, ATA_UDMA6, "88SX6101" },
75*a1917f14Szrj      { ATA_M88SX6145, 0, 2, MV61XX, ATA_UDMA6, "88SX6145" },
76*a1917f14Szrj      { 0, 0, 0, 0, 0, 0}};
77*a1917f14Szrj     char buffer[64];
78*a1917f14Szrj 
79*a1917f14Szrj     if (!(idx = ata_match_chip(dev, ids)))
80*a1917f14Szrj 	return ENXIO;
81*a1917f14Szrj 
82*a1917f14Szrj     ksprintf(buffer, "Marvell %s %s controller",
83*a1917f14Szrj 	    idx->text, ata_mode2str(idx->max_dma));
84*a1917f14Szrj     device_set_desc_copy(dev, buffer);
85*a1917f14Szrj     ctlr->chip = idx;
86*a1917f14Szrj     switch (ctlr->chip->cfg2) {
87*a1917f14Szrj     case MV50XX:
88*a1917f14Szrj     case MV60XX:
89*a1917f14Szrj 	ctlr->chipinit = ata_marvell_edma_chipinit;
90*a1917f14Szrj 	break;
91*a1917f14Szrj     case MV61XX:
92*a1917f14Szrj 	ctlr->chipinit = ata_marvell_pata_chipinit;
93*a1917f14Szrj 	break;
94*a1917f14Szrj     }
95*a1917f14Szrj     return 0;
96*a1917f14Szrj }
97*a1917f14Szrj 
98*a1917f14Szrj static int
99*a1917f14Szrj ata_marvell_pata_chipinit(device_t dev)
100*a1917f14Szrj {
101*a1917f14Szrj     struct ata_pci_controller *ctlr = device_get_softc(dev);
102*a1917f14Szrj 
103*a1917f14Szrj     if (ata_setup_interrupt(dev))
104*a1917f14Szrj 	return ENXIO;
105*a1917f14Szrj 
106*a1917f14Szrj     ctlr->allocate = ata_marvell_pata_allocate;
107*a1917f14Szrj     ctlr->setmode = ata_marvell_pata_setmode;
108*a1917f14Szrj     ctlr->channels = ctlr->chip->cfg1;
109*a1917f14Szrj     return 0;
110*a1917f14Szrj }
111*a1917f14Szrj 
112*a1917f14Szrj static int
113*a1917f14Szrj ata_marvell_pata_allocate(device_t dev)
114*a1917f14Szrj {
115*a1917f14Szrj     struct ata_channel *ch = device_get_softc(dev);
116*a1917f14Szrj 
117*a1917f14Szrj     /* setup the usual register normal pci style */
118*a1917f14Szrj     if (ata_pci_allocate(dev))
119*a1917f14Szrj 	return ENXIO;
120*a1917f14Szrj 
121*a1917f14Szrj     /* dont use 32 bit PIO transfers */
122*a1917f14Szrj     ch->flags |= ATA_USE_16BIT;
123*a1917f14Szrj 
124*a1917f14Szrj     return 0;
125*a1917f14Szrj }
126*a1917f14Szrj 
127*a1917f14Szrj static void
128*a1917f14Szrj ata_marvell_pata_setmode(device_t dev, int mode)
129*a1917f14Szrj {
130*a1917f14Szrj     device_t gparent = GRANDPARENT(dev);
131*a1917f14Szrj     struct ata_pci_controller *ctlr = device_get_softc(gparent);
132*a1917f14Szrj     struct ata_device *atadev = device_get_softc(dev);
133*a1917f14Szrj 
134*a1917f14Szrj     mode = ata_limit_mode(dev, mode, ctlr->chip->max_dma);
135*a1917f14Szrj     mode = ata_check_80pin(dev, mode);
136*a1917f14Szrj     if (!ata_controlcmd(dev, ATA_SETFEATURES, ATA_SF_SETXFER, 0, mode))
137*a1917f14Szrj 	atadev->mode = mode;
138*a1917f14Szrj }
139*a1917f14Szrj 
140*a1917f14Szrj static int
141*a1917f14Szrj ata_marvell_edma_chipinit(device_t dev)
142*a1917f14Szrj {
143*a1917f14Szrj     struct ata_pci_controller *ctlr = device_get_softc(dev);
144*a1917f14Szrj 
145*a1917f14Szrj     if (ata_setup_interrupt(dev))
146*a1917f14Szrj 	return ENXIO;
147*a1917f14Szrj 
148*a1917f14Szrj     ctlr->r_type1 = SYS_RES_MEMORY;
149*a1917f14Szrj     ctlr->r_rid1 = PCIR_BAR(0);
150*a1917f14Szrj     if (!(ctlr->r_res1 = bus_alloc_resource_any(dev, ctlr->r_type1,
151*a1917f14Szrj 						&ctlr->r_rid1, RF_ACTIVE))) {
152*a1917f14Szrj 	ata_teardown_interrupt(dev);
153*a1917f14Szrj 	return ENXIO;
154*a1917f14Szrj     }
155*a1917f14Szrj 
156*a1917f14Szrj     /* mask all host controller interrupts */
157*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x01d64, 0x00000000);
158*a1917f14Szrj 
159*a1917f14Szrj     /* mask all PCI interrupts */
160*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x01d5c, 0x00000000);
161*a1917f14Szrj 
162*a1917f14Szrj     ctlr->allocate = ata_marvell_edma_allocate;
163*a1917f14Szrj     ctlr->reset = ata_marvell_edma_reset;
164*a1917f14Szrj     ctlr->dmainit = ata_marvell_edma_dmainit;
165*a1917f14Szrj     ctlr->setmode = ata_sata_setmode;
166*a1917f14Szrj     ctlr->channels = ctlr->chip->cfg1;
167*a1917f14Szrj 
168*a1917f14Szrj     /* clear host controller interrupts */
169*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x20014, 0x00000000);
170*a1917f14Szrj     if (ctlr->chip->cfg1 > 4)
171*a1917f14Szrj 	ATA_OUTL(ctlr->r_res1, 0x30014, 0x00000000);
172*a1917f14Szrj 
173*a1917f14Szrj     /* clear PCI interrupts */
174*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x01d58, 0x00000000);
175*a1917f14Szrj 
176*a1917f14Szrj     /* unmask PCI interrupts we want */
177*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x01d5c, 0x007fffff);
178*a1917f14Szrj 
179*a1917f14Szrj     /* unmask host controller interrupts we want */
180*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x01d64, 0x000000ff/*HC0*/ | 0x0001fe00/*HC1*/ |
181*a1917f14Szrj 	     /*(1<<19) | (1<<20) | (1<<21) |*/(1<<22) | (1<<24) | (0x7f << 25));
182*a1917f14Szrj 
183*a1917f14Szrj     /* enable PCI interrupt */
184*a1917f14Szrj     pci_write_config(dev, PCIR_COMMAND,
185*a1917f14Szrj 		     pci_read_config(dev, PCIR_COMMAND, 2) & ~0x0400, 2);
186*a1917f14Szrj     return 0;
187*a1917f14Szrj }
188*a1917f14Szrj 
189*a1917f14Szrj static int
190*a1917f14Szrj ata_marvell_edma_allocate(device_t dev)
191*a1917f14Szrj {
192*a1917f14Szrj     struct ata_pci_controller *ctlr = device_get_softc(device_get_parent(dev));
193*a1917f14Szrj     struct ata_channel *ch = device_get_softc(dev);
194*a1917f14Szrj     u_int64_t work = ch->dma->work_bus;
195*a1917f14Szrj     int i;
196*a1917f14Szrj 
197*a1917f14Szrj     /* clear work area */
198*a1917f14Szrj     bzero(ch->dma->work, 1024+256);
199*a1917f14Szrj 
200*a1917f14Szrj     /* set legacy ATA resources */
201*a1917f14Szrj     for (i = ATA_DATA; i <= ATA_COMMAND; i++) {
202*a1917f14Szrj 	ch->r_io[i].res = ctlr->r_res1;
203*a1917f14Szrj 	ch->r_io[i].offset = 0x02100 + (i << 2) + ATA_MV_EDMA_BASE(ch);
204*a1917f14Szrj     }
205*a1917f14Szrj     ch->r_io[ATA_CONTROL].res = ctlr->r_res1;
206*a1917f14Szrj     ch->r_io[ATA_CONTROL].offset = 0x02120 + ATA_MV_EDMA_BASE(ch);
207*a1917f14Szrj     ch->r_io[ATA_IDX_ADDR].res = ctlr->r_res1;
208*a1917f14Szrj     ata_default_registers(dev);
209*a1917f14Szrj 
210*a1917f14Szrj     /* set SATA resources */
211*a1917f14Szrj     switch (ctlr->chip->cfg2) {
212*a1917f14Szrj     case MV50XX:
213*a1917f14Szrj 	ch->r_io[ATA_SSTATUS].res = ctlr->r_res1;
214*a1917f14Szrj 	ch->r_io[ATA_SSTATUS].offset =  0x00100 + ATA_MV_HOST_BASE(ch);
215*a1917f14Szrj 	ch->r_io[ATA_SERROR].res = ctlr->r_res1;
216*a1917f14Szrj 	ch->r_io[ATA_SERROR].offset = 0x00104 + ATA_MV_HOST_BASE(ch);
217*a1917f14Szrj 	ch->r_io[ATA_SCONTROL].res = ctlr->r_res1;
218*a1917f14Szrj 	ch->r_io[ATA_SCONTROL].offset = 0x00108 + ATA_MV_HOST_BASE(ch);
219*a1917f14Szrj 	break;
220*a1917f14Szrj     case MV60XX:
221*a1917f14Szrj 	ch->r_io[ATA_SSTATUS].res = ctlr->r_res1;
222*a1917f14Szrj 	ch->r_io[ATA_SSTATUS].offset =  0x02300 + ATA_MV_EDMA_BASE(ch);
223*a1917f14Szrj 	ch->r_io[ATA_SERROR].res = ctlr->r_res1;
224*a1917f14Szrj 	ch->r_io[ATA_SERROR].offset = 0x02304 + ATA_MV_EDMA_BASE(ch);
225*a1917f14Szrj 	ch->r_io[ATA_SCONTROL].res = ctlr->r_res1;
226*a1917f14Szrj 	ch->r_io[ATA_SCONTROL].offset = 0x02308 + ATA_MV_EDMA_BASE(ch);
227*a1917f14Szrj 	ch->r_io[ATA_SACTIVE].res = ctlr->r_res1;
228*a1917f14Szrj 	ch->r_io[ATA_SACTIVE].offset = 0x02350 + ATA_MV_EDMA_BASE(ch);
229*a1917f14Szrj 	break;
230*a1917f14Szrj     }
231*a1917f14Szrj 
232*a1917f14Szrj     ch->flags |= ATA_NO_SLAVE;
233*a1917f14Szrj     ch->flags |= ATA_USE_16BIT; /* XXX SOS needed ? */
234*a1917f14Szrj     ata_generic_hw(dev);
235*a1917f14Szrj     ch->hw.begin_transaction = ata_marvell_edma_begin_transaction;
236*a1917f14Szrj     ch->hw.end_transaction = ata_marvell_edma_end_transaction;
237*a1917f14Szrj     ch->hw.status = ata_marvell_edma_status;
238*a1917f14Szrj 
239*a1917f14Szrj     /* disable the EDMA machinery */
240*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x02028 + ATA_MV_EDMA_BASE(ch), 0x00000002);
241*a1917f14Szrj     DELAY(100000);       /* SOS should poll for disabled */
242*a1917f14Szrj 
243*a1917f14Szrj     /* set configuration to non-queued 128b read transfers stop on error */
244*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x02000 + ATA_MV_EDMA_BASE(ch), (1<<11) | (1<<13));
245*a1917f14Szrj 
246*a1917f14Szrj     /* request queue base high */
247*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x02010 + ATA_MV_EDMA_BASE(ch), work >> 32);
248*a1917f14Szrj 
249*a1917f14Szrj     /* request queue in ptr */
250*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x02014 + ATA_MV_EDMA_BASE(ch), work & 0xffffffff);
251*a1917f14Szrj 
252*a1917f14Szrj     /* request queue out ptr */
253*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x02018 + ATA_MV_EDMA_BASE(ch), 0x0);
254*a1917f14Szrj 
255*a1917f14Szrj     /* response queue base high */
256*a1917f14Szrj     work += 1024;
257*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x0201c + ATA_MV_EDMA_BASE(ch), work >> 32);
258*a1917f14Szrj 
259*a1917f14Szrj     /* response queue in ptr */
260*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x02020 + ATA_MV_EDMA_BASE(ch), 0x0);
261*a1917f14Szrj 
262*a1917f14Szrj     /* response queue out ptr */
263*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x02024 + ATA_MV_EDMA_BASE(ch), work & 0xffffffff);
264*a1917f14Szrj 
265*a1917f14Szrj     /* clear SATA error register */
266*a1917f14Szrj     ATA_IDX_OUTL(ch, ATA_SERROR, ATA_IDX_INL(ch, ATA_SERROR));
267*a1917f14Szrj 
268*a1917f14Szrj     /* clear any outstanding error interrupts */
269*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x02008 + ATA_MV_EDMA_BASE(ch), 0x0);
270*a1917f14Szrj 
271*a1917f14Szrj     /* unmask all error interrupts */
272*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x0200c + ATA_MV_EDMA_BASE(ch), ~0x0);
273*a1917f14Szrj 
274*a1917f14Szrj     /* enable EDMA machinery */
275*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x02028 + ATA_MV_EDMA_BASE(ch), 0x00000001);
276*a1917f14Szrj     return 0;
277*a1917f14Szrj }
278*a1917f14Szrj 
279*a1917f14Szrj static int
280*a1917f14Szrj ata_marvell_edma_status(device_t dev)
281*a1917f14Szrj {
282*a1917f14Szrj     struct ata_pci_controller *ctlr = device_get_softc(device_get_parent(dev));
283*a1917f14Szrj     struct ata_channel *ch = device_get_softc(dev);
284*a1917f14Szrj     u_int32_t cause = ATA_INL(ctlr->r_res1, 0x01d60);
285*a1917f14Szrj     int shift = (ch->unit << 1) + (ch->unit > 3);
286*a1917f14Szrj 
287*a1917f14Szrj     if (cause & (1 << shift)) {
288*a1917f14Szrj 
289*a1917f14Szrj 	/* clear interrupt(s) */
290*a1917f14Szrj 	ATA_OUTL(ctlr->r_res1, 0x02008 + ATA_MV_EDMA_BASE(ch), 0x0);
291*a1917f14Szrj 
292*a1917f14Szrj 	/* do we have any PHY events ? */
293*a1917f14Szrj 	ata_sata_phy_check_events(dev);
294*a1917f14Szrj     }
295*a1917f14Szrj 
296*a1917f14Szrj     /* do we have any device action ? */
297*a1917f14Szrj     return (cause & (2 << shift));
298*a1917f14Szrj }
299*a1917f14Szrj 
300*a1917f14Szrj /* must be called with ATA channel locked and state_mtx held */
301*a1917f14Szrj static int
302*a1917f14Szrj ata_marvell_edma_begin_transaction(struct ata_request *request)
303*a1917f14Szrj {
304*a1917f14Szrj     struct ata_pci_controller *ctlr=device_get_softc(GRANDPARENT(request->dev));
305*a1917f14Szrj     struct ata_channel *ch = device_get_softc(device_get_parent(request->dev));
306*a1917f14Szrj     u_int32_t req_in;
307*a1917f14Szrj     u_int8_t *bytep;
308*a1917f14Szrj     u_int16_t *wordp;
309*a1917f14Szrj     u_int32_t *quadp;
310*a1917f14Szrj     int i, tag = 0x07;
311*a1917f14Szrj     int dummy, error, slot;
312*a1917f14Szrj 
313*a1917f14Szrj     /* only DMA R/W goes through the EMDA machine */
314*a1917f14Szrj     if (request->u.ata.command != ATA_READ_DMA &&
315*a1917f14Szrj 	request->u.ata.command != ATA_WRITE_DMA) {
316*a1917f14Szrj 
317*a1917f14Szrj 	/* disable the EDMA machinery */
318*a1917f14Szrj 	if (ATA_INL(ctlr->r_res1, 0x02028 + ATA_MV_EDMA_BASE(ch)) & 0x00000001)
319*a1917f14Szrj 	    ATA_OUTL(ctlr->r_res1, 0x02028 + ATA_MV_EDMA_BASE(ch), 0x00000002);
320*a1917f14Szrj 	return ata_begin_transaction(request);
321*a1917f14Szrj     }
322*a1917f14Szrj 
323*a1917f14Szrj     /* check for 48 bit access and convert if needed */
324*a1917f14Szrj     ata_modify_if_48bit(request);
325*a1917f14Szrj 
326*a1917f14Szrj     /* check sanity, setup SG list and DMA engine */
327*a1917f14Szrj     if ((error = ch->dma->load(ch->dev, request->data, request->bytecount,
328*a1917f14Szrj 			       request->flags & ATA_R_READ, ch->dma->sg,
329*a1917f14Szrj 			       &dummy))) {
330*a1917f14Szrj 	device_printf(request->dev, "setting up DMA failed\n");
331*a1917f14Szrj 	request->result = error;
332*a1917f14Szrj 	return ATA_OP_FINISHED;
333*a1917f14Szrj     }
334*a1917f14Szrj 
335*a1917f14Szrj     /* get next free request queue slot */
336*a1917f14Szrj     req_in = ATA_INL(ctlr->r_res1, 0x02014 + ATA_MV_EDMA_BASE(ch));
337*a1917f14Szrj     slot = (((req_in & ~0xfffffc00) >> 5) + 0) & 0x1f;
338*a1917f14Szrj     bytep = (u_int8_t *)(ch->dma->work);
339*a1917f14Szrj     bytep += (slot << 5);
340*a1917f14Szrj     wordp = (u_int16_t *)bytep;
341*a1917f14Szrj     quadp = (u_int32_t *)bytep;
342*a1917f14Szrj 
343*a1917f14Szrj     /* fill in this request */
344*a1917f14Szrj     quadp[0] = (long)ch->dma->sg_bus & 0xffffffff;
345*a1917f14Szrj     quadp[1] = (u_int64_t)ch->dma->sg_bus >> 32;
346*a1917f14Szrj     wordp[4] = (request->flags & ATA_R_READ ? 0x01 : 0x00) | (tag<<1);
347*a1917f14Szrj 
348*a1917f14Szrj 	    i = 10;
349*a1917f14Szrj 	    bytep[i++] = (request->u.ata.count >> 8) & 0xff;
350*a1917f14Szrj 	    bytep[i++] = 0x10 | ATA_COUNT;
351*a1917f14Szrj 	    bytep[i++] = request->u.ata.count & 0xff;
352*a1917f14Szrj 	    bytep[i++] = 0x10 | ATA_COUNT;
353*a1917f14Szrj 
354*a1917f14Szrj 	    bytep[i++] = (request->u.ata.lba >> 24) & 0xff;
355*a1917f14Szrj 	    bytep[i++] = 0x10 | ATA_SECTOR;
356*a1917f14Szrj 	    bytep[i++] = request->u.ata.lba & 0xff;
357*a1917f14Szrj 	    bytep[i++] = 0x10 | ATA_SECTOR;
358*a1917f14Szrj 
359*a1917f14Szrj 	    bytep[i++] = (request->u.ata.lba >> 32) & 0xff;
360*a1917f14Szrj 	    bytep[i++] = 0x10 | ATA_CYL_LSB;
361*a1917f14Szrj 	    bytep[i++] = (request->u.ata.lba >> 8) & 0xff;
362*a1917f14Szrj 	    bytep[i++] = 0x10 | ATA_CYL_LSB;
363*a1917f14Szrj 
364*a1917f14Szrj 	    bytep[i++] = (request->u.ata.lba >> 40) & 0xff;
365*a1917f14Szrj 	    bytep[i++] = 0x10 | ATA_CYL_MSB;
366*a1917f14Szrj 	    bytep[i++] = (request->u.ata.lba >> 16) & 0xff;
367*a1917f14Szrj 	    bytep[i++] = 0x10 | ATA_CYL_MSB;
368*a1917f14Szrj 
369*a1917f14Szrj 	    bytep[i++] = ATA_D_LBA | ATA_D_IBM | ((request->u.ata.lba >> 24) & 0xf);
370*a1917f14Szrj 	    bytep[i++] = 0x10 | ATA_DRIVE;
371*a1917f14Szrj 
372*a1917f14Szrj 	    bytep[i++] = request->u.ata.command;
373*a1917f14Szrj 	    bytep[i++] = 0x90 | ATA_COMMAND;
374*a1917f14Szrj 
375*a1917f14Szrj     /* enable EDMA machinery if needed */
376*a1917f14Szrj     if (!(ATA_INL(ctlr->r_res1, 0x02028 + ATA_MV_EDMA_BASE(ch)) & 0x00000001)) {
377*a1917f14Szrj 	ATA_OUTL(ctlr->r_res1, 0x02028 + ATA_MV_EDMA_BASE(ch), 0x00000001);
378*a1917f14Szrj 	while (!(ATA_INL(ctlr->r_res1,
379*a1917f14Szrj 			 0x02028 + ATA_MV_EDMA_BASE(ch)) & 0x00000001))
380*a1917f14Szrj 	    DELAY(10);
381*a1917f14Szrj     }
382*a1917f14Szrj 
383*a1917f14Szrj     /* tell EDMA it has a new request */
384*a1917f14Szrj     slot = (((req_in & ~0xfffffc00) >> 5) + 1) & 0x1f;
385*a1917f14Szrj     req_in &= 0xfffffc00;
386*a1917f14Szrj     req_in += (slot << 5);
387*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x02014 + ATA_MV_EDMA_BASE(ch), req_in);
388*a1917f14Szrj 
389*a1917f14Szrj     return ATA_OP_CONTINUES;
390*a1917f14Szrj }
391*a1917f14Szrj 
392*a1917f14Szrj /* must be called with ATA channel locked and state_mtx held */
393*a1917f14Szrj static int
394*a1917f14Szrj ata_marvell_edma_end_transaction(struct ata_request *request)
395*a1917f14Szrj {
396*a1917f14Szrj     struct ata_pci_controller *ctlr=device_get_softc(GRANDPARENT(request->dev));
397*a1917f14Szrj     struct ata_channel *ch = device_get_softc(device_get_parent(request->dev));
398*a1917f14Szrj     int offset = (ch->unit > 3 ? 0x30014 : 0x20014);
399*a1917f14Szrj     u_int32_t icr = ATA_INL(ctlr->r_res1, offset);
400*a1917f14Szrj     int res;
401*a1917f14Szrj 
402*a1917f14Szrj     /* EDMA interrupt */
403*a1917f14Szrj     if ((icr & (0x0001 << (ch->unit & 3)))) {
404*a1917f14Szrj 	struct ata_marvell_response *response;
405*a1917f14Szrj 	u_int32_t rsp_in, rsp_out;
406*a1917f14Szrj 	int slot;
407*a1917f14Szrj 
408*a1917f14Szrj 	/* stop timeout */
409*a1917f14Szrj 	callout_stop_sync(&request->callout);
410*a1917f14Szrj 
411*a1917f14Szrj 	/* get response ptr's */
412*a1917f14Szrj 	rsp_in = ATA_INL(ctlr->r_res1, 0x02020 + ATA_MV_EDMA_BASE(ch));
413*a1917f14Szrj 	rsp_out = ATA_INL(ctlr->r_res1, 0x02024 + ATA_MV_EDMA_BASE(ch));
414*a1917f14Szrj 	slot = (((rsp_in & ~0xffffff00) >> 3)) & 0x1f;
415*a1917f14Szrj 	rsp_out &= 0xffffff00;
416*a1917f14Szrj 	rsp_out += (slot << 3);
417*a1917f14Szrj 	response = (struct ata_marvell_response *)
418*a1917f14Szrj 		   (ch->dma->work + 1024 + (slot << 3));
419*a1917f14Szrj 
420*a1917f14Szrj 	/* record status for this request */
421*a1917f14Szrj 	request->status = response->dev_status;
422*a1917f14Szrj 	request->error = 0;
423*a1917f14Szrj 
424*a1917f14Szrj 	/* ack response */
425*a1917f14Szrj 	ATA_OUTL(ctlr->r_res1, 0x02024 + ATA_MV_EDMA_BASE(ch), rsp_out);
426*a1917f14Szrj 
427*a1917f14Szrj 	/* update progress */
428*a1917f14Szrj 	if (!(request->status & ATA_S_ERROR) &&
429*a1917f14Szrj 	    !(request->flags & ATA_R_TIMEOUT))
430*a1917f14Szrj 	    request->donecount = request->bytecount;
431*a1917f14Szrj 
432*a1917f14Szrj 	/* unload SG list */
433*a1917f14Szrj 	ch->dma->unload(ch->dev);
434*a1917f14Szrj 
435*a1917f14Szrj 	res = ATA_OP_FINISHED;
436*a1917f14Szrj     }
437*a1917f14Szrj 
438*a1917f14Szrj     /* legacy ATA interrupt */
439*a1917f14Szrj     else {
440*a1917f14Szrj 	res = ata_end_transaction(request);
441*a1917f14Szrj     }
442*a1917f14Szrj 
443*a1917f14Szrj     /* ack interrupt */
444*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, offset, ~(icr & (0x0101 << (ch->unit & 3))));
445*a1917f14Szrj     return res;
446*a1917f14Szrj }
447*a1917f14Szrj 
448*a1917f14Szrj static void
449*a1917f14Szrj ata_marvell_edma_reset(device_t dev)
450*a1917f14Szrj {
451*a1917f14Szrj     struct ata_pci_controller *ctlr = device_get_softc(device_get_parent(dev));
452*a1917f14Szrj     struct ata_channel *ch = device_get_softc(dev);
453*a1917f14Szrj 
454*a1917f14Szrj     /* disable the EDMA machinery */
455*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x02028 + ATA_MV_EDMA_BASE(ch), 0x00000002);
456*a1917f14Szrj     while ((ATA_INL(ctlr->r_res1, 0x02028 + ATA_MV_EDMA_BASE(ch)) & 0x00000001))
457*a1917f14Szrj 	DELAY(10);
458*a1917f14Szrj 
459*a1917f14Szrj     /* clear SATA error register */
460*a1917f14Szrj     ATA_IDX_OUTL(ch, ATA_SERROR, ATA_IDX_INL(ch, ATA_SERROR));
461*a1917f14Szrj 
462*a1917f14Szrj     /* clear any outstanding error interrupts */
463*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x02008 + ATA_MV_EDMA_BASE(ch), 0x0);
464*a1917f14Szrj 
465*a1917f14Szrj     /* unmask all error interrupts */
466*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x0200c + ATA_MV_EDMA_BASE(ch), ~0x0);
467*a1917f14Szrj 
468*a1917f14Szrj     /* enable channel and test for devices */
469*a1917f14Szrj     if (ata_sata_phy_reset(dev))
470*a1917f14Szrj 	ata_generic_reset(dev);
471*a1917f14Szrj 
472*a1917f14Szrj     /* enable EDMA machinery */
473*a1917f14Szrj     ATA_OUTL(ctlr->r_res1, 0x02028 + ATA_MV_EDMA_BASE(ch), 0x00000001);
474*a1917f14Szrj }
475*a1917f14Szrj 
476*a1917f14Szrj static void
477*a1917f14Szrj ata_marvell_edma_dmasetprd(void *xsc, bus_dma_segment_t *segs, int nsegs,
478*a1917f14Szrj 			   int error)
479*a1917f14Szrj {
480*a1917f14Szrj     struct ata_dmasetprd_args *args = xsc;
481*a1917f14Szrj     struct ata_marvell_dma_prdentry *prd = args->dmatab;
482*a1917f14Szrj     int i;
483*a1917f14Szrj 
484*a1917f14Szrj     if ((args->error = error))
485*a1917f14Szrj 	return;
486*a1917f14Szrj 
487*a1917f14Szrj     for (i = 0; i < nsegs; i++) {
488*a1917f14Szrj 	prd[i].addrlo = htole32(segs[i].ds_addr);
489*a1917f14Szrj 	prd[i].count = htole32(segs[i].ds_len);
490*a1917f14Szrj 	prd[i].addrhi = htole32((u_int64_t)segs[i].ds_addr >> 32);
491*a1917f14Szrj     }
492*a1917f14Szrj     prd[i - 1].count |= htole32(ATA_DMA_EOT);
493*a1917f14Szrj }
494*a1917f14Szrj 
495*a1917f14Szrj static void
496*a1917f14Szrj ata_marvell_edma_dmainit(device_t dev)
497*a1917f14Szrj {
498*a1917f14Szrj     struct ata_pci_controller *ctlr = device_get_softc(device_get_parent(dev));
499*a1917f14Szrj     struct ata_channel *ch = device_get_softc(dev);
500*a1917f14Szrj 
501*a1917f14Szrj     ata_dmainit(dev);
502*a1917f14Szrj     if (ch->dma) {
503*a1917f14Szrj 	/* note start and stop are not used here */
504*a1917f14Szrj 	ch->dma->setprd = ata_marvell_edma_dmasetprd;
505*a1917f14Szrj 
506*a1917f14Szrj 	if (ATA_INL(ctlr->r_res1, 0x00d00) & 0x00000004)
507*a1917f14Szrj 	    ch->dma->max_address = BUS_SPACE_MAXADDR;
508*a1917f14Szrj 
509*a1917f14Szrj 	/* chip does not reliably do 64K DMA transfers */
510*a1917f14Szrj 	ch->dma->max_iosize = 126 * DEV_BSIZE;
511*a1917f14Szrj     }
512*a1917f14Szrj }
513