mips: octeon: Initial minimal support for the Marvell Octeon SoC

This patch adds very basic support for the Octeon III SoCs. Only
CFI parallel NOR flash and UART is supported for now.

Please note that the basic Octeon port does not include the DDR3/4
initialization yet. This will be added in some follow-up patches
later. To still use U-Boot on with this port, the L2 cache (4MiB on
Octeon III CN73xx) is used as RAM. This way, U-Boot can boot to the
prompt on such boards.

Signed-off-by: Aaron Williams <awilliams@marvell.com>
Signed-off-by: Stefan Roese <sr@denx.de>
This commit is contained in:
Aaron Williams 2020-06-30 12:08:56 +02:00 committed by Daniel Schwierzeck
parent 59aea37abf
commit 0dc4ab9c43
14 changed files with 318 additions and 1 deletions

View file

@ -770,6 +770,12 @@ M: Ezequiel Garcia <ezequiel@collabora.com>
S: Maintained
F: arch/mips/mach-jz47xx/
MIPS Octeon
M: Aaron Williams <awilliams@marvell.com>
S: Maintained
F: arch/mips/mach-octeon/
F: arch/mips/include/asm/arch-octeon/
MMC
M: Peng Fan <peng.fan@nxp.com>
S: Maintained

View file

@ -106,6 +106,25 @@ config ARCH_JZ47XX
select OF_CONTROL
select DM
config ARCH_OCTEON
bool "Support Marvell Octeon CN7xxx platforms"
select CPU_CAVIUM_OCTEON
select DISPLAY_CPUINFO
select DMA_ADDR_T_64BIT
select DM
select DM_SERIAL
select DM_GPIO
select DM_ETH
select MIPS_L2_CACHE
select MIPS_TUNE_OCTEON3
select ROM_EXCEPTION_VECTORS
select SUPPORTS_BIG_ENDIAN
select SUPPORTS_CPU_MIPS64_OCTEON
select PHYS_64BIT
select OF_CONTROL
select OF_LIVE
imply CMD_DM
config MACH_PIC32
bool "Support Microchip PIC32"
select DM
@ -160,6 +179,7 @@ source "arch/mips/mach-bmips/Kconfig"
source "arch/mips/mach-jz47xx/Kconfig"
source "arch/mips/mach-pic32/Kconfig"
source "arch/mips/mach-mtmips/Kconfig"
source "arch/mips/mach-octeon/Kconfig"
if MIPS
@ -233,6 +253,14 @@ config CPU_MIPS64_R6
Choose this option to build a kernel for release 6 or later of the
MIPS64 architecture.
config CPU_MIPS64_OCTEON
bool "Marvell Octeon series of CPUs"
depends on SUPPORTS_CPU_MIPS64_OCTEON
select 64BIT
help
Choose this option for Marvell Octeon CPUs. These CPUs are between
MIPS64 R5 and R6 with other extensions.
endchoice
menu "General setup"
@ -431,6 +459,12 @@ config SUPPORTS_CPU_MIPS64_R2
config SUPPORTS_CPU_MIPS64_R6
bool
config SUPPORTS_CPU_MIPS64_OCTEON
bool
config CPU_CAVIUM_OCTEON
bool
config CPU_MIPS32
bool
default y if CPU_MIPS32_R1 || CPU_MIPS32_R2 || CPU_MIPS32_R6
@ -438,6 +472,7 @@ config CPU_MIPS32
config CPU_MIPS64
bool
default y if CPU_MIPS64_R1 || CPU_MIPS64_R2 || CPU_MIPS64_R6
default y if CPU_MIPS64_OCTEON
config MIPS_TUNE_4KC
bool
@ -454,6 +489,9 @@ config MIPS_TUNE_34KC
config MIPS_TUNE_74KC
bool
config MIPS_TUNE_OCTEON3
bool
config 32BIT
bool
@ -486,6 +524,11 @@ config MIPS_SRAM_INIT
before it can be used. If enabled, a function mips_sram_init() will
be called just before setup_stack_gd.
config DMA_ADDR_T_64BIT
bool
help
Select this to enable 64-bit DMA addressing
config SYS_DCACHE_SIZE
int
default 0

View file

