Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
freebsd
GitHub Repository: freebsd/freebsd-src
Path: blob/main/sys/arm/ti/ti_sdhci.c
39481 views
1
/*-
2
* SPDX-License-Identifier: BSD-2-Clause
3
*
4
* Copyright (c) 2013 Ian Lepore <[email protected]>
5
* Copyright (c) 2011 Ben Gray <[email protected]>.
6
* All rights reserved.
7
*
8
* Redistribution and use in source and binary forms, with or without
9
* modification, are permitted provided that the following conditions
10
* are met:
11
* 1. Redistributions of source code must retain the above copyright
12
* notice, this list of conditions and the following disclaimer.
13
* 2. Redistributions in binary form must reproduce the above copyright
14
* notice, this list of conditions and the following disclaimer in the
15
* documentation and/or other materials provided with the distribution.
16
*
17
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
18
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
21
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
22
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
23
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
24
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
26
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
27
* SUCH DAMAGE.
28
*
29
*/
30
31
#include <sys/param.h>
32
#include <sys/systm.h>
33
#include <sys/bus.h>
34
#include <sys/gpio.h>
35
#include <sys/kernel.h>
36
#include <sys/malloc.h>
37
#include <sys/module.h>
38
#include <sys/resource.h>
39
#include <sys/rman.h>
40
#include <sys/sysctl.h>
41
#include <sys/taskqueue.h>
42
#include <sys/lock.h>
43
#include <sys/mutex.h>
44
45
#include <arm/ti/ti_cpuid.h>
46
#include <arm/ti/ti_sysc.h>
47
#include "gpio_if.h"
48
49
#include <dev/clk/clk.h>
50
#include <dev/ofw/ofw_bus.h>
51
#include <dev/ofw/ofw_bus_subr.h>
52
53
#include <dev/mmc/bridge.h>
54
#include <dev/mmc/mmcreg.h>
55
#include <dev/mmc/mmcbrvar.h>
56
57
#include <dev/sdhci/sdhci.h>
58
#include <dev/sdhci/sdhci_fdt_gpio.h>
59
#include "sdhci_if.h"
60
61
#include <machine/bus.h>
62
#include <machine/resource.h>
63
#include <machine/intr.h>
64
65
#include "opt_mmccam.h"
66
67
struct ti_sdhci_softc {
68
device_t dev;
69
struct sdhci_fdt_gpio * gpio;
70
struct resource * mem_res;
71
struct resource * irq_res;
72
void * intr_cookie;
73
struct sdhci_slot slot;
74
uint32_t mmchs_reg_off;
75
uint32_t sdhci_reg_off;
76
uint64_t baseclk_hz;
77
uint32_t cmd_and_mode;
78
uint32_t sdhci_clkdiv;
79
boolean_t disable_highspeed;
80
boolean_t force_card_present;
81
boolean_t disable_readonly;
82
};
83
84
/*
85
* Table of supported FDT compat strings.
86
*
87
* Note that "ti,mmchs" is our own invention, and should be phased out in favor
88
* of the documented names.
89
*
90
* Note that vendor Beaglebone dtsi files use "ti,omap3-hsmmc" for the am335x.
91
*/
92
static struct ofw_compat_data compat_data[] = {
93
{"ti,am335-sdhci", 1},
94
{"ti,omap3-hsmmc", 1},
95
{"ti,omap4-hsmmc", 1},
96
{"ti,mmchs", 1},
97
{NULL, 0},
98
};
99
100
/*
101
* The MMCHS hardware has a few control and status registers at the beginning of
102
* the device's memory map, followed by the standard sdhci register block.
103
* Different SoCs have the register blocks at different offsets from the
104
* beginning of the device. Define some constants to map out the registers we
105
* access, and the various per-SoC offsets. The SDHCI_REG_OFFSET is how far
106
* beyond the MMCHS block the SDHCI block is found; it's the same on all SoCs.
107
*/
108
#define AM335X_MMCHS_REG_OFFSET 0x100
109
#define SDHCI_REG_OFFSET 0x100
110
111
#define MMCHS_SYSCONFIG 0x010
112
#define MMCHS_SYSCONFIG_RESET (1 << 1)
113
#define MMCHS_SYSSTATUS 0x014
114
#define MMCHS_SYSSTATUS_RESETDONE (1 << 0)
115
#define MMCHS_CON 0x02C
116
#define MMCHS_CON_DW8 (1 << 5)
117
#define MMCHS_CON_DVAL_8_4MS (3 << 9)
118
#define MMCHS_CON_OD (1 << 0)
119
#define MMCHS_SYSCTL 0x12C
120
#define MMCHS_SYSCTL_CLKD_MASK 0x3FF
121
#define MMCHS_SYSCTL_CLKD_SHIFT 6
122
#define MMCHS_SD_CAPA 0x140
123
#define MMCHS_SD_CAPA_VS18 (1 << 26)
124
#define MMCHS_SD_CAPA_VS30 (1 << 25)
125
#define MMCHS_SD_CAPA_VS33 (1 << 24)
126
127
/* Forward declarations, CAM-relataed */
128
// static void ti_sdhci_cam_poll(struct cam_sim *);
129
// static void ti_sdhci_cam_action(struct cam_sim *, union ccb *);
130
// static int ti_sdhci_cam_settran_settings(struct ti_sdhci_softc *sc, union ccb *);
131
132
static inline uint32_t
133
ti_mmchs_read_4(struct ti_sdhci_softc *sc, bus_size_t off)
134
{
135
136
return (bus_read_4(sc->mem_res, off + sc->mmchs_reg_off));
137
}
138
139
static inline void
140
ti_mmchs_write_4(struct ti_sdhci_softc *sc, bus_size_t off, uint32_t val)
141
{
142
143
bus_write_4(sc->mem_res, off + sc->mmchs_reg_off, val);
144
}
145
146
static inline uint32_t
147
RD4(struct ti_sdhci_softc *sc, bus_size_t off)
148
{
149
150
return (bus_read_4(sc->mem_res, off + sc->sdhci_reg_off));
151
}
152
153
static inline void
154
WR4(struct ti_sdhci_softc *sc, bus_size_t off, uint32_t val)
155
{
156
157
bus_write_4(sc->mem_res, off + sc->sdhci_reg_off, val);
158
}
159
160
static uint8_t
161
ti_sdhci_read_1(device_t dev, struct sdhci_slot *slot, bus_size_t off)
162
{
163
struct ti_sdhci_softc *sc = device_get_softc(dev);
164
165
return ((RD4(sc, off & ~3) >> (off & 3) * 8) & 0xff);
166
}
167
168
static uint16_t
169
ti_sdhci_read_2(device_t dev, struct sdhci_slot *slot, bus_size_t off)
170
{
171
struct ti_sdhci_softc *sc = device_get_softc(dev);
172
uint32_t clkdiv, val32;
173
174
/*
175
* The MMCHS hardware has a non-standard interpretation of the sdclock
176
* divisor bits. It uses the same bit positions as SDHCI 3.0 (15..6)
177
* but doesn't split them into low:high fields. Instead they're a
178
* single number in the range 0..1023 and the number is exactly the
179
* clock divisor (with 0 and 1 both meaning divide by 1). The SDHCI
180
* driver code expects a v2.0 or v3.0 divisor. The shifting and masking
181
* here extracts the MMCHS representation from the hardware word, cleans
182
* those bits out, applies the 2N adjustment, and plugs the result into
183
* the bit positions for the 2.0 or 3.0 divisor in the returned register
184
* value. The ti_sdhci_write_2() routine performs the opposite
185
* transformation when the SDHCI driver writes to the register.
186
*/
187
if (off == SDHCI_CLOCK_CONTROL) {
188
val32 = RD4(sc, SDHCI_CLOCK_CONTROL);
189
clkdiv = ((val32 >> MMCHS_SYSCTL_CLKD_SHIFT) &
190
MMCHS_SYSCTL_CLKD_MASK) / 2;
191
val32 &= ~(MMCHS_SYSCTL_CLKD_MASK << MMCHS_SYSCTL_CLKD_SHIFT);
192
val32 |= (clkdiv & SDHCI_DIVIDER_MASK) << SDHCI_DIVIDER_SHIFT;
193
if (slot->version >= SDHCI_SPEC_300)
194
val32 |= ((clkdiv >> SDHCI_DIVIDER_MASK_LEN) &
195
SDHCI_DIVIDER_HI_MASK) << SDHCI_DIVIDER_HI_SHIFT;
196
return (val32 & 0xffff);
197
}
198
199
/*
200
* Standard 32-bit handling of command and transfer mode.
201
*/
202
if (off == SDHCI_TRANSFER_MODE) {
203
return (sc->cmd_and_mode >> 16);
204
} else if (off == SDHCI_COMMAND_FLAGS) {
205
return (sc->cmd_and_mode & 0x0000ffff);
206
}
207
208
return ((RD4(sc, off & ~3) >> (off & 3) * 8) & 0xffff);
209
}
210
211
static uint32_t
212
ti_sdhci_read_4(device_t dev, struct sdhci_slot *slot, bus_size_t off)
213
{
214
struct ti_sdhci_softc *sc = device_get_softc(dev);
215
uint32_t val32;
216
217
val32 = RD4(sc, off);
218
219
/*
220
* If we need to disallow highspeed mode due to the OMAP4 erratum, strip
221
* that flag from the returned capabilities.
222
*/
223
if (off == SDHCI_CAPABILITIES && sc->disable_highspeed)
224
val32 &= ~SDHCI_CAN_DO_HISPD;
225
226
/*
227
* Force the card-present state if necessary.
228
*/
229
if (off == SDHCI_PRESENT_STATE && sc->force_card_present)
230
val32 |= SDHCI_CARD_PRESENT;
231
232
return (val32);
233
}
234
235
static void
236
ti_sdhci_read_multi_4(device_t dev, struct sdhci_slot *slot, bus_size_t off,
237
uint32_t *data, bus_size_t count)
238
{
239
struct ti_sdhci_softc *sc = device_get_softc(dev);
240
241
bus_read_multi_4(sc->mem_res, off + sc->sdhci_reg_off, data, count);
242
}
243
244
static void
245
ti_sdhci_write_1(device_t dev, struct sdhci_slot *slot, bus_size_t off,
246
uint8_t val)
247
{
248
struct ti_sdhci_softc *sc = device_get_softc(dev);
249
uint32_t val32;
250
251
#ifdef MMCCAM
252
uint32_t newval32;
253
if (off == SDHCI_HOST_CONTROL) {
254
val32 = ti_mmchs_read_4(sc, MMCHS_CON);
255
newval32 = val32;
256
if (val & SDHCI_CTRL_8BITBUS) {
257
device_printf(dev, "Custom-enabling 8-bit bus\n");
258
newval32 |= MMCHS_CON_DW8;
259
} else {
260
device_printf(dev, "Custom-disabling 8-bit bus\n");
261
newval32 &= ~MMCHS_CON_DW8;
262
}
263
if (newval32 != val32)
264
ti_mmchs_write_4(sc, MMCHS_CON, newval32);
265
}
266
#endif
267
val32 = RD4(sc, off & ~3);
268
val32 &= ~(0xff << (off & 3) * 8);
269
val32 |= (val << (off & 3) * 8);
270
271
WR4(sc, off & ~3, val32);
272
}
273
274
static void
275
ti_sdhci_write_2(device_t dev, struct sdhci_slot *slot, bus_size_t off,
276
uint16_t val)
277
{
278
struct ti_sdhci_softc *sc = device_get_softc(dev);
279
uint32_t clkdiv, val32;
280
281
/*
282
* Translate between the hardware and SDHCI 2.0 or 3.0 representations
283
* of the clock divisor. See the comments in ti_sdhci_read_2() for
284
* details.
285
*/
286
if (off == SDHCI_CLOCK_CONTROL) {
287
clkdiv = (val >> SDHCI_DIVIDER_SHIFT) & SDHCI_DIVIDER_MASK;
288
if (slot->version >= SDHCI_SPEC_300)
289
clkdiv |= ((val >> SDHCI_DIVIDER_HI_SHIFT) &
290
SDHCI_DIVIDER_HI_MASK) << SDHCI_DIVIDER_MASK_LEN;
291
clkdiv *= 2;
292
if (clkdiv > MMCHS_SYSCTL_CLKD_MASK)
293
clkdiv = MMCHS_SYSCTL_CLKD_MASK;
294
val32 = RD4(sc, SDHCI_CLOCK_CONTROL);
295
val32 &= 0xffff0000;
296
val32 |= val & ~(MMCHS_SYSCTL_CLKD_MASK <<
297
MMCHS_SYSCTL_CLKD_SHIFT);
298
val32 |= clkdiv << MMCHS_SYSCTL_CLKD_SHIFT;
299
WR4(sc, SDHCI_CLOCK_CONTROL, val32);
300
return;
301
}
302
303
/*
304
* Standard 32-bit handling of command and transfer mode.
305
*/
306
if (off == SDHCI_TRANSFER_MODE) {
307
sc->cmd_and_mode = (sc->cmd_and_mode & 0xffff0000) |
308
((uint32_t)val & 0x0000ffff);
309
return;
310
} else if (off == SDHCI_COMMAND_FLAGS) {
311
sc->cmd_and_mode = (sc->cmd_and_mode & 0x0000ffff) |
312
((uint32_t)val << 16);
313
WR4(sc, SDHCI_TRANSFER_MODE, sc->cmd_and_mode);
314
return;
315
}
316
317
val32 = RD4(sc, off & ~3);
318
val32 &= ~(0xffff << (off & 3) * 8);
319
val32 |= ((val & 0xffff) << (off & 3) * 8);
320
WR4(sc, off & ~3, val32);
321
}
322
323
static void
324
ti_sdhci_write_4(device_t dev, struct sdhci_slot *slot, bus_size_t off,
325
uint32_t val)
326
{
327
struct ti_sdhci_softc *sc = device_get_softc(dev);
328
329
WR4(sc, off, val);
330
}
331
332
static void
333
ti_sdhci_write_multi_4(device_t dev, struct sdhci_slot *slot, bus_size_t off,
334
uint32_t *data, bus_size_t count)
335
{
336
struct ti_sdhci_softc *sc = device_get_softc(dev);
337
338
bus_write_multi_4(sc->mem_res, off + sc->sdhci_reg_off, data, count);
339
}
340
341
static void
342
ti_sdhci_intr(void *arg)
343
{
344
struct ti_sdhci_softc *sc = arg;
345
346
sdhci_generic_intr(&sc->slot);
347
}
348
349
static int
350
ti_sdhci_update_ios(device_t brdev, device_t reqdev)
351
{
352
struct ti_sdhci_softc *sc = device_get_softc(brdev);
353
struct sdhci_slot *slot;
354
struct mmc_ios *ios;
355
uint32_t val32, newval32;
356
357
slot = device_get_ivars(reqdev);
358
ios = &slot->host.ios;
359
360
/*
361
* There is an 8-bit-bus bit in the MMCHS control register which, when
362
* set, overrides the 1 vs 4 bit setting in the standard SDHCI
363
* registers. Set that bit first according to whether an 8-bit bus is
364
* requested, then let the standard driver handle everything else.
365
*/
366
val32 = ti_mmchs_read_4(sc, MMCHS_CON);
367
newval32 = val32;
368
369
if (ios->bus_width == bus_width_8)
370
newval32 |= MMCHS_CON_DW8;
371
else
372
newval32 &= ~MMCHS_CON_DW8;
373
374
if (ios->bus_mode == opendrain)
375
newval32 |= MMCHS_CON_OD;
376
else /* if (ios->bus_mode == pushpull) */
377
newval32 &= ~MMCHS_CON_OD;
378
379
if (newval32 != val32)
380
ti_mmchs_write_4(sc, MMCHS_CON, newval32);
381
382
return (sdhci_generic_update_ios(brdev, reqdev));
383
}
384
385
static int
386
ti_sdhci_get_ro(device_t brdev, device_t reqdev)
387
{
388
struct ti_sdhci_softc *sc = device_get_softc(brdev);
389
390
if (sc->disable_readonly)
391
return (0);
392
393
return (sdhci_fdt_gpio_get_readonly(sc->gpio));
394
}
395
396
static bool
397
ti_sdhci_get_card_present(device_t dev, struct sdhci_slot *slot)
398
{
399
struct ti_sdhci_softc *sc = device_get_softc(dev);
400
401
return (sdhci_fdt_gpio_get_present(sc->gpio));
402
}
403
404
static int
405
ti_sdhci_detach(device_t dev)
406
{
407
408
/* sdhci_fdt_gpio_teardown(sc->gpio); */
409
410
return (EBUSY);
411
}
412
413
static int
414
ti_sdhci_hw_init(device_t dev)
415
{
416
struct ti_sdhci_softc *sc = device_get_softc(dev);
417
uint32_t regval;
418
unsigned long timeout;
419
clk_t mmc_clk;
420
int err;
421
422
/* Enable the controller and interface/functional clocks */
423
if (ti_sysc_clock_enable(device_get_parent(dev)) != 0) {
424
device_printf(dev, "Error: failed to enable MMC clock\n");
425
return (ENXIO);
426
}
427
428
/* FIXME: Devicetree dosent have any reference to mmc_clk */
429
err = clk_get_by_name(dev, "mmc_clk", &mmc_clk);
430
if (err) {
431
device_printf(dev, "Can not find mmc_clk\n");
432
return (ENXIO);
433
}
434
err = clk_get_freq(mmc_clk, &sc->baseclk_hz);
435
if (err) {
436
device_printf(dev, "Cant get mmc_clk frequency\n");
437
/* AM335x TRM 8.1.6.8 table 8-24 96MHz @ OPP100 */
438
sc->baseclk_hz = 96000000;
439
}
440
441
/* Issue a softreset to the controller */
442
ti_mmchs_write_4(sc, MMCHS_SYSCONFIG, MMCHS_SYSCONFIG_RESET);
443
timeout = 1000;
444
while (!(ti_mmchs_read_4(sc, MMCHS_SYSSTATUS) &
445
MMCHS_SYSSTATUS_RESETDONE)) {
446
if (--timeout == 0) {
447
device_printf(dev,
448
"Error: Controller reset operation timed out\n");
449
break;
450
}
451
DELAY(100);
452
}
453
454
/*
455
* Reset the command and data state machines and also other aspects of
456
* the controller such as bus clock and power.
457
*
458
* If we read the software reset register too fast after writing it we
459
* can get back a zero that means the reset hasn't started yet rather
460
* than that the reset is complete. Per TI recommendations, work around
461
* it by reading until we see the reset bit asserted, then read until
462
* it's clear. We also set the SDHCI_QUIRK_WAITFOR_RESET_ASSERTED quirk
463
* so that the main sdhci driver uses this same logic in its resets.
464
*/
465
ti_sdhci_write_1(dev, NULL, SDHCI_SOFTWARE_RESET, SDHCI_RESET_ALL);
466
timeout = 10000;
467
while ((ti_sdhci_read_1(dev, NULL, SDHCI_SOFTWARE_RESET) &
468
SDHCI_RESET_ALL) != SDHCI_RESET_ALL) {
469
if (--timeout == 0) {
470
break;
471
}
472
DELAY(1);
473
}
474
timeout = 10000;
475
while ((ti_sdhci_read_1(dev, NULL, SDHCI_SOFTWARE_RESET) &
476
SDHCI_RESET_ALL)) {
477
if (--timeout == 0) {
478
device_printf(dev,
479
"Error: Software reset operation timed out\n");
480
break;
481
}
482
DELAY(100);
483
}
484
485
/*
486
* The attach() routine has examined fdt data and set flags in
487
* slot.host.caps to reflect what voltages we can handle. Set those
488
* values in the CAPA register. Empirical testing shows that the
489
* values in this register can be overwritten at any time, but the
490
* manual says that these values should only be set once, "before
491
* initialization" whatever that means, and that they survive a reset.
492
*/
493
regval = ti_mmchs_read_4(sc, MMCHS_SD_CAPA);
494
if (sc->slot.host.caps & MMC_OCR_LOW_VOLTAGE)
495
regval |= MMCHS_SD_CAPA_VS18;
496
if (sc->slot.host.caps & (MMC_OCR_290_300 | MMC_OCR_300_310))
497
regval |= MMCHS_SD_CAPA_VS30;
498
ti_mmchs_write_4(sc, MMCHS_SD_CAPA, regval);
499
500
/* Set initial host configuration (1-bit, std speed, pwr off). */
501
ti_sdhci_write_1(dev, NULL, SDHCI_HOST_CONTROL, 0);
502
ti_sdhci_write_1(dev, NULL, SDHCI_POWER_CONTROL, 0);
503
504
/* Set the initial controller configuration. */
505
ti_mmchs_write_4(sc, MMCHS_CON, MMCHS_CON_DVAL_8_4MS);
506
507
return (0);
508
}
509
510
static int
511
ti_sdhci_attach(device_t dev)
512
{
513
struct ti_sdhci_softc *sc = device_get_softc(dev);
514
int rid, err;
515
pcell_t prop;
516
phandle_t node;
517
518
sc->dev = dev;
519
520
/*
521
* Get the MMCHS device id from FDT. Use rev address to identify the unit.
522
*/
523
node = ofw_bus_get_node(dev);
524
525
/*
526
* The hardware can inherently do dual-voltage (1p8v, 3p0v) on the first
527
* device, and only 1p8v on other devices unless an external transceiver
528
* is used. The only way we could know about a transceiver is fdt data.
529
* Note that we have to do this before calling ti_sdhci_hw_init() so
530
* that it can set the right values in the CAPA register.
531
*/
532
sc->slot.host.caps |= MMC_OCR_LOW_VOLTAGE;
533
534
if (OF_hasprop(node, "ti,dual-volt")) {
535
sc->slot.host.caps |= MMC_OCR_290_300 | MMC_OCR_300_310;
536
}
537
538
/*
539
* Set the offset from the device's memory start to the MMCHS registers.
540
* Also for OMAP4 disable high speed mode due to erratum ID i626.
541
*/
542
switch (ti_chip()) {
543
#ifdef SOC_TI_AM335X
544
case CHIP_AM335X:
545
sc->mmchs_reg_off = AM335X_MMCHS_REG_OFFSET;
546
break;
547
#endif
548
default:
549
panic("Unknown OMAP device\n");
550
}
551
552
/*
553
* The standard SDHCI registers are at a fixed offset (the same on all
554
* SoCs) beyond the MMCHS registers.
555
*/
556
sc->sdhci_reg_off = sc->mmchs_reg_off + SDHCI_REG_OFFSET;
557
558
/* Resource setup. */
559
rid = 0;
560
sc->mem_res = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &rid,
561
RF_ACTIVE);
562
if (!sc->mem_res) {
563
device_printf(dev, "cannot allocate memory window\n");
564
err = ENXIO;
565
goto fail;
566
}
567
568
rid = 0;
569
sc->irq_res = bus_alloc_resource_any(dev, SYS_RES_IRQ, &rid,
570
RF_ACTIVE);
571
if (!sc->irq_res) {
572
device_printf(dev, "cannot allocate interrupt\n");
573
err = ENXIO;
574
goto fail;
575
}
576
577
if (bus_setup_intr(dev, sc->irq_res, INTR_TYPE_BIO | INTR_MPSAFE,
578
NULL, ti_sdhci_intr, sc, &sc->intr_cookie)) {
579
device_printf(dev, "cannot setup interrupt handler\n");
580
err = ENXIO;
581
goto fail;
582
}
583
584
/*
585
* Set up handling of card-detect and write-protect gpio lines.
586
*
587
* If there is no write protect info in the fdt data, fall back to the
588
* historical practice of assuming that the card is writable. This
589
* works around bad fdt data from the upstream source. The alternative
590
* would be to trust the sdhci controller's PRESENT_STATE register WP
591
* bit, but it may say write protect is in effect when it's not if the
592
* pinmux setup doesn't route the WP signal into the sdchi block.
593
*/
594
sc->gpio = sdhci_fdt_gpio_setup(sc->dev, &sc->slot);
595
596
if (!OF_hasprop(node, "wp-gpios") && !OF_hasprop(node, "wp-disable"))
597
sc->disable_readonly = true;
598
599
/* Initialise the MMCHS hardware. */
600
err = ti_sdhci_hw_init(dev);
601
if (err != 0) {
602
/* err should already contain ENXIO from ti_sdhci_hw_init() */
603
goto fail;
604
}
605
606
/*
607
* The capabilities register can only express base clock frequencies in
608
* the range of 0-63MHz for a v2.0 controller. Since our clock runs
609
* faster than that, the hardware sets the frequency to zero in the
610
* register. When the register contains zero, the sdhci driver expects
611
* slot.max_clk to already have the right value in it.
612
*/
613
sc->slot.max_clk = sc->baseclk_hz;
614
615
/*
616
* The MMCHS timeout counter is based on the output sdclock. Tell the
617
* sdhci driver to recalculate the timeout clock whenever the output
618
* sdclock frequency changes.
619
*/
620
sc->slot.quirks |= SDHCI_QUIRK_DATA_TIMEOUT_USES_SDCLK;
621
622
/*
623
* The MMCHS hardware shifts the 136-bit response data (in violation of
624
* the spec), so tell the sdhci driver not to do the same in software.
625
*/
626
sc->slot.quirks |= SDHCI_QUIRK_DONT_SHIFT_RESPONSE;
627
628
/*
629
* Reset bits are broken, have to wait to see the bits asserted
630
* before waiting to see them de-asserted.
631
*/
632
sc->slot.quirks |= SDHCI_QUIRK_WAITFOR_RESET_ASSERTED;
633
634
/*
635
* The controller waits for busy responses.
636
*/
637
sc->slot.quirks |= SDHCI_QUIRK_WAIT_WHILE_BUSY;
638
639
/*
640
* DMA is not really broken, I just haven't implemented it yet.
641
*/
642
sc->slot.quirks |= SDHCI_QUIRK_BROKEN_DMA;
643
644
/*
645
* Set up the hardware and go. Note that this sets many of the
646
* slot.host.* fields, so we have to do this before overriding any of
647
* those values based on fdt data, below.
648
*/
649
sdhci_init_slot(dev, &sc->slot, 0);
650
651
/*
652
* The SDHCI controller doesn't realize it, but we can support 8-bit
653
* even though we're not a v3.0 controller. If there's an fdt bus-width
654
* property, honor it.
655
*/
656
if (OF_getencprop(node, "bus-width", &prop, sizeof(prop)) > 0) {
657
sc->slot.host.caps &= ~(MMC_CAP_4_BIT_DATA |
658
MMC_CAP_8_BIT_DATA);
659
switch (prop) {
660
case 8:
661
sc->slot.host.caps |= MMC_CAP_8_BIT_DATA;
662
/* FALLTHROUGH */
663
case 4:
664
sc->slot.host.caps |= MMC_CAP_4_BIT_DATA;
665
break;
666
case 1:
667
break;
668
default:
669
device_printf(dev, "Bad bus-width value %u\n", prop);
670
break;
671
}
672
}
673
674
/*
675
* If the slot is flagged with the non-removable property, set our flag
676
* to always force the SDHCI_CARD_PRESENT bit on.
677
*/
678
node = ofw_bus_get_node(dev);
679
if (OF_hasprop(node, "non-removable"))
680
sc->force_card_present = true;
681
682
bus_identify_children(dev);
683
bus_attach_children(dev);
684
685
sdhci_start_slot(&sc->slot);
686
return (0);
687
688
fail:
689
if (sc->intr_cookie)
690
bus_teardown_intr(dev, sc->irq_res, sc->intr_cookie);
691
if (sc->irq_res)
692
bus_release_resource(dev, SYS_RES_IRQ, 0, sc->irq_res);
693
if (sc->mem_res)
694
bus_release_resource(dev, SYS_RES_MEMORY, 0, sc->mem_res);
695
696
return (err);
697
}
698
699
static int
700
ti_sdhci_probe(device_t dev)
701
{
702
703
if (!ofw_bus_status_okay(dev))
704
return (ENXIO);
705
706
if (ofw_bus_search_compatible(dev, compat_data)->ocd_data != 0) {
707
device_set_desc(dev, "TI MMCHS (SDHCI 2.0)");
708
return (BUS_PROBE_DEFAULT);
709
}
710
711
return (ENXIO);
712
}
713
714
static device_method_t ti_sdhci_methods[] = {
715
/* Device interface */
716
DEVMETHOD(device_probe, ti_sdhci_probe),
717
DEVMETHOD(device_attach, ti_sdhci_attach),
718
DEVMETHOD(device_detach, ti_sdhci_detach),
719
720
/* Bus interface */
721
DEVMETHOD(bus_read_ivar, sdhci_generic_read_ivar),
722
DEVMETHOD(bus_write_ivar, sdhci_generic_write_ivar),
723
724
/* MMC bridge interface */
725
DEVMETHOD(mmcbr_update_ios, ti_sdhci_update_ios),
726
DEVMETHOD(mmcbr_request, sdhci_generic_request),
727
DEVMETHOD(mmcbr_get_ro, ti_sdhci_get_ro),
728
DEVMETHOD(mmcbr_acquire_host, sdhci_generic_acquire_host),
729
DEVMETHOD(mmcbr_release_host, sdhci_generic_release_host),
730
731
/* SDHCI registers accessors */
732
DEVMETHOD(sdhci_read_1, ti_sdhci_read_1),
733
DEVMETHOD(sdhci_read_2, ti_sdhci_read_2),
734
DEVMETHOD(sdhci_read_4, ti_sdhci_read_4),
735
DEVMETHOD(sdhci_read_multi_4, ti_sdhci_read_multi_4),
736
DEVMETHOD(sdhci_write_1, ti_sdhci_write_1),
737
DEVMETHOD(sdhci_write_2, ti_sdhci_write_2),
738
DEVMETHOD(sdhci_write_4, ti_sdhci_write_4),
739
DEVMETHOD(sdhci_write_multi_4, ti_sdhci_write_multi_4),
740
DEVMETHOD(sdhci_get_card_present, ti_sdhci_get_card_present),
741
742
DEVMETHOD_END
743
};
744
745
static driver_t ti_sdhci_driver = {
746
"sdhci_ti",
747
ti_sdhci_methods,
748
sizeof(struct ti_sdhci_softc),
749
};
750
751
DRIVER_MODULE(sdhci_ti, simplebus, ti_sdhci_driver, NULL, NULL);
752
MODULE_DEPEND(sdhci_ti, ti_sysc, 1, 1, 1);
753
SDHCI_DEPEND(sdhci_ti);
754
755
#ifndef MMCCAM
756
MMC_DECLARE_BRIDGE(sdhci_ti);
757
#endif
758
759