diff options
42 files changed, 489 insertions, 63 deletions
@@ -248,7 +248,8 @@ config SYS_EXTRA_OPTIONS config SYS_TEXT_BASE depends on SPARC || ARC || X86 || ARCH_UNIPHIER || ARCH_ZYNQMP || \ - (M68K && !TARGET_ASTRO_MCF5373L) || MICROBLAZE || MIPS + (M68K && !TARGET_ASTRO_MCF5373L) || MICROBLAZE || MIPS || \ + ARCH_ZYNQ depends on !EFI_APP hex "Text Base" help diff --git a/arch/arm/cpu/armv8/zynqmp/Kconfig b/arch/arm/cpu/armv8/zynqmp/Kconfig index e175e6eceb..499e1ddb22 100644 --- a/arch/arm/cpu/armv8/zynqmp/Kconfig +++ b/arch/arm/cpu/armv8/zynqmp/Kconfig @@ -28,6 +28,7 @@ config SYS_BOARD default "zynqmp" config SYS_VENDOR + string "Vendor name" default "xilinx" config SYS_SOC diff --git a/arch/arm/cpu/armv8/zynqmp/Makefile b/arch/arm/cpu/armv8/zynqmp/Makefile index be8673a7db..013f136707 100644 --- a/arch/arm/cpu/armv8/zynqmp/Makefile +++ b/arch/arm/cpu/armv8/zynqmp/Makefile @@ -9,4 +9,4 @@ obj-y += clk.o obj-y += cpu.o obj-$(CONFIG_MP) += mp.o obj-y += slcr.o -obj-$(CONFIG_SPL_BUILD) += spl.o +obj-$(CONFIG_SPL_BUILD) += spl.o handoff.o diff --git a/arch/arm/cpu/armv8/zynqmp/handoff.c b/arch/arm/cpu/armv8/zynqmp/handoff.c new file mode 100644 index 0000000000..25d6ef3f60 --- /dev/null +++ b/arch/arm/cpu/armv8/zynqmp/handoff.c @@ -0,0 +1,87 @@ +/* + * Copyright 2016 - 2017 Xilinx, Inc. + * + * Michal Simek <michal.simek@xilinx.com> + * + * SPDX-License-Identifier: GPL-2.0+ + */ + +#include <common.h> +#include <asm/io.h> +#include <asm/arch/hardware.h> +#include <asm/arch/sys_proto.h> + +/* + * atfhandoffparams + * Parameter bitfield encoding + * ----------------------------------------------------------------------------- + * Exec State 0 0 -> Aarch64, 1-> Aarch32 + * endianness 1 0 -> LE, 1 -> BE + * secure (TZ) 2 0 -> Non secure, 1 -> secure + * EL 3:4 00 -> EL0, 01 -> EL1, 10 -> EL2, 11 -> EL3 + * CPU# 5:6 00 -> A53_0, 01 -> A53_1, 10 -> A53_2, 11 -> A53_3 + */ + +#define FSBL_FLAGS_ESTATE_SHIFT 0 +#define FSBL_FLAGS_ESTATE_MASK (1 << FSBL_FLAGS_ESTATE_SHIFT) +#define FSBL_FLAGS_ESTATE_A64 0 +#define FSBL_FLAGS_ESTATE_A32 1 + +#define FSBL_FLAGS_ENDIAN_SHIFT 1 +#define FSBL_FLAGS_ENDIAN_MASK (1 << FSBL_FLAGS_ENDIAN_SHIFT) +#define FSBL_FLAGS_ENDIAN_LE 0 +#define FSBL_FLAGS_ENDIAN_BE 1 + +#define FSBL_FLAGS_TZ_SHIFT 2 +#define FSBL_FLAGS_TZ_MASK (1 << FSBL_FLAGS_TZ_SHIFT) +#define FSBL_FLAGS_NON_SECURE 0 +#define FSBL_FLAGS_SECURE 1 + +#define FSBL_FLAGS_EL_SHIFT 3 +#define FSBL_FLAGS_EL_MASK (3 << FSBL_FLAGS_EL_SHIFT) +#define FSBL_FLAGS_EL0 0 +#define FSBL_FLAGS_EL1 1 +#define FSBL_FLAGS_EL2 2 +#define FSBL_FLAGS_EL3 3 + +#define FSBL_FLAGS_CPU_SHIFT 5 +#define FSBL_FLAGS_CPU_MASK (3 << FSBL_FLAGS_CPU_SHIFT) +#define FSBL_FLAGS_A53_0 0 +#define FSBL_FLAGS_A53_1 1 +#define FSBL_FLAGS_A53_2 2 +#define FSBL_FLAGS_A53_3 3 + +#define FSBL_MAX_PARTITIONS 8 + +/* Structure corresponding to each partition entry */ +struct xfsbl_partition { + uint64_t entry_point; + uint64_t flags; +}; + +/* Structure for handoff parameters to ARM Trusted Firmware (ATF) */ +struct xfsbl_atf_handoff_params { + uint8_t magic[4]; + uint32_t num_entries; + struct xfsbl_partition partition[FSBL_MAX_PARTITIONS]; +}; + +#ifdef CONFIG_SPL_OS_BOOT +void handoff_setup(void) +{ + struct xfsbl_atf_handoff_params *atfhandoffparams; + + atfhandoffparams = (void *)CONFIG_SPL_TEXT_BASE; + atfhandoffparams->magic[0] = 'X'; + atfhandoffparams->magic[1] = 'L'; + atfhandoffparams->magic[2] = 'N'; + atfhandoffparams->magic[3] = 'X'; + + atfhandoffparams->num_entries = 1; + atfhandoffparams->partition[0].entry_point = CONFIG_SYS_TEXT_BASE; + atfhandoffparams->partition[0].flags = FSBL_FLAGS_EL2 << + FSBL_FLAGS_EL_SHIFT; + + writel(CONFIG_SPL_TEXT_BASE, &pmu_base->gen_storage6); +} +#endif diff --git a/arch/arm/cpu/armv8/zynqmp/spl.c b/arch/arm/cpu/armv8/zynqmp/spl.c index f5f550f9e2..0a5f4306e8 100644 --- a/arch/arm/cpu/armv8/zynqmp/spl.c +++ b/arch/arm/cpu/armv8/zynqmp/spl.c @@ -128,6 +128,8 @@ __weak void psu_init(void) #ifdef CONFIG_SPL_OS_BOOT int spl_start_uboot(void) { + handoff_setup(); + return 0; } #endif diff --git a/arch/arm/dts/zynq-7000.dtsi b/arch/arm/dts/zynq-7000.dtsi index 668f54ec21..fa9ee276cb 100644 --- a/arch/arm/dts/zynq-7000.dtsi +++ b/arch/arm/dts/zynq-7000.dtsi @@ -177,7 +177,6 @@ interrupts = <0 26 4>; clocks = <&clkc 25>, <&clkc 34>; clock-names = "ref_clk", "pclk"; - spi-max-frequency = <166666700>; #address-cells = <1>; #size-cells = <0>; }; @@ -190,7 +189,6 @@ interrupts = <0 49 4>; clocks = <&clkc 26>, <&clkc 35>; clock-names = "ref_clk", "pclk"; - spi-max-frequency = <166666700>; #address-cells = <1>; #size-cells = <0>; }; diff --git a/arch/arm/dts/zynq-zc702.dts b/arch/arm/dts/zynq-zc702.dts index 478e9fd4ef..2696e70a89 100644 --- a/arch/arm/dts/zynq-zc702.dts +++ b/arch/arm/dts/zynq-zc702.dts @@ -40,14 +40,14 @@ label = "sw14"; gpios = <&gpio0 12 0>; linux,code = <108>; /* down */ - gpio-key,wakeup; + wakeup-source; autorepeat; }; sw13 { label = "sw13"; gpios = <&gpio0 14 0>; linux,code = <103>; /* up */ - gpio-key,wakeup; + wakeup-source; autorepeat; }; }; diff --git a/arch/arm/dts/zynqmp-clk.dtsi b/arch/arm/dts/zynqmp-clk.dtsi index aa848c8646..b64a0a6f6b 100644 --- a/arch/arm/dts/zynqmp-clk.dtsi +++ b/arch/arm/dts/zynqmp-clk.dtsi @@ -218,6 +218,10 @@ clocks = <&clk250>, <&clk250>; }; +&watchdog0 { + clocks = <&clk250>; +}; + &xilinx_drm { clocks = <&drm_clock>; }; diff --git a/arch/arm/dts/zynqmp-ep108.dts b/arch/arm/dts/zynqmp-ep108.dts index 2483180d38..9f6b11180e 100644 --- a/arch/arm/dts/zynqmp-ep108.dts +++ b/arch/arm/dts/zynqmp-ep108.dts @@ -28,6 +28,7 @@ }; chosen { + bootargs = "earlycon"; stdout-path = "serial0:115200n8"; }; diff --git a/arch/arm/dts/zynqmp-zc1751-xm015-dc1.dts b/arch/arm/dts/zynqmp-zc1751-xm015-dc1.dts index b3f42977ab..c2a26c1dbb 100644 --- a/arch/arm/dts/zynqmp-zc1751-xm015-dc1.dts +++ b/arch/arm/dts/zynqmp-zc1751-xm015-dc1.dts @@ -176,6 +176,10 @@ /* ULPI SMSC USB3320 */ &usb0 { status = "okay"; +}; + +&dwc3_0 { + status = "okay"; dr_mode = "host"; }; diff --git a/arch/arm/dts/zynqmp-zc1751-xm016-dc2.dts b/arch/arm/dts/zynqmp-zc1751-xm016-dc2.dts index 09a114be16..32847e1a66 100644 --- a/arch/arm/dts/zynqmp-zc1751-xm016-dc2.dts +++ b/arch/arm/dts/zynqmp-zc1751-xm016-dc2.dts @@ -224,6 +224,10 @@ /* ULPI SMSC USB3320 */ &usb1 { status = "okay"; +}; + +&dwc3_1 { + status = "okay"; dr_mode = "host"; }; diff --git a/arch/arm/dts/zynqmp.dtsi b/arch/arm/dts/zynqmp.dtsi index de1f160308..1fd570bc2f 100644 --- a/arch/arm/dts/zynqmp.dtsi +++ b/arch/arm/dts/zynqmp.dtsi @@ -22,6 +22,7 @@ device_type = "cpu"; enable-method = "psci"; reg = <0x0>; + cpu-idle-states = <&CPU_SLEEP_0>; }; cpu@1 { @@ -29,6 +30,7 @@ device_type = "cpu"; enable-method = "psci"; reg = <0x1>; + cpu-idle-states = <&CPU_SLEEP_0>; }; cpu@2 { @@ -36,6 +38,7 @@ device_type = "cpu"; enable-method = "psci"; reg = <0x2>; + cpu-idle-states = <&CPU_SLEEP_0>; }; cpu@3 { @@ -43,6 +46,20 @@ device_type = "cpu"; enable-method = "psci"; reg = <0x3>; + cpu-idle-states = <&CPU_SLEEP_0>; + }; + + idle-states { + entry-mehod = "arm,psci"; + + CPU_SLEEP_0: cpu-sleep-0 { + compatible = "arm,idle-state"; + arm,psci-suspend-param = <0x40000000>; + local-timer-stop; + entry-latency-us = <300>; + exit-latency-us = <600>; + min-residency-us = <800000>; + }; }; }; @@ -620,7 +637,7 @@ }; i2c0: i2c@ff020000 { - compatible = "cdns,i2c-r1p10"; + compatible = "cdns,i2c-r1p14", "cdns,i2c-r1p10"; status = "disabled"; interrupt-parent = <&gic>; interrupts = <0 17 4>; @@ -631,7 +648,7 @@ }; i2c1: i2c@ff030000 { - compatible = "cdns,i2c-r1p10"; + compatible = "cdns,i2c-r1p14", "cdns,i2c-r1p10"; status = "disabled"; interrupt-parent = <&gic>; interrupts = <0 18 4>; diff --git a/arch/arm/include/asm/arch-zynqmp/hardware.h b/arch/arm/include/asm/arch-zynqmp/hardware.h index 041b43cfe0..cf187f3111 100644 --- a/arch/arm/include/asm/arch-zynqmp/hardware.h +++ b/arch/arm/include/asm/arch-zynqmp/hardware.h @@ -144,4 +144,13 @@ struct csu_regs { #define csu_base ((struct csu_regs *)ZYNQMP_CSU_BASEADDR) +#define ZYNQMP_PMU_BASEADDR 0xFFD80000 + +struct pmu_regs { + u32 reserved[18]; + u32 gen_storage6; /* 0x48 */ +}; + +#define pmu_base ((struct pmu_regs *)ZYNQMP_PMU_BASEADDR) + #endif /* _ASM_ARCH_HARDWARE_H */ diff --git a/arch/arm/include/asm/arch-zynqmp/sys_proto.h b/arch/arm/include/asm/arch-zynqmp/sys_proto.h index 1db2bd6a4f..8c54fcedf4 100644 --- a/arch/arm/include/asm/arch-zynqmp/sys_proto.h +++ b/arch/arm/include/asm/arch-zynqmp/sys_proto.h @@ -8,10 +8,12 @@ #ifndef _ASM_ARCH_SYS_PROTO_H #define _ASM_ARCH_SYS_PROTO_H +#ifndef CONFIG_CLK_ZYNQMP /* Setup clk for network */ static inline void zynq_slcr_gem_clk_setup(u32 gem_id, unsigned long clk_rate) { } +#endif int zynq_slcr_get_mio_pin_status(const char *periph); @@ -19,4 +21,6 @@ unsigned int zynqmp_get_silicon_version(void); void psu_init(void); +void handoff_setup(void); + #endif /* _ASM_ARCH_SYS_PROTO_H */ diff --git a/board/xilinx/microblaze-generic/Kconfig b/board/xilinx/microblaze-generic/Kconfig index 02ac65c1d3..6e93a3d948 100644 --- a/board/xilinx/microblaze-generic/Kconfig +++ b/board/xilinx/microblaze-generic/Kconfig @@ -7,7 +7,12 @@ config SYS_VENDOR default "xilinx" config SYS_CONFIG_NAME + string "Board configuration name" default "microblaze-generic" + help + This option contains information about board configuration name. + Based on this option include/configs/<CONFIG_SYS_CONFIG_NAME>.h header + will be used for board configuration. config XILINX_MICROBLAZE0_USE_MSR_INSTR int "USE_MSR_INSTR range (0:1)" diff --git a/board/xilinx/zynq/board.c b/board/xilinx/zynq/board.c index 5cd9bbf711..6a3cbe0a0d 100644 --- a/board/xilinx/zynq/board.c +++ b/board/xilinx/zynq/board.c @@ -85,6 +85,12 @@ int board_init(void) int board_late_init(void) { switch ((zynq_slcr_get_boot_mode()) & ZYNQ_BM_MASK) { + case ZYNQ_BM_QSPI: + setenv("modeboot", "qspiboot"); + break; + case ZYNQ_BM_NAND: + setenv("modeboot", "nandboot"); + break; case ZYNQ_BM_NOR: setenv("modeboot", "norboot"); break; diff --git a/cmd/fpga.c b/cmd/fpga.c index 8956eb1b65..016349f560 100644 --- a/cmd/fpga.c +++ b/cmd/fpga.c @@ -18,15 +18,17 @@ static int fpga_get_op(char *opstr); /* Local defines */ -#define FPGA_NONE -1 -#define FPGA_INFO 0 -#define FPGA_LOAD 1 -#define FPGA_LOADB 2 -#define FPGA_DUMP 3 -#define FPGA_LOADMK 4 -#define FPGA_LOADP 5 -#define FPGA_LOADBP 6 -#define FPGA_LOADFS 7 +enum { + FPGA_NONE = -1, + FPGA_INFO, + FPGA_LOAD, + FPGA_LOADB, + FPGA_DUMP, + FPGA_LOADMK, + FPGA_LOADP, + FPGA_LOADBP, + FPGA_LOADFS, +}; /* ------------------------------------------------------------------------- */ /* command form: diff --git a/configs/topic_miami_defconfig b/configs/topic_miami_defconfig index e7b6c0fd85..3239d99d54 100644 --- a/configs/topic_miami_defconfig +++ b/configs/topic_miami_defconfig @@ -3,6 +3,7 @@ CONFIG_SYS_VENDOR="topic" CONFIG_SYS_CONFIG_NAME="topic_miami" CONFIG_ARCH_ZYNQ=y CONFIG_BOOT_INIT_FILE="board/topic/zynq/zynq-topic-miami/ps7_regs.txt" +CONFIG_SYS_TEXT_BASE=0x4000000 CONFIG_DEFAULT_DEVICE_TREE="zynq-topic-miami" CONFIG_BOOTDELAY=0 CONFIG_SYS_NO_FLASH=y diff --git a/configs/topic_miamiplus_defconfig b/configs/topic_miamiplus_defconfig index 2141949ef7..906220cdc1 100644 --- a/configs/topic_miamiplus_defconfig +++ b/configs/topic_miamiplus_defconfig @@ -3,6 +3,7 @@ CONFIG_SYS_VENDOR="topic" CONFIG_SYS_CONFIG_NAME="topic_miamiplus" CONFIG_ARCH_ZYNQ=y CONFIG_BOOT_INIT_FILE="board/topic/zynq/zynq-topic-miamiplus/ps7_regs.txt" +CONFIG_SYS_TEXT_BASE=0x4000000 CONFIG_DEFAULT_DEVICE_TREE="zynq-topic-miamiplus" CONFIG_BOOTDELAY=0 CONFIG_SYS_NO_FLASH=y diff --git a/configs/xilinx_zynqmp_zc1751_xm015_dc1_defconfig b/configs/xilinx_zynqmp_zc1751_xm015_dc1_defconfig index 0663e161ef..9da03069bf 100644 --- a/configs/xilinx_zynqmp_zc1751_xm015_dc1_defconfig +++ b/configs/xilinx_zynqmp_zc1751_xm015_dc1_defconfig @@ -6,6 +6,7 @@ CONFIG_ZYNQMP_USB=y CONFIG_IDENT_STRING=" Xilinx ZynqMP ZC1751 xm015 dc1" CONFIG_SYS_TEXT_BASE=0x8000000 CONFIG_DEFAULT_DEVICE_TREE="zynqmp-zc1751-xm015-dc1" +CONFIG_AHCI=y CONFIG_DISTRO_DEFAULTS=y CONFIG_FIT=y CONFIG_FIT_VERBOSE=y diff --git a/configs/zynq_microzed_defconfig b/configs/zynq_microzed_defconfig index 7ec5752aac..361e3b97d3 100644 --- a/configs/zynq_microzed_defconfig +++ b/configs/zynq_microzed_defconfig @@ -1,5 +1,6 @@ CONFIG_ARM=y CONFIG_ARCH_ZYNQ=y +CONFIG_SYS_TEXT_BASE=0x4000000 CONFIG_DEFAULT_DEVICE_TREE="zynq-microzed" CONFIG_FIT=y CONFIG_FIT_VERBOSE=y diff --git a/configs/zynq_picozed_defconfig b/configs/zynq_picozed_defconfig index d8c76a7146..529a9ad5dd 100644 --- a/configs/zynq_picozed_defconfig +++ b/configs/zynq_picozed_defconfig @@ -1,5 +1,6 @@ CONFIG_ARM=y CONFIG_ARCH_ZYNQ=y +CONFIG_SYS_TEXT_BASE=0x4000000 CONFIG_DEFAULT_DEVICE_TREE="zynq-picozed" CONFIG_SYS_NO_FLASH=y # CONFIG_DISPLAY_CPUINFO is not set diff --git a/configs/zynq_zc702_defconfig b/configs/zynq_zc702_defconfig index 4c652318ce..04e60e89a6 100644 --- a/configs/zynq_zc702_defconfig +++ b/configs/zynq_zc702_defconfig @@ -1,6 +1,7 @@ CONFIG_ARM=y CONFIG_SYS_CONFIG_NAME="zynq_zc70x" CONFIG_ARCH_ZYNQ=y +CONFIG_SYS_TEXT_BASE=0x4000000 CONFIG_DEFAULT_DEVICE_TREE="zynq-zc702" CONFIG_FIT=y CONFIG_FIT_VERBOSE=y diff --git a/configs/zynq_zc706_defconfig b/configs/zynq_zc706_defconfig index 935a9c920a..7c2040cb70 100644 --- a/configs/zynq_zc706_defconfig +++ b/configs/zynq_zc706_defconfig @@ -1,6 +1,7 @@ CONFIG_ARM=y CONFIG_SYS_CONFIG_NAME="zynq_zc70x" CONFIG_ARCH_ZYNQ=y +CONFIG_SYS_TEXT_BASE=0x4000000 CONFIG_DEFAULT_DEVICE_TREE="zynq-zc706" CONFIG_FIT=y CONFIG_FIT_VERBOSE=y diff --git a/configs/zynq_zc770_xm010_defconfig b/configs/zynq_zc770_xm010_defconfig index 16a14ae898..a11010cc37 100644 --- a/configs/zynq_zc770_xm010_defconfig +++ b/configs/zynq_zc770_xm010_defconfig @@ -1,5 +1,6 @@ CONFIG_ARM=y CONFIG_ARCH_ZYNQ=y +CONFIG_SYS_TEXT_BASE=0x4000000 CONFIG_DEFAULT_DEVICE_TREE="zynq-zc770-xm010" CONFIG_FIT=y CONFIG_FIT_VERBOSE=y diff --git a/configs/zynq_zc770_xm011_defconfig b/configs/zynq_zc770_xm011_defconfig index 247fb6d7f3..ae7a631b06 100644 --- a/configs/zynq_zc770_xm011_defconfig +++ b/configs/zynq_zc770_xm011_defconfig @@ -1,6 +1,7 @@ CONFIG_ARM=y CONFIG_ARCH_ZYNQ=y # CONFIG_MMC is not set +CONFIG_SYS_TEXT_BASE=0x4000000 CONFIG_DEFAULT_DEVICE_TREE="zynq-zc770-xm011" CONFIG_FIT=y CONFIG_FIT_VERBOSE=y diff --git a/configs/zynq_zc770_xm012_defconfig b/configs/zynq_zc770_xm012_defconfig index 8e80a90165..c01faaacdf 100644 --- a/configs/zynq_zc770_xm012_defconfig +++ b/configs/zynq_zc770_xm012_defconfig @@ -1,6 +1,7 @@ CONFIG_ARM=y CONFIG_ARCH_ZYNQ=y # CONFIG_MMC is not set +CONFIG_SYS_TEXT_BASE=0x4000000 CONFIG_DEFAULT_DEVICE_TREE="zynq-zc770-xm012" CONFIG_FIT=y CONFIG_FIT_VERBOSE=y diff --git a/configs/zynq_zc770_xm013_defconfig b/configs/zynq_zc770_xm013_defconfig index 286f0bdd29..573fc14c1c 100644 --- a/configs/zynq_zc770_xm013_defconfig +++ b/configs/zynq_zc770_xm013_defconfig @@ -1,6 +1,7 @@ CONFIG_ARM=y CONFIG_ARCH_ZYNQ=y # CONFIG_MMC is not set +CONFIG_SYS_TEXT_BASE=0x4000000 CONFIG_DEFAULT_DEVICE_TREE="zynq-zc770-xm013" CONFIG_FIT=y CONFIG_FIT_VERBOSE=y diff --git a/configs/zynq_zed_defconfig b/configs/zynq_zed_defconfig index 6f8f3a63bc..25f03b6f83 100644 --- a/configs/zynq_zed_defconfig +++ b/configs/zynq_zed_defconfig @@ -1,5 +1,6 @@ CONFIG_ARM=y CONFIG_ARCH_ZYNQ=y +CONFIG_SYS_TEXT_BASE=0x4000000 CONFIG_DEFAULT_DEVICE_TREE="zynq-zed" CONFIG_FIT=y CONFIG_FIT_VERBOSE=y diff --git a/configs/zynq_zybo_defconfig b/configs/zynq_zybo_defconfig index 67063245ee..b69fd2f7ed 100644 --- a/configs/zynq_zybo_defconfig +++ b/configs/zynq_zybo_defconfig @@ -1,6 +1,7 @@ CONFIG_ARM=y CONFIG_SYS_CONFIG_NAME="zynq_zybo" CONFIG_ARCH_ZYNQ=y +CONFIG_SYS_TEXT_BASE=0x4000000 CONFIG_DEFAULT_DEVICE_TREE="zynq-zybo" CONFIG_FIT=y CONFIG_FIT_VERBOSE=y diff --git a/drivers/clk/Kconfig b/drivers/clk/Kconfig index c05ce2a9ef..335ef9e1d7 100644 --- a/drivers/clk/Kconfig +++ b/drivers/clk/Kconfig @@ -28,6 +28,13 @@ config CLK_BOSTON help Enable this to support the clocks +config CLK_ZYNQMP + bool "Enable clock driver support for ZynqMP" + depends on ARCH_ZYNQMP + help + This clock driver adds support for clock realted settings for + ZynqMP platform. + source "drivers/clk/tegra/Kconfig" source "drivers/clk/uniphier/Kconfig" source "drivers/clk/exynos/Kconfig" diff --git a/drivers/clk/Makefile b/drivers/clk/Makefile index 40a5e8cae8..f55348e8f1 100644 --- a/drivers/clk/Makefile +++ b/drivers/clk/Makefile @@ -10,6 +10,7 @@ obj-$(CONFIG_ARCH_ROCKCHIP) += rockchip/ obj-$(CONFIG_SANDBOX) += clk_sandbox.o obj-$(CONFIG_SANDBOX) += clk_sandbox_test.o obj-$(CONFIG_MACH_PIC32) += clk_pic32.o +obj-$(CONFIG_CLK_ZYNQMP) += clk_zynqmp.o obj-y += tegra/ obj-$(CONFIG_CLK_UNIPHIER) += uniphier/ diff --git a/drivers/clk/clk_zynqmp.c b/drivers/clk/clk_zynqmp.c new file mode 100644 index 0000000000..694274d991 --- /dev/null +++ b/drivers/clk/clk_zynqmp.c @@ -0,0 +1,241 @@ +/* + * ZynqMP clock driver + * + * Copyright (C) 2016 Xilinx, Inc. + * + * SPDX-License-Identifier: GPL-2.0+ + */ + +#include <common.h> +#include <linux/bitops.h> +#include <clk-uclass.h> +#include <dm/device.h> +#include <clk.h> + +#define ZYNQMP_GEM0_REF_CTRL 0xFF5E0050 +#define ZYNQMP_IOPLL_CTRL 0xFF5E0020 +#define ZYNQMP_RPLL_CTRL 0xFF5E0030 +#define ZYNQMP_DPLL_CTRL 0xFD1A002C +#define ZYNQMP_SIP_SVC_MMIO_WRITE 0xC2000013 +#define ZYNQMP_SIP_SVC_MMIO_WRITE 0xC2000013 +#define ZYNQMP_SIP_SVC_MMIO_WRITE 0xC2000013 +#define ZYNQMP_SIP_SVC_MMIO_READ 0xC2000014 +#define ZYNQMP_DIV_MAX_VAL 0x3F +#define ZYNQMP_DIV1_SHFT 8 +#define ZYNQMP_DIV1_SHFT 8 +#define ZYNQMP_DIV2_SHFT 16 +#define ZYNQMP_DIV_MASK 0x3F +#define ZYNQMP_PLL_CTRL_FBDIV_MASK 0x7F +#define ZYNQMP_PLL_CTRL_FBDIV_SHFT 8 +#define ZYNQMP_GEM_REF_CTRL_SRC_MASK 0x7 +#define ZYNQMP_GEM0_CLK_ID 45 +#define ZYNQMP_GEM1_CLK_ID 46 +#define ZYNQMP_GEM2_CLK_ID 47 +#define ZYNQMP_GEM3_CLK_ID 48 + +static unsigned long pss_ref_clk; + +static int zynqmp_calculate_divisors(unsigned long req_rate, + unsigned long parent_rate, + u32 *div1, u32 *div2) +{ + u32 req_div = 1; + u32 i; + + /* + * calculate two divisors to get + * required rate and each divisor + * should be less than 63 + */ + req_div = DIV_ROUND_UP(parent_rate, req_rate); + + for (i = 1; i <= req_div; i++) { + if ((req_div % i) == 0) { + *div1 = req_div / i; + *div2 = i; + if ((*div1 < ZYNQMP_DIV_MAX_VAL) && + (*div2 < ZYNQMP_DIV_MAX_VAL)) + return 0; + } + } + + return -1; +} + +static int zynqmp_get_periph_id(unsigned long id) +{ + int periph_id; + + switch (id) { + case ZYNQMP_GEM0_CLK_ID: + periph_id = 0; + break; + case ZYNQMP_GEM1_CLK_ID: + periph_id = 1; + break; + case ZYNQMP_GEM2_CLK_ID: + periph_id = 2; + break; + case ZYNQMP_GEM3_CLK_ID: + periph_id = 3; + break; + default: + printf("%s, Invalid clock id:%ld\n", __func__, id); + return -EINVAL; + } + + return periph_id; +} + +static int zynqmp_set_clk(unsigned long id, u32 div1, u32 div2) +{ + struct pt_regs regs; + ulong reg; + u32 mask, value; + + id = zynqmp_get_periph_id(id); + if (id < 0) + return -EINVAL; + + reg = (ulong)((u32 *)ZYNQMP_GEM0_REF_CTRL + id); + mask = (ZYNQMP_DIV_MASK << ZYNQMP_DIV1_SHFT) | + (ZYNQMP_DIV_MASK << ZYNQMP_DIV2_SHFT); + value = (div1 << ZYNQMP_DIV1_SHFT) | (div2 << ZYNQMP_DIV2_SHFT); + + debug("%s: reg:0x%lx, mask:0x%x, value:0x%x\n", __func__, reg, mask, + value); + + regs.regs[0] = ZYNQMP_SIP_SVC_MMIO_WRITE; + regs.regs[1] = ((u64)mask << 32) | reg; + regs.regs[2] = value; + regs.regs[3] = 0; + + smc_call(®s); + + return regs.regs[0]; +} + +static unsigned long zynqmp_clk_get_rate(struct clk *clk) +{ + struct pt_regs regs; + ulong reg; + unsigned long value; + int id; + + id = zynqmp_get_periph_id(clk->id); + if (id < 0) + return -EINVAL; + + reg = (ulong)((u32 *)ZYNQMP_GEM0_REF_CTRL + id); + + regs.regs[0] = ZYNQMP_SIP_SVC_MMIO_READ; + regs.regs[1] = reg; + regs.regs[2] = 0; + regs.regs[3] = 0; + + smc_call(®s); + + value = upper_32_bits(regs.regs[0]); + + value &= ZYNQMP_GEM_REF_CTRL_SRC_MASK; + + switch (value) { + case 0: + regs.regs[1] = ZYNQMP_IOPLL_CTRL; + break; + case 2: + regs.regs[1] = ZYNQMP_RPLL_CTRL; + break; + case 3: + regs.regs[1] = ZYNQMP_DPLL_CTRL; + break; + default: + return -EINVAL; + } + + regs.regs[0] = ZYNQMP_SIP_SVC_MMIO_READ; + regs.regs[2] = 0; + regs.regs[3] = 0; + + smc_call(®s); + + value = upper_32_bits(regs.regs[0]) & + (ZYNQMP_PLL_CTRL_FBDIV_MASK << + ZYNQMP_PLL_CTRL_FBDIV_SHFT); + value >>= ZYNQMP_PLL_CTRL_FBDIV_SHFT; + value *= pss_ref_clk; + + return value; +} + +static ulong zynqmp_clk_set_rate(struct clk *clk, unsigned long clk_rate) +{ + int ret; + u32 div1 = 0; + u32 div2 = 0; + unsigned long input_clk; + + input_clk = zynqmp_clk_get_rate(clk); + if (IS_ERR_VALUE(input_clk)) { + dev_err(dev, "failed to get input_clk\n"); + return -EINVAL; + } + + debug("%s: i/p CLK %ld, clk_rate:0x%ld\n", __func__, input_clk, + clk_rate); + + ret = zynqmp_calculate_divisors(clk_rate, input_clk, &div1, &div2); + if (ret) { + dev_err(dev, "failed to proper divisors\n"); + return -EINVAL; + } + + debug("%s: Div1:%d, Div2:%d\n", __func__, div1, div2); + + ret = zynqmp_set_clk(clk->id, div1, div2); + if (ret) { + dev_err(dev, "failed to set gem clk\n"); + return -EINVAL; + } + + return 0; +} + +static int zynqmp_clk_probe(struct udevice *dev) +{ + struct clk clk; + int ret; + + debug("%s\n", __func__); + ret = clk_get_by_name(dev, "pss_ref_clk", &clk); + if (ret < 0) { + dev_err(dev, "failed to get pss_ref_clk\n"); + return ret; + } + + pss_ref_clk = clk_get_rate(&clk); + if (IS_ERR_VALUE(pss_ref_clk)) { + dev_err(dev, "failed to get rate pss_ref_clk\n"); + return -EINVAL; + } + + return 0; +} + +static struct clk_ops zynqmp_clk_ops = { + .set_rate = zynqmp_clk_set_rate, + .get_rate = zynqmp_clk_get_rate, +}; + +static const struct udevice_id zynqmp_clk_ids[] = { + { .compatible = "xlnx,zynqmp-clkc" }, + { } +}; + +U_BOOT_DRIVER(zynqmp_clk) = { + .name = "zynqmp-clk", + .id = UCLASS_CLK, + .of_match = zynqmp_clk_ids, + .probe = zynqmp_clk_probe, + .ops = &zynqmp_clk_ops, +}; diff --git a/drivers/fpga/zynqpl.c b/drivers/fpga/zynqpl.c index ef889ea4e6..2ff716c252 100644 --- a/drivers/fpga/zynqpl.c +++ b/drivers/fpga/zynqpl.c @@ -38,11 +38,6 @@ #define CONFIG_SYS_FPGA_PROG_TIME (CONFIG_SYS_HZ * 4) /* 4 s */ #endif -static int zynq_info(xilinx_desc *desc) -{ - return FPGA_SUCCESS; -} - #define DUMMY_WORD 0xffffffff /* Xilinx binary format header */ @@ -481,16 +476,9 @@ static int zynq_loadfs(xilinx_desc *desc, const void *buf, size_t bsize, } #endif -static int zynq_dump(xilinx_desc *desc, const void *buf, size_t bsize) -{ - return FPGA_FAIL; -} - struct xilinx_fpga_op zynq_op = { .load = zynq_load, #if defined(CONFIG_CMD_FPGA_LOADFS) .loadfs = zynq_loadfs, #endif - .dump = zynq_dump, - .info = zynq_info, }; diff --git a/drivers/i2c/i2c-cdns.c b/drivers/i2c/i2c-cdns.c index f49f60bb37..ef85a70ed3 100644 --- a/drivers/i2c/i2c-cdns.c +++ b/drivers/i2c/i2c-cdns.c @@ -366,6 +366,7 @@ static const struct dm_i2c_ops cdns_i2c_ops = { static const struct udevice_id cdns_i2c_of_match[] = { { .compatible = "cdns,i2c-r1p10" }, + { .compatible = "cdns,i2c-r1p14" }, { /* end of table */ } }; diff --git a/drivers/net/phy/xilinx_phy.c b/drivers/net/phy/xilinx_phy.c index f3eaf2e97c..920bfcb380 100644 --- a/drivers/net/phy/xilinx_phy.c +++ b/drivers/net/phy/xilinx_phy.c @@ -101,11 +101,11 @@ static int xilinxphy_startup(struct phy_device *phydev) static int xilinxphy_of_init(struct phy_device *phydev) { - struct udevice *dev = (struct udevice *)&phydev->dev; u32 phytype; debug("%s\n", __func__); - phytype = fdtdec_get_int(gd->fdt_blob, dev->of_offset, "phy-type", -1); + phytype = fdtdec_get_int(gd->fdt_blob, phydev->dev->of_offset, + "phy-type", -1); if (phytype == XAE_PHY_TYPE_1000BASE_X) phydev->flags |= XAE_PHY_TYPE_1000BASE_X; diff --git a/drivers/net/zynq_gem.c b/drivers/net/zynq_gem.c index d2e5e7c7cd..6dd87cf28f 100644 --- a/drivers/net/zynq_gem.c +++ b/drivers/net/zynq_gem.c @@ -9,6 +9,7 @@ * SPDX-License-Identifier: GPL-2.0+ */ +#include <clk.h> #include <common.h> #include <dm.h> #include <net.h> @@ -181,35 +182,22 @@ struct zynq_gem_priv { struct phy_device *phydev; int phy_of_handle; struct mii_dev *bus; +#ifdef CONFIG_CLK_ZYNQMP + struct clk clk; +#endif }; -static inline int mdio_wait(struct zynq_gem_regs *regs) -{ - u32 timeout = 20000; - - /* Wait till MDIO interface is ready to accept a new transaction. */ - while (--timeout) { - if (readl(®s->nwsr) & ZYNQ_GEM_NWSR_MDIOIDLE_MASK) - break; - WATCHDOG_RESET(); - } - - if (!timeout) { - printf("%s: Timeout\n", __func__); - return 1; - } - - return 0; -} - static u32 phy_setup_op(struct zynq_gem_priv *priv, u32 phy_addr, u32 regnum, u32 op, u16 *data) { u32 mgtcr; struct zynq_gem_regs *regs = priv->iobase; + int err; - if (mdio_wait(regs)) - return 1; + err = wait_for_bit(__func__, ®s->nwsr, ZYNQ_GEM_NWSR_MDIOIDLE_MASK, + true, 20000, true); + if (err) + return err; /* Construct mgtcr mask for the operation */ mgtcr = ZYNQ_GEM_PHYMNTNC_OP_MASK | op | @@ -219,8 +207,10 @@ static u32 phy_setup_op(struct zynq_gem_priv *priv, u32 phy_addr, u32 regnum, /* Write mgtcr and wait for completion */ writel(mgtcr, ®s->phymntnc); - if (mdio_wait(regs)) - return 1; + err = wait_for_bit(__func__, ®s->nwsr, ZYNQ_GEM_NWSR_MDIOIDLE_MASK, + true, 20000, true); + if (err) + return err; if (op == ZYNQ_GEM_PHYMNTNC_OP_R_MASK) *data = readl(®s->phymntnc); @@ -469,8 +459,14 @@ static int zynq_gem_init(struct udevice *dev) /* Change the rclk and clk only not using EMIO interface */ if (!priv->emio) +#ifndef CONFIG_CLK_ZYNQMP zynq_slcr_gem_clk_setup((ulong)priv->iobase != ZYNQ_GEM_BASEADDR0, clk_rate); +#else + ret = clk_set_rate(&priv->clk, clk_rate); + if (IS_ERR_VALUE(ret)) + return -1; +#endif setbits_le32(®s->nwctrl, ZYNQ_GEM_NWCTRL_RXEN_MASK | ZYNQ_GEM_NWCTRL_TXEN_MASK); @@ -643,6 +639,14 @@ static int zynq_gem_probe(struct udevice *dev) priv->tx_bd = (struct emac_bd *)bd_space; priv->rx_bd = (struct emac_bd *)((ulong)bd_space + BD_SEPRN_SPACE); +#ifdef CONFIG_CLK_ZYNQMP + ret = clk_get_by_name(dev, "tx_clk", &priv->clk); + if (ret < 0) { + dev_err(dev, "failed to get clock\n"); + return -EINVAL; + } +#endif + priv->bus = mdio_alloc(); priv->bus->read = zynq_gem_miiphy_read; priv->bus->write = zynq_gem_miiphy_write; diff --git a/include/configs/microblaze-generic.h b/include/configs/microblaze-generic.h index 7abffdb2ef..36b0a0eb16 100644 --- a/include/configs/microblaze-generic.h +++ b/include/configs/microblaze-generic.h @@ -235,15 +235,13 @@ #define CONFIG_BOOTARGS "root=romfs" #define CONFIG_HOSTNAME XILINX_BOARD_NAME #define CONFIG_BOOTCOMMAND "base 0;tftp 11000000 image.img;bootm" -#define CONFIG_IPADDR 192.168.0.3 -#define CONFIG_SERVERIP 192.168.0.5 -#define CONFIG_GATEWAYIP 192.168.0.1 /* architecture dependent code */ #define CONFIG_SYS_USR_EXCEP /* user exception */ #define CONFIG_PREBOOT "echo U-BOOT for ${hostname};setenv preboot;echo" +#ifndef CONFIG_EXTRA_ENV_SETTINGS #define CONFIG_EXTRA_ENV_SETTINGS "unlock=yes\0" \ "nor0=flash-0\0"\ "mtdparts=mtdparts=flash-0:"\ @@ -253,6 +251,7 @@ "setenv stdin nc\0" \ "serial=setenv stdout serial;"\ "setenv stdin serial\0" +#endif #define CONFIG_CMDLINE_EDITING diff --git a/include/configs/xilinx_zynqmp.h b/include/configs/xilinx_zynqmp.h index 74cbfcf8f3..ea4761c684 100644 --- a/include/configs/xilinx_zynqmp.h +++ b/include/configs/xilinx_zynqmp.h @@ -86,6 +86,10 @@ # ifndef CONFIG_ZYNQ_SDHCI_MAX_FREQ # define CONFIG_ZYNQ_SDHCI_MAX_FREQ 200000000 # endif +# define CONFIG_ENV_IS_IN_FAT +# define FAT_ENV_DEVICE_AND_PART "0:auto" +# define FAT_ENV_FILE "uboot.env" +# define FAT_ENV_INTERFACE "mmc" #endif #if defined(CONFIG_ZYNQ_SDHCI) || defined(CONFIG_ZYNQMP_USB) @@ -123,17 +127,43 @@ #define DFU_ALT_INFO \ DFU_ALT_INFO_RAM + +#ifndef CONFIG_SPL_BUILD +# define CONFIG_USB_FUNCTION_FASTBOOT +# define CONFIG_CMD_FASTBOOT +# define CONFIG_ANDROID_BOOT_IMAGE +# define CONFIG_FASTBOOT_BUF_ADDR 0x100000 +# define CONFIG_FASTBOOT_BUF_SIZE 0x6000000 +# define CONFIG_FASTBOOT_FLASH +# ifdef CONFIG_ZYNQ_SDHCI +# define CONFIG_FASTBOOT_FLASH_MMC_DEV 0 +# endif +# define CONFIG_PARTITION_UUIDS +# define CONFIG_CMD_GPT + +# define CONFIG_RANDOM_UUID +# define PARTS_DEFAULT \ + "partitions=uuid_disk=${uuid_gpt_disk};" \ + "name=""boot"",size=16M,uuid=${uuid_gpt_boot};" \ + "name=""Linux"",size=-M,uuid=${uuid_gpt_Linux}\0" +#endif #endif #if !defined(DFU_ALT_INFO) # define DFU_ALT_INFO #endif +#if !defined(PARTS_DEFAULT) +# define PARTS_DEFAULT +#endif + #define CONFIG_BOARD_LATE_INIT /* Do not preserve environment */ +#if !defined(CONFIG_ENV_IS_IN_FAT) #define CONFIG_ENV_IS_NOWHERE 1 -#define CONFIG_ENV_SIZE 0x1000 +#endif +#define CONFIG_ENV_SIZE 0x8000 /* Monitor Command Prompt */ /* Console I/O Buffer Size */ diff --git a/include/configs/xilinx_zynqmp_zc1751_xm015_dc1.h b/include/configs/xilinx_zynqmp_zc1751_xm015_dc1.h index b19a55219a..e3797a8efd 100644 --- a/include/configs/xilinx_zynqmp_zc1751_xm015_dc1.h +++ b/include/configs/xilinx_zynqmp_zc1751_xm015_dc1.h @@ -12,7 +12,6 @@ #define CONFIG_ZYNQ_SDHCI0 #define CONFIG_ZYNQ_SDHCI1 -#define CONFIG_AHCI #define CONFIG_ZYNQMP_XHCI_LIST {ZYNQMP_USB0_XHCI_BASEADDR} #include <configs/xilinx_zynqmp.h> diff --git a/include/configs/zynq-common.h b/include/configs/zynq-common.h index 2fe6897e31..fd74e809dc 100644 --- a/include/configs/zynq-common.h +++ b/include/configs/zynq-common.h @@ -43,7 +43,6 @@ # define CONFIG_PHY_MARVELL # define CONFIG_PHY_REALTEK # define CONFIG_PHY_XILINX -# define CONFIG_BOOTP_SERVERIP # define CONFIG_BOOTP_BOOTPATH # define CONFIG_BOOTP_GATEWAY # define CONFIG_BOOTP_HOSTNAME @@ -247,9 +246,6 @@ #define CONFIG_SYS_PBSIZE (CONFIG_SYS_CBSIZE + \ sizeof(CONFIG_SYS_PROMPT) + 16) -/* Physical Memory map */ -#define CONFIG_SYS_TEXT_BASE 0x4000000 - #ifndef CONFIG_NR_DRAM_BANKS # define CONFIG_NR_DRAM_BANKS 1 #endif diff --git a/include/wait_bit.h b/include/wait_bit.h index 066e30c118..06ad43a122 100644 --- a/include/wait_bit.h +++ b/include/wait_bit.h @@ -11,6 +11,7 @@ #include <common.h> #include <console.h> +#include <watchdog.h> #include <linux/errno.h> #include <asm/io.h> @@ -59,6 +60,7 @@ static inline int wait_for_bit(const char *prefix, const u32 *reg, } udelay(1); + WATCHDOG_RESET(); } debug("%s: Timeout (reg=%p mask=%08x wait_set=%i)\n", prefix, reg, mask, |