[PATCH v2 0/2] Calculate SDRAM size for Actions OWL SoCs

This small series allows us to calculate SDRAM size instead of guessing it.
Patch (1/2) is re-worked to support S900 SoC along with S700.
These changes have been tested on S700 based Cubieboard7-lite board, and it would be great if this can be tested on S900.
Amit Singh Tomar (2): Actions: OWL: Calculate SDRAM size arm: actions: remove "CONFIG_SYS_SDRAM_SIZE" for Actions Owl Semi SoCs
arch/arm/mach-owl/soc.c | 27 ++++++++++++++++++++++++++- include/configs/owl-common.h | 1 - 2 files changed, 26 insertions(+), 2 deletions(-)

Calculate the SDRAM size from DDR capacity register registers instead of using hard-coded value. This is quite useful to get correct size on differnt boards based on Actions OWL family of SoCs (S700 and S900).
There is no documentation available that talks about DDR registers, and this is very much taken from vendor source.
This commit lets Linux boot on Cubieboard7-lite(based on S700).
Signed-off-by: Amit Singh Tomar amittomer25@gmail.com --- Changes since v1: * added support for S900 * updated the commit message to reflect common OWL support. --- arch/arm/mach-owl/soc.c | 27 ++++++++++++++++++++++++++- 1 file changed, 26 insertions(+), 1 deletion(-)
diff --git a/arch/arm/mach-owl/soc.c b/arch/arm/mach-owl/soc.c index 409cbd319f20..2ae357e3672a 100644 --- a/arch/arm/mach-owl/soc.c +++ b/arch/arm/mach-owl/soc.c @@ -13,15 +13,40 @@ #include <asm/mach-types.h> #include <asm/psci.h>
+#define DMM_INTERLEAVE_BASE (0xe0290020) +#define DMM_INTERLEAVE_PER_CH_CFG (DMM_INTERLEAVE_BASE + 0x08) +#define DMM_MASTER_READ_TO (DMM_INTERLEAVE_BASE + 0x48) + DECLARE_GLOBAL_DATA_PTR;
+unsigned int get_owl_ram_size(void) +{ + __maybe_unused unsigned int val, cap, channel, channel_num; + + /* ddr capacity register initialized by ddr driver + * in early bootloader + */ +#if defined(CONFIG_MACH_S700) + val = (readl(DMM_INTERLEAVE_PER_CH_CFG) >> 8) & 0x7; + cap = (val + 1) * 256; +#elif defined(CONFIG_MACH_S900) + chennel_num = (readl(DMM_INTERLEAVE_BASE) >> 24) & 0xf; + channel = (ch_num >= 3) ? 1 : 0; + val = (readl(DMM_MASTER_READ_TO)) & 0xf; + cap = ((val + 1) << channel) * 256; +#endif + + return cap; +} + /* * dram_init - sets uboots idea of sdram size */ int dram_init(void) { - gd->ram_size = CONFIG_SYS_SDRAM_SIZE; + gd->ram_size = get_owl_ram_size() * 1024 * 1024; return 0; + }
/* This is called after dram_init() so use get_ram_size result */

Hi Amit,
On Fri, May 08, 2020 at 03:53:45PM +0530, Amit Singh Tomar wrote:
Calculate the SDRAM size from DDR capacity register registers instead of using hard-coded value. This is quite useful to get correct size on differnt boards based on Actions OWL family of SoCs (S700 and S900).
There is no documentation available that talks about DDR registers, and this is very much taken from vendor source.
This commit lets Linux boot on Cubieboard7-lite(based on S700).
Signed-off-by: Amit Singh Tomar amittomer25@gmail.com
Changes since v1:
- added support for S900
- updated the commit message to reflect common OWL support.
arch/arm/mach-owl/soc.c | 27 ++++++++++++++++++++++++++- 1 file changed, 26 insertions(+), 1 deletion(-)
diff --git a/arch/arm/mach-owl/soc.c b/arch/arm/mach-owl/soc.c index 409cbd319f20..2ae357e3672a 100644 --- a/arch/arm/mach-owl/soc.c +++ b/arch/arm/mach-owl/soc.c @@ -13,15 +13,40 @@ #include <asm/mach-types.h> #include <asm/psci.h>
+#define DMM_INTERLEAVE_BASE (0xe0290020) +#define DMM_INTERLEAVE_PER_CH_CFG (DMM_INTERLEAVE_BASE + 0x08) +#define DMM_MASTER_READ_TO (DMM_INTERLEAVE_BASE + 0x48)
DECLARE_GLOBAL_DATA_PTR;
+unsigned int get_owl_ram_size(void) +{
- __maybe_unused unsigned int val, cap, channel, channel_num;
- /* ddr capacity register initialized by ddr driver
* in early bootloader
*/
+#if defined(CONFIG_MACH_S700)
- val = (readl(DMM_INTERLEAVE_PER_CH_CFG) >> 8) & 0x7;
- cap = (val + 1) * 256;
+#elif defined(CONFIG_MACH_S900)
- chennel_num = (readl(DMM_INTERLEAVE_BASE) >> 24) & 0xf;
- channel = (ch_num >= 3) ? 1 : 0;
- val = (readl(DMM_MASTER_READ_TO)) & 0xf;
- cap = ((val + 1) << channel) * 256;
This doesn't work on Bubblegum96. But poking into the vendor tree, I'm able to come up with below working code:
val = (readl(DMM_INTERLEAVE_PER_CH_CFG) >> 8) & 0xf; cap = 64 * (1 << val);
So, you can use this and remove other stuffs. Also this function should be named as owl_get_ddr_cap().
Thanks, Mani
+#endif
- return cap;
+}
/*
- dram_init - sets uboots idea of sdram size
*/ int dram_init(void) {
- gd->ram_size = CONFIG_SYS_SDRAM_SIZE;
- gd->ram_size = get_owl_ram_size() * 1024 * 1024; return 0;
}
/* This is called after dram_init() so use get_ram_size result */
2.7.4

Hi Mani,
This doesn't work on Bubblegum96. But poking into the vendor tree, I'm able to come up with below working code:
val = (readl(DMM_INTERLEAVE_PER_CH_CFG) >> 8) & 0xf; cap = 64 * (1 << val);
So, you can use this and remove other stuffs. Also this function should be named as owl_get_ddr_cap().
Thanks for pointing this out, and I just sent v3 as v2 didn't even compile for Bubblegum96.
Would send the updated version that works on S900.
Thanks Amit.

Now that, we calculate SDRAM size by reading DDR registers, "CONFIG_SYS_SDRAM_SIZE" is no more needed.
This commit removes "CONFIG_SYS_SDRAM_SIZE" from common configuration file.
Signed-off-by: Amit Singh Tomar amittomer25@gmail.com --- include/configs/owl-common.h | 1 - 1 file changed, 1 deletion(-)
diff --git a/include/configs/owl-common.h b/include/configs/owl-common.h index f77a5fa4c114..7634578f856d 100644 --- a/include/configs/owl-common.h +++ b/include/configs/owl-common.h @@ -12,7 +12,6 @@
/* SDRAM Definitions */ #define CONFIG_SYS_SDRAM_BASE 0x0 -#define CONFIG_SYS_SDRAM_SIZE 0x80000000
/* Generic Timer Definitions */ #define COUNTER_FREQUENCY (24000000) /* 24MHz */
participants (3)
-
Amit Singh Tomar
-
Amit Tomer
-
Manivannan Sadhasivam