[Armadeus-commitlog] armadeus/u-boot branch, armadeus-2024.01, updated. 4be1b355534698ab738ab74e82
Brought to you by:
sszy
|
From: sszy <ss...@us...> - 2024-11-13 12:03:50
|
This is an automated email from the git hooks/post-receive script. It was
generated because a ref change was pushed to the repository containing
the project "armadeus/u-boot".
The branch, armadeus-2024.01 has been updated
via 4be1b355534698ab738ab74e82d2000550ce7d04 (commit)
via 81914fa8e182d456b1c68e446e0dd7da8f2dd9a5 (commit)
via 67c04f0ae2235b5a3960e6a1eb5f4a3114fbe9f3 (commit)
via 69af6c83b8b33776886380faf1b441cd5f789421 (commit)
via bdf64093bd36c44737b7808a860ae7b75abe533c (commit)
via 5054cf3ba2178ffc9013ab5fea9bd592c92727d2 (commit)
via 67c1e47e512e7348676e3c3b416aca3bd91f827d (commit)
via 25d11bb117a222f0a5d92ecfc82cb85c85a7005f (commit)
via 52814d53ab98c2fb5b84d7ca034fd250677b73dc (commit)
via 15b2cee915148f78736205f835ab435531d35561 (commit)
via a91bc0fd7a4c847167932f58d7b2e0f06af1ec3e (commit)
via 9311a40e6176758b48605dcc5e890b77f6f5806d (commit)
via 2215fe740f71832e1b340f132029c2a8e0e7dfeb (commit)
via 9a74b4723abaea74b6e31d268c0f01e73b1837f1 (commit)
via be0386b08dac39380da00ec31d29004990e4a998 (commit)
via 8ab6fa52806f1833c33e4f5c766cd0e98cdbe30a (commit)
via ed08e731239ea1890817323beedef76c4cca6eb2 (commit)
via f158f14f78e688fc68d51ea8c5800ccab13fd1e4 (commit)
via 21770d5b93791a429062381be0c91dcf577ba2b3 (commit)
via dd6e77a8d66bdcbee77ca6d8f56638575ae29ec3 (commit)
via 7e05a33df47bb7b3944179d54f72b56aa24a3f65 (commit)
via a046344ef5880353772affada28c9da6fe649bec (commit)
via 406a451e8e2aacd98f578fdaf4f082f4acf556d9 (commit)
via 4ff376c0e443a094e6804d317634b568ad3ce73e (commit)
from 750950a0beb840862c3642477038361ff63d2520 (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
- Log -----------------------------------------------------------------
commit 4be1b355534698ab738ab74e82d2000550ce7d04
Author: Sébastien Szymanski <seb...@ar...>
Date: Tue Nov 12 14:43:08 2024 +0100
imx: fix disable_thermal_cpu_nodes()
Pass correct type to fdt_setprop. This fixes the following error seen on
Linux:
[ 1.359376] OF: /thermal-zones/cpu-thermal/cooling-maps/map0: could not find phandle -1058540899
[ 1.368221] thermal_sys: Add a cooling_device property with at least one device
[ 1.375526] thermal thermal_zone0: binding zone cpu-thermal with cdev thermal-devfreq-0 failed:-2
Fixes: ed08e731239e ("imx: Generalize disable_cpu_nodes")
commit 81914fa8e182d456b1c68e446e0dd7da8f2dd9a5
Author: Sébastien Szymanski <seb...@ar...>
Date: Fri Nov 8 12:37:45 2024 +0100
imx9: opos93: add opos93 with i.MX9301 and 512MB of RAM support
commit 67c04f0ae2235b5a3960e6a1eb5f4a3114fbe9f3
Author: Sébastien Szymanski <seb...@ar...>
Date: Fri Nov 8 12:24:22 2024 +0100
imx9: opos93: rename lpddr4 timings
commit 69af6c83b8b33776886380faf1b441cd5f789421
Author: Sébastien Szymanski <seb...@ar...>
Date: Fri Nov 8 12:06:09 2024 +0100
configs: opos93dev_defconfig: enable ARCH_MISC_INIT
commit bdf64093bd36c44737b7808a860ae7b75abe533c
Author: Michael Trimarchi <mi...@am...>
Date: Tue Jul 2 12:26:18 2024 +0200
clk: imx: Fix wrong flags assignment clk-composite-93
The mux flags (u8), div flags (u8), and gate flags (u8) are not the clk
flags (unsigned long). They have different meanings
Signed-off-by: Michael Trimarchi <mi...@am...>
(cherry picked from commit a66b2ce6bda1c91754a4a0cfe9ec849a387b279e)
commit 5054cf3ba2178ffc9013ab5fea9bd592c92727d2
Author: Ye Li <ye...@nx...>
Date: Thu Sep 19 12:01:29 2024 +0800
imx9: Add 233Mhz DDR PLL frequency
To support 1.866GTS LPDDR4x timing script, need to add 233Mhz freq
to DDR PLL for second mission point at 933MTS. Otherwise DDR training
will fail.
Reviewed-by: Peng Fan <pen...@nx...>
Signed-off-by: Ye Li <ye...@nx...>
Signed-off-by: Peng Fan <pen...@nx...>
(cherry picked from commit 1b631589d4844a129e1019160fef7aeda6fb50ff)
commit 67c1e47e512e7348676e3c3b416aca3bd91f827d
Author: Ye Li <ye...@nx...>
Date: Thu Sep 19 12:01:33 2024 +0800
imx93: Add Low performance parts 9302/9301 support
Add support for iMX93 low performance parts 9302 and 9301 which
restrict to low drive voltage only.
The parts run A55 max speed at 900Mhz and M33 at 133Mhz, have NPU
and A55 core1 (9301) disabled.
Reviewed-by: Peng Fan <pen...@nx...>
Signed-off-by: Ye Li <ye...@nx...>
Signed-off-by: Peng Fan <pen...@nx...>
[sszy: add disable_lpm() as done by downstream]
(cherry picked from commit 5ee773e60b3f5e024d1177d4be52c07d741c228d)
commit 25d11bb117a222f0a5d92ecfc82cb85c85a7005f
Author: Hou Zhiqiang <Zhi...@nx...>
Date: Thu Aug 1 11:59:54 2024 +0800
cpu: imx: implement release_core callback
Release the secondary cores through the PSCI request.
Signed-off-by: Hou Zhiqiang <Zhi...@nx...>
(cherry picked from commit 8a73b5b680a849193287decf0ca3470fbd764e42)
commit 52814d53ab98c2fb5b84d7ca034fd250677b73dc
Author: Hou Zhiqiang <Zhi...@nx...>
Date: Thu Aug 1 11:59:48 2024 +0800
cpu: sandbox: implement release_core callback
Add empty release CPU core function for testing.
Signed-off-by: Hou Zhiqiang <Zhi...@nx...>
Reviewed-by: Simon Glass <sj...@ch...>
(cherry picked from commit 3694edcabc4b62717cd71f64caacd4df2dbd5abd)
commit 15b2cee915148f78736205f835ab435531d35561
Author: Hou Zhiqiang <Zhi...@nx...>
Date: Thu Aug 1 11:59:47 2024 +0800
cpu: add release_core callback
Add a new callback release_core to the cpu_ops, which is used to
release a CPU core to run baremetal or RTOS application on a SoC
with multiple CPU cores.
Signed-off-by: Hou Zhiqiang <Zhi...@nx...>
Reviewed-by: Simon Glass <sj...@ch...>
(cherry picked from commit f2c306cd991a1c383de66ece1dd2301cd6b4b54b)
commit a91bc0fd7a4c847167932f58d7b2e0f06af1ec3e
Author: Peng Fan <pen...@nx...>
Date: Fri Oct 18 15:34:32 2024 +0800
cpu: imx8_cpu: Avoid revision to corrupt device tree
U-Boot device tree is padded just after U-Boot proper.
After the whole stuff loaded to DRAM space, the device tree
area is conflict with BSS region before U-Boot relocation.
So any write to BSS area before reloc_fdt will corrupt the
device tree. Without the fix, there is issue that âbinman_init
failed:-2â on i.MX8MP-EVK board.
Drop 'revision' and use malloc area in cpu_imx_plat->rev.
Signed-off-by: Peng Fan <pen...@nx...>
(cherry picked from commit 9b1cecdd9b6eaf22c4fa268430669ceff0c48786)
commit 9311a40e6176758b48605dcc5e890b77f6f5806d
Author: Hou Zhiqiang <Zhi...@nx...>
Date: Thu Aug 1 11:59:53 2024 +0800
cpu: imx: Add i.MX 8M series SoCs
Add i.MX 8M Mini, Nano and Plus SoCs support.
Signed-off-by: Hou Zhiqiang <Zhi...@nx...>
(cherry picked from commit 01d94d006a2a9f02e76fb1660a6e8f64731bfe03)
commit 2215fe740f71832e1b340f132029c2a8e0e7dfeb
Author: Hou Zhiqiang <Zhi...@nx...>
Date: Thu Aug 1 11:59:52 2024 +0800
cpu: imx: removed the tail '\n' of the CPU description
Return CPU description string without newline character in the end.
Signed-off-by: Hou Zhiqiang <Zhi...@nx...>
(cherry picked from commit b7ed7418edb5378fb42a0e3744197b3d6a0383c8)
commit 9a74b4723abaea74b6e31d268c0f01e73b1837f1
Author: Hou Zhiqiang <Zhi...@nx...>
Date: Thu Aug 1 11:59:51 2024 +0800
cpu: imx: fix the CPU type field width
Increase one more bit to cover all CPU types. Otherwise it shows
wrong CPU info on some platforms, such as i.MX8M Plus:
U-Boot 2024.04+g674440bc73e+p0 (Jun 06 2024 - 10:05:34 +0000)
CPU: NXP i.MX8MM Rev1.1 A53 at 4154504685 MHz at 30C
Model: NXP i.MX8MPlus LPDDR4 EVK board
Signed-off-by: Hou Zhiqiang <Zhi...@nx...>
(cherry picked from commit 37adedfb2116ed28b49c2581baf0f7eae69b97e1)
commit be0386b08dac39380da00ec31d29004990e4a998
Author: Hou Zhiqiang <Zhi...@nx...>
Date: Thu Aug 1 11:59:50 2024 +0800
cpu: imx: fix the CPU frequency in cpu_imx_get_info()
The cpu_freq stores the current CPU frequency in Hz.
Signed-off-by: Hou Zhiqiang <Zhi...@nx...>
Reviewed-by: Michael Trimarchi <mi...@am...>
(cherry picked from commit dc86c11556c194a6a0beda82ee96549ad66d0aec)
commit 8ab6fa52806f1833c33e4f5c766cd0e98cdbe30a
Author: Peng Fan <pen...@nx...>
Date: Thu Sep 19 12:01:32 2024 +0800
imx9: soc: Disable cpu1 for variants that only has one A55 core
Disale CPU1 for i.MX93 variants that only has one A55 core and update
cooling maps.
Signed-off-by: Peng Fan <pen...@nx...>
(cherry picked from commit 98f948ec531ab42942becd4cfaea63da53a38b73)
commit ed08e731239ea1890817323beedef76c4cca6eb2
Author: Peng Fan <pen...@nx...>
Date: Thu Sep 19 12:01:31 2024 +0800
imx: Generalize disable_cpu_nodes
disable_cpu_nodes could be reused by i.MX9, so move disable_cpu_nodes
out from mach-imx/imx8m/soc.c to mach-imx/fdt.c and update
disable_cpu_nodes to make it easy to support different socs.
Signed-off-by: Peng Fan <pen...@nx...>
(cherry picked from commit cd9b3de763563f628a2aaedc4b19841970035a21)
commit f158f14f78e688fc68d51ea8c5800ccab13fd1e4
Author: Peng Fan <pen...@nx...>
Date: Thu Sep 19 12:01:30 2024 +0800
imx8m: soc: Drop disable_pmu_cpu_nodes
i.MX8M use PPI for PMU interrupts, there is no reason to update
interrupt-affinity for PMU even interrupt-affinity was wrongly added
to device tree before.
Signed-off-by: Peng Fan <pen...@nx...>
(cherry picked from commit 16fc64b5533e97f0eb43e82113e62b236728d23e)
commit 21770d5b93791a429062381be0c91dcf577ba2b3
Author: Ye Li <ye...@nx...>
Date: Thu Sep 19 12:01:27 2024 +0800
imx9: clock: Update clock init function and sequence
Since we use SPEED GRADE fuse to set A55 frequency, remove the
set_arm_core_low_drive_clk function which has hard coded frequency.
And adjust clock_init called sequence and split it to early and late
functions.
Set the authen register in early function, because CCF driver checks
NS bit.
Set bus and core clock in late function, because the fuse read and
SoC type/rev depend on ELE.
Reviewed-by: Peng Fan <pen...@nx...>
Signed-off-by: Ye Li <ye...@nx...>
Signed-off-by: Peng Fan <pen...@nx...>
(cherry picked from commit 7872a986e5834bcc387788968e7f9f520f2cb140)
commit dd6e77a8d66bdcbee77ca6d8f56638575ae29ec3
Author: Ye Li <ye...@nx...>
Date: Thu Sep 19 12:01:26 2024 +0800
imx9: soc: Add function to get target voltage mode
Replace the static CONFIG_IMX9_LOW_DRIVE_MODE with runtime target
voltage mode by checking the part's SPEED GRADE fuse.
SPL will configure to highest A55 speed which is indicated by the SPEED
fuse and select corresponding voltage mode.
Reviewed-by: Peng Fan <pen...@nx...>
Signed-off-by: Ye Li <ye...@nx...>
Signed-off-by: Peng Fan <pen...@nx...>
[sszy: reduce lcd controller clock as down on downstream]
(cherry picked from commit 46f72ebad960c5b7d66ec3d901fc6c957dd2a395)
commit 7e05a33df47bb7b3944179d54f72b56aa24a3f65
Author: Peng Fan <pen...@nx...>
Date: Thu Sep 19 12:01:25 2024 +0800
imx9: soc: Print ELE information
The boot image includes Edgelock Enclave(ELE) Firmware. Print the
information out to let user know which version firmware is being used.
Signed-off-by: Peng Fan <pen...@nx...>
(cherry picked from commit 3166537ae42006df649c654fd7ceba40554643fa)
commit a046344ef5880353772affada28c9da6fe649bec
Author: Peng Fan <pen...@nx...>
Date: Thu Sep 19 12:01:23 2024 +0800
imx9: soc: Change FSB directly access to fuse API
To support OSCCA enabled part which has disabled FSB access from SOC,
change directly read from FSB to use fuse_read API.
Signed-off-by: Peng Fan <pen...@nx...>
(cherry picked from commit 2f00c3e493473553cb47ef9ae6918d38b7ba9c63)
commit 406a451e8e2aacd98f578fdaf4f082f4acf556d9
Author: Ye Li <ye...@nx...>
Date: Thu Mar 28 18:49:18 2024 +0800
arm: imx9: Fix MMU map table overlap
The size for flexspi AHB buffer space is wrong, so correct it.
Signed-off-by: Ye Li <ye...@nx...>
(cherry picked from commit f6ee245cabc470f8f9f51fd49c264aa31e7340ed)
commit 4ff376c0e443a094e6804d317634b568ad3ce73e
Author: Primoz Fiser <pri...@no...>
Date: Thu Jan 11 13:56:25 2024 +0100
imx: imx9: fixup thermal trips from fuses
Read i.MX9 CPU temp grade from fuses and fixup thermal trips in Linux
device-tree accordingly.
Based on commit 0543a1ed2787 ("imx8m: fixup thermal trips")
Signed-off-by: Primoz Fiser <pri...@no...>
(cherry picked from commit 3233349fa6e2f64ae7f03d9d0ccce3df7a5e7721)
-----------------------------------------------------------------------
Summary of changes:
arch/arm/include/asm/arch-imx/cpu.h | 2 +
arch/arm/include/asm/arch-imx9/clock.h | 3 +-
arch/arm/include/asm/arch-imx9/imx-regs.h | 3 +
arch/arm/include/asm/arch-imx9/opos93.h | 4 +-
arch/arm/include/asm/arch-imx9/sys_proto.h | 11 +
arch/arm/include/asm/mach-imx/sys_proto.h | 7 +-
arch/arm/mach-imx/Makefile | 7 +
arch/arm/mach-imx/fdt.c | 87 +++++++
arch/arm/mach-imx/imx8m/soc.c | 137 +----------
arch/arm/mach-imx/imx9/Kconfig | 3 +
arch/arm/mach-imx/imx9/Makefile | 3 +-
arch/arm/mach-imx/imx9/clock.c | 39 ++-
arch/arm/mach-imx/imx9/opos93.c | 16 +-
...dr4_timing.c => opos9301_512mb_lpddr4_timing.c} | 182 +++++++-------
...pddr4_timing.c => opos9352_1gb_lpddr4_timing.c} | 2 +-
...dr4_timing.c => opos9352_512mb_lpddr4_timing.c} | 2 +-
arch/arm/mach-imx/imx9/soc.c | 271 ++++++++++++++++++++-
board/freescale/imx93_evk/spl.c | 6 +-
configs/opos93dev_defconfig | 1 +
drivers/clk/imx/clk-composite-93.c | 2 -
drivers/cpu/cpu-uclass.c | 10 +
drivers/cpu/cpu_sandbox.c | 6 +
drivers/cpu/imx8_cpu.c | 74 ++++--
drivers/ddr/imx/phy/ddrphy_utils.c | 4 +
include/cpu.h | 15 ++
25 files changed, 630 insertions(+), 267 deletions(-)
create mode 100644 arch/arm/mach-imx/fdt.c
copy arch/arm/mach-imx/imx9/{opos93_lpddr4_timing.c => opos9301_512mb_lpddr4_timing.c} (94%)
rename arch/arm/mach-imx/imx9/{opos93_1gb_lpddr4_timing.c => opos9352_1gb_lpddr4_timing.c} (99%)
rename arch/arm/mach-imx/imx9/{opos93_lpddr4_timing.c => opos9352_512mb_lpddr4_timing.c} (99%)
diff --git a/arch/arm/include/asm/arch-imx/cpu.h b/arch/arm/include/asm/arch-imx/cpu.h
index cbd2717f97..b0468a1a13 100644
--- a/arch/arm/include/asm/arch-imx/cpu.h
+++ b/arch/arm/include/asm/arch-imx/cpu.h
@@ -68,6 +68,8 @@
#define MXC_CPU_IMX9321 0xC6 /* dummy ID */
#define MXC_CPU_IMX9312 0xC7 /* dummy ID */
#define MXC_CPU_IMX9311 0xC8 /* dummy ID */
+#define MXC_CPU_IMX9302 0xC9 /* dummy ID */
+#define MXC_CPU_IMX9301 0xCA /* dummy ID */
#define MXC_SOC_MX6 0x60
#define MXC_SOC_MX7 0x70
diff --git a/arch/arm/include/asm/arch-imx9/clock.h b/arch/arm/include/asm/arch-imx9/clock.h
index 1169ffd74d..a257d1557c 100644
--- a/arch/arm/include/asm/arch-imx9/clock.h
+++ b/arch/arm/include/asm/arch-imx9/clock.h
@@ -211,7 +211,8 @@ struct imx_clk_setting {
u32 div;
};
-int clock_init(void);
+int clock_init_early(void);
+int clock_init_late(void);
u32 get_clk_src_rate(enum ccm_clk_src source);
u32 get_lpuart_clk(void);
void init_uart_clk(u32 index);
diff --git a/arch/arm/include/asm/arch-imx9/imx-regs.h b/arch/arm/include/asm/arch-imx9/imx-regs.h
index 9953c33b73..b8c22a26ca 100644
--- a/arch/arm/include/asm/arch-imx9/imx-regs.h
+++ b/arch/arm/include/asm/arch-imx9/imx-regs.h
@@ -51,6 +51,9 @@
#define MARKETING_GRADING_MASK GENMASK(5, 4)
#define SPEED_GRADING_MASK GENMASK(11, 6)
+#define NUM_WORDS_PER_BANK 8
+#define HW_CFG1 19
+#define HW_CFG2 20
#if !(defined(__KERNEL_STRICT_NAMES) || defined(__ASSEMBLY__))
#include <asm/types.h>
diff --git a/arch/arm/include/asm/arch-imx9/opos93.h b/arch/arm/include/asm/arch-imx9/opos93.h
index d5beb7df14..dfa6405453 100644
--- a/arch/arm/include/asm/arch-imx9/opos93.h
+++ b/arch/arm/include/asm/arch-imx9/opos93.h
@@ -7,6 +7,8 @@
#ifndef __ASM_ARCH_IMX93_OPOS93_H
#define __ASM_ARCH_IMX93_OPOS93_H
-extern struct dram_timing_info opos93_1gb_dram_timing;
+extern struct dram_timing_info opos9301_512mb_dram_timing;
+extern struct dram_timing_info opos9352_512mb_dram_timing;
+extern struct dram_timing_info opos9352_1gb_dram_timing;
#endif
diff --git a/arch/arm/include/asm/arch-imx9/sys_proto.h b/arch/arm/include/asm/arch-imx9/sys_proto.h
index 2f7a129275..e4bf6a6342 100644
--- a/arch/arm/include/asm/arch-imx9/sys_proto.h
+++ b/arch/arm/include/asm/arch-imx9/sys_proto.h
@@ -8,7 +8,18 @@
#include <asm/mach-imx/sys_proto.h>
+enum imx9_soc_voltage_mode {
+ VOLT_LOW_DRIVE = 0,
+ VOLT_NOMINAL_DRIVE,
+ VOLT_OVER_DRIVE,
+};
+
void soc_power_init(void);
bool m33_is_rom_kicked(void);
int m33_prepare(void);
+
+enum imx9_soc_voltage_mode soc_target_voltage_mode(void);
+
+#define is_voltage_mode(mode) (soc_target_voltage_mode() == (mode))
+
#endif
diff --git a/arch/arm/include/asm/mach-imx/sys_proto.h b/arch/arm/include/asm/mach-imx/sys_proto.h
index 31ae179b21..c146a223b7 100644
--- a/arch/arm/include/asm/mach-imx/sys_proto.h
+++ b/arch/arm/include/asm/mach-imx/sys_proto.h
@@ -85,7 +85,8 @@ struct bd_info;
#define is_imx93() (is_cpu_type(MXC_CPU_IMX93) || is_cpu_type(MXC_CPU_IMX9331) || \
is_cpu_type(MXC_CPU_IMX9332) || is_cpu_type(MXC_CPU_IMX9351) || \
is_cpu_type(MXC_CPU_IMX9322) || is_cpu_type(MXC_CPU_IMX9321) || \
- is_cpu_type(MXC_CPU_IMX9312) || is_cpu_type(MXC_CPU_IMX9311))
+ is_cpu_type(MXC_CPU_IMX9312) || is_cpu_type(MXC_CPU_IMX9311) || \
+ is_cpu_type(MXC_CPU_IMX9302) || is_cpu_type(MXC_CPU_IMX9301))
#define is_imx9351() (is_cpu_type(MXC_CPU_IMX9351))
#define is_imx9332() (is_cpu_type(MXC_CPU_IMX9332))
#define is_imx9331() (is_cpu_type(MXC_CPU_IMX9331))
@@ -93,6 +94,8 @@ struct bd_info;
#define is_imx9321() (is_cpu_type(MXC_CPU_IMX9321))
#define is_imx9312() (is_cpu_type(MXC_CPU_IMX9312))
#define is_imx9311() (is_cpu_type(MXC_CPU_IMX9311))
+#define is_imx9302() (is_cpu_type(MXC_CPU_IMX9302))
+#define is_imx9301() (is_cpu_type(MXC_CPU_IMX9301))
#define is_imxrt1020() (is_cpu_type(MXC_CPU_IMXRT1020))
#define is_imxrt1050() (is_cpu_type(MXC_CPU_IMXRT1050))
@@ -275,4 +278,6 @@ void enable_ca7_smp(void);
enum boot_device get_boot_device(void);
+int disable_cpu_nodes(void *blob, const char * const *nodes_path,
+ u32 num_disabled_cores, u32 max_cores);
#endif
diff --git a/arch/arm/mach-imx/Makefile b/arch/arm/mach-imx/Makefile
index a3b44c93e3..ab6d370add 100644
--- a/arch/arm/mach-imx/Makefile
+++ b/arch/arm/mach-imx/Makefile
@@ -12,6 +12,7 @@ endif
ifeq ($(SOC),$(filter $(SOC),imx8m))
ifneq ($(CONFIG_SPL_BUILD),y)
obj-$(CONFIG_IMX_BOOTAUX) += imx_bootaux.o
+obj-y += fdt.o
endif
obj-$(CONFIG_ENV_IS_IN_MMC) += mmc_env.o
obj-$(CONFIG_FEC_MXC) += mac.o
@@ -21,6 +22,12 @@ obj-$(CONFIG_IMX_HAB) += hab.o
obj-y += cpu.o
endif
+ifeq ($(SOC),$(filter $(SOC),imx8m imx9))
+ifneq ($(CONFIG_SPL_BUILD),y)
+obj-y += fdt.o
+endif
+endif
+
ifeq ($(SOC),$(filter $(SOC),mx5 mx6))
obj-y += cpu.o speed.o
ifneq ($(CONFIG_MX51),y)
diff --git a/arch/arm/mach-imx/fdt.c b/arch/arm/mach-imx/fdt.c
new file mode 100644
index 0000000000..6db43c3760
--- /dev/null
+++ b/arch/arm/mach-imx/fdt.c
@@ -0,0 +1,87 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * Copyright 2024 NXP
+ */
+
+#include <errno.h>
+#include <fdtdec.h>
+#include <malloc.h>
+#include <asm/arch/sys_proto.h>
+
+static void disable_thermal_cpu_nodes(void *blob, u32 num_disabled_cores, u32 max_cores)
+{
+ static const char * const thermal_path[] = {
+ "/thermal-zones/cpu-thermal/cooling-maps/map0"
+ };
+
+ int nodeoff, cnt, i, ret, j;
+ u32 num_le32 = max_cores * 3;
+ u32 *cooling_dev = (u32 *)malloc(num_le32 * sizeof(__le32));
+
+ if (!cooling_dev) {
+ printf("failed to alloc cooling dev\n");
+ return;
+ }
+
+ for (i = 0; i < ARRAY_SIZE(thermal_path); i++) {
+ nodeoff = fdt_path_offset(blob, thermal_path[i]);
+ if (nodeoff < 0)
+ continue; /* Not found, skip it */
+
+ cnt = fdtdec_get_int_array_count(blob, nodeoff, "cooling-device",
+ cooling_dev, num_le32);
+ if (cnt < 0)
+ continue;
+
+ if (cnt != num_le32)
+ printf("Warning: %s, cooling-device count %d\n", thermal_path[i], cnt);
+
+ for (j = 0; j < cnt; j++)
+ cooling_dev[j] = cpu_to_fdt32(cooling_dev[j]);
+
+ ret = fdt_setprop(blob, nodeoff, "cooling-device", cooling_dev,
+ sizeof(__le32) * (num_le32 - num_disabled_cores * 3));
+ if (ret < 0) {
+ printf("Warning: %s, cooling-device setprop failed %d\n",
+ thermal_path[i], ret);
+ continue;
+ }
+
+ printf("Update node %s, cooling-device prop\n", thermal_path[i]);
+ }
+
+ free(cooling_dev);
+}
+
+int disable_cpu_nodes(void *blob, const char * const *nodes_path, u32 num_disabled_cores,
+ u32 max_cores)
+{
+ u32 i = 0;
+ int rc;
+ int nodeoff;
+
+ if (max_cores == 0 || (num_disabled_cores > (max_cores - 1)))
+ return -EINVAL;
+
+ i = max_cores - num_disabled_cores;
+
+ for (; i < max_cores; i++) {
+ nodeoff = fdt_path_offset(blob, nodes_path[i]);
+ if (nodeoff < 0)
+ continue; /* Not found, skip it */
+
+ debug("Found %s node\n", nodes_path[i]);
+
+ rc = fdt_del_node(blob, nodeoff);
+ if (rc < 0) {
+ printf("Unable to delete node %s, err=%s\n",
+ nodes_path[i], fdt_strerror(rc));
+ } else {
+ printf("Delete node %s\n", nodes_path[i]);
+ }
+ }
+
+ disable_thermal_cpu_nodes(blob, num_disabled_cores, max_cores);
+
+ return 0;
+}
diff --git a/arch/arm/mach-imx/imx8m/soc.c b/arch/arm/mach-imx/imx8m/soc.c
index 39802d6a79..d25b92e46e 100644
--- a/arch/arm/mach-imx/imx8m/soc.c
+++ b/arch/arm/mach-imx/imx8m/soc.c
@@ -1125,117 +1125,6 @@ int disable_dsp_nodes(void *blob)
return disable_fdt_nodes(blob, nodes_path_8mp, ARRAY_SIZE(nodes_path_8mp));
}
-static void disable_thermal_cpu_nodes(void *blob, u32 disabled_cores)
-{
- static const char * const thermal_path[] = {
- "/thermal-zones/cpu-thermal/cooling-maps/map0"
- };
-
- int nodeoff, cnt, i, ret, j;
- u32 cooling_dev[12];
-
- for (i = 0; i < ARRAY_SIZE(thermal_path); i++) {
- nodeoff = fdt_path_offset(blob, thermal_path[i]);
- if (nodeoff < 0)
- continue; /* Not found, skip it */
-
- cnt = fdtdec_get_int_array_count(blob, nodeoff, "cooling-device", cooling_dev, 12);
- if (cnt < 0)
- continue;
-
- if (cnt != 12)
- printf("Warning: %s, cooling-device count %d\n", thermal_path[i], cnt);
-
- for (j = 0; j < cnt; j++)
- cooling_dev[j] = cpu_to_fdt32(cooling_dev[j]);
-
- ret = fdt_setprop(blob, nodeoff, "cooling-device", &cooling_dev,
- sizeof(u32) * (12 - disabled_cores * 3));
- if (ret < 0) {
- printf("Warning: %s, cooling-device setprop failed %d\n",
- thermal_path[i], ret);
- continue;
- }
-
- printf("Update node %s, cooling-device prop\n", thermal_path[i]);
- }
-}
-
-static void disable_pmu_cpu_nodes(void *blob, u32 disabled_cores)
-{
- static const char * const pmu_path[] = {
- "/pmu"
- };
-
- int nodeoff, cnt, i, ret, j;
- u32 irq_affinity[4];
-
- for (i = 0; i < ARRAY_SIZE(pmu_path); i++) {
- nodeoff = fdt_path_offset(blob, pmu_path[i]);
- if (nodeoff < 0)
- continue; /* Not found, skip it */
-
- cnt = fdtdec_get_int_array_count(blob, nodeoff, "interrupt-affinity",
- irq_affinity, 4);
- if (cnt < 0)
- continue;
-
- if (cnt != 4)
- printf("Warning: %s, interrupt-affinity count %d\n", pmu_path[i], cnt);
-
- for (j = 0; j < cnt; j++)
- irq_affinity[j] = cpu_to_fdt32(irq_affinity[j]);
-
- ret = fdt_setprop(blob, nodeoff, "interrupt-affinity", &irq_affinity,
- sizeof(u32) * (4 - disabled_cores));
- if (ret < 0) {
- printf("Warning: %s, interrupt-affinity setprop failed %d\n",
- pmu_path[i], ret);
- continue;
- }
-
- printf("Update node %s, interrupt-affinity prop\n", pmu_path[i]);
- }
-}
-
-static int disable_cpu_nodes(void *blob, u32 disabled_cores)
-{
- static const char * const nodes_path[] = {
- "/cpus/cpu@1",
- "/cpus/cpu@2",
- "/cpus/cpu@3",
- };
- u32 i = 0;
- int rc;
- int nodeoff;
-
- if (disabled_cores > 3)
- return -EINVAL;
-
- i = 3 - disabled_cores;
-
- for (; i < 3; i++) {
- nodeoff = fdt_path_offset(blob, nodes_path[i]);
- if (nodeoff < 0)
- continue; /* Not found, skip it */
-
- debug("Found %s node\n", nodes_path[i]);
-
- rc = fdt_del_node(blob, nodeoff);
- if (rc < 0) {
- printf("Unable to delete node %s, err=%s\n",
- nodes_path[i], fdt_strerror(rc));
- } else {
- printf("Delete node %s\n", nodes_path[i]);
- }
- }
-
- disable_thermal_cpu_nodes(blob, disabled_cores);
- disable_pmu_cpu_nodes(blob, disabled_cores);
-
- return 0;
-}
-
static int cleanup_nodes_for_efi(void *blob)
{
static const char * const path[][2] = {
@@ -1387,6 +1276,13 @@ static int ft_add_optee_node(void *fdt, struct bd_info *bd)
int ft_system_setup(void *blob, struct bd_info *bd)
{
+ static const char * const nodes_path[] = {
+ "/cpus/cpu@0",
+ "/cpus/cpu@1",
+ "/cpus/cpu@2",
+ "/cpus/cpu@3",
+ };
+
#ifdef CONFIG_IMX8MQ
int i = 0;
int rc;
@@ -1430,13 +1326,6 @@ usb_modify_speed:
/* Disable the CPU idle for A0 chip since the HW does not support it */
if (is_soc_rev(CHIP_REV_1_0)) {
- static const char * const nodes_path[] = {
- "/cpus/cpu@0",
- "/cpus/cpu@1",
- "/cpus/cpu@2",
- "/cpus/cpu@3",
- };
-
for (i = 0; i < ARRAY_SIZE(nodes_path); i++) {
nodeoff = fdt_path_offset(blob, nodes_path[i]);
if (nodeoff < 0)
@@ -1468,16 +1357,16 @@ usb_modify_speed:
}
if (is_imx8md())
- disable_cpu_nodes(blob, 2);
+ disable_cpu_nodes(blob, nodes_path, 2, 4);
#elif defined(CONFIG_IMX8MM)
if (is_imx8mml() || is_imx8mmdl() || is_imx8mmsl())
disable_vpu_nodes(blob);
if (is_imx8mmd() || is_imx8mmdl())
- disable_cpu_nodes(blob, 2);
+ disable_cpu_nodes(blob, nodes_path, 2, 4);
else if (is_imx8mms() || is_imx8mmsl())
- disable_cpu_nodes(blob, 3);
+ disable_cpu_nodes(blob, nodes_path, 3, 4);
#elif defined(CONFIG_IMX8MN)
if (is_imx8mnl() || is_imx8mndl() || is_imx8mnsl())
@@ -1494,9 +1383,9 @@ usb_modify_speed:
#endif
if (is_imx8mnd() || is_imx8mndl() || is_imx8mnud())
- disable_cpu_nodes(blob, 2);
+ disable_cpu_nodes(blob, nodes_path, 2, 4);
else if (is_imx8mns() || is_imx8mnsl() || is_imx8mnus())
- disable_cpu_nodes(blob, 3);
+ disable_cpu_nodes(blob, nodes_path, 3, 4);
#elif defined(CONFIG_IMX8MP)
if (is_imx8mpul()) {
@@ -1523,7 +1412,7 @@ usb_modify_speed:
disable_dsp_nodes(blob);
if (is_imx8mpd())
- disable_cpu_nodes(blob, 2);
+ disable_cpu_nodes(blob, nodes_path, 2, 4);
#endif
cleanup_nodes_for_efi(blob);
diff --git a/arch/arm/mach-imx/imx9/Kconfig b/arch/arm/mach-imx/imx9/Kconfig
index 84fee0b70c..230d08c368 100644
--- a/arch/arm/mach-imx/imx9/Kconfig
+++ b/arch/arm/mach-imx/imx9/Kconfig
@@ -23,6 +23,8 @@ config IMX93
config IMX93_OPOS93
bool
select IMX93
+ select OF_SYSTEM_SETUP
+ select OF_BOARD_FIXUP
config SYS_SOC
default "imx9"
@@ -33,6 +35,7 @@ choice
config TARGET_IMX93_11X11_EVK
bool "imx93_11x11_evk"
+ select OF_BOARD_FIXUP
select IMX93
config TARGET_OPOS93DEV
diff --git a/arch/arm/mach-imx/imx9/Makefile b/arch/arm/mach-imx/imx9/Makefile
index 7376d51f8a..b4d28e7f5c 100644
--- a/arch/arm/mach-imx/imx9/Makefile
+++ b/arch/arm/mach-imx/imx9/Makefile
@@ -4,7 +4,8 @@
obj-y += lowlevel_init.o
obj-y += soc.o clock.o clock_root.o trdc.o
-obj-$(CONFIG_IMX93_OPOS93) += opos93_lpddr4_timing.o opos93_1gb_lpddr4_timing.o opos93.o
+obj-$(CONFIG_IMX93_OPOS93) += opos9352_512mb_lpddr4_timing.o opos9352_1gb_lpddr4_timing.o \
+ opos9301_512mb_lpddr4_timing.o opos93.o
#ifndef CONFIG_SPL_BUILD
obj-y += imx_bootaux.o
diff --git a/arch/arm/mach-imx/imx9/clock.c b/arch/arm/mach-imx/imx9/clock.c
index 3e6118df3d..8b26fe5278 100644
--- a/arch/arm/mach-imx/imx9/clock.c
+++ b/arch/arm/mach-imx/imx9/clock.c
@@ -609,7 +609,7 @@ void init_clk_usdhc(u32 index)
{
u32 div;
- if (IS_ENABLED(CONFIG_IMX9_LOW_DRIVE_MODE))
+ if (is_voltage_mode(VOLT_LOW_DRIVE))
div = 3; /* 266.67 Mhz */
else
div = 2; /* 400 Mhz */
@@ -706,8 +706,7 @@ void set_arm_core_max_clk(void)
#endif
-#if IS_ENABLED(CONFIG_IMX9_LOW_DRIVE_MODE)
-struct imx_clk_setting imx_clk_settings[] = {
+struct imx_clk_setting imx_clk_ld_settings[] = {
/* Set A55 clk to 500M */
{ARM_A55_CLK_ROOT, SYS_PLL_PFD0, 2},
/* Set A55 periphal to 200M */
@@ -734,7 +733,7 @@ struct imx_clk_setting imx_clk_settings[] = {
/* NIC_APB to 133M */
{NIC_APB_CLK_ROOT, SYS_PLL_PFD1_DIV2, 3}
};
-#else
+
struct imx_clk_setting imx_clk_settings[] = {
/*
* Set A55 clk to 500M. This clock root is normally used as intermediate
@@ -768,9 +767,18 @@ struct imx_clk_setting imx_clk_settings[] = {
/* NIC_APB to 133M */
{NIC_APB_CLK_ROOT, SYS_PLL_PFD1_DIV2, 3}
};
-#endif
-int clock_init(void)
+void bus_clock_init_low_drive(void)
+{
+ int i;
+
+ for (i = 0; i < ARRAY_SIZE(imx_clk_ld_settings); i++) {
+ ccm_clk_root_cfg(imx_clk_ld_settings[i].clk_root,
+ imx_clk_ld_settings[i].src, imx_clk_ld_settings[i].div);
+ }
+}
+
+void bus_clock_init(void)
{
int i;
@@ -778,9 +786,11 @@ int clock_init(void)
ccm_clk_root_cfg(imx_clk_settings[i].clk_root,
imx_clk_settings[i].src, imx_clk_settings[i].div);
}
+}
- if (IS_ENABLED(CONFIG_IMX9_LOW_DRIVE_MODE))
- set_arm_clk(MHZ(900));
+int clock_init_early(void)
+{
+ int i;
/* allow for non-secure access */
for (i = 0; i < OSCPLL_END; i++)
@@ -798,6 +808,19 @@ int clock_init(void)
return 0;
}
+/* Set bus and A55 core clock per voltage mode */
+int clock_init_late(void)
+{
+ if (is_voltage_mode(VOLT_LOW_DRIVE)) {
+ bus_clock_init_low_drive();
+ set_arm_core_max_clk();
+ } else {
+ bus_clock_init();
+ }
+
+ return 0;
+}
+
int set_clk_eqos(enum enet_freq type)
{
u32 eqos_post_div;
diff --git a/arch/arm/mach-imx/imx9/opos93.c b/arch/arm/mach-imx/imx9/opos93.c
index 2d7cbba119..768dcfe978 100644
--- a/arch/arm/mach-imx/imx9/opos93.c
+++ b/arch/arm/mach-imx/imx9/opos93.c
@@ -90,12 +90,16 @@ void spl_dram_init(void)
{
u32 val;
- fuse_read(47, 0, &val);
+ if (is_imx9301() || is_imx9302()) {
+ ddr_init(&opos9301_512mb_dram_timing);
+ } else {
+ fuse_read(47, 0, &val);
- if (val & 0x1)
- ddr_init(&opos93_1gb_dram_timing);
- else
- ddr_init(&dram_timing);
+ if (val & 0x1)
+ ddr_init(&opos9352_1gb_dram_timing);
+ else
+ ddr_init(&opos9352_512mb_dram_timing);
+ }
}
void board_init_f(ulong dummy)
@@ -120,6 +124,8 @@ void board_init_f(ulong dummy)
printf("LC: 0x%x\n", gd->arch.lifecycle);
}
+ clock_init_late();
+
set_arm_clk(get_cpu_speed_grade_hz());
/* Init power of mix */
diff --git a/arch/arm/mach-imx/imx9/opos93_lpddr4_timing.c b/arch/arm/mach-imx/imx9/opos9301_512mb_lpddr4_timing.c
similarity index 94%
copy from arch/arm/mach-imx/imx9/opos93_lpddr4_timing.c
copy to arch/arm/mach-imx/imx9/opos9301_512mb_lpddr4_timing.c
index 0c927a3ce2..75d9d005b0 100644
--- a/arch/arm/mach-imx/imx9/opos93_lpddr4_timing.c
+++ b/arch/arm/mach-imx/imx9/opos9301_512mb_lpddr4_timing.c
@@ -37,55 +37,55 @@ static struct dram_cfg_param ddr_ddrc_cfg[] = {
static struct dram_fsp_cfg ddr_dram_fsp_cfg[] = {
{
{
- {0x4e300100, 0x1451311B},
- {0x4e300104, 0xF8CC0017},
- {0x4e300108, 0xD4D68E00},
- {0x4e30010C, 0x0071E100},
- {0x4e300124, 0x18660000},
- {0x4e300160, 0x00009101},
- {0x4e30016C, 0x33F00000},
- {0x4e300170, 0x8B0B0608},
- {0x4e300250, 0x00000022},
+ {0x4e300100, 0x124A2100},
+ {0x4e300104, 0xF877000E},
+ {0x4e300108, 0x181604AA},
+ {0x4e30010C, 0x0051E1E6},
+ {0x4e300124, 0x0E3A0000},
+ {0x4e300160, 0x00009100},
+ {0x4e30016C, 0x30900000},
+ {0x4e300170, 0x8A0A0508},
+ {0x4e300250, 0x00000014},
{0x4e300254, 0x00000000},
{0x4e300258, 0x00000008},
{0x4e30025C, 0x00000400},
- {0x4e300300, 0x1D441D0D},
- {0x4e300304, 0x00881E10},
- {0x4e300308, 0x0C3C0C34},
+ {0x4e300300, 0x11281109},
+ {0x4e300304, 0x004C140A},
+ {0x4e300308, 0x063C071E},
},
{
- {0x01, 0xD4},
- {0x02, 0x2D},
+ {0x01, 0xB4},
+ {0x02, 0x1B},
{0x03, 0x33},
{0x0b, 0x46},
{0x0c, 0x49},
- {0x0e, 0x18},
+ {0x0e, 0x1D},
{0x16, 0x04},
},
0,
},
{
{
- {0x4e300100, 0x02081100},
- {0x4e300104, 0xF866000C},
- {0x4e300108, 0xF2FA8088},
- {0x4e30010C, 0x006101A0},
- {0x4e300124, 0x0C340000},
+ {0x4e300100, 0x01041000},
+ {0x4e300104, 0xF855000A},
+ {0x4e300108, 0x9492CA58},
+ {0x4e30010C, 0x00310113},
+ {0x4e300124, 0x071E0000},
{0x4e300160, 0x00009100},
- {0x4e30016C, 0x30700000},
- {0x4e300170, 0x8A0A0508},
- {0x4e300250, 0x00000011},
+ {0x4e30016C, 0x30200000},
+ {0x4e300170, 0x89090408},
+ {0x4e300250, 0x0000000A},
{0x4e300254, 0x00000000},
{0x4e300258, 0x00000008},
{0x4e30025C, 0x00000400},
},
{
- {0x01, 0xA4},
- {0x02, 0x52},
+ {0x01, 0x94},
+ {0x02, 0x9},
{0x03, 0x33},
{0x0b, 0x46},
{0x0c, 0x49},
- {0x0e, 0x18},
+ {0x0e, 0x1D},
{0x16, 0x04},
},
0,
@@ -111,7 +111,7 @@ static struct dram_fsp_cfg ddr_dram_fsp_cfg[] = {
{0x03, 0x33},
{0x0b, 0x46},
{0x0c, 0x49},
- {0x0e, 0x18},
+ {0x0e, 0x1D},
{0x16, 0x04},
},
1,
@@ -152,8 +152,8 @@ static struct dram_cfg_param ddr_ddrphy_cfg[] = {
{0x55, 0x1ff},
{0x1055, 0x1ff},
{0x2055, 0x1ff},
- {0x200c5, 0x19},
- {0x1200c5, 0xb},
+ {0x200c5, 0xb},
+ {0x1200c5, 0x3},
{0x2200c5, 0x7},
{0x2002e, 0x2},
{0x12002e, 0x1},
@@ -207,21 +207,21 @@ static struct dram_cfg_param ddr_ddrphy_cfg[] = {
{0x20075, 0x4},
{0x20050, 0x11},
{0x2009b, 0x2},
- {0x20008, 0x320},
- {0x120008, 0x190},
+ {0x20008, 0x1d3},
+ {0x120008, 0xe9},
{0x220008, 0x9c},
{0x20088, 0x9},
- {0x200b2, 0x134},
+ {0x200b2, 0x15c},
{0x10043, 0x5a1},
{0x10143, 0x5a1},
{0x11043, 0x5a1},
{0x11143, 0x5a1},
- {0x1200b2, 0x134},
+ {0x1200b2, 0x15c},
{0x110043, 0x5a1},
{0x110143, 0x5a1},
{0x111043, 0x5a1},
{0x111143, 0x5a1},
- {0x2200b2, 0x134},
+ {0x2200b2, 0x15c},
{0x210043, 0x5a1},
{0x210143, 0x5a1},
{0x211043, 0x5a1},
@@ -249,7 +249,7 @@ static struct dram_cfg_param ddr_ddrphy_cfg[] = {
{0x2002c, 0x0},
{0x20021, 0x0},
{0x200c7, 0x21},
- {0x1200c7, 0x21},
+ {0x1200c7, 0x41},
{0x200ca, 0x24},
{0x1200ca, 0x24},
};
@@ -1237,36 +1237,36 @@ static struct dram_cfg_param ddr_ddrphy_trained_csr[] = {
/* P0 message block parameter for training firmware */
static struct dram_cfg_param ddr_fsp0_cfg[] = {
{0xd0000, 0x0},
- {0x54003, 0xc80},
+ {0x54003, 0x74a},
{0x54004, 0x4},
- {0x54006, 0x18},
+ {0x54006, 0x1b},
{0x54008, 0x131f},
{0x54009, 0xc8},
{0x5400b, 0x4},
{0x5400d, 0x100},
{0x5400f, 0x100},
{0x54012, 0x110},
- {0x54019, 0x2dd4},
+ {0x54019, 0x1bb4},
{0x5401a, 0x33},
{0x5401b, 0x4946},
- {0x5401c, 0x1808},
+ {0x5401c, 0x1d08},
{0x5401e, 0x4},
- {0x5401f, 0x2dd4},
+ {0x5401f, 0x1bb4},
{0x54020, 0x33},
{0x54021, 0x4946},
- {0x54022, 0x1808},
+ {0x54022, 0x1d08},
{0x54024, 0x4},
- {0x54032, 0xd400},
- {0x54033, 0x332d},
+ {0x54032, 0xb400},
+ {0x54033, 0x331b},
{0x54034, 0x4600},
{0x54035, 0x849},
- {0x54036, 0x18},
+ {0x54036, 0x1d},
{0x54037, 0x400},
- {0x54038, 0xd400},
- {0x54039, 0x332d},
+ {0x54038, 0xb400},
+ {0x54039, 0x331b},
{0x5403a, 0x4600},
{0x5403b, 0x849},
- {0x5403c, 0x18},
+ {0x5403c, 0x1d},
{0x5403d, 0x400},
{0xd0000, 0x1}
};
@@ -1275,36 +1275,36 @@ static struct dram_cfg_param ddr_fsp0_cfg[] = {
static struct dram_cfg_param ddr_fsp1_cfg[] = {
{0xd0000, 0x0},
{0x54002, 0x1},
- {0x54003, 0x640},
+ {0x54003, 0x3a4},
{0x54004, 0x4},
- {0x54006, 0x18},
+ {0x54006, 0x1b},
{0x54008, 0x121f},
{0x54009, 0xc8},
{0x5400b, 0x4},
{0x5400d, 0x100},
{0x5400f, 0x100},
{0x54012, 0x110},
- {0x54019, 0x52a4},
+ {0x54019, 0x994},
{0x5401a, 0x33},
{0x5401b, 0x4946},
- {0x5401c, 0x1808},
+ {0x5401c, 0x1d08},
{0x5401e, 0x4},
- {0x5401f, 0x52a4},
+ {0x5401f, 0x994},
{0x54020, 0x33},
{0x54021, 0x4946},
- {0x54022, 0x1808},
+ {0x54022, 0x1d08},
{0x54024, 0x4},
- {0x54032, 0xa400},
- {0x54033, 0x3352},
+ {0x54032, 0x9400},
+ {0x54033, 0x3309},
{0x54034, 0x4600},
{0x54035, 0x849},
- {0x54036, 0x18},
+ {0x54036, 0x1d},
{0x54037, 0x400},
- {0x54038, 0xa400},
- {0x54039, 0x3352},
+ {0x54038, 0x9400},
+ {0x54039, 0x3309},
{0x5403a, 0x4600},
{0x5403b, 0x849},
- {0x5403c, 0x18},
+ {0x5403c, 0x1d},
{0x5403d, 0x400},
{0xd0000, 0x1}
};
@@ -1315,7 +1315,7 @@ static struct dram_cfg_param ddr_fsp2_cfg[] = {
{0x54002, 0x102},
{0x54003, 0x270},
{0x54004, 0x4},
- {0x54006, 0x18},
+ {0x54006, 0x1b},
{0x54008, 0x121f},
{0x54009, 0xc8},
{0x5400b, 0x4},
@@ -1325,24 +1325,24 @@ static struct dram_cfg_param ddr_fsp2_cfg[] = {
{0x54019, 0x994},
{0x5401a, 0x33},
{0x5401b, 0x4946},
- {0x5401c, 0x1800},
+ {0x5401c, 0x1d00},
{0x5401e, 0x4},
{0x5401f, 0x994},
{0x54020, 0x33},
{0x54021, 0x4946},
- {0x54022, 0x1800},
+ {0x54022, 0x1d00},
{0x54024, 0x4},
{0x54032, 0x9400},
{0x54033, 0x3309},
{0x54034, 0x4600},
{0x54035, 0x49},
- {0x54036, 0x18},
+ {0x54036, 0x1d},
{0x54037, 0x400},
{0x54038, 0x9400},
{0x54039, 0x3309},
{0x5403a, 0x4600},
{0x5403b, 0x49},
- {0x5403c, 0x18},
+ {0x5403c, 0x1d},
{0x5403d, 0x400},
{0xd0000, 0x1}
};
@@ -1351,9 +1351,9 @@ static struct dram_cfg_param ddr_fsp2_cfg[] = {
/* P0 2D message block parameter for training firmware */
static struct dram_cfg_param ddr_fsp0_2d_cfg[] = {
{0xd0000, 0x0},
- {0x54003, 0xc80},
+ {0x54003, 0x74a},
{0x54004, 0x4},
- {0x54006, 0x18},
+ {0x54006, 0x1b},
{0x54008, 0x61},
{0x54009, 0xc8},
{0x5400b, 0x4},
@@ -1361,27 +1361,27 @@ static struct dram_cfg_param ddr_fsp0_2d_cfg[] = {
{0x5400f, 0x100},
{0x54010, 0x2080},
{0x54012, 0x110},
- {0x54019, 0x2dd4},
+ {0x54019, 0x1bb4},
{0x5401a, 0x33},
{0x5401b, 0x4946},
- {0x5401c, 0x1808},
+ {0x5401c, 0x1d08},
{0x5401e, 0x4},
- {0x5401f, 0x2dd4},
+ {0x5401f, 0x1bb4},
{0x54020, 0x33},
{0x54021, 0x4946},
- {0x54022, 0x1808},
+ {0x54022, 0x1d08},
{0x54024, 0x4},
- {0x54032, 0xd400},
- {0x54033, 0x332d},
+ {0x54032, 0xb400},
+ {0x54033, 0x331b},
{0x54034, 0x4600},
{0x54035, 0x849},
- {0x54036, 0x18},
+ {0x54036, 0x1d},
{0x54037, 0x400},
- {0x54038, 0xd400},
- {0x54039, 0x332d},
+ {0x54038, 0xb400},
+ {0x54039, 0x331b},
{0x5403a, 0x4600},
{0x5403b, 0x849},
- {0x5403c, 0x18},
+ {0x5403c, 0x1d},
{0x5403d, 0x400},
{0xd0000, 0x1}
};
@@ -1871,14 +1871,14 @@ static struct dram_cfg_param ddr_phy_pie[] = {
{0x400d7, 0x20b},
{0x2003a, 0x2},
{0x200be, 0x3},
- {0x2000b, 0x384},
- {0x2000c, 0xc8},
- {0x2000d, 0x7d0},
+ {0x2000b, 0x20d},
+ {0x2000c, 0x74},
+ {0x2000d, 0x48e},
{0x2000e, 0x2c},
- {0x12000b, 0x1c2},
- {0x12000c, 0x64},
- {0x12000d, 0x3e8},
- {0x12000e, 0x2c},
+ {0x12000b, 0x107},
+ {0x12000c, 0x3a},
+ {0x12000d, 0x246},
+ {0x12000e, 0x21},
{0x22000b, 0xb0},
{0x22000c, 0x27},
{0x22000d, 0x186},
@@ -1951,15 +1951,15 @@ static struct dram_cfg_param ddr_phy_pie[] = {
static struct dram_fsp_msg ddr_dram_fsp_msg[] = {
{
- /* P0 3200mts 1D */
- .drate = 3200,
+ /* P0 1866mts 1D */
+ .drate = 1866,
.fw_type = FW_1D_IMAGE,
.fsp_cfg = ddr_fsp0_cfg,
.fsp_cfg_num = ARRAY_SIZE(ddr_fsp0_cfg),
},
{
- /* P1 1600mts 1D */
- .drate = 1600,
+ /* P1 933mts 1D */
+ .drate = 933,
.fw_type = FW_1D_IMAGE,
.fsp_cfg = ddr_fsp1_cfg,
.fsp_cfg_num = ARRAY_SIZE(ddr_fsp1_cfg),
@@ -1972,8 +1972,8 @@ static struct dram_fsp_msg ddr_dram_fsp_msg[] = {
.fsp_cfg_num = ARRAY_SIZE(ddr_fsp2_cfg),
},
{
- /* P0 3200mts 2D */
- .drate = 3200,
+ /* P0 1866mts 2D */
+ .drate = 1866,
.fw_type = FW_2D_IMAGE,
.fsp_cfg = ddr_fsp0_2d_cfg,
.fsp_cfg_num = ARRAY_SIZE(ddr_fsp0_2d_cfg),
@@ -1981,7 +1981,7 @@ static struct dram_fsp_msg ddr_dram_fsp_msg[] = {
};
/* ddr timing config params */
-struct dram_timing_info dram_timing = {
+struct dram_timing_info opos9301_512mb_dram_timing = {
.ddrc_cfg = ddr_ddrc_cfg,
.ddrc_cfg_num = ARRAY_SIZE(ddr_ddrc_cfg),
.ddrphy_cfg = ddr_ddrphy_cfg,
@@ -1992,7 +1992,7 @@ struct dram_timing_info dram_timing = {
.ddrphy_trained_csr_num = ARRAY_SIZE(ddr_ddrphy_trained_csr),
.ddrphy_pie = ddr_phy_pie,
.ddrphy_pie_num = ARRAY_SIZE(ddr_phy_pie),
- .fsp_table = { 3200, 1600, 625, },
+ .fsp_table = { 1866, 933, 625, },
.fsp_cfg = ddr_dram_fsp_cfg,
.fsp_cfg_num = ARRAY_SIZE(ddr_dram_fsp_cfg),
};
diff --git a/arch/arm/mach-imx/imx9/opos93_1gb_lpddr4_timing.c b/arch/arm/mach-imx/imx9/opos9352_1gb_lpddr4_timing.c
similarity index 99%
rename from arch/arm/mach-imx/imx9/opos93_1gb_lpddr4_timing.c
rename to arch/arm/mach-imx/imx9/opos9352_1gb_lpddr4_timing.c
index c3c2b410aa..6cc1083be5 100644
--- a/arch/arm/mach-imx/imx9/opos93_1gb_lpddr4_timing.c
+++ b/arch/arm/mach-imx/imx9/opos9352_1gb_lpddr4_timing.c
@@ -1981,7 +1981,7 @@ static struct dram_fsp_msg ddr_dram_fsp_msg[] = {
};
/* ddr timing config params */
-struct dram_timing_info opos93_1gb_dram_timing = {
+struct dram_timing_info opos9352_1gb_dram_timing = {
.ddrc_cfg = ddr_ddrc_cfg,
.ddrc_cfg_num = ARRAY_SIZE(ddr_ddrc_cfg),
.ddrphy_cfg = ddr_ddrphy_cfg,
diff --git a/arch/arm/mach-imx/imx9/opos93_lpddr4_timing.c b/arch/arm/mach-imx/imx9/opos9352_512mb_lpddr4_timing.c
similarity index 99%
rename from arch/arm/mach-imx/imx9/opos93_lpddr4_timing.c
rename to arch/arm/mach-imx/imx9/opos9352_512mb_lpddr4_timing.c
index 0c927a3ce2..2b2ccef195 100644
--- a/arch/arm/mach-imx/imx9/opos93_lpddr4_timing.c
+++ b/arch/arm/mach-imx/imx9/opos9352_512mb_lpddr4_timing.c
@@ -1981,7 +1981,7 @@ static struct dram_fsp_msg ddr_dram_fsp_msg[] = {
};
/* ddr timing config params */
-struct dram_timing_info dram_timing = {
+struct dram_timing_info opos9352_512mb_dram_timing = {
.ddrc_cfg = ddr_ddrc_cfg,
.ddrc_cfg_num = ARRAY_SIZE(ddr_ddrc_cfg),
.ddrphy_cfg = ddr_ddrphy_cfg,
diff --git a/arch/arm/mach-imx/imx9/soc.c b/arch/arm/mach-imx/imx9/soc.c
index 8980819f9a..626c27552a 100644
--- a/arch/arm/mach-imx/imx9/soc.c
+++ b/arch/arm/mach-imx/imx9/soc.c
@@ -96,10 +96,16 @@ int mmc_get_env_dev(void)
*/
u32 get_cpu_speed_grade_hz(void)
{
- u32 speed, max_speed;
+ int ret;
+ u32 bank, word, speed, max_speed;
u32 val;
- fuse_read(2, 3, &val);
+ bank = HW_CFG1 / NUM_WORDS_PER_BANK;
+ word = HW_CFG1 % NUM_WORDS_PER_BANK;
+ ret = fuse_read(bank, word, &val);
+ if (ret)
+ val = 0; /* If read fuse failed, return as blank fuse */
+
val = FIELD_GET(SPEED_GRADING_MASK, val) & 0xF;
speed = MHZ(2300) - val * MHZ(100);
@@ -122,9 +128,15 @@ u32 get_cpu_speed_grade_hz(void)
*/
u32 get_cpu_temp_grade(int *minc, int *maxc)
{
- u32 val;
+ int ret;
+ u32 bank, word, val;
+
+ bank = HW_CFG1 / NUM_WORDS_PER_BANK;
+ word = HW_CFG1 % NUM_WORDS_PER_BANK;
+ ret = fuse_read(bank, word, &val);
+ if (ret)
+ val = 0; /* If read fuse failed, return as blank fuse */
- fuse_read(2, 3, &val);
val = FIELD_GET(MARKETING_GRADING_MASK, val);
if (minc && maxc) {
@@ -160,13 +172,29 @@ static void set_cpu_info(struct ele_get_info_data *info)
static u32 get_cpu_variant_type(u32 type)
{
- /* word 19 */
- u32 val = readl((ulong)FSB_BASE_ADDR + 0x8000 + (19 << 2));
- u32 val2 = readl((ulong)FSB_BASE_ADDR + 0x8000 + (20 << 2));
+ u32 bank, word, val, val2;
+ int ret;
+
+ bank = HW_CFG1 / NUM_WORDS_PER_BANK;
+ word = HW_CFG1 % NUM_WORDS_PER_BANK;
+ ret = fuse_read(bank, word, &val);
+ if (ret)
+ val = 0; /* If read fuse failed, return as blank fuse */
+
+ bank = HW_CFG2 / NUM_WORDS_PER_BANK;
+ word = HW_CFG2 % NUM_WORDS_PER_BANK;
+ ret = fuse_read(bank, word, &val2);
+ if (ret)
+ val2 = 0; /* If read fuse failed, return as blank fuse */
+
bool npu_disable = !!(val & BIT(13));
bool core1_disable = !!(val & BIT(15));
u32 pack_9x9_fused = BIT(4) | BIT(17) | BIT(19) | BIT(24);
+ /* Low performance 93 part */
+ if (((val >> 6) & 0x3F) == 0xE && npu_disable)
+ return core1_disable ? MXC_CPU_IMX9301 : MXC_CPU_IMX9302;
+
if ((val2 & pack_9x9_fused) == pack_9x9_fused)
type = MXC_CPU_IMX9322;
@@ -262,7 +290,7 @@ static struct mm_region imx93_mem_map[] = {
/* Flexible Serial Peripheral Interface */
.virt = 0x28000000UL,
.phys = 0x28000000UL,
- .size = 0x30000000UL,
+ .size = 0x08000000UL,
.attrs = PTE_BLOCK_MEMTYPE(MT_DEVICE_NGNRNE) |
PTE_BLOCK_NON_SHARE |
PTE_BLOCK_PXN | PTE_BLOCK_UXN
@@ -507,8 +535,214 @@ int print_cpuinfo(void)
return 0;
}
+static int fixup_thermal_trips(void *blob, const char *name)
+{
+ int minc, maxc;
+ int node, trip;
+
+ node = fdt_path_offset(blob, "/thermal-zones");
+ if (node < 0)
+ return node;
+
+ node = fdt_subnode_offset(blob, node, name);
+ if (node < 0)
+ return node;
+
+ node = fdt_subnode_offset(blob, node, "trips");
+ if (node < 0)
+ return node;
+
+ get_cpu_temp_grade(&minc, &maxc);
+
+ fdt_for_each_subnode(trip, blob, node) {
+ const char *type;
+ int temp, ret;
+
+ type = fdt_getprop(blob, trip, "type", NULL);
+ if (!type)
+ continue;
+
+ temp = 0;
+ if (!strcmp(type, "critical"))
+ temp = 1000 * (maxc - 5);
+ else if (!strcmp(type, "passive"))
+ temp = 1000 * (maxc - 10);
+ if (temp) {
+ ret = fdt_setprop_u32(blob, trip, "temperature", temp);
+ if (ret)
+ return ret;
+ }
+ }
+
+ return 0;
+}
+
+void build_info(void)
+{
+ u32 fw_version, sha1, res, status;
+ int ret;
+
+ printf("\nBuildInfo:\n");
+
+ ret = ele_get_fw_status(&status, &res);
+ if (ret) {
+ printf(" - ELE firmware status failed %d, 0x%x\n", ret, res);
+ } else if ((status & 0xff) == 1) {
+ ret = ele_get_fw_version(&fw_version, &sha1, &res);
+ if (ret) {
+ printf(" - ELE firmware version failed %d, 0x%x\n", ret, res);
+ } else {
+ printf(" - ELE firmware version %u.%u.%u-%x",
+ (fw_version & (0x00ff0000)) >> 16,
+ (fw_version & (0x0000fff0)) >> 4,
+ (fw_version & (0x0000000f)), sha1);
+ ((fw_version & (0x80000000)) >> 31) == 1 ? puts("-dirty\n") : puts("\n");
+ }
+ } else {
+ printf(" - ELE firmware not included\n");
+ }
+ puts("\n");
+}
+
+int arch_misc_init(void)
+{
+ build_info();
+ return 0;
+}
+
+struct low_drive_freq_entry {
+ const char *node_path;
+ u32 clk;
+ u32 new_rate;
+};
+
+static int low_drive_fdt_fix_clock(void *fdt, int node_off, u32 clk_index, u32 new_rate)
+{
+#define MAX_ASSIGNED_CLKS 8
+ int cnt, j;
+ u32 assignedclks[MAX_ASSIGNED_CLKS]; /* max 8 clocks*/
+
+ cnt = fdtdec_get_int_array_count(fdt, node_off, "assigned-clock-rates",
+ assignedclks, MAX_ASSIGNED_CLKS);
+ if (cnt > 0) {
+ if (cnt <= clk_index)
+ return -ENOENT;
+
+ if (assignedclks[clk_index] <= new_rate)
+ return 0;
+
+ assignedclks[clk_index] = new_rate;
+ for (j = 0; j < cnt; j++)
+ assignedclks[j] = cpu_to_fdt32(assignedclks[j]);
+
+ return fdt_setprop(fdt, node_off, "assigned-clock-rates", &assignedclks,
+ cnt * sizeof(u32));
+ }
+
+ return -ENOENT;
+}
+
+static int low_drive_freq_update(void *blob)
+{
+ int nodeoff, ret;
+ int i;
+
+ /* Update kernel dtb clocks for low drive mode */
+ struct low_drive_freq_entry table[] = {
+ {"/soc@0/lcd-controller@4ae30000", 2, 200000000},
+ {"/soc@0/bus@42800000/mmc@42850000", 0, 266666667},
+ {"/soc@0/bus@42800000/mmc@42860000", 0, 266666667},
+ {"/soc@0/bus@42800000/mmc@428b0000", 0, 266666667},
+ };
+
+ for (i = 0; i < ARRAY_SIZE(table); i++) {
+ nodeoff = fdt_path_offset(blob, table[i].node_path);
+ if (nodeoff >= 0) {
+ ret = low_drive_fdt_fix_clock(blob, nodeoff, table[i].clk,
+ table[i].new_rate);
+ if (!ret)
+ printf("%s freq updated\n", table[i].node_path);
+ }
+ }
+
+ return 0;
+}
+
+static int disable_lpm(void *blob)
+{
+ int rc;
+ char path[64];
+ static const char *compat_lpm = "nxp,imx93-lpm";
+
+ int offset = fdt_node_offset_by_compatible(blob, -1, compat_lpm);
+
+ if (offset < 0) {
+ printf("node with compatible \"%s\" not found\n", compat_lpm);
+ return 0;
+ }
+
+ rc = fdt_get_path(blob, offset, path, sizeof(path));
+ if (rc) {
+ printf("Fail to get lpm node path, err=%s\n", fdt_strerror(rc));
+ return -ENOENT;
+ }
+
+ rc = fdt_del_node(blob, offset);
+ if (rc < 0)
+ printf("Unable to delete lpm node %s, err=%s\n",
+ path, fdt_strerror(rc));
+ else
+ printf("Delete node %s\n", path);
+
+ return 0;
+}
+
+#ifdef CONFIG_OF_BOARD_FIXUP
+#ifndef CONFIG_SPL_BUILD
+int board_fix_fdt(void *fdt)
+{
+ /* Update dtb clocks for low drive mode */
+ if (is_voltage_mode(VOLT_LOW_DRIVE)) {
+ int nodeoff;
+ int i;
+
+ struct low_drive_freq_entry table[] = {
+ {"/soc@0/bus@42800000/mmc@42850000", 0, 266666667},
+ {"/soc@0/bus@42800000/mmc@42860000", 0, 266666667},
+ {"/soc@0/bus@42800000/mmc@428b0000", 0, 266666667},
+ };
+
+ for (i = 0; i < ARRAY_SIZE(table); i++) {
+ nodeoff = fdt_path_offset(fdt, table[i].node_path);
+ if (nodeoff >= 0)
+ low_drive_fdt_fix_clock(fdt, nodeoff, table[i].clk,
+ table[i].new_rate);
+ }
+ }
+
+ return 0;
+}
+#endif
+#endif
+
int ft_system_setup(void *blob, struct bd_info *bd)
{
+ static const char * const nodes_path[] = {
+ "/cpus/cpu@0",
+ "/cpus/cpu@100",
+ };
+
+ if (fixup_thermal_trips(blob, "cpu-thermal"))
+ printf("Failed to update cpu-thermal trip(s)");
+
+ if (is_imx9351() || is_imx9331() || is_imx9321() || is_imx9311() || is_imx9301())
+ disable_cpu_nodes(blob, nodes_path, 1, 2);
+
+ if (is_voltage_mode(VOLT_LOW_DRIVE)) {
+ low_drive_freq_update(blob);
+ disable_lpm(blob);
+ }
+
return 0;
}
@@ -541,7 +775,7 @@ int arch_cpu_init(void)
/* Disable wdog */
init_wdog();
- clock_init();
+ clock_init_early();
trdc_early_init();
@@ -833,3 +1067,22 @@ int psci_sysreset_get_status(struct udevice *dev, char *buf, int size)
return 0;
}
+
+enum imx9_soc_voltage_mode soc_target_voltage_mode(void)
+{
+ u32 speed = get_cpu_speed_grade_hz();
+ enum imx9_soc_voltage_mode voltage = VOLT_OVER_DRIVE;
+
+ if (is_imx93()) {
+ if (speed == 1700000000)
+ voltage = VOLT_OVER_DRIVE;
+ else if (speed == 1400000000)
+ voltage = VOLT_NOMINAL_DRIVE;
+ else if (speed == 900000000 || speed == 800000000)
+ voltage = VOLT_LOW_DRIVE;
+ else
+ printf("Unexpected A55 freq %u, default to OD\n", speed);
+ }
+
+ return voltage;
+}
diff --git a/board/freescale/imx93_evk/spl.c b/board/freescale/imx93_evk/spl.c
index be9c24fc0d..84f5875a78 100644
--- a/board/freescale/imx93_evk/spl.c
+++ b/board/freescale/imx93_evk/spl.c
@@ -70,7 +70,7 @@ int power_init_board(void)
/* enable DVS control through PMIC_STBY_REQ */
pmic_reg_write(dev, PCA9450_BUCK1CTRL, 0x59);
- if (IS_ENABLED(CONFIG_IMX9_LOW_DRIVE_MODE)) {
+ if (is_voltage_mode(VOLT_LOW_DRIVE))
/* 0.75v for Low drive mode
*/
pmic_reg_write(dev, PCA9450_BUCK1OUT_DVS0, 0x0c);
@@ -117,9 +117,11 @@ void board_init_f(ulong dummy)
printf("LC: 0x%x\n", gd->arch.lifecycle);
}
+ clock_init_late();
+
power_init_board();
- if (!IS_ENABLED(CONFIG_IMX9_LOW_DRIVE_MODE))
+ if (!is_voltage_mode(VOLT_LOW_DRIVE))
set_arm_clk(get_cpu_speed_grade_hz());
/* Init power of mix */
diff --git a/configs/opos93dev_defconfig b/configs/opos93dev_defconfig
index fee131eb79..2ba056cc7f 100644
--- a/configs/opos93dev_defconfig
+++ b/configs/opos93dev_defconfig
@@ -31,6 +31,7 @@ CONFIG_BOOTCOMMAND="run emmcboot"
CONFIG_USE_PREBOOT=y
CONFIG_PREBOOT="run check_env"
CONFIG_DEFAULT_FDT_FILE="imx93-opos93dev.dtb"
+CONFIG_ARCH_MISC_INIT=y
CONFIG_BOARD_EARLY_INIT_F=y
CONFIG_BOARD_LATE_INIT=y
CONFIG_SPL_MAX_SIZE=0x26000
diff --git a/drivers/clk/imx/clk-composite-93.c b/drivers/clk/imx/clk-composite-93.c
index 6d71c0c03f..34026c5e42 100644
--- a/drivers/clk/imx/clk-composite-93.c
+++ b/drivers/clk/imx/clk-composite-93.c
@@ -103,7 +103,6 @@ struct clk *imx93_clk_composite_flags(const char *name,
mux->mask = CCM_MUX_MASK;
mux->num_parents = num_parents;
mux->parent_names = parent_names;
- mux->flags = flags;
div = kzalloc(sizeof(*div), GFP_KERNEL);
if (!div)
@@ -120,7 +119,6 @@ struct clk *imx93_clk_composite_flags(const char *name,
gate->reg = reg;
gate->bit_idx = CCM_OFF_SHIFT;
- gate->flags = flags;
clk = clk_register_composite(NULL, name,
parent_names, num_parents,
diff --git a/drivers/cpu/cpu-uclass.c b/drivers/cpu/cpu-uclass.c
index 9772578968..1eb4fbd179 100644
--- a/drivers/cpu/cpu-uclass.c
+++ b/drivers/cpu/cpu-uclass.c
@@ -105,6 +105,16 @@ int cpu_get_vendor(const struct udevice *dev, char *buf, int size)
return ops->get_vendor(dev, buf, size);
}
+int cpu_release_core(const struct udevice *dev, phys_addr_t addr)
+{
+ struct cpu_ops *ops = cpu_get_ops(dev);
+
+ if (!ops->release_core)
+ return -ENOSYS;
+
+ return ops->release_core(dev, addr);
+}
+
U_BOOT_DRIVER(cpu_bus) = {
.name = "cpu_bus",
.id = UCLASS_SIMPLE_BUS,
diff --git a/drivers/cpu/cpu_sandbox.c b/drivers/cpu/cpu_sandbox.c
index 2e871fe313..cffa338334 100644
--- a/drivers/cpu/cpu_sandbox.c
+++ b/drivers/cpu/cpu_sandbox.c
@@ -45,6 +45,11 @@ void cpu_sandbox_set_current(const char *name)
cpu_current = name;
}
+static int cpu_sandbox_release_core(const struct udevice *dev, phys_addr_t addr)
+{
+ return 0;
+}
+
static int cpu_sandbox_is_current(struct udevice *dev)
{
if (!strcmp(dev->name, cpu_current))
@@ -59,6 +64,7 @@ static const struct cpu_ops cpu_sandbox_ops = {
.get_count = cpu_sandbox_get_count,
.get_vendor = cpu_sandbox_get_vendor,
.is_current = cpu_sandbox_is_current,
+ .release_core = cpu_sandbox_release_core,
};
static int cpu_sandbox_bind(struct udevice *dev)
diff --git a/drivers/cpu/imx8_cpu.c b/drivers/cpu/imx8_cpu.c
index 98ff95f5ff..fdd0705707 100644
--- a/drivers/cpu/imx8_cpu.c
+++ b/drivers/cpu/imx8_cpu.c
@@ -1,6 +1,6 @@
// SPDX-License-Identifier: GPL-2.0+
/*
- * Copyright 2019 NXP
+ * Copyright 2019, 2024 NXP
*/
#include <common.h>
@@ -8,6 +8,7 @@
#include <dm.h>
#include <thermal.h>
#include <asm/global_data.h>
+#include <asm/ptrace.h>
#include <asm/system.h>
#include <firmware/imx/sci/sci.h>
#include <asm/arch/sys_proto.h>
@@ -16,13 +17,15 @@
#include <imx_thermal.h>
#include <linux/bitops.h>
#include <linux/clk-provider.h>
+#include <linux/psci.h>
DECLARE_GLOBAL_DATA_PTR;
+#define IMX_REV_LEN 4
struct cpu_imx_plat {
const char *name;
- const char *rev;
const char *type;
+ char rev[IMX_REV_LEN];
u32 cpu_rsrc;
u32 cpurev;
u32 freq_mhz;
@@ -32,6 +35,12 @@ struct cpu_imx_plat {
static const char *get_imx_type_str(u32 imxtype)
{
switch (imxtype) {
+ case MXC_CPU_IMX8MM:
+ return "8MM";
+ case MXC_CPU_IMX8MN:
+ return "8MN";
+ case MXC_CPU_IMX8MP:
+ return "8MP";
case MXC_CPU_IMX8QXP:
case MXC_CPU_IMX8QXP_A0:
return "8QXP";
@@ -53,33 +62,38 @@ static const char *get_imx_type_str(u32 imxtype)
return "93(12)";/* iMX93 9x9 Dual core without NPU */
case MXC_CPU_IMX9311:
return "93(11)";/* iMX93 9x9 Single core without NPU */
+ case MXC_CPU_IMX9302:
+ return "93(02)";/* iMX93 900Mhz Low performance Dual core without NPU */
+ case MXC_CPU_IMX9301:
+ return "93(01)";/* iMX93 900Mhz Low performance Single core without NPU */
default:
return "??";
}
}
-static const char *get_imx_rev_str(u32 rev)
+static void get_imx_rev_str(struct cpu_imx_plat *plat, u32 rev)
{
- static char revision[4];
-
if (IS_ENABLED(CONFIG_IMX8)) {
switch (rev) {
case CHIP_REV_A:
- return "A";
+ plat->rev[0] = 'A';
+ break;
case CHIP_REV_B:
- return "B";
+ plat->rev[0] = 'B';
+ break;
case CHIP_REV_C:
- return "C";
+ plat->rev[0] = 'C';
+ break;
default:
- return "?";
+ plat->rev[0] = '?';
+ break;
}
+ plat->rev[1] = '\0';
} else {
- revision[0] = '1' + (((rev & 0xf0) - CHIP_REV_1_0) >> 4);
- revision[1] = '.';
- revision[2] = '0' + (rev & 0xf);
- revision[3] = '\0';
-
- return revision;
+ plat->rev[0] = '1' + (((rev & 0xf0) - CHIP_REV_1_0) >> 4);
+ plat->rev[1] = '.';
+ plat->rev[2] = '0' + (rev & 0xf);
+ plat->rev[3] = '\0';
}
}
@@ -185,8 +199,6 @@ static int cpu_imx_get_desc(const struct udevice *dev, char *buf, int size)
ret = snprintf(buf, size, " - invalid sensor data");
}
- snprintf(buf + ret, size - ret, "\n");
-
return 0;
}
@@ -194,7 +206,7 @@ static int cpu_imx_get_info(const struct udevice *dev, struct cpu_info *info)
{
struct cpu_imx_plat *plat = dev_get_plat(dev);
- info->cpu_freq = plat->freq_mhz * 1000;
+ info->cpu_freq = plat->freq_mhz * 1000000;
info->features = BIT(CPU_FEAT_L1_CACHE) | BIT(CPU_FEAT_MMU);
return 0;
}
@@ -237,12 +249,34 @@ static int cpu_imx_is_current(struct udevice *dev)
return 0;
}
+static int cpu_imx_release_core(const struct udevice *dev, phys_addr_t addr)
+{
+ struct cpu_imx_plat *plat = dev_get_plat(dev);
+ struct pt_regs regs;
+
+ regs.regs[0] = PSCI_0_2_FN64_CPU_ON;
+ regs.regs[1] = plat->mpidr;
+ regs.regs[2] = addr;
+ regs.regs[3] = 0;
+
+ smc_call(®s);
+ if (regs.regs[0]) {
+ printf("Failed to release CPU core (mpidr: 0x%x)\n", plat->mpidr);
+ return -1;
+ }
+
+ printf("Released CPU core (mpidr: 0x%x) to address 0x%llx\n", plat->mpidr, addr);
+
+ return 0;
+}
+
static const struct cpu_ops cpu_imx_ops = {
.get_desc = cpu_imx_get_desc,
.get_info = cpu_imx_get_info,
.get_count = cpu_imx_get_count,
.get_vendor = cpu_imx_get_vendor,
.is_current = cpu_imx_is_current,
+ .release_core = cpu_imx_release_core,
};
static const struct udevice_id cpu_imx_ids[] = {
@@ -287,8 +321,8 @@ static int imx_cpu_probe(struct udevice *dev)
set_core_data(dev);
cpurev = get_cpu_rev();
plat->cpurev = cpurev;
- plat->rev = get_imx_rev_str(cpurev & 0xFFF);
- plat->type = get_imx_type_str((cpurev & 0xFF000) >> 12);
+ get_imx_rev_str(plat, cpurev & 0xFFF);
+ plat->type = get_imx_type_str((cpurev & 0x1FF000) >> 12);
plat->freq_mhz = imx_get_cpu_rate(dev) / 1000000;
plat->mpidr = dev_read_addr(dev);
if (plat->mpidr == FDT_ADDR_T_NONE) {
diff --git a/drivers/ddr/imx/phy/ddrphy_utils.c b/drivers/ddr/imx/phy/ddrphy_utils.c
index 45e1a70dbd..f0b717074e 100644
--- a/drivers/ddr/imx/phy/ddrphy_utils.c
+++ b/drivers/ddr/imx/phy/ddrphy_utils.c
@@ -149,6 +149,10 @@ void ddrphy_init_set_dfi_clk(unsigned int drate)
dram_pll_init(...
[truncated message content] |