@ -17,6 +17,7 @@ machine-$(CONFIG_ARCH_JZ47XX) += jz47xx
machine-$(CONFIG_MACH_PIC32) += pic32
machine-$(CONFIG_ARCH_MTMIPS) += mtmips
machine-$(CONFIG_ARCH_MSCC) += mscc
machine-${CONFIG_ARCH_OCTEON} += octeon
machdirs := $(patsubst %,arch/mips/mach-%/,$(machine-y))
libs-y += $(machdirs)
@ -30,6 +31,7 @@ arch-$(CONFIG_CPU_MIPS32_R6) += -march=mips32r6 -Wa,-mips32r6
arch-$(CONFIG_CPU_MIPS64_R1) += -march=mips64 -Wa,-mips64
arch-$(CONFIG_CPU_MIPS64_R2) += -march=mips64r2 -Wa,-mips64r2
arch-$(CONFIG_CPU_MIPS64_R6) += -march=mips64r6 -Wa,-mips64r6
arch-${CONFIG_CPU_MIPS64_OCTEON} += -march=octeon2
# Allow extra optimization for specific CPUs/SoCs
tune-$(CONFIG_MIPS_TUNE_4KC) += -mtune=4kc
@ -37,6 +39,7 @@ tune-$(CONFIG_MIPS_TUNE_14KC) += -mtune=14kc
tune-$(CONFIG_MIPS_TUNE_24KC) += -mtune=24kc
tune-$(CONFIG_MIPS_TUNE_34KC) += -mtune=34kc
tune-$(CONFIG_MIPS_TUNE_74KC) += -mtune=74kc
tune-${CONFIG_MIPS_TUNE_OCTEON3} += -mtune=octeon2
# Include default header files
cflags-y += -I$(srctree)/arch/mips/include/asm/mach-generic

View file

@ -0,0 +1,46 @@
menu "Octeon platforms"
depends on ARCH_OCTEON
config SYS_SOC
string
default "octeon"
config OCTEON_CN7XXX
bool "Octeon CN7XXX SoC"
config OCTEON_CN70XX
bool "Octeon CN70XX SoC"
select OCTEON_CN7XXX
config OCTEON_CN73XX
bool "Octeon CN73XX SoC"
select OCTEON_CN7XXX
config OCTEON_CN78XX
bool "Octeon CN78XX SoC"
select OCTEON_CN7XXX
choice
prompt "Octeon MIPS family select"
config SOC_OCTEON3
bool "Octeon III family"
help
This selects the Octeon III SoC family CN70xx, CN73XX, CN78xx
and CNF75XX.
endchoice
config SYS_DCACHE_SIZE
default 32768
config SYS_DCACHE_LINE_SIZE
default 128
config SYS_ICACHE_SIZE
default 79872
config SYS_ICACHE_LINE_SIZE
default 128
endmenu

View file

@ -0,0 +1,10 @@
# (C) Copyright 2019 Marvell, Inc.
#
# SPDX-License-Identifier: GPL-2.0+
#
obj-y += lowlevel_init.o
obj-y += cache.o
obj-y += clock.o
obj-y += cpu.o
obj-y += dram.o

View file

@ -0,0 +1,24 @@
// SPDX-License-Identifier: GPL-2.0+
/*
* Copyright (C) 2020 Marvell International Ltd.
*/
#include <cpu_func.h>
/*
* The Octeon platform is cache coherent and cache flushes and invalidates
* are not needed. Define some platform specific empty flush_foo()
* functions here to overwrite the _weak common function as a no-op.
* This effectively disables all cache operations.
*/
void flush_dcache_range(ulong start_addr, ulong stop)
{
}
void flush_cache(ulong start_addr, ulong size)
{
}
void invalidate_dcache_range(ulong start_addr, ulong stop)
{
}

View file

@ -0,0 +1,14 @@
// SPDX-License-Identifier: GPL-2.0
/*
* Copyright (C) 2018, 2019 Marvell International Ltd.
*/
#include <asm/global_data.h>
#include <mach/clock.h>
DECLARE_GLOBAL_DATA_PTR;
ulong notrace get_tbclk(void)
{
return gd->cpu_clk;
}

View file

@ -0,0 +1,66 @@
// SPDX-License-Identifier: GPL-2.0+
/*
* Copyright (C) 2020 Marvell International Ltd.
*/
#include <asm/global_data.h>
#include <linux/bitfield.h>
#include <linux/bitops.h>
#include <linux/compat.h>
#include <linux/io.h>
#include <mach/clock.h>
#include <mach/cavm-reg.h>
DECLARE_GLOBAL_DATA_PTR;
static int get_clocks(void)
{
const u64 ref_clock = PLL_REF_CLK;
void __iomem *rst_boot;
u64 val;
rst_boot = ioremap(CAVM_RST_BOOT, 0);
val = ioread64(rst_boot);
gd->cpu_clk = ref_clock * FIELD_GET(RST_BOOT_C_MUL, val);
gd->bus_clk = ref_clock * FIELD_GET(RST_BOOT_PNR_MUL, val);
debug("%s: cpu: %lu, bus: %lu\n", __func__, gd->cpu_clk, gd->bus_clk);
return 0;
}
/* Early mach init code run from flash */
int mach_cpu_init(void)
{
void __iomem *mio_boot_reg_cfg0;
/* Remap boot-bus 0x1fc0.0000 -> 0x1f40.0000 */
/* ToDo: Move this to an early running bus (bootbus) DM driver */
mio_boot_reg_cfg0 = ioremap(CAVM_MIO_BOOT_REG_CFG0, 0);
clrsetbits_be64(mio_boot_reg_cfg0, 0xffff, 0x1f40);
/* Get clocks and store them in GD */
get_clocks();
return 0;
}
/**
* Returns number of cores
*
* @return number of CPU cores for the specified node
*/
static int cavm_octeon_num_cores(void)
{
void __iomem *ciu_fuse;
ciu_fuse = ioremap(CAVM_CIU_FUSE, 0);
return fls64(ioread64(ciu_fuse) & 0xffffffffffff);
}
int print_cpuinfo(void)
{
printf("SoC: Octeon CN73xx (%d cores)\n", cavm_octeon_num_cores());
return 0;
}

