Module Name: src
Committed By: skrll
Date: Sat Jan 18 17:20:05 UTC 2025
Modified Files:
src/sys/arch/riscv/starfive: jh7100_clkc.c
Log Message:
risc-v: add support for the StarFive JH7100 audio clocks
To generate a diff of this commit:
cvs rdiff -u -r1.4 -r1.5 src/sys/arch/riscv/starfive/jh7100_clkc.c
Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.
Modified files:
Index: src/sys/arch/riscv/starfive/jh7100_clkc.c
diff -u src/sys/arch/riscv/starfive/jh7100_clkc.c:1.4 src/sys/arch/riscv/starfive/jh7100_clkc.c:1.5
--- src/sys/arch/riscv/starfive/jh7100_clkc.c:1.4 Wed Sep 18 08:31:50 2024
+++ src/sys/arch/riscv/starfive/jh7100_clkc.c Sat Jan 18 17:20:05 2025
@@ -1,4 +1,4 @@
-/* $NetBSD: jh7100_clkc.c,v 1.4 2024/09/18 08:31:50 skrll Exp $ */
+/* $NetBSD: jh7100_clkc.c,v 1.5 2025/01/18 17:20:05 skrll Exp $ */
/*-
* Copyright (c) 2023 The NetBSD Foundation, Inc.
@@ -30,7 +30,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: jh7100_clkc.c,v 1.4 2024/09/18 08:31:50 skrll Exp $");
+__KERNEL_RCSID(0, "$NetBSD: jh7100_clkc.c,v 1.5 2025/01/18 17:20:05 skrll Exp $");
#include <sys/param.h>
@@ -133,6 +133,38 @@ __KERNEL_RCSID(0, "$NetBSD: jh7100_clkc.
#define JH7100_NCLKS 189
+#define JH7100_AUDCLK_ADC_MCLK 0
+#define JH7100_AUDCLK_I2S1_MCLK 1
+#define JH7100_AUDCLK_I2SADC_APB 2
+#define JH7100_AUDCLK_I2SADC_BCLK 3
+#define JH7100_AUDCLK_I2SADC_BCLK_N 4
+#define JH7100_AUDCLK_I2SADC_LRCLK 5
+#define JH7100_AUDCLK_PDM_APB 6
+#define JH7100_AUDCLK_PDM_MCLK 7
+#define JH7100_AUDCLK_I2SVAD_APB 8
+#define JH7100_AUDCLK_SPDIF 9
+#define JH7100_AUDCLK_SPDIF_APB 10
+#define JH7100_AUDCLK_PWMDAC_APB 11
+#define JH7100_AUDCLK_DAC_MCLK 12
+#define JH7100_AUDCLK_I2SDAC_APB 13
+#define JH7100_AUDCLK_I2SDAC_BCLK 14
+#define JH7100_AUDCLK_I2SDAC_BCLK_N 15
+#define JH7100_AUDCLK_I2SDAC_LRCLK 16
+#define JH7100_AUDCLK_I2S1_APB 17
+#define JH7100_AUDCLK_I2S1_BCLK 18
+#define JH7100_AUDCLK_I2S1_BCLK_N 19
+#define JH7100_AUDCLK_I2S1_LRCLK 20
+#define JH7100_AUDCLK_I2SDAC16K_APB 21
+#define JH7100_AUDCLK_APB0_BUS 22
+#define JH7100_AUDCLK_DMA1P_AHB 23
+#define JH7100_AUDCLK_USB_APB 24
+#define JH7100_AUDCLK_USB_LPM 25
+#define JH7100_AUDCLK_USB_STB 26
+#define JH7100_AUDCLK_APB_EN 27
+#define JH7100_AUDCLK_VAD_MEM 28
+
+#define JH7100_AUDCLK_NCLKS 29
+
static const char *cpundbus_root_parents[] = {
"osc_sys", "pll0_out", "pll1_out", "pll2_out",
@@ -279,8 +311,112 @@ static struct jh71x0_clkc_clk jh7100_clo
};
+static const char *adc_mclk_parents[] = {
+ "audio_src", "audio_12288",
+};
+
+static const char *i2s1_mclk_parents[] = {
+ "audio_src", "audio_12288",
+};
+
+static const char *i2sadc_bclk_parents[] = {
+ "adc_mclk", "i2sadc_bclk_iopad"
+};
+
+static const char *i2sadc_lrclk_parents[] = {
+ "i2sadc_bclk_n", "i2sadc_lrclk_iopad", "i2sadc_bclk",
+};
+
+static const char *pdm_mclk_parents[] = {
+ "audio_src", "audio_12288",
+};
+
+static const char *spdif_parents[] = {
+ "audio_src", "audio_12288",
+};
+
+static const char *dac_mclk_parents[] = {
+ "audio_src", "audio_12288",
+};
+
+static const char *i2sdac_bclk_parents[] = {
+ "dac_mclk", "i2sadc_blk_iopad",
+};
+
+static const char *i2sdac_lrclk_parents[] = {
+ "i2s1_mclk", "i2sadc_blk_iopad",
+};
+
+static const char *i2s1_bclk_parents[] = {
+ "i2s1_mclk", "i2sadc_blk_iopad",
+};
+
+static const char *i2s1_lrclk_parents[] = {
+ "i2s1_bclk_n", "i2sadc_lrclk_iopad",
+};
+
+static const char *vad_mem_parents[] = {
+ "vad_intmem", "audio_12288",
+};
+
+
+static struct jh71x0_clkc_clk jh7100_audclk_clocks[] = {
+ JH71X0CLKC_MUXDIVGATE(JH7100_AUDCLK_ADC_MCLK, "adc_mclk", 15, adc_mclk_parents),
+ JH71X0CLKC_MUXDIVGATE(JH7100_AUDCLK_I2S1_MCLK, "i2s1_mclk", 15, i2s1_mclk_parents),
+
+ JH71X0CLKC_GATE(JH7100_AUDCLK_I2SADC_APB, "i2sadc_apb", "apb0_bus"),
+
+ JH71X0CLKC_MUXDIV(JH7100_AUDCLK_I2SADC_BCLK, "i2sadc_bclk", 31, i2sadc_bclk_parents),
+
+ JH71X0CLKC_INV(JH7100_AUDCLK_I2SADC_BCLK_N, "i2sadc_bclk_n", "i2sadc_bclk"),
+ JH71X0CLKC_MUXDIV(JH7100_AUDCLK_I2SADC_LRCLK, "i2sadc_lrclk", 63, i2sadc_lrclk_parents),
+ JH71X0CLKC_GATE(JH7100_AUDCLK_PDM_APB, "pdm_apb", "apb0_bus"),
+ JH71X0CLKC_MUXDIVGATE(JH7100_AUDCLK_PDM_MCLK, "pdm_mclk", 15, pdm_mclk_parents),
+ JH71X0CLKC_GATE(JH7100_AUDCLK_I2SVAD_APB, "i2svad_apb", "apb0_bus"),
+ JH71X0CLKC_MUXDIVGATE(JH7100_AUDCLK_SPDIF, "spdif", 15, spdif_parents),
+ JH71X0CLKC_GATE(JH7100_AUDCLK_SPDIF_APB, "spdif_apb", "apb0_bus"),
+ JH71X0CLKC_GATE(JH7100_AUDCLK_PWMDAC_APB, "pwmdac_apb", "apb0_bus"),
+ JH71X0CLKC_MUXDIVGATE(JH7100_AUDCLK_DAC_MCLK, "dac_mclk", 15, dac_mclk_parents),
+ JH71X0CLKC_GATE(JH7100_AUDCLK_I2SDAC_APB, "i2sdac_apb", "apb0_bus"),
+ JH71X0CLKC_MUXDIV(JH7100_AUDCLK_I2SDAC_BCLK, "i2sdac_bclk", 31, i2sdac_bclk_parents),
+ JH71X0CLKC_INV(JH7100_AUDCLK_I2SDAC_BCLK_N, "i2sdac_bclk_n", "i2sdac_bclk"),
+ JH71X0CLKC_MUXDIV(JH7100_AUDCLK_I2SDAC_LRCLK, "i2sdac_lrclk", 31, i2sdac_lrclk_parents),
+ JH71X0CLKC_GATE(JH7100_AUDCLK_I2S1_APB, "i2s1_apb", "apb0_bus"),
+ JH71X0CLKC_MUXDIV(JH7100_AUDCLK_I2S1_BCLK, "i2s1_bclk", 31, i2s1_bclk_parents),
+ JH71X0CLKC_INV(JH7100_AUDCLK_I2S1_BCLK_N, "i2s1_bclk_n", "i2s1_bclk"),
+ JH71X0CLKC_MUXDIV(JH7100_AUDCLK_I2S1_LRCLK, "i2s1_lrclk", 63, i2s1_lrclk_parents),
+ JH71X0CLKC_GATE(JH7100_AUDCLK_I2SDAC16K_APB, "i2s1dac16k_apb", "apb0_bus"),
+ JH71X0CLKC_DIV(JH7100_AUDCLK_APB0_BUS, "apb0_bus", 8, "dom7ahb_bus"),
+ JH71X0CLKC_GATE(JH7100_AUDCLK_DMA1P_AHB, "dma1p_ahb", "dom7ahb_bus"),
+ JH71X0CLKC_GATE(JH7100_AUDCLK_USB_APB, "usb_apb", /*CLK_IGNORE_UNUSED,*/ "apb_en"),
+ JH71X0CLKC_GATEDIV(JH7100_AUDCLK_USB_LPM, "usb_lpm", /*CLK_IGNORE_UNUSED,*/ 4, "usb_apb"),
+ JH71X0CLKC_GATEDIV(JH7100_AUDCLK_USB_STB, "usb_stb", /*CLK_IGNORE_UNUSED,*/ 3, "usb_apb"),
+ JH71X0CLKC_DIV(JH7100_AUDCLK_APB_EN, "apb_en", 8, "dom7ahb_bus"),
+ JH71X0CLKC_MUX(JH7100_AUDCLK_VAD_MEM, "vad_mem", vad_mem_parents),
+};
+
+struct jh7100_clk_config {
+ const char *jhcc_name;
+ struct jh71x0_clkc_clk *jhcc_clocks;
+ size_t jhcc_nclks;
+};
+
+static struct jh7100_clk_config jh7100_clk_config = {
+ .jhcc_name = "System",
+ .jhcc_clocks = jh7100_clocks,
+ .jhcc_nclks = __arraycount(jh7100_clocks),
+};
+
+
+static struct jh7100_clk_config jh7110_audclk_config = {
+ .jhcc_name = "Audio",
+ .jhcc_clocks = jh7100_audclk_clocks,
+ .jhcc_nclks = __arraycount(jh7100_audclk_clocks),
+};
+
static const struct device_compatible_entry compat_data[] = {
- { .compat = "starfive,jh7100-clkgen" },
+ { .compat = "starfive,jh7100-clkgen", .data = &jh7100_clk_config },
+ { .compat = "starfive,jh7100-audclk", .data = &jh7110_audclk_config },
DEVICE_COMPAT_EOL
};
@@ -323,6 +459,7 @@ jh7100_clkc_attach(device_t parent, devi
struct jh71x0_clkc_softc * const sc = device_private(self);
struct fdt_attach_args * const faa = aux;
const int phandle = faa->faa_phandle;
+ char infomsg[128] = "";
bus_addr_t addr;
bus_size_t size;
int error;
@@ -342,26 +479,35 @@ jh7100_clkc_attach(device_t parent, devi
return;
}
- struct clk * const osclk = fdtbus_clock_get(phandle, "osc_sys");
- if (osclk == NULL) {
- aprint_error(": couldn't get osc_sys\n");
- return;
- }
- u_int osclk_rate = clk_get_rate(osclk);
+ const struct jh7100_clk_config *jhcc =
+ of_compatible_lookup(phandle, compat_data)->data;
+ KASSERT(jhcc != NULL);
+
+ if (jhcc == &jh7100_clk_config) {
+ struct clk * const osclk = fdtbus_clock_get(phandle, "osc_sys");
+ if (osclk == NULL) {
+ aprint_error(": couldn't get osc_sys\n");
+ return;
+ }
+ u_int osclk_rate = clk_get_rate(osclk);
+
+ struct clk * const oaclk = fdtbus_clock_get(phandle, "osc_aud");
+ if (oaclk == NULL) {
+ aprint_error(": couldn't get osc_aud\n");
+ return;
+ }
+ u_int oaclk_rate = clk_get_rate(oaclk);
- struct clk * const oaclk = fdtbus_clock_get(phandle, "osc_aud");
- if (oaclk == NULL) {
- aprint_error(": couldn't get osc_aud\n");
- return;
+ snprintf(infomsg, sizeof(infomsg), "(OSC0 %u Hz, OSC1 %u Hz)",
+ osclk_rate, oaclk_rate);
}
- u_int oaclk_rate = clk_get_rate(oaclk);
sc->sc_clkdom.name = device_xname(self);
sc->sc_clkdom.funcs = &jh71x0_clkc_funcs;
sc->sc_clkdom.priv = sc;
- sc->sc_clk = jh7100_clocks;
- sc->sc_nclks = __arraycount(jh7100_clocks);
+ sc->sc_clk = jhcc->jhcc_clocks;
+ sc->sc_nclks = jhcc->jhcc_nclks;
for (size_t id = 0; id < sc->sc_nclks; id++) {
if (sc->sc_clk[id].jcc_type == JH71X0CLK_UNKNOWN)
continue;
@@ -371,8 +517,7 @@ jh7100_clkc_attach(device_t parent, devi
}
aprint_naive("\n");
- aprint_normal(": JH7100 (OSC0 %u Hz, OSC1 %u Hz)\n",
- osclk_rate, oaclk_rate);
+ aprint_normal(": JH7100 %s clocks %s\n", jhcc->jhcc_name, infomsg);
for (size_t id = 0; id < sc->sc_nclks; id++) {
if (sc->sc_clk[id].jcc_type == JH71X0CLK_UNKNOWN)