Module Name:    src
Committed By:   jmcneill
Date:           Tue Sep 11 10:06:53 UTC 2018

Modified Files:
        src/sys/arch/arm/samsung: exynos_platform.c files.exynos mct.c
        src/sys/arch/evbarm/conf: EXYNOS
        src/sys/arch/evbarm/exynos: exynos_start.S

Log Message:
Add Exynos5 SMP support.


To generate a diff of this commit:
cvs rdiff -u -r1.14 -r1.15 src/sys/arch/arm/samsung/exynos_platform.c \
    src/sys/arch/arm/samsung/mct.c
cvs rdiff -u -r1.31 -r1.32 src/sys/arch/arm/samsung/files.exynos
cvs rdiff -u -r1.32 -r1.33 src/sys/arch/evbarm/conf/EXYNOS
cvs rdiff -u -r1.7 -r1.8 src/sys/arch/evbarm/exynos/exynos_start.S

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/arm/samsung/exynos_platform.c
diff -u src/sys/arch/arm/samsung/exynos_platform.c:1.14 src/sys/arch/arm/samsung/exynos_platform.c:1.15
--- src/sys/arch/arm/samsung/exynos_platform.c:1.14	Wed Aug 22 07:43:02 2018
+++ src/sys/arch/arm/samsung/exynos_platform.c	Tue Sep 11 10:06:53 2018
@@ -1,4 +1,4 @@
-/* $NetBSD: exynos_platform.c,v 1.14 2018/08/22 07:43:02 skrll Exp $ */
+/* $NetBSD: exynos_platform.c,v 1.15 2018/09/11 10:06:53 jmcneill Exp $ */
 
 /*-
  * Copyright (c) 2017 Jared D. McNeill <jmcne...@invisible.ca>
@@ -34,7 +34,7 @@
 #include "ukbd.h"
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: exynos_platform.c,v 1.14 2018/08/22 07:43:02 skrll Exp $");
+__KERNEL_RCSID(0, "$NetBSD: exynos_platform.c,v 1.15 2018/09/11 10:06:53 jmcneill Exp $");
 
 #include <sys/param.h>
 #include <sys/bus.h>
@@ -65,11 +65,73 @@ void exynos_platform_early_putchar(char)
 #define EXYNOS_IOPHYSTOVIRT(a) \
     ((vaddr_t)(((a) - EXYNOS_CORE_PBASE) + EXYNOS_CORE_VBASE))
 
+#define	EXYNOS5800_PMU_BASE		0x10040000
+#define	EXYNOS5800_PMU_SIZE		0x20000
+#define	 EXYNOS5800_PMU_CORE_CONFIG(n)	(0x2000 + 0x80 * (n))
+#define	 EXYNOS5800_PMU_CORE_STATUS(n)	(0x2004 + 0x80 * (n))
+#define	 EXYNOS5800_PMU_CORE_POWER_EN	0x3
+#define	EXYNOS5800_SYSRAM_BASE		0x0207301c
+#define	EXYNOS5800_SYSRAM_SIZE		0x4
+
+static void
+exynos5800_mp_bootstrap(void)
+{
+#if defined(MULTIPROCESSOR)
+	extern void cortex_mpstart(void);
+	bus_space_tag_t bst = &armv7_generic_bs_tag;
+	bus_space_handle_t pmu_bsh, sysram_bsh;
+	uint32_t val, started = 0;
+	int n;
+
+	arm_cpu_max = 1 + __SHIFTOUT(armreg_l2ctrl_read(), L2CTRL_NUMCPU);
+
+	bus_space_map(bst, EXYNOS5800_PMU_BASE, EXYNOS5800_PMU_SIZE, 0, &pmu_bsh);
+	bus_space_map(bst, EXYNOS5800_SYSRAM_BASE, EXYNOS5800_SYSRAM_SIZE, 0, &sysram_bsh);
+
+	bus_space_write_4(bst, sysram_bsh, 0, (uint32_t)cortex_mpstart);
+	bus_space_barrier(bst, sysram_bsh, 0, 4, BUS_SPACE_BARRIER_READ | BUS_SPACE_BARRIER_WRITE);
+
+	for (n = 1; n < arm_cpu_max; n++) {
+		bus_space_write_4(bst, pmu_bsh, EXYNOS5800_PMU_CORE_CONFIG(n),
+		    EXYNOS5800_PMU_CORE_POWER_EN);
+		for (u_int i = 0x01000000; i > 0; i--) {
+			val = bus_space_read_4(bst, pmu_bsh, EXYNOS5800_PMU_CORE_STATUS(n));
+			if ((val & EXYNOS5800_PMU_CORE_POWER_EN) == EXYNOS5800_PMU_CORE_POWER_EN) {
+				started |= __BIT(n);
+				break;
+			}
+		}
+	}
+
+	for (u_int i = 0x10000000; i > 0; i--) {
+		arm_dmb();
+		if (arm_cpu_hatched == started)
+			break;
+	}
+
+	bus_space_unmap(bst, sysram_bsh, EXYNOS5800_SYSRAM_SIZE);
+	bus_space_unmap(bst, pmu_bsh, EXYNOS5800_PMU_SIZE);
+#endif
+}
+
+static struct of_compat_data mp_compat_data[] = {
+	{ "samsung,exynos5800",		(uintptr_t)exynos5800_mp_bootstrap },
+	{ NULL }
+};
+
 static void
 exynos_platform_bootstrap(void)
 {
 
 	exynos_bootstrap(EXYNOS_CORE_VBASE);
+
+	void (*mp_bootstrap)(void) = NULL;
+	const struct of_compat_data *cd = of_search_compatible(OF_finddevice("/"), mp_compat_data);
+	if (cd)
+		mp_bootstrap = (void (*)(void))cd->data;
+
+	if (mp_bootstrap)
+		mp_bootstrap();
 }
 
 static void
@@ -168,6 +230,9 @@ exynos5_platform_devmap(void)
 		DEVMAP_ENTRY(EXYNOS5_AUDIOCORE_VBASE,
 			     EXYNOS5_AUDIOCORE_PBASE,
 			     EXYNOS5_AUDIOCORE_SIZE),
+		DEVMAP_ENTRY(EXYNOS5_SYSRAM_VBASE,
+			     EXYNOS5_SYSRAM_PBASE,
+			     EXYNOS5_SYSRAM_SIZE),
 		DEVMAP_ENTRY_END
 	};
 
Index: src/sys/arch/arm/samsung/mct.c
diff -u src/sys/arch/arm/samsung/mct.c:1.14 src/sys/arch/arm/samsung/mct.c:1.15
--- src/sys/arch/arm/samsung/mct.c:1.14	Mon Jul  2 12:49:37 2018
+++ src/sys/arch/arm/samsung/mct.c	Tue Sep 11 10:06:53 2018
@@ -1,4 +1,4 @@
-/*	$NetBSD: mct.c,v 1.14 2018/07/02 12:49:37 jmcneill Exp $	*/
+/*	$NetBSD: mct.c,v 1.15 2018/09/11 10:06:53 jmcneill Exp $	*/
 
 /*-
  * Copyright (c) 2014-2018 The NetBSD Foundation, Inc.
@@ -29,9 +29,12 @@
  * POSSIBILITY OF SUCH DAMAGE.
  */
 
