svn commit: r291008 - in head/sys: conf powerpc/mpc85xx

Justin Hibbits jhibbits at FreeBSD.org
Wed Nov 18 01:54:20 UTC 2015


Author: jhibbits
Date: Wed Nov 18 01:54:19 2015
New Revision: 291008
URL: https://svnweb.freebsd.org/changeset/base/291008

Log:
  Add support for new LAW registers in QorIQ SoCs.
  
  QorIQ SoCs (e5500 core, P5 family) have 2 BARs for local access windows, while
  MPC85XX, and P1/P2 families use only a single BAR register.
  
  This also adds the QORIQ_DPAA option, mutually exclusive to MPC85XX, to handle
  this difference.
  
  Obtained from:	Semihalf
  Sponsored by:	Alex Perez/Inertial Computing

Modified:
  head/sys/conf/files.powerpc
  head/sys/conf/options.powerpc
  head/sys/powerpc/mpc85xx/mpc85xx.c
  head/sys/powerpc/mpc85xx/mpc85xx.h

Modified: head/sys/conf/files.powerpc
==============================================================================
--- head/sys/conf/files.powerpc	Tue Nov 17 21:29:26 2015	(r291007)
+++ head/sys/conf/files.powerpc	Wed Nov 18 01:54:19 2015	(r291008)
@@ -74,7 +74,7 @@ dev/syscons/scvtb.c		optional	sc
 dev/tsec/if_tsec.c		optional	tsec
 dev/tsec/if_tsec_fdt.c		optional	tsec fdt
 dev/uart/uart_cpu_powerpc.c	optional	uart
-dev/usb/controller/ehci_fsl.c	optional	ehci mpc85xx
+dev/usb/controller/ehci_fsl.c	optional	ehci mpc85xx | ehci qoriq_dpaa
 dev/vt/hw/ofwfb/ofwfb.c		optional	vt aim
 kern/kern_clocksource.c		standard
 kern/subr_dummy_vdso_tc.c	standard
@@ -133,15 +133,15 @@ powerpc/mikrotik/platform_rb.c	optional	
 powerpc/mpc85xx/atpic.c		optional	mpc85xx isa
 powerpc/mpc85xx/ds1553_bus_fdt.c	optional	ds1553 fdt
 powerpc/mpc85xx/ds1553_core.c	optional	ds1553
-powerpc/mpc85xx/fsl_sdhc.c	optional	mpc85xx sdhc
+powerpc/mpc85xx/fsl_sdhc.c	optional	mpc85xx sdhc | qoriq_dpaa sdhc
 powerpc/mpc85xx/i2c.c		optional	iicbus fdt
 powerpc/mpc85xx/isa.c		optional	mpc85xx isa
-powerpc/mpc85xx/lbc.c		optional	mpc85xx
-powerpc/mpc85xx/mpc85xx.c	optional	mpc85xx
+powerpc/mpc85xx/lbc.c		optional	mpc85xx | qoriq_dpaa
+powerpc/mpc85xx/mpc85xx.c	optional	mpc85xx | qoriq_dpaa
 powerpc/mpc85xx/mpc85xx_gpio.c	optional	mpc85xx gpio
-powerpc/mpc85xx/platform_mpc85xx.c	optional	mpc85xx
-powerpc/mpc85xx/pci_mpc85xx.c	optional	pci mpc85xx
-powerpc/mpc85xx/pci_mpc85xx_pcib.c	optional	pci mpc85xx
+powerpc/mpc85xx/platform_mpc85xx.c	optional	mpc85xx | qoriq_dpaa
+powerpc/mpc85xx/pci_mpc85xx.c	optional	pci mpc85xx | pci qoriq_dpaa
+powerpc/mpc85xx/pci_mpc85xx_pcib.c	optional	pci mpc85xx | pci qoriq_dpaa
 powerpc/ofw/ofw_machdep.c	standard
 powerpc/ofw/ofw_pci.c		optional	pci
 powerpc/ofw/ofw_pcibus.c	optional	pci

Modified: head/sys/conf/options.powerpc
==============================================================================
--- head/sys/conf/options.powerpc	Tue Nov 17 21:29:26 2015	(r291007)
+++ head/sys/conf/options.powerpc	Wed Nov 18 01:54:19 2015	(r291008)
@@ -21,6 +21,7 @@ GFB_NO_MODE_CHANGE	opt_gfb.h
 MPC85XX			opt_platform.h
 POWERMAC		opt_platform.h
 PS3			opt_platform.h
+QORIQ_DPAA		opt_platform.h
 MAMBO
 PSERIES
 PSIM

Modified: head/sys/powerpc/mpc85xx/mpc85xx.c
==============================================================================
--- head/sys/powerpc/mpc85xx/mpc85xx.c	Tue Nov 17 21:29:26 2015	(r291007)
+++ head/sys/powerpc/mpc85xx/mpc85xx.c	Wed Nov 18 01:54:19 2015	(r291008)
@@ -27,6 +27,7 @@
 #include <sys/cdefs.h>
 __FBSDID("$FreeBSD$");
 
