xref: /openbsd/sys/dev/fdt/dwmmc.c (revision 2b571f7f)
1 /*	$OpenBSD: dwmmc.c,v 1.29 2023/07/01 08:27:26 jsing Exp $	*/
2 /*
3  * Copyright (c) 2017 Mark Kettenis
4  *
5  * Permission to use, copy, modify, and distribute this software for any
6  * purpose with or without fee is hereby granted, provided that the above
7  * copyright notice and this permission notice appear in all copies.
8  *
9  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
10  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
11  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
12  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
13  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
14  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
15  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
16  */
17 
18 #include <sys/param.h>
19 #include <sys/kernel.h>
20 #include <sys/malloc.h>
21 #include <sys/systm.h>
22 
23 #include <machine/bus.h>
24 #include <machine/fdt.h>
25 #include <machine/intr.h>
26 
27 #include <dev/ofw/openfirm.h>
28 #include <dev/ofw/ofw_clock.h>
29 #include <dev/ofw/ofw_gpio.h>
30 #include <dev/ofw/ofw_pinctrl.h>
31 #include <dev/ofw/fdt.h>
32 
33 #include <dev/sdmmc/sdmmcvar.h>
34 #include <dev/sdmmc/sdmmc_ioreg.h>
35 
36 #define SDMMC_CTRL		0x0000
37 #define  SDMMC_CTRL_USE_INTERNAL_DMAC	(1 << 25)
38 #define  SDMMC_CTRL_DMA_ENABLE		(1 << 5)
39 #define  SDMMC_CTRL_INT_ENABLE		(1 << 4)
40 #define  SDMMC_CTRL_DMA_RESET		(1 << 2)
41 #define  SDMMC_CTRL_FIFO_RESET		(1 << 1)
42 #define  SDMMC_CTRL_CONTROLLER_RESET	(1 << 0)
43 #define  SDMMC_CTRL_ALL_RESET	(SDMMC_CTRL_CONTROLLER_RESET | \
44     SDMMC_CTRL_FIFO_RESET | SDMMC_CTRL_DMA_RESET)
45 #define SDMMC_PWREN		0x0004
46 #define SDMMC_CLKDIV		0x0008
47 #define SDMMC_CLKSRC		0x000c
48 #define SDMMC_CLKENA		0x0010
49 #define  SDMMC_CLKENA_CCLK_LOW_POWER	(1 << 16)
50 #define  SDMMC_CLKENA_CCLK_ENABLE	(1 << 0)
51 #define SDMMC_TMOUT		0x0014
52 #define SDMMC_CTYPE		0x0018
53 #define  SDMMC_CTYPE_8BIT		(1 << 16)
54 #define  SDMMC_CTYPE_4BIT		(1 << 0)
55 #define SDMMC_BLKSIZ		0x001c
56 #define SDMMC_BYTCNT		0x0020
57 #define SDMMC_INTMASK		0x0024
58 #define SDMMC_CMDARG		0x0028
59 #define SDMMC_CMD		0x002c
60 #define  SDMMC_CMD_START_CMD		(1U << 31)
61 #define  SDMMC_CMD_USE_HOLD_REG		(1 << 29)
62 #define  SDMMC_CMD_UPDATE_CLOCK_REGISTERS_ONLY	(1 << 21)
63 #define  SDMMC_CMD_SEND_INITIALIZATION	(1 << 15)
64 #define  SDMMC_CMD_STOP_ABORT_CMD	(1 << 14)
65 #define  SDMMC_CMD_WAIT_PRVDATA_COMPLETE	(1 << 13)
66 #define  SDMMC_CMD_SEND_AUTO_STOP	(1 << 12)
67 #define  SDMMC_CMD_WR			(1 << 10)
68 #define  SDMMC_CMD_DATA_EXPECTED	(1 << 9)
69 #define  SDMMC_CMD_CHECK_REPONSE_CRC	(1 << 8)
70 #define  SDMMC_CMD_RESPONSE_LENGTH	(1 << 7)
71 #define  SDMMC_CMD_RESPONSE_EXPECT	(1 << 6)
72 #define SDMMC_RESP0		0x0030
73 #define SDMMC_RESP1		0x0034
74 #define SDMMC_RESP2		0x0038
75 #define SDMMC_RESP3		0x003c
76 #define SDMMC_MINTSTS		0x0040
77 #define SDMMC_RINTSTS		0x0044
78 #define  SDMMC_RINTSTS_SDIO		(1 << 24)
79 #define  SDMMC_RINTSTS_EBE		(1 << 15)
80 #define  SDMMC_RINTSTS_ACD		(1 << 14)
81 #define  SDMMC_RINTSTS_SBE		(1 << 13)
82 #define  SDMMC_RINTSTS_HLE		(1 << 12)
83 #define  SDMMC_RINTSTS_FRUN		(1 << 11)
84 #define  SDMMC_RINTSTS_HTO		(1 << 10)
85 #define  SDMMC_RINTSTS_DRTO		(1 << 9)
86 #define  SDMMC_RINTSTS_RTO		(1 << 8)
87 #define  SDMMC_RINTSTS_DCRC		(1 << 7)
88 #define  SDMMC_RINTSTS_RCRC		(1 << 6)
89 #define  SDMMC_RINTSTS_RXDR		(1 << 5)
90 #define  SDMMC_RINTSTS_TXDR		(1 << 4)
91 #define  SDMMC_RINTSTS_DTO		(1 << 3)
92 #define  SDMMC_RINTSTS_CD		(1 << 2)
93 #define  SDMMC_RINTSTS_RE		(1 << 1)
94 #define  SDMMC_RINTSTS_CDT		(1 << 0)
95 #define  SDMMC_RINTSTS_DATA_ERR	(SDMMC_RINTSTS_EBE | SDMMC_RINTSTS_SBE | \
96     SDMMC_RINTSTS_HLE | SDMMC_RINTSTS_FRUN | SDMMC_RINTSTS_DCRC)
97 #define  SDMMC_RINTSTS_DATA_TO	(SDMMC_RINTSTS_HTO | SDMMC_RINTSTS_DRTO)
98 #define SDMMC_STATUS		0x0048
99 #define SDMMC_STATUS_FIFO_COUNT(x)	(((x) >> 17) & 0x1fff)
100 #define  SDMMC_STATUS_DATA_BUSY		(1 << 9)
101 #define SDMMC_FIFOTH		0x004c
102 #define  SDMMC_FIFOTH_MSIZE_SHIFT	28
103 #define  SDMMC_FIFOTH_RXWM_SHIFT	16
104 #define  SDMMC_FIFOTH_RXWM(x)		(((x) >> 16) & 0xfff)
105 #define  SDMMC_FIFOTH_TXWM_SHIFT	0
106 #define SDMMC_CDETECT		0x0050
107 #define  SDMMC_CDETECT_CARD_DETECT_0	(1 << 0)
108 #define SDMMC_WRTPRT		0x0054
109 #define SDMMC_TCBCNT		0x005c
110 #define SDMMC_TBBCNT		0x0060
111 #define SDMMC_DEBNCE		0x0064
112 #define SDMMC_USRID		0x0068
113 #define SDMMC_VERID		0x006c
114 #define SDMMC_HCON		0x0070
115 #define  SDMMC_HCON_DATA_WIDTH(x)	(((x) >> 7) & 0x7)
116 #define  SDMMC_HCON_DMA64		(1 << 27)
117 #define SDMMC_UHS_REG		0x0074
118 #define SDMMC_RST_n		0x0078
119 #define SDMMC_BMOD		0x0080
120 #define  SDMMC_BMOD_DE			(1 << 7)
121 #define  SDMMC_BMOD_FB			(1 << 1)
122 #define  SDMMC_BMOD_SWR			(1 << 0)
123 #define SDMMC_PLDMND		0x0084
124 #define SDMMC_DBADDR		0x0088
125 #define SDMMC_IDSTS32		0x008c
126 #define  SDMMC_IDSTS_NIS		(1 << 8)
127 #define  SDMMC_IDSTS_RI			(1 << 1)
128 #define  SDMMC_IDSTS_TI			(1 << 0)
129 #define SDMMC_IDINTEN32		0x0090
130 #define  SDMMC_IDINTEN_NI		(1 << 8)
131 #define  SDMMC_IDINTEN_RI		(1 << 1)
132 #define  SDMMC_IDINTEN_TI		(1 << 0)
133 #define SDMMC_DSCADDR		0x0094
134 #define SDMMC_BUFADDR		0x0098
135 #define SDMMC_CLKSEL		0x009c
136 #define SDMMC_CARDTHRCTL	0x0100
137 #define  SDMMC_CARDTHRCTL_RDTHR_SHIFT	16
138 #define  SDMMC_CARDTHRCTL_RDTHREN	(1 << 0)
139 #define SDMMC_BACK_END_POWER	0x0104
140 #define SDMMC_EMMC_DDR_REG	0x0108
141 #define SDMMC_FIFO_BASE		0x0200
142 
143 #define SDMMC_DBADDRL		0x0088
144 #define SDMMC_DBADDRH		0x008c
145 #define SDMMC_IDSTS64		0x0090
146 #define SDMMC_IDINTEN64		0x0094
147 #define SDMMC_DSCADDRL		0x0098
148 #define SDMMC_DSCADDRH		0x009c
149 #define SDMMC_BUFADDRL		0x00a0
150 #define SDMMC_BUFADDRH		0x00a4
151 
152 #define SDMMC_IDSTS(sc) \
153     ((sc)->sc_dma64 ? SDMMC_IDSTS64 : SDMMC_IDSTS32)
154 
155 #define HREAD4(sc, reg)							\
156     (bus_space_read_4((sc)->sc_iot, (sc)->sc_ioh, (reg)))
157 #define HWRITE4(sc, reg, val)						\
158     bus_space_write_4((sc)->sc_iot, (sc)->sc_ioh, (reg), (val))
159 #define HSET4(sc, reg, bits)						\
160     HWRITE4((sc), (reg), HREAD4((sc), (reg)) | (bits))
161 #define HCLR4(sc, reg, bits)						\
162     HWRITE4((sc), (reg), HREAD4((sc), (reg)) & ~(bits))
163 
164 struct dwmmc_desc32 {
165 	uint32_t des[4];
166 };
167 
168 struct dwmmc_desc64 {
169 	uint32_t des[8];
170 };
171 
172 #define DWMMC_NDESC	(PAGE_SIZE / sizeof(struct dwmmc_desc64))
173 #define DWMMC_MAXSEGSZ	0x1000
174 
175 #define DES0_OWN	(1U << 31)
176 #define DES0_CES	(1 << 30)
177 #define DES0_ER		(1 << 5)
178 #define DES0_CH		(1 << 4)
179 #define DES0_FS		(1 << 3)
180 #define DES0_LD		(1 << 2)
181 #define DES0_DIC	(1 << 1)
182 
183 #define DES1_BS2(sz)	(((sz) & 0x1fff) << 13)
184 #define DES1_BS1(sz)	(((sz) & 0x1fff) << 0)
185 #define DES2_BS2(sz)	DES1_BS2(sz)
186 #define DES2_BS1(sz)	DES1_BS1(sz)
187 
188 struct dwmmc_softc {
189 	struct device		sc_dev;
190 	bus_space_tag_t		sc_iot;
191 	bus_space_handle_t	sc_ioh;
192 	bus_size_t		sc_size;
193 	bus_dma_tag_t		sc_dmat;
194 	bus_dmamap_t		sc_dmap;
195 	int			sc_node;
196 
197 	void			*sc_ih;
198 
199 	uint32_t		sc_clkbase;
200 	uint32_t		sc_fifo_depth;
201 	uint32_t		sc_fifo_width;
202 	void (*sc_read_data)(struct dwmmc_softc *, u_char *, int);
203 	void (*sc_write_data)(struct dwmmc_softc *, u_char *, int);
204 	int			sc_blklen;
205 
206 	bus_dmamap_t		sc_desc_map;
207 	bus_dma_segment_t	sc_desc_segs[1];
208 	caddr_t			sc_desc;
209 	int			sc_dma64;
210 	int			sc_dmamode;
211 	uint32_t		sc_idsts;
212 
213 	uint32_t		sc_gpio[4];
214 	int			sc_sdio_irq;
215 	uint32_t		sc_pwrseq;
216 	uint32_t		sc_vdd;
217 
218 	struct device		*sc_sdmmc;
219 };
220 
221 int	dwmmc_match(struct device *, void *, void *);
222 void	dwmmc_attach(struct device *, struct device *, void *);
223 
224 const struct cfattach dwmmc_ca = {
225 	sizeof(struct dwmmc_softc), dwmmc_match, dwmmc_attach
226 };
227 
228 struct cfdriver dwmmc_cd = {
229 	NULL, "dwmmc", DV_DULL
230 };
231 
232 int	dwmmc_intr(void *);
233 
234 int	dwmmc_host_reset(sdmmc_chipset_handle_t);
235 uint32_t dwmmc_host_ocr(sdmmc_chipset_handle_t);
236 int	dwmmc_host_maxblklen(sdmmc_chipset_handle_t);
237 int	dwmmc_card_detect(sdmmc_chipset_handle_t);
238 int	dwmmc_bus_power(sdmmc_chipset_handle_t, uint32_t);
239 int	dwmmc_bus_clock(sdmmc_chipset_handle_t, int, int);
240 int	dwmmc_bus_width(sdmmc_chipset_handle_t, int);
241 void	dwmmc_exec_command(sdmmc_chipset_handle_t, struct sdmmc_command *);
242 void	dwmmc_card_intr_mask(sdmmc_chipset_handle_t, int);
243 void	dwmmc_card_intr_ack(sdmmc_chipset_handle_t);
244 
245 struct sdmmc_chip_functions dwmmc_chip_functions = {
246 	.host_reset = dwmmc_host_reset,
247 	.host_ocr = dwmmc_host_ocr,
248 	.host_maxblklen = dwmmc_host_maxblklen,
249 	.card_detect = dwmmc_card_detect,
250 	.bus_power = dwmmc_bus_power,
251 	.bus_clock = dwmmc_bus_clock,
252 	.bus_width = dwmmc_bus_width,
253 	.exec_command = dwmmc_exec_command,
254 	.card_intr_mask = dwmmc_card_intr_mask,
255 	.card_intr_ack = dwmmc_card_intr_ack,
256 };
257 
258 void	dwmmc_pio_mode(struct dwmmc_softc *);
259 int	dwmmc_alloc_descriptors(struct dwmmc_softc *);
260 void	dwmmc_init_descriptors(struct dwmmc_softc *);
261 void	dwmmc_transfer_data(struct dwmmc_softc *, struct sdmmc_command *);
262 void	dwmmc_read_data32(struct dwmmc_softc *, u_char *, int);
263 void	dwmmc_write_data32(struct dwmmc_softc *, u_char *, int);
264 void	dwmmc_read_data64(struct dwmmc_softc *, u_char *, int);
265 void	dwmmc_write_data64(struct dwmmc_softc *, u_char *, int);
266 void	dwmmc_pwrseq_pre(uint32_t);
267 void	dwmmc_pwrseq_post(uint32_t);
268 
269 int
dwmmc_match(struct device * parent,void * match,void * aux)270 dwmmc_match(struct device *parent, void *match, void *aux)
271 {
272 	struct fdt_attach_args *faa = aux;
273 
274 	return (OF_is_compatible(faa->fa_node, "hisilicon,hi3660-dw-mshc") ||
275 	    OF_is_compatible(faa->fa_node, "hisilicon,hi3670-dw-mshc") ||
276 	    OF_is_compatible(faa->fa_node, "rockchip,rk3288-dw-mshc") ||
277 	    OF_is_compatible(faa->fa_node, "samsung,exynos5420-dw-mshc") ||
278 	    OF_is_compatible(faa->fa_node, "snps,dw-mshc") ||
279 	    OF_is_compatible(faa->fa_node, "starfive,jh7110-mmc"));
280 }
281 
282 void
dwmmc_attach(struct device * parent,struct device * self,void * aux)283 dwmmc_attach(struct device *parent, struct device *self, void *aux)
284 {
285 	struct dwmmc_softc *sc = (struct dwmmc_softc *)self;
286 	struct fdt_attach_args *faa = aux;
287 	struct sdmmcbus_attach_args saa;
288 	uint32_t freq = 0, div = 0;
289 	uint32_t hcon, width;
290 	uint32_t fifoth;
291 	int error, timeout;
292 
293 	if (faa->fa_nreg < 1) {
294 		printf(": no registers\n");
295 		return;
296 	}
297 
298 	sc->sc_node = faa->fa_node;
299 	sc->sc_iot = faa->fa_iot;
300 	sc->sc_size = faa->fa_reg[0].size;
301 
302 	if (bus_space_map(sc->sc_iot, faa->fa_reg[0].addr,
303 	    faa->fa_reg[0].size, 0, &sc->sc_ioh)) {
304 		printf(": can't map registers\n");
305 		return;
306 	}
307 
308 	pinctrl_byname(faa->fa_node, "default");
309 
310 	clock_enable_all(faa->fa_node);
311 	reset_deassert_all(faa->fa_node);
312 
313 	/*
314 	 * Determine FIFO width from hardware configuration register.
315 	 * We only support 32-bit and 64-bit FIFOs.
316 	 */
317 	hcon = HREAD4(sc, SDMMC_HCON);
318 	switch (SDMMC_HCON_DATA_WIDTH(hcon)) {
319 	case 1:
320 		sc->sc_fifo_width = 4;
321 		sc->sc_read_data = dwmmc_read_data32;
322 		sc->sc_write_data = dwmmc_write_data32;
323 		break;
324 	case 2:
325 		sc->sc_fifo_width = 8;
326 		sc->sc_read_data = dwmmc_read_data64;
327 		sc->sc_write_data = dwmmc_write_data64;
328 		break;
329 	default:
330 		printf(": unsupported FIFO width\n");
331 		return;
332 	}
333 
334 	sc->sc_fifo_depth = OF_getpropint(faa->fa_node, "fifo-depth", 0);
335 	if (sc->sc_fifo_depth == 0) {
336 		fifoth = HREAD4(sc, SDMMC_FIFOTH);
337 		sc->sc_fifo_depth = SDMMC_FIFOTH_RXWM(fifoth) + 1;
338 	}
339 
340 	if (hcon & SDMMC_HCON_DMA64)
341 		sc->sc_dma64 = 1;
342 
343 	/* Some SoCs pre-divide the clock. */
344 	if (OF_is_compatible(faa->fa_node, "rockchip,rk3288-dw-mshc"))
345 		div = 1;
346 	if (OF_is_compatible(faa->fa_node, "hisilicon,hi3660-dw-mshc") ||
347 	    OF_is_compatible(faa->fa_node, "hisilicon,hi3670-dw-mshc"))
348 		div = 7;
349 
350 	/* Force the base clock to 50MHz on Rockchip SoCs. */
351 	if (OF_is_compatible(faa->fa_node, "rockchip,rk3288-dw-mshc"))
352 		freq = 50000000;
353 
354 	freq = OF_getpropint(faa->fa_node, "clock-frequency", freq);
355 	if (freq > 0)
356 		clock_set_frequency(faa->fa_node, "ciu", (div + 1) * freq);
357 
358 	sc->sc_clkbase = clock_get_frequency(faa->fa_node, "ciu");
359 	/* if ciu clock is missing the rate is clock-frequency */
360 	if (sc->sc_clkbase == 0)
361 		sc->sc_clkbase = freq;
362 	if (sc->sc_clkbase == 0) {
363 		printf(": no clock base\n");
364 		return;
365 	}
366 	div = OF_getpropint(faa->fa_node, "samsung,dw-mshc-ciu-div", div);
367 	sc->sc_clkbase /= (div + 1);
368 
369 	sc->sc_ih = fdt_intr_establish(faa->fa_node, IPL_BIO,
370 	    dwmmc_intr, sc, sc->sc_dev.dv_xname);
371 	if (sc->sc_ih == NULL) {
372 		printf(": can't establish interrupt\n");
373 		goto unmap;
374 	}
375 
376 	OF_getpropintarray(faa->fa_node, "cd-gpios", sc->sc_gpio,
377 	    sizeof(sc->sc_gpio));
378 	if (sc->sc_gpio[0])
379 		gpio_controller_config_pin(sc->sc_gpio, GPIO_CONFIG_INPUT);
380 
381 	sc->sc_sdio_irq = (OF_getproplen(sc->sc_node, "cap-sdio-irq") == 0);
382 	sc->sc_pwrseq = OF_getpropint(sc->sc_node, "mmc-pwrseq", 0);
383 
384 	printf(": %d MHz base clock\n", sc->sc_clkbase / 1000000);
385 
386 	HSET4(sc, SDMMC_CTRL, SDMMC_CTRL_ALL_RESET);
387 	for (timeout = 5000; timeout > 0; timeout--) {
388 		if ((HREAD4(sc, SDMMC_CTRL) & SDMMC_CTRL_ALL_RESET) == 0)
389 			break;
390 		delay(100);
391 	}
392 	if (timeout == 0)
393 		printf("%s: reset failed\n", sc->sc_dev.dv_xname);
394 
395 	/* Enable interrupts, but mask them all. */
396 	HWRITE4(sc, SDMMC_INTMASK, 0);
397 	HWRITE4(sc, SDMMC_RINTSTS, 0xffffffff);
398 	HSET4(sc, SDMMC_CTRL, SDMMC_CTRL_INT_ENABLE);
399 
400 	dwmmc_bus_width(sc, 1);
401 
402 	/* Start out in non-DMA mode. */
403 	dwmmc_pio_mode(sc);
404 
405 	sc->sc_dmat = faa->fa_dmat;
406 	dwmmc_alloc_descriptors(sc);
407 	dwmmc_init_descriptors(sc);
408 
409 	error = bus_dmamap_create(sc->sc_dmat, MAXPHYS, DWMMC_NDESC,
410 	    DWMMC_MAXSEGSZ, 0, BUS_DMA_WAITOK|BUS_DMA_ALLOCNOW, &sc->sc_dmap);
411 	if (error) {
412 		printf(": can't create DMA map\n");
413 		goto unmap;
414 	}
415 
416 	memset(&saa, 0, sizeof(saa));
417 	saa.saa_busname = "sdmmc";
418 	saa.sct = &dwmmc_chip_functions;
419 	saa.sch = sc;
420 	saa.dmat = sc->sc_dmat;
421 	saa.dmap = sc->sc_dmap;
422 	saa.caps |= SMC_CAPS_DMA;
423 
424 	if (OF_getproplen(sc->sc_node, "cap-mmc-highspeed") == 0)
425 		saa.caps |= SMC_CAPS_MMC_HIGHSPEED;
426 	if (OF_getproplen(sc->sc_node, "cap-sd-highspeed") == 0)
427 		saa.caps |= SMC_CAPS_SD_HIGHSPEED;
428 
429 	width = OF_getpropint(faa->fa_node, "bus-width", 1);
430 	if (width >= 8)
431 		saa.caps |= SMC_CAPS_8BIT_MODE;
432 	if (width >= 4)
433 		saa.caps |= SMC_CAPS_4BIT_MODE;
434 
435 	sc->sc_sdmmc = config_found(self, &saa, NULL);
436 	return;
437 
438 unmap:
439 	bus_space_unmap(sc->sc_iot, sc->sc_ioh, sc->sc_size);
440 }
441 
442 int
dwmmc_alloc_descriptors(struct dwmmc_softc * sc)443 dwmmc_alloc_descriptors(struct dwmmc_softc *sc)
444 {
445 	int error, rseg;
446 
447 	/* Allocate descriptor memory */
448 	error = bus_dmamem_alloc(sc->sc_dmat, PAGE_SIZE, PAGE_SIZE,
449 	    PAGE_SIZE, sc->sc_desc_segs, 1, &rseg,
450 	    BUS_DMA_WAITOK | BUS_DMA_ZERO);
451 	if (error)
452 		return error;
453 	error = bus_dmamem_map(sc->sc_dmat, sc->sc_desc_segs, rseg,
454 	    PAGE_SIZE, &sc->sc_desc, BUS_DMA_WAITOK | BUS_DMA_COHERENT);
455 	if (error) {
456 		bus_dmamem_free(sc->sc_dmat, sc->sc_desc_segs, rseg);
457 		return error;
458 	}
459 	error = bus_dmamap_create(sc->sc_dmat, PAGE_SIZE, 1, PAGE_SIZE,
460 	    0, BUS_DMA_WAITOK, &sc->sc_desc_map);
461 	if (error) {
462 		bus_dmamem_unmap(sc->sc_dmat, sc->sc_desc, PAGE_SIZE);
463 		bus_dmamem_free(sc->sc_dmat, sc->sc_desc_segs, rseg);
464 		return error;
465 	}
466 	error = bus_dmamap_load(sc->sc_dmat, sc->sc_desc_map,
467 	    sc->sc_desc, PAGE_SIZE, NULL, BUS_DMA_WAITOK | BUS_DMA_WRITE);
468 	if (error) {
469 		bus_dmamap_destroy(sc->sc_dmat, sc->sc_desc_map);
470 		bus_dmamem_unmap(sc->sc_dmat, sc->sc_desc, PAGE_SIZE);
471 		bus_dmamem_free(sc->sc_dmat, sc->sc_desc_segs, rseg);
472 		return error;
473 	}
474 
475 	return 0;
476 }
477 
478 void
dwmmc_init_descriptors32(struct dwmmc_softc * sc)479 dwmmc_init_descriptors32(struct dwmmc_softc *sc)
480 {
481 	struct dwmmc_desc32 *desc;
482 	bus_addr_t addr;
483 	int i;
484 
485 	desc = (void *)sc->sc_desc;
486 	addr = sc->sc_desc_map->dm_segs[0].ds_addr;
487 	for (i = 0; i < DWMMC_NDESC; i++) {
488 		addr += sizeof(struct dwmmc_desc32);
489 		desc[i].des[3] = addr;
490 	}
491 	desc[DWMMC_NDESC - 1].des[3] = sc->sc_desc_map->dm_segs[0].ds_addr;
492 	desc[DWMMC_NDESC - 1].des[0] = DES0_ER;
493 	bus_dmamap_sync(sc->sc_dmat, sc->sc_desc_map, 0,
494 	    PAGE_SIZE, BUS_DMASYNC_PREWRITE);
495 
496 	HWRITE4(sc, SDMMC_IDSTS32, 0xffffffff);
497 	HWRITE4(sc, SDMMC_IDINTEN32,
498 	    SDMMC_IDINTEN_NI | SDMMC_IDINTEN_RI | SDMMC_IDINTEN_TI);
499 	HWRITE4(sc, SDMMC_DBADDR, sc->sc_desc_map->dm_segs[0].ds_addr);
500 }
501 
502 void
dwmmc_init_descriptors64(struct dwmmc_softc * sc)503 dwmmc_init_descriptors64(struct dwmmc_softc *sc)
504 {
505 	struct dwmmc_desc64 *desc;
506 	bus_addr_t addr;
507 	int i;
508 
509 	desc = (void *)sc->sc_desc;
510 	addr = sc->sc_desc_map->dm_segs[0].ds_addr;
511 	for (i = 0; i < DWMMC_NDESC; i++) {
512 		addr += sizeof(struct dwmmc_desc64);
513 		desc[i].des[6] = addr;
514 		desc[i].des[7] = (uint64_t)addr >> 32;
515 	}
516 	desc[DWMMC_NDESC - 1].des[6] = sc->sc_desc_map->dm_segs[0].ds_addr;
517 	desc[DWMMC_NDESC - 1].des[7] =
518 	    (uint64_t)sc->sc_desc_map->dm_segs[0].ds_addr >> 32;
519 	desc[DWMMC_NDESC - 1].des[0] = DES0_ER;
520 	bus_dmamap_sync(sc->sc_dmat, sc->sc_desc_map, 0,
521 	    PAGE_SIZE, BUS_DMASYNC_PREWRITE);
522 
523 	HWRITE4(sc, SDMMC_IDSTS64, 0xffffffff);
524 	HWRITE4(sc, SDMMC_IDINTEN64,
525 	    SDMMC_IDINTEN_NI | SDMMC_IDINTEN_RI | SDMMC_IDINTEN_TI);
526 	HWRITE4(sc, SDMMC_DBADDRL, sc->sc_desc_map->dm_segs[0].ds_addr);
527 	HWRITE4(sc, SDMMC_DBADDRH,
528 	    (uint64_t)sc->sc_desc_map->dm_segs[0].ds_addr >> 32);
529 }
530 
531 void
dwmmc_init_descriptors(struct dwmmc_softc * sc)532 dwmmc_init_descriptors(struct dwmmc_softc *sc)
533 {
534 	if (sc->sc_dma64)
535 		dwmmc_init_descriptors64(sc);
536 	else
537 		dwmmc_init_descriptors32(sc);
538 }
539 
540 int
dwmmc_intr(void * arg)541 dwmmc_intr(void *arg)
542 {
543 	struct dwmmc_softc *sc = arg;
544 	uint32_t stat;
545 	int handled = 0;
546 
547 	stat = HREAD4(sc, SDMMC_IDSTS(sc));
548 	if (stat) {
549 		HWRITE4(sc, SDMMC_IDSTS(sc), stat);
550 		sc->sc_idsts |= stat;
551 		wakeup(&sc->sc_idsts);
552 		handled = 1;
553 	}
554 
555 	stat = HREAD4(sc, SDMMC_MINTSTS);
556 	if (stat & SDMMC_RINTSTS_SDIO) {
557 		HWRITE4(sc, SDMMC_RINTSTS, SDMMC_RINTSTS_SDIO);
558 		HCLR4(sc, SDMMC_INTMASK, SDMMC_RINTSTS_SDIO);
559 		sdmmc_card_intr(sc->sc_sdmmc);
560 		handled = 1;
561 	}
562 
563 	return handled;
564 }
565 
566 void
dwmmc_card_intr_mask(sdmmc_chipset_handle_t sch,int enable)567 dwmmc_card_intr_mask(sdmmc_chipset_handle_t sch, int enable)
568 {
569 	struct dwmmc_softc *sc = sch;
570 
571 	if (enable)
572 		HSET4(sc, SDMMC_INTMASK, SDMMC_RINTSTS_SDIO);
573 	else
574 		HCLR4(sc, SDMMC_INTMASK, SDMMC_RINTSTS_SDIO);
575 }
576 
577 void
dwmmc_card_intr_ack(sdmmc_chipset_handle_t sch)578 dwmmc_card_intr_ack(sdmmc_chipset_handle_t sch)
579 {
580 	struct dwmmc_softc *sc = sch;
581 
582 	HSET4(sc, SDMMC_INTMASK, SDMMC_RINTSTS_SDIO);
583 }
584 
585 int
dwmmc_host_reset(sdmmc_chipset_handle_t sch)586 dwmmc_host_reset(sdmmc_chipset_handle_t sch)
587 {
588 	printf("%s\n", __func__);
589 	return 0;
590 }
591 
592 uint32_t
dwmmc_host_ocr(sdmmc_chipset_handle_t sch)593 dwmmc_host_ocr(sdmmc_chipset_handle_t sch)
594 {
595 	return MMC_OCR_3_2V_3_3V | MMC_OCR_3_3V_3_4V;
596 }
597 
598 int
dwmmc_host_maxblklen(sdmmc_chipset_handle_t sch)599 dwmmc_host_maxblklen(sdmmc_chipset_handle_t sch)
600 {
601 	return 512;
602 }
603 
604 int
dwmmc_card_detect(sdmmc_chipset_handle_t sch)605 dwmmc_card_detect(sdmmc_chipset_handle_t sch)
606 {
607 	struct dwmmc_softc *sc = sch;
608 	uint32_t cdetect;
609 
610 	/* XXX treat broken-cd as non-removable */
611 	if (OF_getproplen(sc->sc_node, "non-removable") == 0 ||
612 	    OF_getproplen(sc->sc_node, "broken-cd") == 0)
613 		return 1;
614 
615 	if (sc->sc_gpio[0]) {
616 		int inverted, val;
617 
618 		val = gpio_controller_get_pin(sc->sc_gpio);
619 
620 		inverted = (OF_getproplen(sc->sc_node, "cd-inverted") == 0);
621 		return inverted ? !val : val;
622 	}
623 
624 	cdetect = HREAD4(sc, SDMMC_CDETECT);
625 	return !(cdetect & SDMMC_CDETECT_CARD_DETECT_0);
626 }
627 
628 int
dwmmc_bus_power(sdmmc_chipset_handle_t sch,uint32_t ocr)629 dwmmc_bus_power(sdmmc_chipset_handle_t sch, uint32_t ocr)
630 {
631 	struct dwmmc_softc *sc = sch;
632 	uint32_t vdd = 0;
633 
634 	if (ISSET(ocr, MMC_OCR_3_2V_3_3V|MMC_OCR_3_3V_3_4V))
635 		vdd = 3300000;
636 
637 	if (sc->sc_vdd == 0 && vdd > 0)
638 		dwmmc_pwrseq_pre(sc->sc_pwrseq);
639 
640 	if (ISSET(ocr, MMC_OCR_3_2V_3_3V|MMC_OCR_3_3V_3_4V))
641 		HSET4(sc, SDMMC_PWREN, 1);
642 	else
643 		HCLR4(sc, SDMMC_PWREN, 0);
644 
645 	if (sc->sc_vdd == 0 && vdd > 0)
646 		dwmmc_pwrseq_post(sc->sc_pwrseq);
647 
648 	sc->sc_vdd = vdd;
649 	return 0;
650 }
651 
652 int
dwmmc_bus_clock(sdmmc_chipset_handle_t sch,int freq,int timing)653 dwmmc_bus_clock(sdmmc_chipset_handle_t sch, int freq, int timing)
654 {
655 	struct dwmmc_softc *sc = sch;
656 	int div = 0, timeout;
657 	uint32_t clkena;
658 
659 	HWRITE4(sc, SDMMC_CLKENA, 0);
660 	HWRITE4(sc, SDMMC_CLKSRC, 0);
661 
662 	if (freq == 0)
663 		return 0;
664 
665 	if (sc->sc_clkbase / 1000 > freq) {
666 		for (div = 1; div < 256; div++)
667 			if (sc->sc_clkbase / (2 * 1000 * div) <= freq)
668 				break;
669 	}
670 	HWRITE4(sc, SDMMC_CLKDIV, div);
671 
672 	/* Update clock. */
673 	HWRITE4(sc, SDMMC_CMD, SDMMC_CMD_START_CMD |
674 	    SDMMC_CMD_WAIT_PRVDATA_COMPLETE |
675 	    SDMMC_CMD_UPDATE_CLOCK_REGISTERS_ONLY);
676 	for (timeout = 1000; timeout > 0; timeout--) {
677 		if ((HREAD4(sc, SDMMC_CMD) & SDMMC_CMD_START_CMD) == 0)
678 			break;
679 	}
680 	if (timeout == 0) {
681 		printf("%s: timeout\n", __func__);
682 		return ETIMEDOUT;
683 	}
684 
685 	/* Enable clock; low power mode only for memory mode. */
686 	clkena = SDMMC_CLKENA_CCLK_ENABLE;
687 	if (!sc->sc_sdio_irq)
688 		clkena |= SDMMC_CLKENA_CCLK_LOW_POWER;
689 	HWRITE4(sc, SDMMC_CLKENA, clkena);
690 
691 	/* Update clock again. */
692 	HWRITE4(sc, SDMMC_CMD, SDMMC_CMD_START_CMD |
693 	    SDMMC_CMD_WAIT_PRVDATA_COMPLETE |
694 	    SDMMC_CMD_UPDATE_CLOCK_REGISTERS_ONLY);
695 	for (timeout = 1000; timeout > 0; timeout--) {
696 		if ((HREAD4(sc, SDMMC_CMD) & SDMMC_CMD_START_CMD) == 0)
697 			break;
698 	}
699 	if (timeout == 0) {
700 		printf("%s: timeout\n", __func__);
701 		return ETIMEDOUT;
702 	}
703 
704 	delay(1000000);
705 
706 	return 0;
707 }
708 
709 int
dwmmc_bus_width(sdmmc_chipset_handle_t sch,int width)710 dwmmc_bus_width(sdmmc_chipset_handle_t sch, int width)
711 {
712 	struct dwmmc_softc *sc = sch;
713 
714 	switch (width) {
715 	case 1:
716 		HCLR4(sc, SDMMC_CTYPE, SDMMC_CTYPE_8BIT|SDMMC_CTYPE_4BIT);
717 		break;
718 	case 4:
719 		HSET4(sc, SDMMC_CTYPE, SDMMC_CTYPE_4BIT);
720 		HCLR4(sc, SDMMC_CTYPE, SDMMC_CTYPE_8BIT);
721 		break;
722 	case 8:
723 		HSET4(sc, SDMMC_CTYPE, SDMMC_CTYPE_8BIT);
724 		break;
725 	default:
726 		return EINVAL;
727 	}
728 
729 	return 0;
730 }
731 
732 void
dwmmc_pio_mode(struct dwmmc_softc * sc)733 dwmmc_pio_mode(struct dwmmc_softc *sc)
734 {
735 	/* Disable DMA. */
736 	HCLR4(sc, SDMMC_CTRL, SDMMC_CTRL_USE_INTERNAL_DMAC |
737 	    SDMMC_CTRL_DMA_ENABLE);
738 
739 	/* Set FIFO thresholds. */
740 	HWRITE4(sc, SDMMC_FIFOTH, 2 << SDMMC_FIFOTH_MSIZE_SHIFT |
741 	    (sc->sc_fifo_depth / 2 - 1) << SDMMC_FIFOTH_RXWM_SHIFT |
742 	    (sc->sc_fifo_depth / 2) << SDMMC_FIFOTH_TXWM_SHIFT);
743 
744 	sc->sc_dmamode = 0;
745 	sc->sc_blklen = 0;
746 }
747 
748 void
dwmmc_dma_mode(struct dwmmc_softc * sc)749 dwmmc_dma_mode(struct dwmmc_softc *sc)
750 {
751 	int timeout;
752 
753 	/* Reset DMA. */
754 	HSET4(sc, SDMMC_BMOD, SDMMC_BMOD_SWR);
755 	for (timeout = 1000; timeout > 0; timeout--) {
756 		if ((HREAD4(sc, SDMMC_BMOD) & SDMMC_BMOD_SWR) == 0)
757 			break;
758 		delay(100);
759 	}
760 	if (timeout == 0)
761 		printf("%s: DMA reset failed\n", sc->sc_dev.dv_xname);
762 
763 	/* Enable DMA. */
764 	HSET4(sc, SDMMC_CTRL, SDMMC_CTRL_USE_INTERNAL_DMAC |
765 	    SDMMC_CTRL_DMA_ENABLE);
766 	HSET4(sc, SDMMC_BMOD, SDMMC_BMOD_FB | SDMMC_BMOD_DE);
767 
768 	sc->sc_dmamode = 1;
769 }
770 
771 void
dwmmc_dma_setup32(struct dwmmc_softc * sc,struct sdmmc_command * cmd)772 dwmmc_dma_setup32(struct dwmmc_softc *sc, struct sdmmc_command *cmd)
773 {
774 	struct dwmmc_desc32 *desc = (void *)sc->sc_desc;
775 	uint32_t flags;
776 	int seg;
777 
778 	flags = DES0_OWN | DES0_FS | DES0_CH | DES0_DIC;
779 	for (seg = 0; seg < cmd->c_dmamap->dm_nsegs; seg++) {
780 		bus_addr_t addr = cmd->c_dmamap->dm_segs[seg].ds_addr;
781 		bus_size_t len = cmd->c_dmamap->dm_segs[seg].ds_len;
782 
783 		if (seg == cmd->c_dmamap->dm_nsegs - 1) {
784 			flags |= DES0_LD;
785 			flags &= ~DES0_DIC;
786 		}
787 
788 		KASSERT((desc[seg].des[0] & DES0_OWN) == 0);
789 		desc[seg].des[0] = flags;
790 		desc[seg].des[1] = DES1_BS1(len);
791 		desc[seg].des[2] = addr;
792 		flags &= ~DES0_FS;
793 	}
794 }
795 
796 void
dwmmc_dma_setup64(struct dwmmc_softc * sc,struct sdmmc_command * cmd)797 dwmmc_dma_setup64(struct dwmmc_softc *sc, struct sdmmc_command *cmd)
798 {
799 	struct dwmmc_desc64 *desc = (void *)sc->sc_desc;
800 	uint32_t flags;
801 	int seg;
802 
803 	flags = DES0_OWN | DES0_FS | DES0_CH | DES0_DIC;
804 	for (seg = 0; seg < cmd->c_dmamap->dm_nsegs; seg++) {
805 		bus_addr_t addr = cmd->c_dmamap->dm_segs[seg].ds_addr;
806 		bus_size_t len = cmd->c_dmamap->dm_segs[seg].ds_len;
807 
808 		if (seg == cmd->c_dmamap->dm_nsegs - 1) {
809 			flags |= DES0_LD;
810 			flags &= ~DES0_DIC;
811 		}
812 
813 		KASSERT((desc[seg].des[0] & DES0_OWN) == 0);
814 		desc[seg].des[0] = flags;
815 		desc[seg].des[2] = DES2_BS1(len);
816 		desc[seg].des[4] = addr;
817 		desc[seg].des[5] = (uint64_t)addr >> 32;
818 		flags &= ~DES0_FS;
819 	}
820 }
821 
822 void
dwmmc_dma_setup(struct dwmmc_softc * sc,struct sdmmc_command * cmd)823 dwmmc_dma_setup(struct dwmmc_softc *sc, struct sdmmc_command *cmd)
824 {
825 	if (sc->sc_dma64)
826 		dwmmc_dma_setup64(sc, cmd);
827 	else
828 		dwmmc_dma_setup32(sc, cmd);
829 
830 	bus_dmamap_sync(sc->sc_dmat, sc->sc_desc_map, 0, PAGE_SIZE,
831 	    BUS_DMASYNC_PREWRITE);
832 
833 	sc->sc_idsts = 0;
834 }
835 
836 void
dwmmc_dma_reset(struct dwmmc_softc * sc,struct sdmmc_command * cmd)837 dwmmc_dma_reset(struct dwmmc_softc *sc, struct sdmmc_command *cmd)
838 {
839 	int timeout;
840 
841 	/* Reset DMA unit. */
842 	HSET4(sc, SDMMC_BMOD, SDMMC_BMOD_SWR);
843 	for (timeout = 1000; timeout > 0; timeout--) {
844 		if ((HREAD4(sc, SDMMC_BMOD) &
845 		    SDMMC_BMOD_SWR) == 0)
846 			break;
847 		delay(100);
848 	}
849 
850 	dwmmc_pio_mode(sc);
851 
852 	/* Clear descriptors that were in use, */
853 	memset(sc->sc_desc, 0, PAGE_SIZE);
854 	dwmmc_init_descriptors(sc);
855 }
856 
857 void
dwmmc_fifo_setup(struct dwmmc_softc * sc,int blklen)858 dwmmc_fifo_setup(struct dwmmc_softc *sc, int blklen)
859 {
860 	int blkdepth = blklen / sc->sc_fifo_width;
861 	int txwm = sc->sc_fifo_depth / 2;
862 	int rxwm, msize = 0;
863 
864 	/*
865 	 * Bursting is only possible of the block size is a multiple of
866 	 * the FIFO width.
867 	 */
868 	if (blklen % sc->sc_fifo_width == 0)
869 		msize = 7;
870 
871 	/* Magic to calculate the maximum burst size. */
872 	while (msize > 0) {
873 		if (blkdepth % (2 << msize) == 0 &&
874 		    (sc->sc_fifo_depth - txwm) % (2 << msize) == 0)
875 			break;
876 		msize--;
877 	}
878 	rxwm = (2 << msize) - 1;
879 
880 	HWRITE4(sc, SDMMC_FIFOTH,
881 	    msize << SDMMC_FIFOTH_MSIZE_SHIFT |
882 	    rxwm << SDMMC_FIFOTH_RXWM_SHIFT |
883 	    txwm << SDMMC_FIFOTH_TXWM_SHIFT);
884 
885 	sc->sc_blklen = blklen;
886 }
887 
888 void
dwmmc_exec_command(sdmmc_chipset_handle_t sch,struct sdmmc_command * cmd)889 dwmmc_exec_command(sdmmc_chipset_handle_t sch, struct sdmmc_command *cmd)
890 {
891 	struct dwmmc_softc *sc = sch;
892 	uint32_t cmdval = SDMMC_CMD_START_CMD | SDMMC_CMD_USE_HOLD_REG;
893 	uint32_t status;
894 	int error, timeout;
895 	int s;
896 
897 #if 0
898 	printf("%s: cmd %d arg 0x%x flags 0x%x data %p datalen %d blklen %d\n",
899 	    sc->sc_dev.dv_xname, cmd->c_opcode, cmd->c_arg, cmd->c_flags,
900 	    cmd->c_data, cmd->c_datalen, cmd->c_blklen);
901 #endif
902 
903 	s = splbio();
904 
905 	for (timeout = 10000; timeout > 0; timeout--) {
906 		status = HREAD4(sc, SDMMC_STATUS);
907 		if ((status & SDMMC_STATUS_DATA_BUSY) == 0)
908 			break;
909 		delay(100);
910 	}
911 	if (timeout == 0) {
912 		printf("%s: timeout on data busy\n", sc->sc_dev.dv_xname);
913 		goto done;
914 	}
915 
916 	if (cmd->c_opcode == MMC_STOP_TRANSMISSION)
917 		cmdval |= SDMMC_CMD_STOP_ABORT_CMD;
918 	else if (cmd->c_opcode != MMC_SEND_STATUS)
919 		cmdval |= SDMMC_CMD_WAIT_PRVDATA_COMPLETE;
920 
921 	if (cmd->c_opcode == 0)
922 		cmdval |= SDMMC_CMD_SEND_INITIALIZATION;
923 	if (cmd->c_flags & SCF_RSP_PRESENT)
924 		cmdval |= SDMMC_CMD_RESPONSE_EXPECT;
925 	if (cmd->c_flags & SCF_RSP_136)
926 		cmdval |= SDMMC_CMD_RESPONSE_LENGTH;
927 	if (cmd->c_flags & SCF_RSP_CRC)
928 		cmdval |= SDMMC_CMD_CHECK_REPONSE_CRC;
929 
930 	if (cmd->c_datalen > 0) {
931 		HWRITE4(sc, SDMMC_TMOUT, 0xffffffff);
932 		HWRITE4(sc, SDMMC_BYTCNT, cmd->c_datalen);
933 		HWRITE4(sc, SDMMC_BLKSIZ, cmd->c_blklen);
934 
935 		if (ISSET(cmd->c_flags, SCF_CMD_READ)) {
936 			/* Set card read threshold to the size of a block. */
937 			HWRITE4(sc, SDMMC_CARDTHRCTL,
938 			    cmd->c_blklen << SDMMC_CARDTHRCTL_RDTHR_SHIFT |
939 			    SDMMC_CARDTHRCTL_RDTHREN);
940 		}
941 
942 		cmdval |= SDMMC_CMD_DATA_EXPECTED;
943 		if (!ISSET(cmd->c_flags, SCF_CMD_READ))
944 			cmdval |= SDMMC_CMD_WR;
945 		if (cmd->c_datalen > cmd->c_blklen &&
946 		    cmd->c_opcode != SD_IO_RW_EXTENDED)
947 			cmdval |= SDMMC_CMD_SEND_AUTO_STOP;
948 	}
949 
950 	if (cmd->c_datalen > 0 && !cmd->c_dmamap) {
951 		HSET4(sc, SDMMC_CTRL, SDMMC_CTRL_FIFO_RESET);
952 		for (timeout = 1000; timeout > 0; timeout--) {
953 			if ((HREAD4(sc, SDMMC_CTRL) &
954 			    SDMMC_CTRL_FIFO_RESET) == 0)
955 				break;
956 			delay(100);
957 		}
958 		if (timeout == 0)
959 			printf("%s: FIFO reset failed\n", sc->sc_dev.dv_xname);
960 
961 		/* Disable DMA if we are switching back to PIO. */
962 		if (sc->sc_dmamode)
963 			dwmmc_pio_mode(sc);
964 	}
965 
966 	if (cmd->c_datalen > 0 && cmd->c_dmamap) {
967 		dwmmc_dma_setup(sc, cmd);
968 		HWRITE4(sc, SDMMC_PLDMND, 1);
969 
970 		/* Enable DMA if we did PIO before. */
971 		if (!sc->sc_dmamode)
972 			dwmmc_dma_mode(sc);
973 
974 		/* Reconfigure FIFO thresholds if block size changed. */
975 		if (cmd->c_blklen != sc->sc_blklen)
976 			dwmmc_fifo_setup(sc, cmd->c_blklen);
977 	}
978 
979 	HWRITE4(sc, SDMMC_RINTSTS, ~SDMMC_RINTSTS_SDIO);
980 
981 	HWRITE4(sc, SDMMC_CMDARG, cmd->c_arg);
982 	HWRITE4(sc, SDMMC_CMD, cmdval | cmd->c_opcode);
983 
984 	for (timeout = 1000; timeout > 0; timeout--) {
985 		status = HREAD4(sc, SDMMC_RINTSTS);
986 		if (status & SDMMC_RINTSTS_CD)
987 			break;
988 		delay(100);
989 	}
990 	if (timeout == 0 || status & SDMMC_RINTSTS_RTO) {
991 		cmd->c_error = ETIMEDOUT;
992 		dwmmc_dma_reset(sc, cmd);
993 		goto done;
994 	}
995 
996 	if (cmd->c_flags & SCF_RSP_PRESENT) {
997 		if (cmd->c_flags & SCF_RSP_136) {
998 			cmd->c_resp[0] = HREAD4(sc, SDMMC_RESP0);
999 			cmd->c_resp[1] = HREAD4(sc, SDMMC_RESP1);
1000 			cmd->c_resp[2] = HREAD4(sc, SDMMC_RESP2);
1001 			cmd->c_resp[3] = HREAD4(sc, SDMMC_RESP3);
1002 			if (cmd->c_flags & SCF_RSP_CRC) {
1003 				cmd->c_resp[0] = (cmd->c_resp[0] >> 8) |
1004 				    (cmd->c_resp[1] << 24);
1005 				cmd->c_resp[1] = (cmd->c_resp[1] >> 8) |
1006 				    (cmd->c_resp[2] << 24);
1007 				cmd->c_resp[2] = (cmd->c_resp[2] >> 8) |
1008 				    (cmd->c_resp[3] << 24);
1009 				cmd->c_resp[3] = (cmd->c_resp[3] >> 8);
1010 			}
1011 		} else {
1012 			cmd->c_resp[0] = HREAD4(sc, SDMMC_RESP0);
1013 		}
1014 	}
1015 
1016 	if (cmd->c_datalen > 0 && !cmd->c_dmamap)
1017 		dwmmc_transfer_data(sc, cmd);
1018 
1019 	if (cmd->c_datalen > 0 && cmd->c_dmamap) {
1020 		while (sc->sc_idsts == 0) {
1021 			error = tsleep_nsec(&sc->sc_idsts, PWAIT, "idsts",
1022 			    SEC_TO_NSEC(1));
1023 			if (error) {
1024 				cmd->c_error = error;
1025 				dwmmc_dma_reset(sc, cmd);
1026 				goto done;
1027 			}
1028 		}
1029 
1030 		for (timeout = 10000; timeout > 0; timeout--) {
1031 			status = HREAD4(sc, SDMMC_RINTSTS);
1032 			if (status & SDMMC_RINTSTS_DTO)
1033 				break;
1034 			delay(100);
1035 		}
1036 		if (timeout == 0) {
1037 			cmd->c_error = ETIMEDOUT;
1038 			dwmmc_dma_reset(sc, cmd);
1039 			goto done;
1040 		}
1041 	}
1042 
1043 	if (cmdval & SDMMC_CMD_SEND_AUTO_STOP) {
1044 		for (timeout = 10000; timeout > 0; timeout--) {
1045 			status = HREAD4(sc, SDMMC_RINTSTS);
1046 			if (status & SDMMC_RINTSTS_ACD)
1047 				break;
1048 			delay(10);
1049 		}
1050 		if (timeout == 0) {
1051 			cmd->c_error = ETIMEDOUT;
1052 			dwmmc_dma_reset(sc, cmd);
1053 			goto done;
1054 		}
1055 	}
1056 
1057 done:
1058 	cmd->c_flags |= SCF_ITSDONE;
1059 #if 0
1060 	printf("%s: err %d rintsts 0x%x\n", sc->sc_dev.dv_xname, cmd->c_error,
1061 	    HREAD4(sc, SDMMC_RINTSTS));
1062 #endif
1063 	splx(s);
1064 }
1065 
1066 void
dwmmc_transfer_data(struct dwmmc_softc * sc,struct sdmmc_command * cmd)1067 dwmmc_transfer_data(struct dwmmc_softc *sc, struct sdmmc_command *cmd)
1068 {
1069 	int datalen = cmd->c_datalen;
1070 	u_char *datap = cmd->c_data;
1071 	uint32_t status;
1072 	int count, timeout;
1073 	int fifodr = SDMMC_RINTSTS_DTO | SDMMC_RINTSTS_HTO;
1074 
1075 	if (ISSET(cmd->c_flags, SCF_CMD_READ))
1076 		fifodr |= SDMMC_RINTSTS_RXDR;
1077 	else
1078 		fifodr |= SDMMC_RINTSTS_TXDR;
1079 
1080 	while (datalen > 0) {
1081 		status = HREAD4(sc, SDMMC_RINTSTS);
1082 		if (status & SDMMC_RINTSTS_DATA_ERR) {
1083 			cmd->c_error = EIO;
1084 			return;
1085 		}
1086 		if (status & SDMMC_RINTSTS_DRTO) {
1087 			cmd->c_error = ETIMEDOUT;
1088 			return;
1089 		}
1090 
1091 		for (timeout = 10000; timeout > 0; timeout--) {
1092 			status = HREAD4(sc, SDMMC_RINTSTS);
1093 			if (status & fifodr)
1094 				break;
1095 			delay(100);
1096 		}
1097 		if (timeout == 0) {
1098 			cmd->c_error = ETIMEDOUT;
1099 			return;
1100 		}
1101 
1102 		count = SDMMC_STATUS_FIFO_COUNT(HREAD4(sc, SDMMC_STATUS));
1103 		if (!ISSET(cmd->c_flags, SCF_CMD_READ))
1104 		    count = sc->sc_fifo_depth - count;
1105 
1106 		count = MIN(datalen, count * sc->sc_fifo_width);
1107 		if (ISSET(cmd->c_flags, SCF_CMD_READ))
1108 			sc->sc_read_data(sc, datap, count);
1109 		else
1110 			sc->sc_write_data(sc, datap, count);
1111 
1112 		datap += count;
1113 		datalen -= count;
1114 	}
1115 
1116 	for (timeout = 10000; timeout > 0; timeout--) {
1117 		status = HREAD4(sc, SDMMC_RINTSTS);
1118 		if (status & SDMMC_RINTSTS_DTO)
1119 			break;
1120 		delay(100);
1121 	}
1122 	if (timeout == 0)
1123 		cmd->c_error = ETIMEDOUT;
1124 }
1125 
1126 void
dwmmc_read_data32(struct dwmmc_softc * sc,u_char * datap,int datalen)1127 dwmmc_read_data32(struct dwmmc_softc *sc, u_char *datap, int datalen)
1128 {
1129 	while (datalen > 3) {
1130 		*(uint32_t *)datap = HREAD4(sc, SDMMC_FIFO_BASE);
1131 		datap += 4;
1132 		datalen -= 4;
1133 	}
1134 	if (datalen > 0) {
1135 		uint32_t rv = HREAD4(sc, SDMMC_FIFO_BASE);
1136 		do {
1137 			*datap++ = rv & 0xff;
1138 			rv = rv >> 8;
1139 		} while (--datalen > 0);
1140 	}
1141 	HWRITE4(sc, SDMMC_RINTSTS, SDMMC_RINTSTS_RXDR);
1142 }
1143 
1144 void
dwmmc_write_data32(struct dwmmc_softc * sc,u_char * datap,int datalen)1145 dwmmc_write_data32(struct dwmmc_softc *sc, u_char *datap, int datalen)
1146 {
1147 	while (datalen > 3) {
1148 		HWRITE4(sc, SDMMC_FIFO_BASE, *((uint32_t *)datap));
1149 		datap += 4;
1150 		datalen -= 4;
1151 	}
1152 	if (datalen > 0) {
1153 		uint32_t rv = *datap++;
1154 		if (datalen > 1)
1155 			rv |= *datap++ << 8;
1156 		if (datalen > 2)
1157 			rv |= *datap++ << 16;
1158 		HWRITE4(sc, SDMMC_FIFO_BASE, rv);
1159 	}
1160 	HWRITE4(sc, SDMMC_RINTSTS, SDMMC_RINTSTS_TXDR);
1161 }
1162 
1163 void
dwmmc_read_data64(struct dwmmc_softc * sc,u_char * datap,int datalen)1164 dwmmc_read_data64(struct dwmmc_softc *sc, u_char *datap, int datalen)
1165 {
1166 	while (datalen > 7) {
1167 		*(uint32_t *)datap = HREAD4(sc, SDMMC_FIFO_BASE);
1168 		datap += 4;
1169 		datalen -= 4;
1170 		*(uint32_t *)datap = HREAD4(sc, SDMMC_FIFO_BASE + 4);
1171 		datap += 4;
1172 		datalen -= 4;
1173 	}
1174 	if (datalen > 0) {
1175 		uint64_t rv = HREAD4(sc, SDMMC_FIFO_BASE) |
1176 		    ((uint64_t)HREAD4(sc, SDMMC_FIFO_BASE + 4) << 32);
1177 		do {
1178 			*datap++ = rv & 0xff;
1179 			rv = rv >> 8;
1180 		} while (--datalen > 0);
1181 	}
1182 	HWRITE4(sc, SDMMC_RINTSTS, SDMMC_RINTSTS_RXDR);
1183 }
1184 
1185 void
dwmmc_write_data64(struct dwmmc_softc * sc,u_char * datap,int datalen)1186 dwmmc_write_data64(struct dwmmc_softc *sc, u_char *datap, int datalen)
1187 {
1188 	while (datalen > 7) {
1189 		HWRITE4(sc, SDMMC_FIFO_BASE, *((uint32_t *)datap));
1190 		datap += 4;
1191 		datalen -= 4;
1192 		HWRITE4(sc, SDMMC_FIFO_BASE + 4, *((uint32_t *)datap));
1193 		datap += 4;
1194 		datalen -= 4;
1195 	}
1196 	if (datalen > 0) {
1197 		uint32_t rv = *datap++;
1198 		if (datalen > 1)
1199 			rv |= *datap++ << 8;
1200 		if (datalen > 2)
1201 			rv |= *datap++ << 16;
1202 		if (datalen > 3)
1203 			rv |= *datap++ << 24;
1204 		HWRITE4(sc, SDMMC_FIFO_BASE, rv);
1205 		if (datalen > 4)
1206 			rv = *datap++;
1207 		if (datalen > 5)
1208 			rv |= *datap++ << 8;
1209 		if (datalen > 6)
1210 			rv |= *datap++ << 16;
1211 		HWRITE4(sc, SDMMC_FIFO_BASE + 4, rv);
1212 	}
1213 	HWRITE4(sc, SDMMC_RINTSTS, SDMMC_RINTSTS_TXDR);
1214 }
1215 
1216 void
dwmmc_pwrseq_pre(uint32_t phandle)1217 dwmmc_pwrseq_pre(uint32_t phandle)
1218 {
1219 	uint32_t *gpios, *gpio;
1220 	int node;
1221 	int len;
1222 
1223 	node = OF_getnodebyphandle(phandle);
1224 	if (node == 0)
1225 		return;
1226 
1227 	if (!OF_is_compatible(node, "mmc-pwrseq-simple"))
1228 		return;
1229 
1230 	pinctrl_byname(node, "default");
1231 
1232 	clock_enable(node, "ext_clock");
1233 
1234 	len = OF_getproplen(node, "reset-gpios");
1235 	if (len <= 0)
1236 		return;
1237 
1238 	gpios = malloc(len, M_TEMP, M_WAITOK);
1239 	OF_getpropintarray(node, "reset-gpios", gpios, len);
1240 
1241 	gpio = gpios;
1242 	while (gpio && gpio < gpios + (len / sizeof(uint32_t))) {
1243 		gpio_controller_config_pin(gpio, GPIO_CONFIG_OUTPUT);
1244 		gpio_controller_set_pin(gpio, 1);
1245 		gpio = gpio_controller_next_pin(gpio);
1246 	}
1247 
1248 	free(gpios, M_TEMP, len);
1249 }
1250 
1251 void
dwmmc_pwrseq_post(uint32_t phandle)1252 dwmmc_pwrseq_post(uint32_t phandle)
1253 {
1254 	uint32_t *gpios, *gpio;
1255 	int node;
1256 	int len;
1257 
1258 	node = OF_getnodebyphandle(phandle);
1259 	if (node == 0)
1260 		return;
1261 
1262 	if (!OF_is_compatible(node, "mmc-pwrseq-simple"))
1263 		return;
1264 
1265 	len = OF_getproplen(node, "reset-gpios");
1266 	if (len <= 0)
1267 		return;
1268 
1269 	gpios = malloc(len, M_TEMP, M_WAITOK);
1270 	OF_getpropintarray(node, "reset-gpios", gpios, len);
1271 
1272 	gpio = gpios;
1273 	while (gpio && gpio < gpios + (len / sizeof(uint32_t))) {
1274 		gpio_controller_set_pin(gpio, 0);
1275 		gpio = gpio_controller_next_pin(gpio);
1276 	}
1277 
1278 	free(gpios, M_TEMP, len);
1279 }
1280