Module Name: src
Committed By: jmcneill
Date: Fri Oct 10 07:36:11 UTC 2014
Modified Files:
src/sys/arch/arm/allwinner: awin_board.c awin_intr.h awin_io.c
awin_mmc.c awin_reg.h awin_usb.c awin_wdt.c
Log Message:
Work-in-progress support for the AllWinner A31 SoC.
To generate a diff of this commit:
cvs rdiff -u -r1.20 -r1.21 src/sys/arch/arm/allwinner/awin_board.c
cvs rdiff -u -r1.4 -r1.5 src/sys/arch/arm/allwinner/awin_intr.h
cvs rdiff -u -r1.15 -r1.16 src/sys/arch/arm/allwinner/awin_io.c
cvs rdiff -u -r1.11 -r1.12 src/sys/arch/arm/allwinner/awin_mmc.c
cvs rdiff -u -r1.26 -r1.27 src/sys/arch/arm/allwinner/awin_reg.h
cvs rdiff -u -r1.13 -r1.14 src/sys/arch/arm/allwinner/awin_usb.c
cvs rdiff -u -r1.3 -r1.4 src/sys/arch/arm/allwinner/awin_wdt.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/arm/allwinner/awin_board.c
diff -u src/sys/arch/arm/allwinner/awin_board.c:1.20 src/sys/arch/arm/allwinner/awin_board.c:1.21
--- src/sys/arch/arm/allwinner/awin_board.c:1.20 Sat Oct 4 19:38:17 2014
+++ src/sys/arch/arm/allwinner/awin_board.c Fri Oct 10 07:36:11 2014
@@ -1,4 +1,4 @@
-/* $NetBSD: awin_board.c,v 1.20 2014/10/04 19:38:17 martin Exp $ */
+/* $NetBSD: awin_board.c,v 1.21 2014/10/10 07:36:11 jmcneill Exp $ */
/*-
* Copyright (c) 2012 The NetBSD Foundation, Inc.
* All rights reserved.
@@ -35,7 +35,7 @@
#include <sys/cdefs.h>
-__KERNEL_RCSID(1, "$NetBSD: awin_board.c,v 1.20 2014/10/04 19:38:17 martin Exp $");
+__KERNEL_RCSID(1, "$NetBSD: awin_board.c,v 1.21 2014/10/10 07:36:11 jmcneill Exp $");
#include <sys/param.h>
#include <sys/bus.h>
@@ -123,8 +123,11 @@ static void
awin_cpu_clk(void)
{
struct cpu_info * const ci = curcpu();
+ u_int reg = awin_chip_id() == AWIN_CHIP_ID_A31 ?
+ AWIN_A31_CPU_AXI_CFG_REG :
+ AWIN_CPU_AHB_APB0_CFG_REG;
const uint32_t cpu0_cfg = bus_space_read_4(&awin_bs_tag, awin_core_bsh,
- AWIN_CCM_OFFSET + AWIN_CPU_AHB_APB0_CFG_REG);
+ AWIN_CCM_OFFSET + reg);
const u_int cpu_clk_sel = __SHIFTIN(cpu0_cfg, AWIN_CPU_CLK_SRC_SEL);
switch (__SHIFTOUT(cpu_clk_sel, AWIN_CPU_CLK_SRC_SEL)) {
case AWIN_CPU_CLK_SRC_SEL_LOSC:
@@ -136,10 +139,18 @@ awin_cpu_clk(void)
case AWIN_CPU_CLK_SRC_SEL_PLL1: {
const uint32_t pll1_cfg = bus_space_read_4(&awin_bs_tag,
awin_core_bsh, AWIN_CCM_OFFSET + AWIN_PLL1_CFG_REG);
- u_int p = __SHIFTOUT(pll1_cfg, AWIN_PLL_CFG_OUT_EXP_DIVP);
- u_int n = __SHIFTOUT(pll1_cfg, AWIN_PLL_CFG_FACTOR_N);
- u_int k = __SHIFTOUT(pll1_cfg, AWIN_PLL_CFG_FACTOR_K) + 1;
- u_int m = __SHIFTOUT(pll1_cfg, AWIN_PLL_CFG_FACTOR_M) + 1;
+ u_int p, n, k, m;
+ if (awin_chip_id() == AWIN_CHIP_ID_A31) {
+ p = 0;
+ n = __SHIFTOUT(pll1_cfg, AWIN_PLL_CFG_FACTOR_N) + 1;
+ k = __SHIFTOUT(pll1_cfg, AWIN_PLL_CFG_FACTOR_K) + 1;
+ m = __SHIFTOUT(pll1_cfg, AWIN_PLL_CFG_FACTOR_M) + 1;
+ } else {
+ p = __SHIFTOUT(pll1_cfg, AWIN_PLL_CFG_OUT_EXP_DIVP);
+ n = __SHIFTOUT(pll1_cfg, AWIN_PLL_CFG_FACTOR_N);
+ k = __SHIFTOUT(pll1_cfg, AWIN_PLL_CFG_FACTOR_K) + 1;
+ m = __SHIFTOUT(pll1_cfg, AWIN_PLL_CFG_FACTOR_M) + 1;
+ }
ci->ci_data.cpu_cc_freq =
((uint64_t)AWIN_REF_FREQ * (n ? n : 1) * k / m) >> p;
break;
@@ -185,11 +196,24 @@ awin_bootstrap(vaddr_t iobase, vaddr_t u
#endif
#ifdef VERBOSE_INIT_ARM
- uint32_t s0 = bus_space_read_4(&awin_bs_tag, awin_core_bsh,
- AWIN_CPUCFG_OFFSET + AWIN_CPUCFG_CPU0_STATUS_REG);
- uint32_t s1 = bus_space_read_4(&awin_bs_tag, awin_core_bsh,
- AWIN_CPUCFG_OFFSET + AWIN_CPUCFG_CPU1_STATUS_REG);
- printf("%s: cpu status: 0=%#x 1=%#x\n", __func__, s0, s1);
+ if (awin_chip_id() == AWIN_CHIP_ID_A31) {
+ uint32_t s0 = bus_space_read_4(&awin_bs_tag, awin_core_bsh,
+ AWIN_A31_CPUCFG_OFFSET + AWIN_A31_CPUCFG_CPU0_STATUS_REG);
+ uint32_t s1 = bus_space_read_4(&awin_bs_tag, awin_core_bsh,
+ AWIN_A31_CPUCFG_OFFSET + AWIN_A31_CPUCFG_CPU1_STATUS_REG);
+ uint32_t s2 = bus_space_read_4(&awin_bs_tag, awin_core_bsh,
+ AWIN_A31_CPUCFG_OFFSET + AWIN_A31_CPUCFG_CPU2_STATUS_REG);
+ uint32_t s3 = bus_space_read_4(&awin_bs_tag, awin_core_bsh,
+ AWIN_A31_CPUCFG_OFFSET + AWIN_A31_CPUCFG_CPU3_STATUS_REG);
+ printf("%s: cpu status: 0=%#x 1=%#x 2=%#x 3=%#x\n", __func__,
+ s0, s1, s2, s3);
+ } else {
+ uint32_t s0 = bus_space_read_4(&awin_bs_tag, awin_core_bsh,
+ AWIN_CPUCFG_OFFSET + AWIN_CPUCFG_CPU0_STATUS_REG);
+ uint32_t s1 = bus_space_read_4(&awin_bs_tag, awin_core_bsh,
+ AWIN_CPUCFG_OFFSET + AWIN_CPUCFG_CPU1_STATUS_REG);
+ printf("%s: cpu status: 0=%#x 1=%#x\n", __func__, s0, s1);
+ }
#endif
#if !defined(MULTIPROCESSOR) && defined(VERBOSE_INIT_ARM)
@@ -228,16 +252,27 @@ awin_cpu_hatch(struct cpu_info *ci)
psize_t
awin_memprobe(void)
{
- const uint32_t dcr = bus_space_read_4(&awin_bs_tag, awin_core_bsh,
- AWIN_DRAM_OFFSET + AWIN_DRAM_DCR_REG);
+ psize_t memsize;
- psize_t memsize = (__SHIFTOUT(dcr, AWIN_DRAM_DCR_BUS_WIDTH) + 1)
- / __SHIFTOUT(dcr, AWIN_DRAM_DCR_IO_WIDTH);
- memsize *= 1 << (__SHIFTOUT(dcr, AWIN_DRAM_DCR_CHIP_DENSITY) + 28 - 3);
+ if (awin_chip_id() == AWIN_CHIP_ID_A31) {
#ifdef VERBOSE_INIT_ARM
- printf("sdram_config = %#x, memsize = %uMB\n", dcr,
- (u_int)(memsize >> 20));
+ printf("memprobe not supported on A31\n");
#endif
+ memsize = 0;
+ } else {
+ const uint32_t dcr = bus_space_read_4(&awin_bs_tag,
+ awin_core_bsh,
+ AWIN_DRAM_OFFSET + AWIN_DRAM_DCR_REG);
+
+ memsize = (__SHIFTOUT(dcr, AWIN_DRAM_DCR_BUS_WIDTH) + 1)
+ / __SHIFTOUT(dcr, AWIN_DRAM_DCR_IO_WIDTH);
+ memsize *= 1 << (__SHIFTOUT(dcr, AWIN_DRAM_DCR_CHIP_DENSITY)
+ + 28 - 3);
+#ifdef VERBOSE_INIT_ARM
+ printf("sdram_config = %#x, memsize = %uMB\n", dcr,
+ (u_int)(memsize >> 20));
+#endif
+ }
return memsize;
}
Index: src/sys/arch/arm/allwinner/awin_intr.h
diff -u src/sys/arch/arm/allwinner/awin_intr.h:1.4 src/sys/arch/arm/allwinner/awin_intr.h:1.5
--- src/sys/arch/arm/allwinner/awin_intr.h:1.4 Wed Sep 3 21:42:46 2014
+++ src/sys/arch/arm/allwinner/awin_intr.h Fri Oct 10 07:36:11 2014
@@ -1,4 +1,4 @@
-/* $NetBSD: awin_intr.h,v 1.4 2014/09/03 21:42:46 jmcneill Exp $ */
+/* $NetBSD: awin_intr.h,v 1.5 2014/10/10 07:36:11 jmcneill Exp $ */
/*-
* Copyright (c) 2013 The NetBSD Foundation, Inc.
* All rights reserved.
@@ -134,4 +134,21 @@
#define AWIN_IRQ_TWI4 121
#define AWIN_IRQ_IIS2 122
+/*
+ * A31
+ */
+#define AWIN_A31_IRQ_UART0 32
+#define AWIN_A31_IRQ_AC 61
+#define AWIN_A31_IRQ_DMA 82
+#define AWIN_A31_IRQ_SDMMC0 92
+#define AWIN_A31_IRQ_SDMMC1 93
+#define AWIN_A31_IRQ_SDMMC2 94
+#define AWIN_A31_IRQ_SDMMC3 95
+#define AWIN_A31_IRQ_USB0 103
+#define AWIN_A31_IRQ_USB1 104
+#define AWIN_A31_IRQ_USB2 105
+#define AWIN_A31_IRQ_USB3 106
+#define AWIN_A31_IRQ_USB4 108
+#define AWIN_A31_IRQ_GMAC 114
+
#endif /* _ARM_ALLWINNER_AWIN_INTR_H_ */
Index: src/sys/arch/arm/allwinner/awin_io.c
diff -u src/sys/arch/arm/allwinner/awin_io.c:1.15 src/sys/arch/arm/allwinner/awin_io.c:1.16
--- src/sys/arch/arm/allwinner/awin_io.c:1.15 Thu Sep 11 02:21:19 2014
+++ src/sys/arch/arm/allwinner/awin_io.c Fri Oct 10 07:36:11 2014
@@ -31,7 +31,7 @@
#include <sys/cdefs.h>
-__KERNEL_RCSID(1, "$NetBSD: awin_io.c,v 1.15 2014/09/11 02:21:19 jmcneill Exp $");
+__KERNEL_RCSID(1, "$NetBSD: awin_io.c,v 1.16 2014/10/10 07:36:11 jmcneill Exp $");
#include <sys/param.h>
#include <sys/bus.h>
@@ -94,27 +94,33 @@ awinio_print(void *aux, const char *pnp)
static const struct awin_locators awin_locators[] = {
{ "awinicu", OFFANDSIZE(INTC), NOPORT, NOINTR, A10|REQ },
{ "awingpio", OFFANDSIZE(PIO), NOPORT, NOINTR, AANY|REQ },
- { "awindma", OFFANDSIZE(DMA), NOPORT, AWIN_IRQ_DMA, AANY|REQ },
+ { "awindma", OFFANDSIZE(DMA), NOPORT, AWIN_IRQ_DMA, A10|A20|REQ },
+ { "awindma", OFFANDSIZE(DMA), NOPORT, AWIN_A31_IRQ_DMA, A31|REQ },
{ "awintmr", OFFANDSIZE(TMR), NOPORT, AWIN_IRQ_TMR0, A10 },
- { "com", OFFANDSIZE(UART0), 0, AWIN_IRQ_UART0, AANY },
- { "com", OFFANDSIZE(UART1), 1, AWIN_IRQ_UART1, AANY },
- { "com", OFFANDSIZE(UART2), 2, AWIN_IRQ_UART2, AANY },
- { "com", OFFANDSIZE(UART3), 3, AWIN_IRQ_UART3, AANY },
- { "com", OFFANDSIZE(UART4), 4, AWIN_IRQ_UART4, AANY },
- { "com", OFFANDSIZE(UART5), 5, AWIN_IRQ_UART5, AANY },
- { "com", OFFANDSIZE(UART6), 6, AWIN_IRQ_UART6, AANY },
- { "com", OFFANDSIZE(UART7), 7, AWIN_IRQ_UART7, AANY },
+ { "com", OFFANDSIZE(UART0), 0, AWIN_IRQ_UART0, A10|A20 },
+ { "com", OFFANDSIZE(UART1), 1, AWIN_IRQ_UART1, A10|A20 },
+ { "com", OFFANDSIZE(UART2), 2, AWIN_IRQ_UART2, A10|A20 },
+ { "com", OFFANDSIZE(UART3), 3, AWIN_IRQ_UART3, A10|A20 },
+ { "com", OFFANDSIZE(UART4), 4, AWIN_IRQ_UART4, A10|A20 },
+ { "com", OFFANDSIZE(UART5), 5, AWIN_IRQ_UART5, A10|A20 },
+ { "com", OFFANDSIZE(UART6), 6, AWIN_IRQ_UART6, A10|A20 },
+ { "com", OFFANDSIZE(UART7), 7, AWIN_IRQ_UART7, A10|A20 },
+ { "com", OFFANDSIZE(UART0), 0, AWIN_A31_IRQ_UART0, A31 },
{ "awinwdt", OFFANDSIZE(TMR), NOPORT, NOINTR, AANY },
{ "awinrtc", OFFANDSIZE(TMR), NOPORT, NOINTR, AANY },
{ "awinhdmi", OFFANDSIZE(HDMI), NOPORT, AWIN_IRQ_HDMI0, A20 },
- { "awinusb", OFFANDSIZE(USB1), 0, NOINTR, AANY },
- { "awinusb", OFFANDSIZE(USB2), 1, NOINTR, AANY },
- { "motg", OFFANDSIZE(USB0), NOPORT, AWIN_IRQ_USB0, AANY },
- { "awinmmc", OFFANDSIZE(SDMMC0), 0, AWIN_IRQ_SDMMC0, AANY },
- { "awinmmc", OFFANDSIZE(SDMMC1), 1, AWIN_IRQ_SDMMC1, AANY },
- { "awinmmc", OFFANDSIZE(SDMMC2), 2, AWIN_IRQ_SDMMC2, AANY },
- { "awinmmc", OFFANDSIZE(SDMMC3), 3, AWIN_IRQ_SDMMC3, AANY },
- { "awinmmc", OFFANDSIZE(SDMMC1), 4, AWIN_IRQ_SDMMC1, AANY },
+ { "awinusb", OFFANDSIZE(USB1), 0, NOINTR, A10|A20 },
+ { "awinusb", OFFANDSIZE(USB2), 1, NOINTR, A10|A20 },
+ { "awinusb", OFFANDSIZE(A31_USB1), 0, NOINTR, A31 },
+ { "awinusb", OFFANDSIZE(A31_USB2), 1, NOINTR, A31 },
+ { "motg", OFFANDSIZE(USB0), NOPORT, AWIN_IRQ_USB0, A10|A20 },
+ { "motg", OFFANDSIZE(A31_USB0), NOPORT, AWIN_A31_IRQ_USB0, A31 },
+ { "awinmmc", OFFANDSIZE(SDMMC0), 0, AWIN_IRQ_SDMMC0, A10|A20 },
+ { "awinmmc", OFFANDSIZE(SDMMC1), 1, AWIN_IRQ_SDMMC1, A10|A20 },
+ { "awinmmc", OFFANDSIZE(SDMMC2), 2, AWIN_IRQ_SDMMC2, A10|A20 },
+ { "awinmmc", OFFANDSIZE(SDMMC3), 3, AWIN_IRQ_SDMMC3, A10|A20 },
+ { "awinmmc", OFFANDSIZE(SDMMC1), 4, AWIN_IRQ_SDMMC1, A10|A20 },
+ { "awinmmc", OFFANDSIZE(SDMMC0), 0, AWIN_A31_IRQ_SDMMC0, A31 },
{ "ahcisata", OFFANDSIZE(SATA), NOPORT, AWIN_IRQ_SATA, AANY },
{ "awiniic", OFFANDSIZE(TWI0), 0, AWIN_IRQ_TWI0, AANY },
{ "awiniic", OFFANDSIZE(TWI1), 1, AWIN_IRQ_TWI1, AANY },
@@ -126,9 +132,11 @@ static const struct awin_locators awin_l
{ "spi", OFFANDSIZE(SPI2), 1, AWIN_IRQ_SPI2, AANY },
{ "spi", OFFANDSIZE(SPI3), 3, AWIN_IRQ_SPI3, AANY },
{ "awe", OFFANDSIZE(EMAC), NOPORT, AWIN_IRQ_EMAC, AANY },
- { "awge", OFFANDSIZE(GMAC), NOPORT, AWIN_IRQ_GMAC, A20|A31 },
+ { "awge", OFFANDSIZE(GMAC), NOPORT, AWIN_IRQ_GMAC, A20 },
+ { "awge", OFFANDSIZE(GMAC), NOPORT, AWIN_A31_IRQ_GMAC, A31 },
{ "awincrypto", OFFANDSIZE(SS), NOPORT, AWIN_IRQ_SS, AANY },
- { "awinac", OFFANDSIZE(AC), NOPORT, AWIN_IRQ_AC, AANY },
+ { "awinac", OFFANDSIZE(AC), NOPORT, AWIN_IRQ_AC, A10|A20 },
+ { "awinac", OFFANDSIZE(AC), NOPORT, AWIN_A31_IRQ_AC, A31 },
};
static int
Index: src/sys/arch/arm/allwinner/awin_mmc.c
diff -u src/sys/arch/arm/allwinner/awin_mmc.c:1.11 src/sys/arch/arm/allwinner/awin_mmc.c:1.12
--- src/sys/arch/arm/allwinner/awin_mmc.c:1.11 Fri Oct 3 11:23:29 2014
+++ src/sys/arch/arm/allwinner/awin_mmc.c Fri Oct 10 07:36:11 2014
@@ -1,4 +1,4 @@
-/* $NetBSD: awin_mmc.c,v 1.11 2014/10/03 11:23:29 jmcneill Exp $ */
+/* $NetBSD: awin_mmc.c,v 1.12 2014/10/10 07:36:11 jmcneill Exp $ */
/*-
* Copyright (c) 2014 Jared D. McNeill <[email protected]>
@@ -29,7 +29,7 @@
#include "locators.h"
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: awin_mmc.c,v 1.11 2014/10/03 11:23:29 jmcneill Exp $");
+__KERNEL_RCSID(0, "$NetBSD: awin_mmc.c,v 1.12 2014/10/10 07:36:11 jmcneill Exp $");
#include <sys/param.h>
#include <sys/bus.h>
@@ -46,7 +46,6 @@ __KERNEL_RCSID(0, "$NetBSD: awin_mmc.c,v
#include <arm/allwinner/awin_var.h>
#define AWIN_MMC_NDESC 16
-#define AWIN_MMC_WATERMARK 0x20070008
static int awin_mmc_match(device_t, cfdata_t, void *);
static void awin_mmc_attach(device_t, device_t, void *);
@@ -105,6 +104,9 @@ struct awin_mmc_softc {
unsigned int sc_pll_freq;
unsigned int sc_mod_clk;
+ uint32_t sc_dma_ftrgl;
+ uint32_t sc_fifo_reg;
+
uint32_t sc_idma_xferlen;
bus_dma_segment_t sc_idma_segs[1];
int sc_idma_nsegs;
@@ -158,11 +160,24 @@ awin_mmc_probe_clocks(struct awin_mmc_so
val = bus_space_read_4(aio->aio_core_bst, aio->aio_ccm_bsh,
AWIN_PLL6_CFG_REG);
- n = (val >> 8) & 0x1f;
- k = ((val >> 4) & 3) + 1;
- p = 1 << ((val >> 16) & 3);
-
- freq = 24000000 * n * k / p;
+ if (awin_chip_id() == AWIN_CHIP_ID_A31) {
+ n = ((val >> 8) & 0x1f) + 1;
+ k = ((val >> 4) & 3) + 1;
+ freq = 24000000 * n * k / 2;
+#ifdef AWIN_MMC_DEBUG
+ device_printf(sc->sc_dev, "n = %d k = %d freq = %u\n",
+ n, k, freq);
+#endif
+ } else {
+ n = (val >> 8) & 0x1f;
+ k = ((val >> 4) & 3) + 1;
+ p = 1 << ((val >> 16) & 3);
+ freq = 24000000 * n * k / p;
+#ifdef AWIN_MMC_DEBUG
+ device_printf(sc->sc_dev, "n = %d k = %d p = %d freq = %u\n",
+ n, k, p, freq);
+#endif
+ }
sc->sc_pll_freq = freq;
div = ((sc->sc_pll_freq + 99999999) / 100000000) - 1;
@@ -275,6 +290,14 @@ awin_mmc_attach(device_t parent, device_
}
}
+ if (awin_chip_id() == AWIN_CHIP_ID_A31) {
+ sc->sc_dma_ftrgl = 0x2007000f;
+ sc->sc_fifo_reg = AWIN_A31_MMC_FIFO;
+ } else {
+ sc->sc_dma_ftrgl = 0x20070008;
+ sc->sc_fifo_reg = AWIN_MMC_FIFO;
+ }
+
if (sc->sc_use_dma) {
if (awin_mmc_idma_setup(sc) != 0) {
aprint_error_dev(self, "failed to setup DMA\n");
@@ -302,6 +325,7 @@ awin_mmc_attach_i(device_t self)
awin_mmc_host_reset(sc);
awin_mmc_bus_width(sc, 1);
+ awin_mmc_bus_clock(sc, 400);
memset(&saa, 0, sizeof(saa));
saa.saa_busname = "sdmmc";
@@ -344,6 +368,11 @@ awin_mmc_intr(void *priv)
MMC_WRITE(sc, AWIN_MMC_RINT, rint);
MMC_WRITE(sc, AWIN_MMC_MINT, mint);
+#ifdef AWIN_MMC_DEBUG
+ device_printf(sc->sc_dev, "mmc intr idst=%08X rint=%08X mint=%08X\n",
+ idst, rint, mint);
+#endif
+
if (idst) {
sc->sc_idma_idst |= idst;
cv_broadcast(&sc->sc_idst_cv);
@@ -362,7 +391,7 @@ awin_mmc_intr(void *priv)
static int
awin_mmc_wait_rint(struct awin_mmc_softc *sc, uint32_t mask, int timeout)
{
- int retry = timeout;
+ int retry;
int error;
KASSERT(mutex_owned(&sc->sc_intr_lock));
@@ -370,13 +399,22 @@ awin_mmc_wait_rint(struct awin_mmc_softc
if (sc->sc_intr_rint & mask)
return 0;
+ retry = sc->sc_use_dma ? (timeout / hz) : 10000;
+
while (retry > 0) {
- error = cv_timedwait(&sc->sc_intr_cv,
- &sc->sc_intr_lock, hz);
- if (error && error != EWOULDBLOCK)
- return error;
- if (sc->sc_intr_rint & mask)
- return 0;
+ if (sc->sc_use_dma) {
+ error = cv_timedwait(&sc->sc_intr_cv,
+ &sc->sc_intr_lock, hz);
+ if (error && error != EWOULDBLOCK)
+ return error;
+ if (sc->sc_intr_rint & mask)
+ return 0;
+ } else {
+ sc->sc_intr_rint |= MMC_READ(sc, AWIN_MMC_RINT);
+ if (sc->sc_intr_rint & mask)
+ return 0;
+ delay(1000);
+ }
--retry;
}
@@ -609,9 +647,9 @@ awin_mmc_pio_transfer(struct awin_mmc_so
if (awin_mmc_pio_wait(sc, cmd))
return ETIMEDOUT;
if (cmd->c_flags & SCF_CMD_READ) {
- datap[i] = MMC_READ(sc, AWIN_MMC_FIFO);
+ datap[i] = MMC_READ(sc, sc->sc_fifo_reg);
} else {
- MMC_WRITE(sc, AWIN_MMC_FIFO, datap[i]);
+ MMC_WRITE(sc, sc->sc_fifo_reg, datap[i]);
}
}
@@ -690,7 +728,7 @@ awin_mmc_dma_prepare(struct awin_mmc_sof
val |= AWIN_MMC_IDST_TRANSMIT_INT;
MMC_WRITE(sc, AWIN_MMC_IDIE, val);
MMC_WRITE(sc, AWIN_MMC_DLBA, desc_paddr);
- MMC_WRITE(sc, AWIN_MMC_FTRGLEVEL, AWIN_MMC_WATERMARK);
+ MMC_WRITE(sc, AWIN_MMC_FTRGLEVEL, sc->sc_dma_ftrgl);
return 0;
}
Index: src/sys/arch/arm/allwinner/awin_reg.h
diff -u src/sys/arch/arm/allwinner/awin_reg.h:1.26 src/sys/arch/arm/allwinner/awin_reg.h:1.27
--- src/sys/arch/arm/allwinner/awin_reg.h:1.26 Fri Oct 3 11:21:56 2014
+++ src/sys/arch/arm/allwinner/awin_reg.h Fri Oct 10 07:36:11 2014
@@ -52,7 +52,7 @@
#define AWIN_SRAMB_SIZE 0x00010000 /* Secure */
#define AWIN_CORE_PBASE 0x01C00000
-#define AWIN_CORE_SIZE 0x00300000
+#define AWIN_CORE_SIZE 0x00400000
#define AWIN_SRAM_OFFSET 0x00000000
#define AWIN_DRAM_OFFSET 0x00001000
#define AWIN_DMA_OFFSET 0x00002000
@@ -1687,4 +1687,52 @@ struct awin_mmc_idma_descriptor {
#define AWIN_HDMI_DDC_CLOCK_M __BITS(6,3)
#define AWIN_HDMI_DDC_CLOCK_N __BITS(2,0)
+/*
+ * A31 registers
+ */
+#define AWIN_A31_USB0_OFFSET 0x00019000 /* OTG */
+#define AWIN_A31_USB1_OFFSET 0x0001a000 /* EHCI0/OHCI0 */
+#define AWIN_A31_USB2_OFFSET 0x0001b000 /* EHCI1/OHCI1 */
+#define AWIN_A31_USB3_OFFSET 0x0001b000 /* OHCI2 */
+
+#define AWIN_A31_CPUCFG_OFFSET 0x00031C00
+
+#define AWIN_A31_CPU_AXI_CFG_REG 0x0050
+
+#define AWIN_A31_AHB_GATING0_USB_OHCI2 __BIT(31)
+#define AWIN_A31_AHB_GATING0_USB_OHCI1 __BIT(30)
+#define AWIN_A31_AHB_GATING0_USB_OHCI0 __BIT(29)
+#define AWIN_A31_AHB_GATING0_USB_EHCI1 __BIT(27)
+#define AWIN_A31_AHB_GATING0_USB_EHCI0 __BIT(26)
+#define AWIN_A31_AHB_GATING0_USB0 __BIT(24)
+
+#define AWIN_A31_USB_CLK_OHCI2_ENABLE __BIT(18)
+#define AWIN_A31_USB_CLK_OHCI1_ENABLE __BIT(17)
+#define AWIN_A31_USB_CLK_OHCI0_ENABLE __BIT(16)
+#define AWIN_A31_USB_CLK_USBPHY2_ENABLE __BIT(10)
+#define AWIN_A31_USB_CLK_USBPHY1_ENABLE __BIT(9)
+#define AWIN_A31_USB_CLK_USBPHY0_ENABLE __BIT(8)
+#define AWIN_A31_USB_CLK_PHY2_ENABLE __BIT(2)
+#define AWIN_A31_USB_CLK_PHY1_ENABLE __BIT(1)
+#define AWIN_A31_USB_CLK_PHY0_ENABLE __BIT(0)
+
+#define AWIN_A31_CPUCFG_CPU0_STATUS_REG 0x0048
+#define AWIN_A31_CPUCFG_CPU1_STATUS_REG 0x0088
+#define AWIN_A31_CPUCFG_CPU2_STATUS_REG 0x00C8
+#define AWIN_A31_CPUCFG_CPU3_STATUS_REG 0x00108
+
+#define AWIN_A31_WDOG1_IRQ_EN_REG 0x00A0
+#define AWIN_A31_WDOG1_IRQ_STA_REG 0x00A4
+#define AWIN_A31_WDOG1_CTRL_REG 0x00B0
+#define AWIN_A31_WDOG1_CFG_REG 0x00B4
+#define AWIN_A31_WDOG1_MODE_REG 0x00B8
+
+#define AWIN_A31_WDOG_CFG_CONFIG __BITS(1,0)
+#define AWIN_A31_WDOG_CFG_CONFIG_SYS 1
+#define AWIN_A31_WDOG_CFG_CONFIG_INT 2
+
+#define AWIN_A31_WDOG_MODE_EN __BIT(0)
+
+#define AWIN_A31_MMC_FIFO 0x0200
+
#endif /* _ARM_ALLWINNER_AWIN_REG_H_ */
Index: src/sys/arch/arm/allwinner/awin_usb.c
diff -u src/sys/arch/arm/allwinner/awin_usb.c:1.13 src/sys/arch/arm/allwinner/awin_usb.c:1.14
--- src/sys/arch/arm/allwinner/awin_usb.c:1.13 Sat Sep 13 17:48:00 2014
+++ src/sys/arch/arm/allwinner/awin_usb.c Fri Oct 10 07:36:11 2014
@@ -34,7 +34,7 @@
#include <sys/cdefs.h>
-__KERNEL_RCSID(1, "$NetBSD: awin_usb.c,v 1.13 2014/09/13 17:48:00 jmcneill Exp $");
+__KERNEL_RCSID(1, "$NetBSD: awin_usb.c,v 1.14 2014/10/10 07:36:11 jmcneill Exp $");
#include <sys/param.h>
#include <sys/bus.h>
@@ -90,6 +90,8 @@ struct awinusb_attach_args {
#if NOHCI > 0
static const int awinusb_ohci_irqs[2] = { AWIN_IRQ_USB3, AWIN_IRQ_USB4 };
+static const int awinusb_ohci_irqs_a31[2] = { AWIN_A31_IRQ_USB3,
+ AWIN_A31_IRQ_USB4 };
#ifdef OHCI_DEBUG
#define OHCI_DPRINTF(x) if (ohcidebug) printf x
@@ -145,7 +147,9 @@ ohci_awinusb_attach(device_t parent, dev
/* Attach usb device. */
sc->sc_child = config_found(self, &sc->sc_bus, usbctlprint);
- const int irq = awinusb_ohci_irqs[usbaa->usbaa_port];
+ const int irq = awin_chip_id() == AWIN_CHIP_ID_A31 ?
+ awinusb_ohci_irqs_a31[usbaa->usbaa_port] :
+ awinusb_ohci_irqs[usbaa->usbaa_port];
usbsc->usbsc_ohci_ih = intr_establish(irq, IPL_USB,
IST_LEVEL, ohci_intr, sc);
if (usbsc->usbsc_ohci_ih == NULL) {
@@ -169,6 +173,8 @@ static int ehci_awinusb_match(device_t,
static void ehci_awinusb_attach(device_t, device_t, void *);
static const int awinusb_ehci_irqs[2] = { AWIN_IRQ_USB1, AWIN_IRQ_USB2 };
+static const int awinusb_ehci_irqs_a31[2] = { AWIN_A31_IRQ_USB1,
+ AWIN_A31_IRQ_USB2 };
CFATTACH_DECL_NEW(ehci_awinusb, sizeof(struct ehci_softc),
ehci_awinusb_match, ehci_awinusb_attach, NULL, NULL);
@@ -218,7 +224,9 @@ ehci_awinusb_attach(device_t parent, dev
/* Attach usb device. */
sc->sc_child = config_found(self, &sc->sc_bus, usbctlprint);
- const int irq = awinusb_ehci_irqs[usbaa->usbaa_port];
+ const int irq = awin_chip_id() == AWIN_CHIP_ID_A31 ?
+ awinusb_ehci_irqs_a31[usbaa->usbaa_port] :
+ awinusb_ehci_irqs[usbaa->usbaa_port];
usbsc->usbsc_ehci_ih = intr_establish(irq, IPL_USB,
IST_LEVEL, ehci_intr, sc);
if (usbsc->usbsc_ehci_ih == NULL) {
@@ -289,6 +297,16 @@ static const uint32_t awinusb_ahb_gating
#endif
AWIN_AHB_GATING0_USB_EHCI1,
};
+static const uint32_t awinusb_ahb_gating_a31[2] = {
+#if NOHCI > 0
+ AWIN_A31_AHB_GATING0_USB_OHCI0 |
+#endif
+ AWIN_A31_AHB_GATING0_USB_EHCI0,
+#if NOHCI > 0
+ AWIN_A31_AHB_GATING0_USB_OHCI1 |
+#endif
+ AWIN_A31_AHB_GATING0_USB_EHCI1,
+};
static const uint32_t awinusb_usb_clk_set[2] = {
#if NOHCI > 0
AWIN_USB_CLK_OHCI0_ENABLE |
@@ -299,6 +317,20 @@ static const uint32_t awinusb_usb_clk_se
#endif
AWIN_USB_CLK_USBPHY_ENABLE|AWIN_USB_CLK_PHY2_ENABLE,
};
+static const uint32_t awinusb_usb_clk_set_a31[2] = {
+#if NOHCI > 0
+ AWIN_A31_USB_CLK_OHCI0_ENABLE |
+#endif
+ AWIN_A31_USB_CLK_USBPHY0_ENABLE |
+ AWIN_A31_USB_CLK_USBPHY1_ENABLE |
+ AWIN_A31_USB_CLK_PHY1_ENABLE,
+#if NOHCI > 0
+ AWIN_A31_USB_CLK_OHCI1_ENABLE |
+#endif
+ AWIN_A31_USB_CLK_USBPHY0_ENABLE |
+ AWIN_A31_USB_CLK_USBPHY2_ENABLE |
+ AWIN_A31_USB_CLK_PHY2_ENABLE,
+};
int
awinusb_match(device_t parent, cfdata_t cf, void *aux)
@@ -341,19 +373,35 @@ awinusb_attach(device_t parent, device_t
aprint_naive("\n");
aprint_normal("\n");
- /*
- * Access to the USB phy is off USB0 so make sure it's on.
- */
- awin_reg_set_clear(usbsc->usbsc_bst, aio->aio_ccm_bsh,
- AWIN_AHB_GATING0_REG,
- AWIN_AHB_GATING0_USB0 | awinusb_ahb_gating[loc->loc_port], 0);
-
-
- /*
- * Enable the USB phy for this port.
- */
- awin_reg_set_clear(usbsc->usbsc_bst, aio->aio_ccm_bsh,
- AWIN_USB_CLK_REG, awinusb_usb_clk_set[loc->loc_port], 0);
+ if (awin_chip_id() == AWIN_CHIP_ID_A31) {
+ /*
+ * Access to the USB phy is off USB0 so make sure it's on.
+ */
+ awin_reg_set_clear(usbsc->usbsc_bst, aio->aio_ccm_bsh,
+ AWIN_AHB_GATING0_REG,
+ awinusb_ahb_gating_a31[loc->loc_port], 0);
+
+ /*
+ * Enable the USB phy for this port.
+ */
+ awin_reg_set_clear(usbsc->usbsc_bst, aio->aio_ccm_bsh,
+ AWIN_USB_CLK_REG, awinusb_usb_clk_set_a31[loc->loc_port],
+ 0);
+ } else {
+ /*
+ * Access to the USB phy is off USB0 so make sure it's on.
+ */
+ awin_reg_set_clear(usbsc->usbsc_bst, aio->aio_ccm_bsh,
+ AWIN_AHB_GATING0_REG,
+ AWIN_AHB_GATING0_USB0 | awinusb_ahb_gating[loc->loc_port],
+ 0);
+
+ /*
+ * Enable the USB phy for this port.
+ */
+ awin_reg_set_clear(usbsc->usbsc_bst, aio->aio_ccm_bsh,
+ AWIN_USB_CLK_REG, awinusb_usb_clk_set[loc->loc_port], 0);
+ }
/*
* Allow USB DMA engine access to the DRAM.
@@ -361,11 +409,13 @@ awinusb_attach(device_t parent, device_t
awin_reg_set_clear(usbsc->usbsc_bst, aio->aio_core_bsh,
loc->loc_offset + AWIN_USB_PMU_IRQ_REG,
AWIN_USB_PMU_IRQ_AHB_INCR8 | AWIN_USB_PMU_IRQ_AHB_INCR4
- | AWIN_USB_PMU_IRQ_AHB_INCRX | AWIN_USB_PMU_IRQ_ULPI_BYPASS,
- 0);
- awin_reg_set_clear(usbsc->usbsc_bst, aio->aio_core_bsh,
- AWIN_DRAM_OFFSET + awinusb_dram_hpcr_regs[loc->loc_port],
- AWIN_DRAM_HPCR_ACCESS_EN, 0);
+ | AWIN_USB_PMU_IRQ_AHB_INCRX | AWIN_USB_PMU_IRQ_ULPI_BYPASS, 0);
+
+ if (awin_chip_id() != AWIN_CHIP_ID_A31) {
+ awin_reg_set_clear(usbsc->usbsc_bst, aio->aio_core_bsh,
+ AWIN_DRAM_OFFSET + awinusb_dram_hpcr_regs[loc->loc_port],
+ AWIN_DRAM_HPCR_ACCESS_EN, 0);
+ }
/* initialize the USB phy */
awin_usb_phy_write(usbsc, 0x20, 0x14, 5);
Index: src/sys/arch/arm/allwinner/awin_wdt.c
diff -u src/sys/arch/arm/allwinner/awin_wdt.c:1.3 src/sys/arch/arm/allwinner/awin_wdt.c:1.4
--- src/sys/arch/arm/allwinner/awin_wdt.c:1.3 Thu Feb 20 21:48:38 2014
+++ src/sys/arch/arm/allwinner/awin_wdt.c Fri Oct 10 07:36:11 2014
@@ -33,7 +33,7 @@
#include <sys/cdefs.h>
-__KERNEL_RCSID(1, "$NetBSD: awin_wdt.c,v 1.3 2014/02/20 21:48:38 matt Exp $");
+__KERNEL_RCSID(1, "$NetBSD: awin_wdt.c,v 1.4 2014/10/10 07:36:11 jmcneill Exp $");
#include <sys/param.h>
#include <sys/bus.h>
@@ -200,9 +200,19 @@ void
awin_wdog_reset(void)
{
cpsid(I32_bit|F32_bit);
- bus_space_write_4(&awin_bs_tag, awin_core_bsh,
- AWIN_TMR_OFFSET + AWIN_WDOG_MODE_REG,
- AWIN_WDOG_MODE_EN | AWIN_WDOG_MODE_RST_EN);
+ if (awin_chip_id() == AWIN_CHIP_ID_A31) {
+ bus_space_write_4(&awin_bs_tag, awin_core_bsh,
+ AWIN_TMR_OFFSET + AWIN_A31_WDOG1_CFG_REG,
+ __SHIFTIN(AWIN_A31_WDOG_CFG_CONFIG_SYS,
+ AWIN_A31_WDOG_CFG_CONFIG));
+ bus_space_write_4(&awin_bs_tag, awin_core_bsh,
+ AWIN_TMR_OFFSET + AWIN_A31_WDOG1_MODE_REG,
+ AWIN_A31_WDOG_MODE_EN);
+ } else {
+ bus_space_write_4(&awin_bs_tag, awin_core_bsh,
+ AWIN_TMR_OFFSET + AWIN_WDOG_MODE_REG,
+ AWIN_WDOG_MODE_EN | AWIN_WDOG_MODE_RST_EN);
+ }
for (;;) {
__asm("wfi");
}