+#include "opt_platform.h"
 #include <sys/param.h>
 #include <sys/systm.h>
 #include <sys/lock.h>
@@ -45,6 +46,7 @@ __FBSDID("$FreeBSD$");
 
 #include <powerpc/mpc85xx/mpc85xx.h>
 
+
 /*
  * MPC85xx system specific routines
  */
@@ -70,70 +72,133 @@ int
 law_getmax(void)
 {
 	uint32_t ver;
+	int law_max;
 
 	ver = SVR_VER(mfspr(SPR_SVR));
-	if (ver == SVR_MPC8555E || ver == SVR_MPC8555)
-		return (8);
-	if (ver == SVR_MPC8548E || ver == SVR_MPC8548 ||
-	    ver == SVR_MPC8533E || ver == SVR_MPC8533)
-		return (10);
+	switch (ver) {
+	case SVR_MPC8555:
+	case SVR_MPC8555E:
+		law_max = 8;
+		break;
+	case SVR_MPC8533:
+	case SVR_MPC8533E:
+	case SVR_MPC8548:
+	case SVR_MPC8548E:
+		law_max = 10;
+		break;
+	case SVR_P5020:
+	case SVR_P5020E:
+		law_max = 32;
+		break;
+	default:
+		law_max = 8;
+	}
 
-	return (12);
+	return (law_max);
+}
+
+static inline void
+law_write(uint32_t n, uint64_t bar, uint32_t sr)
+{
+#if defined(QORIQ_DPAA)
+	ccsr_write4(OCP85XX_LAWBARH(n), bar >> 32);
+	ccsr_write4(OCP85XX_LAWBARL(n), bar);
+#else
+	ccsr_write4(OCP85XX_LAWBAR(n), bar >> 12);
+#endif
+	ccsr_write4(OCP85XX_LAWSR(n), sr);
+
+	/*
+	 * The last write to LAWAR should be followed by a read
+	 * of LAWAR before any device try to use any of windows.
+	 * What more the read of LAWAR should be followed by isync
+	 * instruction.
+	 */
+
+	ccsr_read4(OCP85XX_LAWSR(n));
+	isync();
+}
+
+static inline void
+law_read(uint32_t n, uint64_t *bar, uint32_t *sr)
+{
+#if defined(QORIQ_DPAA)
+	*bar = (uint64_t)ccsr_read4(OCP85XX_LAWBARH(n)) << 32 |
+	    ccsr_read4(OCP85XX_LAWBARL(n));
+#else
+	*bar = (uint64_t)ccsr_read4(OCP85XX_LAWBAR(n)) << 12;
+#endif
+	*sr = ccsr_read4(OCP85XX_LAWSR(n));
+}
+
+static int
+law_find_free(void)
+{
+	uint32_t i,sr;
+	uint64_t bar;
+	int law_max;
+
+	law_max = law_getmax();
+	/* Find free LAW */
+	for (i = 0; i < law_max; i++) {
+		law_read(i, &bar, &sr);
+		if ((sr & 0x80000000) == 0)
+			break;
+	}
+
+	return (i);
 }
 
 #define	_LAW_SR(trgt,size)	(0x80000000 | (trgt << 20) | (ffsl(size) - 2))
-#define	_LAW_BAR(addr)		(addr >> 12)
 
 int
-law_enable(int trgt, u_long addr, u_long size)
+law_enable(int trgt, uint64_t bar, uint32_t size)
 {
-	uint32_t bar, sr;
+	uint64_t bar_tmp;
+	uint32_t sr, sr_tmp;
 	int i, law_max;
 
 	if (size == 0)
 		return (0);
 
 	law_max = law_getmax();
-	bar = _LAW_BAR(addr);
 	sr = _LAW_SR(trgt, size);
 
 	/* Bail if already programmed. */
-	for (i = 0; i < law_max; i++)
-		if (sr == ccsr_read4(OCP85XX_LAWSR(i)) &&
-		    bar == ccsr_read4(OCP85XX_LAWBAR(i)))
+	for (i = 0; i < law_max; i++) {
+		law_read(i, &bar_tmp, &sr_tmp);
+		if (sr == sr_tmp && bar == bar_tmp)
 			return (0);
+	}
 
 	/* Find an unused access window. */
-	for (i = 0; i < law_max; i++)
-		if ((ccsr_read4(OCP85XX_LAWSR(i)) & 0x80000000) == 0)
-			break;
+	i = law_find_free();
 
 	if (i == law_max)
 		return (ENOSPC);
 
-	ccsr_write4(OCP85XX_LAWBAR(i), bar);
-	ccsr_write4(OCP85XX_LAWSR(i), sr);
+	law_write(i, bar, sr);
 	return (0);
 }
 
 int
