arm64: dts: qcom: sm8550: add TRNG node
[linux-modified.git] / drivers / mmc / host / sdhci-cadence.c
1 // SPDX-License-Identifier: GPL-2.0-or-later
2 /*
3  * Copyright (C) 2016 Socionext Inc.
4  *   Author: Masahiro Yamada <yamada.masahiro@socionext.com>
5  */
6
7 #include <linux/bitfield.h>
8 #include <linux/bits.h>
9 #include <linux/iopoll.h>
10 #include <linux/module.h>
11 #include <linux/mmc/host.h>
12 #include <linux/mmc/mmc.h>
13 #include <linux/of.h>
14 #include <linux/platform_device.h>
15 #include <linux/reset.h>
16
17 #include "sdhci-pltfm.h"
18
19 /* HRS - Host Register Set (specific to Cadence) */
20 #define SDHCI_CDNS_HRS04                0x10            /* PHY access port */
21 #define   SDHCI_CDNS_HRS04_ACK                  BIT(26)
22 #define   SDHCI_CDNS_HRS04_RD                   BIT(25)
23 #define   SDHCI_CDNS_HRS04_WR                   BIT(24)
24 #define   SDHCI_CDNS_HRS04_RDATA                GENMASK(23, 16)
25 #define   SDHCI_CDNS_HRS04_WDATA                GENMASK(15, 8)
26 #define   SDHCI_CDNS_HRS04_ADDR                 GENMASK(5, 0)
27
28 #define SDHCI_CDNS_HRS06                0x18            /* eMMC control */
29 #define   SDHCI_CDNS_HRS06_TUNE_UP              BIT(15)
30 #define   SDHCI_CDNS_HRS06_TUNE                 GENMASK(13, 8)
31 #define   SDHCI_CDNS_HRS06_MODE                 GENMASK(2, 0)
32 #define   SDHCI_CDNS_HRS06_MODE_SD              0x0
33 #define   SDHCI_CDNS_HRS06_MODE_MMC_SDR         0x2
34 #define   SDHCI_CDNS_HRS06_MODE_MMC_DDR         0x3
35 #define   SDHCI_CDNS_HRS06_MODE_MMC_HS200       0x4
36 #define   SDHCI_CDNS_HRS06_MODE_MMC_HS400       0x5
37 #define   SDHCI_CDNS_HRS06_MODE_MMC_HS400ES     0x6
38
39 /* SRS - Slot Register Set (SDHCI-compatible) */
40 #define SDHCI_CDNS_SRS_BASE             0x200
41
42 /* PHY */
43 #define SDHCI_CDNS_PHY_DLY_SD_HS        0x00
44 #define SDHCI_CDNS_PHY_DLY_SD_DEFAULT   0x01
45 #define SDHCI_CDNS_PHY_DLY_UHS_SDR12    0x02
46 #define SDHCI_CDNS_PHY_DLY_UHS_SDR25    0x03
47 #define SDHCI_CDNS_PHY_DLY_UHS_SDR50    0x04
48 #define SDHCI_CDNS_PHY_DLY_UHS_DDR50    0x05
49 #define SDHCI_CDNS_PHY_DLY_EMMC_LEGACY  0x06
50 #define SDHCI_CDNS_PHY_DLY_EMMC_SDR     0x07
51 #define SDHCI_CDNS_PHY_DLY_EMMC_DDR     0x08
52 #define SDHCI_CDNS_PHY_DLY_SDCLK        0x0b
53 #define SDHCI_CDNS_PHY_DLY_HSMMC        0x0c
54 #define SDHCI_CDNS_PHY_DLY_STROBE       0x0d
55
56 /*
57  * The tuned val register is 6 bit-wide, but not the whole of the range is
58  * available.  The range 0-42 seems to be available (then 43 wraps around to 0)
59  * but I am not quite sure if it is official.  Use only 0 to 39 for safety.
60  */
61 #define SDHCI_CDNS_MAX_TUNING_LOOP      40
62
63 struct sdhci_cdns_phy_param {
64         u8 addr;
65         u8 data;
66 };
67
68 struct sdhci_cdns_priv {
69         void __iomem *hrs_addr;
70         void __iomem *ctl_addr; /* write control */
71         spinlock_t wrlock;      /* write lock */
72         bool enhanced_strobe;
73         void (*priv_writel)(struct sdhci_cdns_priv *priv, u32 val, void __iomem *reg);
74         struct reset_control *rst_hw;
75         unsigned int nr_phy_params;
76         struct sdhci_cdns_phy_param phy_params[];
77 };
78
79 struct sdhci_cdns_phy_cfg {
80         const char *property;
81         u8 addr;
82 };
83
84 struct sdhci_cdns_drv_data {
85         int (*init)(struct platform_device *pdev);
86         const struct sdhci_pltfm_data pltfm_data;
87 };
88
89 static const struct sdhci_cdns_phy_cfg sdhci_cdns_phy_cfgs[] = {
90         { "cdns,phy-input-delay-sd-highspeed", SDHCI_CDNS_PHY_DLY_SD_HS, },
91         { "cdns,phy-input-delay-legacy", SDHCI_CDNS_PHY_DLY_SD_DEFAULT, },
92         { "cdns,phy-input-delay-sd-uhs-sdr12", SDHCI_CDNS_PHY_DLY_UHS_SDR12, },
93         { "cdns,phy-input-delay-sd-uhs-sdr25", SDHCI_CDNS_PHY_DLY_UHS_SDR25, },
94         { "cdns,phy-input-delay-sd-uhs-sdr50", SDHCI_CDNS_PHY_DLY_UHS_SDR50, },
95         { "cdns,phy-input-delay-sd-uhs-ddr50", SDHCI_CDNS_PHY_DLY_UHS_DDR50, },
96         { "cdns,phy-input-delay-mmc-highspeed", SDHCI_CDNS_PHY_DLY_EMMC_SDR, },
97         { "cdns,phy-input-delay-mmc-ddr", SDHCI_CDNS_PHY_DLY_EMMC_DDR, },
98         { "cdns,phy-dll-delay-sdclk", SDHCI_CDNS_PHY_DLY_SDCLK, },
99         { "cdns,phy-dll-delay-sdclk-hsmmc", SDHCI_CDNS_PHY_DLY_HSMMC, },
100         { "cdns,phy-dll-delay-strobe", SDHCI_CDNS_PHY_DLY_STROBE, },
101 };
102
103 static inline void cdns_writel(struct sdhci_cdns_priv *priv, u32 val,
104                                void __iomem *reg)
105 {
106         writel(val, reg);
107 }
108
109 static int sdhci_cdns_write_phy_reg(struct sdhci_cdns_priv *priv,
110                                     u8 addr, u8 data)
111 {
112         void __iomem *reg = priv->hrs_addr + SDHCI_CDNS_HRS04;
113         u32 tmp;
114         int ret;
115
116         ret = readl_poll_timeout(reg, tmp, !(tmp & SDHCI_CDNS_HRS04_ACK),
117                                  0, 10);
118         if (ret)
119                 return ret;
120
121         tmp = FIELD_PREP(SDHCI_CDNS_HRS04_WDATA, data) |
122               FIELD_PREP(SDHCI_CDNS_HRS04_ADDR, addr);
123         priv->priv_writel(priv, tmp, reg);
124
125         tmp |= SDHCI_CDNS_HRS04_WR;
126         priv->priv_writel(priv, tmp, reg);
127
128         ret = readl_poll_timeout(reg, tmp, tmp & SDHCI_CDNS_HRS04_ACK, 0, 10);
129         if (ret)
130                 return ret;
131
132         tmp &= ~SDHCI_CDNS_HRS04_WR;
133         priv->priv_writel(priv, tmp, reg);
134
135         ret = readl_poll_timeout(reg, tmp, !(tmp & SDHCI_CDNS_HRS04_ACK),
136                                  0, 10);
137
138         return ret;
139 }
140
141 static unsigned int sdhci_cdns_phy_param_count(struct device_node *np)
142 {
143         unsigned int count = 0;
144         int i;
145
146         for (i = 0; i < ARRAY_SIZE(sdhci_cdns_phy_cfgs); i++)
147                 if (of_property_read_bool(np, sdhci_cdns_phy_cfgs[i].property))
148                         count++;
149
150         return count;
151 }
152
153 static void sdhci_cdns_phy_param_parse(struct device_node *np,
154                                        struct sdhci_cdns_priv *priv)
155 {
156         struct sdhci_cdns_phy_param *p = priv->phy_params;
157         u32 val;
158         int ret, i;
159
160         for (i = 0; i < ARRAY_SIZE(sdhci_cdns_phy_cfgs); i++) {
161                 ret = of_property_read_u32(np, sdhci_cdns_phy_cfgs[i].property,
162                                            &val);
163                 if (ret)
164                         continue;
165
166                 p->addr = sdhci_cdns_phy_cfgs[i].addr;
167                 p->data = val;
168                 p++;
169         }
170 }
171
172 static int sdhci_cdns_phy_init(struct sdhci_cdns_priv *priv)
173 {
174         int ret, i;
175
176         for (i = 0; i < priv->nr_phy_params; i++) {
177                 ret = sdhci_cdns_write_phy_reg(priv, priv->phy_params[i].addr,
178                                                priv->phy_params[i].data);
179                 if (ret)
180                         return ret;
181         }
182
183         return 0;
184 }
185
186 static void *sdhci_cdns_priv(struct sdhci_host *host)
187 {
188         struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
189
190         return sdhci_pltfm_priv(pltfm_host);
191 }
192
193 static unsigned int sdhci_cdns_get_timeout_clock(struct sdhci_host *host)
194 {
195         /*
196          * Cadence's spec says the Timeout Clock Frequency is the same as the
197          * Base Clock Frequency.
198          */
199         return host->max_clk;
200 }
201
202 static void sdhci_cdns_set_emmc_mode(struct sdhci_cdns_priv *priv, u32 mode)
203 {
204         u32 tmp;
205
206         /* The speed mode for eMMC is selected by HRS06 register */
207         tmp = readl(priv->hrs_addr + SDHCI_CDNS_HRS06);
208         tmp &= ~SDHCI_CDNS_HRS06_MODE;
209         tmp |= FIELD_PREP(SDHCI_CDNS_HRS06_MODE, mode);
210         priv->priv_writel(priv, tmp, priv->hrs_addr + SDHCI_CDNS_HRS06);
211 }
212
213 static u32 sdhci_cdns_get_emmc_mode(struct sdhci_cdns_priv *priv)
214 {
215         u32 tmp;
216
217         tmp = readl(priv->hrs_addr + SDHCI_CDNS_HRS06);
218         return FIELD_GET(SDHCI_CDNS_HRS06_MODE, tmp);
219 }
220
221 static int sdhci_cdns_set_tune_val(struct sdhci_host *host, unsigned int val)
222 {
223         struct sdhci_cdns_priv *priv = sdhci_cdns_priv(host);
224         void __iomem *reg = priv->hrs_addr + SDHCI_CDNS_HRS06;
225         u32 tmp;
226         int i, ret;
227
228         if (WARN_ON(!FIELD_FIT(SDHCI_CDNS_HRS06_TUNE, val)))
229                 return -EINVAL;
230
231         tmp = readl(reg);
232         tmp &= ~SDHCI_CDNS_HRS06_TUNE;
233         tmp |= FIELD_PREP(SDHCI_CDNS_HRS06_TUNE, val);
234
235         /*
236          * Workaround for IP errata:
237          * The IP6116 SD/eMMC PHY design has a timing issue on receive data
238          * path. Send tune request twice.
239          */
240         for (i = 0; i < 2; i++) {
241                 tmp |= SDHCI_CDNS_HRS06_TUNE_UP;
242                 priv->priv_writel(priv, tmp, reg);
243
244                 ret = readl_poll_timeout(reg, tmp,
245                                          !(tmp & SDHCI_CDNS_HRS06_TUNE_UP),
246                                          0, 1);
247                 if (ret)
248                         return ret;
249         }
250
251         return 0;
252 }
253
254 /*
255  * In SD mode, software must not use the hardware tuning and instead perform
256  * an almost identical procedure to eMMC.
257  */
258 static int sdhci_cdns_execute_tuning(struct sdhci_host *host, u32 opcode)
259 {
260         int cur_streak = 0;
261         int max_streak = 0;
262         int end_of_streak = 0;
263         int i;
264
265         /*
266          * Do not execute tuning for UHS_SDR50 or UHS_DDR50.
267          * The delay is set by probe, based on the DT properties.
268          */
269         if (host->timing != MMC_TIMING_MMC_HS200 &&
270             host->timing != MMC_TIMING_UHS_SDR104)
271                 return 0;
272
273         for (i = 0; i < SDHCI_CDNS_MAX_TUNING_LOOP; i++) {
274                 if (sdhci_cdns_set_tune_val(host, i) ||
275                     mmc_send_tuning(host->mmc, opcode, NULL)) { /* bad */
276                         cur_streak = 0;
277                 } else { /* good */
278                         cur_streak++;
279                         if (cur_streak > max_streak) {
280                                 max_streak = cur_streak;
281                                 end_of_streak = i;
282                         }
283                 }
284         }
285
286         if (!max_streak) {
287                 dev_err(mmc_dev(host->mmc), "no tuning point found\n");
288                 return -EIO;
289         }
290
291         return sdhci_cdns_set_tune_val(host, end_of_streak - max_streak / 2);
292 }
293
294 static void sdhci_cdns_set_uhs_signaling(struct sdhci_host *host,
295                                          unsigned int timing)
296 {
297         struct sdhci_cdns_priv *priv = sdhci_cdns_priv(host);
298         u32 mode;
299
300         switch (timing) {
301         case MMC_TIMING_MMC_HS:
302                 mode = SDHCI_CDNS_HRS06_MODE_MMC_SDR;
303                 break;
304         case MMC_TIMING_MMC_DDR52:
305                 mode = SDHCI_CDNS_HRS06_MODE_MMC_DDR;
306                 break;
307         case MMC_TIMING_MMC_HS200:
308                 mode = SDHCI_CDNS_HRS06_MODE_MMC_HS200;
309                 break;
310         case MMC_TIMING_MMC_HS400:
311                 if (priv->enhanced_strobe)
312                         mode = SDHCI_CDNS_HRS06_MODE_MMC_HS400ES;
313                 else
314                         mode = SDHCI_CDNS_HRS06_MODE_MMC_HS400;
315                 break;
316         default:
317                 mode = SDHCI_CDNS_HRS06_MODE_SD;
318                 break;
319         }
320
321         sdhci_cdns_set_emmc_mode(priv, mode);
322
323         /* For SD, fall back to the default handler */
324         if (mode == SDHCI_CDNS_HRS06_MODE_SD)
325                 sdhci_set_uhs_signaling(host, timing);
326 }
327
328 /* Elba control register bits [6:3] are byte-lane enables */
329 #define ELBA_BYTE_ENABLE_MASK(x)        ((x) << 3)
330
331 /*
332  * The Pensando Elba SoC explicitly controls byte-lane enabling on writes
333  * which includes writes to the HRS registers.  The write lock (wrlock)
334  * is used to ensure byte-lane enable, using write control (ctl_addr),
335  * occurs before the data write.
336  */
337 static void elba_priv_writel(struct sdhci_cdns_priv *priv, u32 val,
338                              void __iomem *reg)
339 {
340         unsigned long flags;
341
342         spin_lock_irqsave(&priv->wrlock, flags);
343         writel(GENMASK(7, 3), priv->ctl_addr);
344         writel(val, reg);
345         spin_unlock_irqrestore(&priv->wrlock, flags);
346 }
347
348 static void elba_write_l(struct sdhci_host *host, u32 val, int reg)
349 {
350         elba_priv_writel(sdhci_cdns_priv(host), val, host->ioaddr + reg);
351 }
352
353 static void elba_write_w(struct sdhci_host *host, u16 val, int reg)
354 {
355         struct sdhci_cdns_priv *priv = sdhci_cdns_priv(host);
356         u32 shift = reg & GENMASK(1, 0);
357         unsigned long flags;
358         u32 byte_enables;
359
360         byte_enables = GENMASK(1, 0) << shift;
361         spin_lock_irqsave(&priv->wrlock, flags);
362         writel(ELBA_BYTE_ENABLE_MASK(byte_enables), priv->ctl_addr);
363         writew(val, host->ioaddr + reg);
364         spin_unlock_irqrestore(&priv->wrlock, flags);
365 }
366
367 static void elba_write_b(struct sdhci_host *host, u8 val, int reg)
368 {
369         struct sdhci_cdns_priv *priv = sdhci_cdns_priv(host);
370         u32 shift = reg & GENMASK(1, 0);
371         unsigned long flags;
372         u32 byte_enables;
373
374         byte_enables = BIT(0) << shift;
375         spin_lock_irqsave(&priv->wrlock, flags);
376         writel(ELBA_BYTE_ENABLE_MASK(byte_enables), priv->ctl_addr);
377         writeb(val, host->ioaddr + reg);
378         spin_unlock_irqrestore(&priv->wrlock, flags);
379 }
380
381 static const struct sdhci_ops sdhci_elba_ops = {
382         .write_l = elba_write_l,
383         .write_w = elba_write_w,
384         .write_b = elba_write_b,
385         .set_clock = sdhci_set_clock,
386         .get_timeout_clock = sdhci_cdns_get_timeout_clock,
387         .set_bus_width = sdhci_set_bus_width,
388         .reset = sdhci_reset,
389         .set_uhs_signaling = sdhci_cdns_set_uhs_signaling,
390 };
391
392 static int elba_drv_init(struct platform_device *pdev)
393 {
394         struct sdhci_host *host = platform_get_drvdata(pdev);
395         struct sdhci_cdns_priv *priv = sdhci_cdns_priv(host);
396         void __iomem *ioaddr;
397
398         host->mmc->caps |= MMC_CAP_1_8V_DDR | MMC_CAP_8_BIT_DATA;
399         spin_lock_init(&priv->wrlock);
400
401         /* Byte-lane control register */
402         ioaddr = devm_platform_ioremap_resource(pdev, 1);
403         if (IS_ERR(ioaddr))
404                 return PTR_ERR(ioaddr);
405
406         priv->ctl_addr = ioaddr;
407         priv->priv_writel = elba_priv_writel;
408         writel(ELBA_BYTE_ENABLE_MASK(0xf), priv->ctl_addr);
409
410         return 0;
411 }
412
413 static const struct sdhci_ops sdhci_cdns_ops = {
414         .set_clock = sdhci_set_clock,
415         .get_timeout_clock = sdhci_cdns_get_timeout_clock,
416         .set_bus_width = sdhci_set_bus_width,
417         .reset = sdhci_reset,
418         .platform_execute_tuning = sdhci_cdns_execute_tuning,
419         .set_uhs_signaling = sdhci_cdns_set_uhs_signaling,
420 };
421
422 static const struct sdhci_cdns_drv_data sdhci_cdns_uniphier_drv_data = {
423         .pltfm_data = {
424                 .ops = &sdhci_cdns_ops,
425                 .quirks2 = SDHCI_QUIRK2_PRESET_VALUE_BROKEN,
426         },
427 };
428
429 static const struct sdhci_cdns_drv_data sdhci_elba_drv_data = {
430         .init = elba_drv_init,
431         .pltfm_data = {
432                 .ops = &sdhci_elba_ops,
433         },
434 };
435
436 static const struct sdhci_cdns_drv_data sdhci_cdns_drv_data = {
437         .pltfm_data = {
438                 .ops = &sdhci_cdns_ops,
439         },
440 };
441
442 static void sdhci_cdns_hs400_enhanced_strobe(struct mmc_host *mmc,
443                                              struct mmc_ios *ios)
444 {
445         struct sdhci_host *host = mmc_priv(mmc);
446         struct sdhci_cdns_priv *priv = sdhci_cdns_priv(host);
447         u32 mode;
448
449         priv->enhanced_strobe = ios->enhanced_strobe;
450
451         mode = sdhci_cdns_get_emmc_mode(priv);
452
453         if (mode == SDHCI_CDNS_HRS06_MODE_MMC_HS400 && ios->enhanced_strobe)
454                 sdhci_cdns_set_emmc_mode(priv,
455                                          SDHCI_CDNS_HRS06_MODE_MMC_HS400ES);
456
457         if (mode == SDHCI_CDNS_HRS06_MODE_MMC_HS400ES && !ios->enhanced_strobe)
458                 sdhci_cdns_set_emmc_mode(priv,
459                                          SDHCI_CDNS_HRS06_MODE_MMC_HS400);
460 }
461
462 static void sdhci_cdns_mmc_hw_reset(struct mmc_host *mmc)
463 {
464         struct sdhci_host *host = mmc_priv(mmc);
465         struct sdhci_cdns_priv *priv = sdhci_cdns_priv(host);
466
467         dev_dbg(mmc_dev(host->mmc), "emmc hardware reset\n");
468
469         reset_control_assert(priv->rst_hw);
470         /* For eMMC, minimum is 1us but give it 3us for good measure */
471         udelay(3);
472
473         reset_control_deassert(priv->rst_hw);
474         /* For eMMC, minimum is 200us but give it 300us for good measure */
475         usleep_range(300, 1000);
476 }
477
478 static int sdhci_cdns_probe(struct platform_device *pdev)
479 {
480         struct sdhci_host *host;
481         const struct sdhci_cdns_drv_data *data;
482         struct sdhci_pltfm_host *pltfm_host;
483         struct sdhci_cdns_priv *priv;
484         struct clk *clk;
485         unsigned int nr_phy_params;
486         int ret;
487         struct device *dev = &pdev->dev;
488         static const u16 version = SDHCI_SPEC_400 << SDHCI_SPEC_VER_SHIFT;
489
490         clk = devm_clk_get_enabled(dev, NULL);
491         if (IS_ERR(clk))
492                 return PTR_ERR(clk);
493
494         data = of_device_get_match_data(dev);
495         if (!data)
496                 data = &sdhci_cdns_drv_data;
497
498         nr_phy_params = sdhci_cdns_phy_param_count(dev->of_node);
499         host = sdhci_pltfm_init(pdev, &data->pltfm_data,
500                                 struct_size(priv, phy_params, nr_phy_params));
501         if (IS_ERR(host))
502                 return PTR_ERR(host);
503
504         pltfm_host = sdhci_priv(host);
505         pltfm_host->clk = clk;
506
507         priv = sdhci_pltfm_priv(pltfm_host);
508         priv->nr_phy_params = nr_phy_params;
509         priv->hrs_addr = host->ioaddr;
510         priv->enhanced_strobe = false;
511         priv->priv_writel = cdns_writel;
512         host->ioaddr += SDHCI_CDNS_SRS_BASE;
513         host->mmc_host_ops.hs400_enhanced_strobe =
514                                 sdhci_cdns_hs400_enhanced_strobe;
515         if (data->init) {
516                 ret = data->init(pdev);
517                 if (ret)
518                         goto free;
519         }
520         sdhci_enable_v4_mode(host);
521         __sdhci_read_caps(host, &version, NULL, NULL);
522
523         sdhci_get_of_property(pdev);
524
525         ret = mmc_of_parse(host->mmc);
526         if (ret)
527                 goto free;
528
529         sdhci_cdns_phy_param_parse(dev->of_node, priv);
530
531         ret = sdhci_cdns_phy_init(priv);
532         if (ret)
533                 goto free;
534
535         if (host->mmc->caps & MMC_CAP_HW_RESET) {
536                 priv->rst_hw = devm_reset_control_get_optional_exclusive(dev, NULL);
537                 if (IS_ERR(priv->rst_hw)) {
538                         ret = dev_err_probe(mmc_dev(host->mmc), PTR_ERR(priv->rst_hw),
539                                             "reset controller error\n");
540                         goto free;
541                 }
542                 if (priv->rst_hw)
543                         host->mmc_host_ops.card_hw_reset = sdhci_cdns_mmc_hw_reset;
544         }
545
546         ret = sdhci_add_host(host);
547         if (ret)
548                 goto free;
549
550         return 0;
551 free:
552         sdhci_pltfm_free(pdev);
553         return ret;
554 }
555
556 #ifdef CONFIG_PM_SLEEP
557 static int sdhci_cdns_resume(struct device *dev)
558 {
559         struct sdhci_host *host = dev_get_drvdata(dev);
560         struct sdhci_pltfm_host *pltfm_host = sdhci_priv(host);
561         struct sdhci_cdns_priv *priv = sdhci_pltfm_priv(pltfm_host);
562         int ret;
563
564         ret = clk_prepare_enable(pltfm_host->clk);
565         if (ret)
566                 return ret;
567
568         ret = sdhci_cdns_phy_init(priv);
569         if (ret)
570                 goto disable_clk;
571
572         ret = sdhci_resume_host(host);
573         if (ret)
574                 goto disable_clk;
575
576         return 0;
577
578 disable_clk:
579         clk_disable_unprepare(pltfm_host->clk);
580
581         return ret;
582 }
583 #endif
584
585 static const struct dev_pm_ops sdhci_cdns_pm_ops = {
586         SET_SYSTEM_SLEEP_PM_OPS(sdhci_pltfm_suspend, sdhci_cdns_resume)
587 };
588
589 static const struct of_device_id sdhci_cdns_match[] = {
590         {
591                 .compatible = "socionext,uniphier-sd4hc",
592                 .data = &sdhci_cdns_uniphier_drv_data,
593         },
594         {
595                 .compatible = "amd,pensando-elba-sd4hc",
596                 .data = &sdhci_elba_drv_data,
597         },
598         { .compatible = "cdns,sd4hc" },
599         { /* sentinel */ }
600 };
601 MODULE_DEVICE_TABLE(of, sdhci_cdns_match);
602
603 static struct platform_driver sdhci_cdns_driver = {
604         .driver = {
605                 .name = "sdhci-cdns",
606                 .probe_type = PROBE_PREFER_ASYNCHRONOUS,
607                 .pm = &sdhci_cdns_pm_ops,
608                 .of_match_table = sdhci_cdns_match,
609         },
610         .probe = sdhci_cdns_probe,
611         .remove_new = sdhci_pltfm_remove,
612 };
613 module_platform_driver(sdhci_cdns_driver);
614
615 MODULE_AUTHOR("Masahiro Yamada <yamada.masahiro@socionext.com>");
616 MODULE_DESCRIPTION("Cadence SD/SDIO/eMMC Host Controller Driver");
617 MODULE_LICENSE("GPL");