+#include "opt_arm_timer.h"
+#include "opt_multiprocessor.h"
+
 #include <sys/cdefs.h>
 
-__KERNEL_RCSID(1, "$NetBSD: mct.c,v 1.14 2018/07/02 12:49:37 jmcneill Exp $");
+__KERNEL_RCSID(1, "$NetBSD: mct.c,v 1.15 2018/09/11 10:06:53 jmcneill Exp $");
 
 #include <sys/param.h>
 #include <sys/bus.h>
@@ -53,6 +56,15 @@ __KERNEL_RCSID(1, "$NetBSD: mct.c,v 1.14
 #include <dev/fdt/fdtvar.h>
 #include <arm/fdt/arm_fdtvar.h>
 
+#if defined(MULTIPROCESSOR)
+#if !defined(__HAVE_GENERIC_CPU_INITCLOCKS)
+#error MULTIPROCESSOR kernels require __HAVE_GENERIC_CPU_INITCLOCKS
+#endif
+#include <arm/cortex/gtmr_intr.h>
+#include <arm/cortex/mpcore_var.h>
+#include <arm/cortex/gtmr_var.h>
+#endif
+
 static struct mct_softc mct_sc;
 
 static int  mct_match(device_t, cfdata_t, void *);
@@ -65,7 +77,7 @@ static struct timecounter mct_timecounte
 	.tc_counter_mask = ~0u,
 	.tc_frequency = EXYNOS_F_IN_FREQ,
 	.tc_name = "MCT",
-	.tc_quality = 500,
+	.tc_quality = 400,
 	.tc_priv = &mct_sc,
 };
 
