We already have support to read back memory size from the SDRAM controller on older AT91 processor via the at91_get_sdram_size() function, but that's mostly called from board code. Add a proper driver that can probe the SDRAM device in the DT to dynamically detect the memory without hardcoding. Signed-off-by: Ahmad Fatoum <a.fatoum@xxxxxxxxxxxxxx> --- arch/arm/mach-at91/Kconfig | 3 ++ arch/arm/mach-at91/Makefile | 1 + arch/arm/mach-at91/sdramc.c | 47 +++++++++++++++++++++++++++++ include/mach/at91/at91sam9_sdramc.h | 4 +++ 4 files changed, 55 insertions(+) create mode 100644 arch/arm/mach-at91/sdramc.c diff --git a/arch/arm/mach-at91/Kconfig b/arch/arm/mach-at91/Kconfig index d2499747252d..1197e06670c7 100644 --- a/arch/arm/mach-at91/Kconfig +++ b/arch/arm/mach-at91/Kconfig @@ -42,6 +42,9 @@ config HAVE_AT91_I2S_MUX_CLK config HAVE_AT91_SAM9X60_PLL bool +config HAVE_AT91_SDRAMC + bool + config HAVE_AT91_DDRAMC bool diff --git a/arch/arm/mach-at91/Makefile b/arch/arm/mach-at91/Makefile index 301e0b761b26..777dc6d1aa3c 100644 --- a/arch/arm/mach-at91/Makefile +++ b/arch/arm/mach-at91/Makefile @@ -16,6 +16,7 @@ obj-$(CONFIG_BOOTM) += bootm-barebox.o obj-y += at91sam9_reset.o obj-y += at91sam9g45_reset.o obj-pbl-$(CONFIG_HAVE_AT91_DDRAMC) += ddramc.o +obj-pbl-$(CONFIG_HAVE_AT91_SDRAMC) += sdramc.o pbl-$(CONFIG_AT91_MCI_PBL) += xload-mmc.o pbl-$(CONFIG_AT91_MCI_PBL) += at91sam9_xload_mmc.o diff --git a/arch/arm/mach-at91/sdramc.c b/arch/arm/mach-at91/sdramc.c new file mode 100644 index 000000000000..655f24ecd9ad --- /dev/null +++ b/arch/arm/mach-at91/sdramc.c @@ -0,0 +1,47 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Copyright (c) 2020 Ahmad Fatoum <a.fatoum@xxxxxxxxxxxxxx> + */ + +#include <common.h> +#include <init.h> +#include <mach/at91/hardware.h> +#include <asm/barebox-arm.h> +#include <mach/at91/at91sam9_sdramc.h> +#include <asm/memory.h> +#include <pbl.h> +#include <io.h> + +void __noreturn at91sam9260_barebox_entry(void *boarddata) +{ + barebox_arm_entry(AT91_CHIPSELECT_1, + at91_get_sdram_size(IOMEM(AT91SAM9260_BASE_SDRAMC)), + boarddata); +} + +static int at91_sdramc_probe(struct device *dev) +{ + struct resource *iores; + void __iomem *base; + + iores = dev_request_mem_resource(dev, 0); + if (IS_ERR(iores)) + return PTR_ERR(iores); + base = IOMEM(iores->start); + + return arm_add_mem_device("ram0", AT91_CHIPSELECT_1, + at91_get_sdram_size(base)); +} + +static struct of_device_id at91_sdramc_dt_ids[] = { + { .compatible = "atmel,at91sam9260-sdramc" }, + { /* sentinel */ } +}; +MODULE_DEVICE_TABLE(of, at91_sdramc_dt_ids); + +static struct driver at91_sdramc_driver = { + .name = "at91sam9260-sdramc", + .probe = at91_sdramc_probe, + .of_compatible = at91_sdramc_dt_ids, +}; +mem_platform_driver(at91_sdramc_driver); diff --git a/include/mach/at91/at91sam9_sdramc.h b/include/mach/at91/at91sam9_sdramc.h index a4c88b24d4a0..2ba73cd2f2dc 100644 --- a/include/mach/at91/at91sam9_sdramc.h +++ b/include/mach/at91/at91sam9_sdramc.h @@ -13,6 +13,8 @@ #ifndef AT91SAM9_SDRAMC_H #define AT91SAM9_SDRAMC_H +#include <linux/compiler.h> + /* SDRAM Controller (SDRAMC) registers */ #define AT91_SDRAMC_MR 0x00 /* SDRAM Controller Mode Register */ #define AT91_SDRAMC_MODE (0xf << 0) /* Command Mode */ @@ -268,5 +270,7 @@ static inline bool at91sam9263_is_low_power_sdram(int bank) } } +void __noreturn at91sam9260_barebox_entry(void *boarddata); + #endif #endif -- 2.39.2