View file

@ -0,0 +1,28 @@
// SPDX-License-Identifier: GPL-2.0+
/*
* Copyright (C) Stefan Roese <sr@denx.de>
*/
#include <dm.h>
#include <ram.h>
#include <asm/global_data.h>
#include <linux/compat.h>
DECLARE_GLOBAL_DATA_PTR;
int dram_init(void)
{
/*
* No DDR init yet -> run in L2 cache
*/
gd->ram_size = (4 << 20);
gd->bd->bi_dram[0].size = gd->ram_size;
gd->bd->bi_dram[1].size = 0;
return 0;
}
ulong board_get_usable_ram_top(ulong total_size)
{
return gd->ram_top;
}

View file

@ -0,0 +1,30 @@
/* SPDX-License-Identifier: GPL-2.0 */
#ifndef __ASM_MACH_OCTEON_IOREMAP_H
#define __ASM_MACH_OCTEON_IOREMAP_H
#include <linux/types.h>
/*
* Allow physical addresses to be fixed up to help peripherals located
* outside the low 32-bit range -- generic pass-through version.
*/
static inline phys_addr_t fixup_bigphys_addr(phys_addr_t phys_addr,
phys_addr_t size)
{
return phys_addr;
}
static inline void __iomem *plat_ioremap(phys_addr_t offset, unsigned long size,
unsigned long flags)
{
return (void __iomem *)(XKPHYS | offset);
}
static inline int plat_iounmap(const volatile void __iomem *addr)
{
return 0;
}
#define _page_cachable_default _CACHE_CACHABLE_NONCOHERENT
#endif /* __ASM_MACH_OCTEON_IOREMAP_H */

View file

@ -0,0 +1,17 @@
/* SPDX-License-Identifier: GPL-2.0 */
/*
* Copyright (C) 2020 Marvell International Ltd.
*/
#ifndef __CAVM_REG_H__
/* Register offsets */
#define CAVM_CIU_FUSE 0x00010100000001a0
#define CAVM_MIO_BOOT_REG_CFG0 0x0001180000000000
#define CAVM_RST_BOOT 0x0001180006001600
/* Register bits */
#define RST_BOOT_C_MUL GENMASK_ULL(36, 30)
#define RST_BOOT_PNR_MUL GENMASK_ULL(29, 24)
#endif /* __CAVM_REG_H__ */

View file

@ -0,0 +1,12 @@
/* SPDX-License-Identifier: GPL-2.0 */
/*
* Copyright (C) 2018, 2019 Marvell International Ltd.
*/
#ifndef __CLOCK_H__
/** System PLL reference clock */
#define PLL_REF_CLK 50000000 /* 50 MHz */
#define NS_PER_REF_CLK_TICK (1000000000 / PLL_REF_CLK)
#endif /* __CLOCK_H__ */

View file

@ -0,0 +1,19 @@
/* SPDX-License-Identifier: GPL-2.0 */
/*
* Copyright (C) 2020 Stefan Roese <sr@denx.de>
*/
#include <config.h>
#include <asm-offsets.h>
#include <asm/cacheops.h>
#include <asm/regdef.h>
#include <asm/mipsregs.h>
#include <asm/addrspace.h>
#include <asm/asm.h>
.set noreorder
LEAF(lowlevel_init)
jr ra
nop
END(lowlevel_init)

View file

@ -228,7 +228,6 @@ CONFIG_CPLD_BR_PRELIM
CONFIG_CPLD_OR_PRELIM
CONFIG_CPM2
CONFIG_CPU_ARMV8
CONFIG_CPU_CAVIUM_OCTEON
CONFIG_CPU_FREQ_HZ
CONFIG_CPU_HAS_LLSC
CONFIG_CPU_HAS_PREFETCH