@@ -137,21 +149,16 @@ mct_write_global(struct mct_softc *sc, b
 	panic("MCT hangs after writing %#x at %#x", v, (uint32_t) o);
 }
 
-static void
-mct_fdt_cpu_hatch(void *priv, struct cpu_info *ci)
-{
-	panic("%s: not implemented", __func__);
-}
-
 static int
 mct_intr(void *arg)
 {
 	struct mct_softc * const sc = &mct_sc;
-	struct clockframe *frame = arg;
 
 	mct_write_global(sc, MCT_G_INT_CSTAT, G_INT_CSTAT_CLEAR);
 
-	hardclock(frame);
+#if !defined(MULTIPROCESSOR)
+	hardclock(arg);
+#endif
 
 	return 1;
 }
@@ -203,6 +210,19 @@ mct_cpu_initclocks(void)
 	mct_write_global(sc, MCT_G_COMP0_U, (uint32_t)(comp0 >> 32));
 	mct_write_global(sc, MCT_G_INT_ENB, G_INT_ENB_ENABLE);
 	mct_write_global(sc, MCT_G_TCON, G_TCON_START | G_TCON_COMP0_ENABLE | G_TCON_COMP0_AUTOINC);
+
+#if defined(MULTIPROCESSOR)
+	/* Initialize gtmr */
+	gtmr_cpu_initclocks();
+#endif
+}
+
+static void
+mct_fdt_cpu_hatch(void *priv, struct cpu_info *ci)
+{
+#if defined(MULTIPROCESSOR)
+	gtmr_init_cpu_clock(ci);
+#endif
 }
 
 static int
@@ -248,6 +268,17 @@ mct_attach(device_t parent, device_t sel
 
 	arm_fdt_cpu_hatch_register(self, mct_fdt_cpu_hatch);
 	arm_fdt_timer_register(mct_cpu_initclocks);
+
+#if defined(MULTIPROCESSOR)
+	/* Start the timer */
+	mct_write_global(sc, MCT_G_TCON, G_TCON_START);
+
+	struct mpcore_attach_args mpcaa = {
+		.mpcaa_name = "armgtmr",
+		.mpcaa_irq = IRQ_GTMR_PPI_VTIMER,
+	};
+	config_found(self, &mpcaa, NULL);
+#endif
 }
 
 void

Index: src/sys/arch/arm/samsung/files.exynos
diff -u src/sys/arch/arm/samsung/files.exynos:1.31 src/sys/arch/arm/samsung/files.exynos:1.32
--- src/sys/arch/arm/samsung/files.exynos:1.31	Sun Aug 19 07:27:33 2018
+++ src/sys/arch/arm/samsung/files.exynos	Tue Sep 11 10:06:53 2018
@@ -1,4 +1,4 @@
-#	$NetBSD: files.exynos,v 1.31 2018/08/19 07:27:33 skrll Exp $
+#	$NetBSD: files.exynos,v 1.32 2018/09/11 10:06:53 jmcneill Exp $
 #
 # Configuration info for Samsung Exynos SoC ARM Peripherals
 #
