Page MenuHomeFreeBSD

D20156.id57033.diff
No OneTemporary

D20156.id57033.diff

Index: sys/dev/sdhci/sdhci_fdt.c
===================================================================
--- sys/dev/sdhci/sdhci_fdt.c
+++ sys/dev/sdhci/sdhci_fdt.c
@@ -52,6 +52,9 @@
#include <dev/ofw/ofw_bus.h>
#include <dev/ofw/ofw_bus_subr.h>
+#include <dev/extres/clk/clk.h>
+#include <dev/extres/syscon/syscon.h>
+
#include <dev/mmc/bridge.h>
#include <dev/sdhci/sdhci.h>
@@ -61,16 +64,30 @@
#include "opt_mmccam.h"
+#include "syscon_if.h"
+
#define MAX_SLOTS 6
#define SDHCI_FDT_ARMADA38X 1
#define SDHCI_FDT_GENERIC 2
#define SDHCI_FDT_XLNX_ZY7 3
#define SDHCI_FDT_QUALCOMM 4
+#define SDHCI_FDT_RK3399 5
+#define RK3399_GRF_EMMCCORE_CON0 0xf000
+#define RK3399_CORECFG_BASECLKFREQ (1 << 15) | (1 << 8)
+#define RK3399_CORECFG_TIMEOUTCLKUNIT (1 << 7)
+#define RK3399_CORECFG_TUNINGCOUNT (1 << 5) | (1 << 0)
+#define RK3399_GRF_EMMCCORE_CON11 0xf02c
+#define RK3399_CORECFG_CLOCKMULTIPLIER (1 << 7) | (1 << 0)
+
+#define LOWEST_SET_BIT(mask) ((((mask) - 1) & (mask)) ^ (mask))
+#define SHIFTIN(x, mask) ((x) * LOWEST_SET_BIT(mask))
+
static struct ofw_compat_data compat_data[] = {
{ "marvell,armada-380-sdhci", SDHCI_FDT_ARMADA38X },
{ "sdhci_generic", SDHCI_FDT_GENERIC },
{ "qcom,sdhci-msm-v4", SDHCI_FDT_QUALCOMM },
+ { "rockchip,rk3399-sdhci-5.1", SDHCI_FDT_RK3399 },
{ "xlnx,zy7_sdhci", SDHCI_FDT_XLNX_ZY7 },
{ NULL, 0 }
};
@@ -90,8 +107,28 @@
bool wp_inverted; /* WP pin is inverted */
bool no_18v; /* No 1.8V support */
+
+ clk_t clk_xin;
+ clk_t clk_ahb;
};
+static void
+sdhc_init_rk3399(struct syscon *grf, phandle_t node, uint64_t freq)
+{
+ uint32_t mask, val;
+
+ /* Disable clock multiplier */
+ mask = RK3399_CORECFG_CLOCKMULTIPLIER;
+ val = 0;
+ SYSCON_WRITE_4(grf, RK3399_GRF_EMMCCORE_CON11, (mask << 16) | val);
+
+ /* Set base clock frequency */
+ mask = RK3399_CORECFG_BASECLKFREQ;
+ val = SHIFTIN((freq + (1000000 / 2)) / 1000000,
+ RK3399_CORECFG_BASECLKFREQ);
+ SYSCON_WRITE_4(grf, RK3399_GRF_EMMCCORE_CON0, (mask << 16) | val);
+}
+
static uint8_t
sdhci_fdt_read_1(device_t dev, struct sdhci_slot *slot, bus_size_t off)
{
@@ -188,8 +225,11 @@
sdhci_fdt_probe(device_t dev)
{
struct sdhci_fdt_softc *sc = device_get_softc(dev);
+ struct syscon *grf = NULL;
phandle_t node;
pcell_t cid;
+ uint64_t freq;
+ int error;
sc->quirks = 0;
sc->num_slots = 1;
@@ -198,6 +238,8 @@
if (!ofw_bus_status_okay(dev))
return (ENXIO);
+ node = ofw_bus_get_node(dev);
+
switch (ofw_bus_search_compatible(dev, compat_data)->ocd_data) {
case SDHCI_FDT_ARMADA38X:
sc->quirks = SDHCI_QUIRK_BROKEN_AUTO_STOP;
@@ -212,6 +254,42 @@
sc->sdma_boundary = SDHCI_BLKSZ_SDMA_BNDRY_4K;
device_set_desc(dev, "Qualcomm FDT SDHCI controller");
break;
+ case SDHCI_FDT_RK3399:
+ /* Get and activate clocks */
+ error = clk_get_by_ofw_name(dev, 0, "clk_xin", &sc->clk_xin);
+ if (error != 0) {
+ device_printf(dev, "cannot get xin clock\n");
+ return (ENXIO);
+ }
+ error = clk_enable(sc->clk_xin);
+ if (error != 0) {
+ device_printf(dev, "cannot enable xin clock\n");
+ return (ENXIO);
+ }
+ error = clk_get_freq(sc->clk_xin, &freq);
+ if (error != 0) {
+ device_printf(dev, "cannot get xin clock frequency\n");
+ return (ENXIO);
+ }
+ error = clk_get_by_ofw_name(dev, 0, "clk_ahb", &sc->clk_ahb);
+ if (error != 0) {
+ device_printf(dev, "cannot get ahb clock\n");
+ return (ENXIO);
+ }
+ error = clk_enable(sc->clk_ahb);
+ if (error != 0) {
+ device_printf(dev, "cannot enable ahb clock\n");
+ return (ENXIO);
+ }
+ if (OF_hasprop(node, "arasan,soc-ctl-syscon") &&
+ syscon_get_by_ofw_property(dev, node,
+ "arasan,soc-ctl-syscon", &grf) != 0) {
+ device_printf(dev, "cannot get grf driver handle\n");
+ return (ENXIO);
+ }
+ sdhc_init_rk3399(grf, node, freq);
+ device_set_desc(dev, "Rockchip RK3399 fdt SDHCI controller");
+ break;
case SDHCI_FDT_XLNX_ZY7:
sc->quirks = SDHCI_QUIRK_DATA_TIMEOUT_USES_SDCLK;
device_set_desc(dev, "Zynq-7000 generic fdt SDHCI controller");
@@ -220,8 +298,6 @@
return (ENXIO);
}
- node = ofw_bus_get_node(dev);
-
/* Allow dts to patch quirks, slots, and max-frequency. */
if ((OF_getencprop(node, "quirks", &cid, sizeof(cid))) > 0)
sc->quirks = cid;

File Metadata

Mime Type
text/plain
Expires
Thu, Mar 26, 6:19 AM (15 h, 36 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
30367775
Default Alt Text
D20156.id57033.diff (4 KB)

Event Timeline