-law_disable(int trgt, u_long addr, u_long size)
+law_disable(int trgt, uint64_t bar, uint32_t size)
 {
-	uint32_t bar, sr;
+	uint64_t bar_tmp;
+	uint32_t sr, sr_tmp;
 	int i, law_max;
 
 	law_max = law_getmax();
-	bar = _LAW_BAR(addr);
 	sr = _LAW_SR(trgt, size);
 
 	/* Find and disable requested LAW. */
-	for (i = 0; i < law_max; i++)
-		if (sr == ccsr_read4(OCP85XX_LAWSR(i)) &&
-		    bar == ccsr_read4(OCP85XX_LAWBAR(i))) {
-			ccsr_write4(OCP85XX_LAWBAR(i), 0);
-			ccsr_write4(OCP85XX_LAWSR(i), 0);
+	for (i = 0; i < law_max; i++) {
+		law_read(i, &bar_tmp, &sr_tmp);
+		if (sr == sr_tmp && bar == bar_tmp) {
+			law_write(i, 0, 0);
 			return (0);
 		}
+	}
 
 	return (ENOENT);
 }
@@ -152,18 +217,22 @@ law_pci_target(struct resource *res, int
 	rv = 0;
 	trgt = -1;
 	switch (start) {
+	case 0x0000:
 	case 0x8000:
 		trgt = 0;
 		break;
+	case 0x1000:
 	case 0x9000:
 		trgt = 1;
 		break;
+	case 0x2000:
 	case 0xa000:
 		if (ver == SVR_MPC8548E || ver == SVR_MPC8548)
 			trgt = 3;
 		else
 			trgt = 2;
 		break;
+	case 0x3000:
 	case 0xb000:
 		if (ver == SVR_MPC8548E || ver == SVR_MPC8548)
 			rv = EINVAL;

Modified: head/sys/powerpc/mpc85xx/mpc85xx.h
==============================================================================
--- head/sys/powerpc/mpc85xx/mpc85xx.h	Tue Nov 17 21:29:26 2015	(r291007)
+++ head/sys/powerpc/mpc85xx/mpc85xx.h	Wed Nov 18 01:54:19 2015	(r291008)
@@ -48,14 +48,35 @@ extern vm_offset_t		ccsrbar_va;
 /*
  * Local access registers
  */
-#define	OCP85XX_LAWBAR(n)	(CCSRBAR_VA + 0xc08 + 0x20 * (n))
-#define	OCP85XX_LAWSR(n)	(CCSRBAR_VA + 0xc10 + 0x20 * (n))
-
-#define	OCP85XX_TGTIF_LBC	4
-#define	OCP85XX_TGTIF_RAM_INTL	11
-#define	OCP85XX_TGTIF_RIO	12
-#define	OCP85XX_TGTIF_RAM1	15
-#define	OCP85XX_TGTIF_RAM2	22
+#if defined(QORIQ_DPAA)
+/* Write order: OCP_LAWBARH -> OCP_LAWBARL -> OCP_LAWSR */
+#define	OCP85XX_LAWBARH(n)	(CCSRBAR_VA + 0xc00 + 0x10 * (n))
+#define	OCP85XX_LAWBARL(n)	(CCSRBAR_VA + 0xc04 + 0x10 * (n))
+#define	OCP85XX_LAWSR(n)	(CCSRBAR_VA + 0xc08 + 0x10 * (n))
+#else
+#define	OCP85XX_LAWBAR(n)	(CCSRBAR_VA + 0xc08 + 0x10 * (n))
+#define	OCP85XX_LAWSR(n)	(CCSRBAR_VA + 0xc10 + 0x10 * (n))
+#endif
+
+/* Attribute register */
+#define	OCP85XX_ENA_MASK	0x80000000
+#define	OCP85XX_DIS_MASK	0x7fffffff
+
+#if defined(QORIQ_DPAA)
+#define	OCP85XX_TGTIF_LBC	0x1f
+#define	OCP85XX_TGTIF_RAM_INTL	0x14
+#define	OCP85XX_TGTIF_RAM1	0x10
+#define	OCP85XX_TGTIF_RAM2	0x11
+#define	OCP85XX_TGTIF_BMAN	0x18
+#define	OCP85XX_TGTIF_QMAN	0x3C
+#define	OCP85XX_TRGT_SHIFT	20
+#else
+#define	OCP85XX_TGTIF_LBC	0x04
+#define	OCP85XX_TGTIF_RAM_INTL	0x0b
+#define	OCP85XX_TGTIF_RIO	0x0c
+#define	OCP85XX_TGTIF_RAM1	0x0f
+#define	OCP85XX_TGTIF_RAM2	0x16
+#endif
 
 /*
  * L2 cache registers
@@ -81,8 +102,8 @@ extern vm_offset_t		ccsrbar_va;
  */
 uint32_t ccsr_read4(uintptr_t addr);
 void ccsr_write4(uintptr_t addr, uint32_t val);
-int law_enable(int trgt, u_long addr, u_long size);
-int law_disable(int trgt, u_long addr, u_long size);
+int law_enable(int trgt, uint64_t bar, uint32_t size);
+int law_disable(int trgt, uint64_t bar, uint32_t size);
 int law_getmax(void);
 int law_pci_target(struct resource *, int *, int *);
 


More information about the svn-src-all mailing list