@@ -55,7 +55,7 @@ attach  exyortc at fdt with exynos_rtc
 file    arch/arm/samsung/exynos_rtc.c		exynos_rtc
 
 # Multi Core timer
-device	mct
+device	mct : mpcorebus
 attach	mct at fdt with exyo_mct
 file	arch/arm/samsung/mct.c			exyo_mct
 

Index: src/sys/arch/evbarm/conf/EXYNOS
diff -u src/sys/arch/evbarm/conf/EXYNOS:1.32 src/sys/arch/evbarm/conf/EXYNOS:1.33
--- src/sys/arch/evbarm/conf/EXYNOS:1.32	Sun Aug 19 07:27:33 2018
+++ src/sys/arch/evbarm/conf/EXYNOS	Tue Sep 11 10:06:53 2018
@@ -1,5 +1,5 @@
 #
-#	$NetBSD: EXYNOS,v 1.32 2018/08/19 07:27:33 skrll Exp $
+#	$NetBSD: EXYNOS,v 1.33 2018/09/11 10:06:53 jmcneill Exp $
 #
 #	Samsung Exynos SoC kernel
 #
@@ -54,8 +54,9 @@ syscon*		at fdt? pass 1		# Generic Syste
 
 # Timer
 mct*		at fdt? pass 2		# Exynos Multi Core Timer (MCT)
+armgtmr*	at mct?
 gtmr*		at fdt? pass 2
-armgtmr0	at gtmr?
+armgtmr*	at gtmr?
 
 # Interrupt controller
 exyointr*	at fdt? pass 1

Index: src/sys/arch/evbarm/exynos/exynos_start.S
diff -u src/sys/arch/evbarm/exynos/exynos_start.S:1.7 src/sys/arch/evbarm/exynos/exynos_start.S:1.8
--- src/sys/arch/evbarm/exynos/exynos_start.S:1.7	Sun Aug 19 07:27:33 2018
+++ src/sys/arch/evbarm/exynos/exynos_start.S	Tue Sep 11 10:06:53 2018
@@ -1,4 +1,4 @@
-/*	$NetBSD: exynos_start.S,v 1.7 2018/08/19 07:27:33 skrll Exp $	*/
+/*	$NetBSD: exynos_start.S,v 1.8 2018/09/11 10:06:53 jmcneill Exp $	*/
 
 /*-
  * Copyright (c) 2014 The NetBSD Foundation, Inc.
@@ -46,7 +46,7 @@
 
 #include <evbarm/exynos/platform.h>
 
-RCSID("$NetBSD: exynos_start.S,v 1.7 2018/08/19 07:27:33 skrll Exp $")
+RCSID("$NetBSD: exynos_start.S,v 1.8 2018/09/11 10:06:53 jmcneill Exp $")
 
 #if defined(KERNEL_BASES_EQUAL)
 #define CALL(f)		bl	_C_LABEL(f)
@@ -242,7 +242,6 @@ mmu_init_table:
 		EXYNOS_CORE_SIZE / L1_S_SIZE,
 		L1_S_PROTO_armv7 | L1_S_APv7_KRW | L1_S_V6_XN)
 
-#if 0
 	/* Map EXYNOS AUDIOBASE */
 	MMU_INIT(EXYNOS5_AUDIOCORE_VBASE, EXYNOS5_AUDIOCORE_VBASE,
 	        EXYNOS5_AUDIOCORE_SIZE / L1_S_SIZE,
@@ -262,7 +261,6 @@ mmu_init_table:
 	MMU_INIT(EXYNOS5_SYSRAM_PBASE, EXYNOS5_SYSRAM_PBASE,
 	        EXYNOS5_SYSRAM_SIZE / L1_S_SIZE,
 		L1_S_PROTO_armv7 | L1_S_APv7_KRW | L1_S_V6_XN)
-#endif
 
 	/* Map DTB location in SDRAM, patched in later */
 .Lmmu_init_table_dtb:

Reply via email to