blob: 109725c8ac2cfd1d002d7130d8223657f67958b8 [file] [log] [blame]
Yann Gautier3edc7c32019-05-20 19:17:08 +02001/*
Yann Gautiera18f61b2020-05-05 17:58:40 +02002 * Copyright (c) 2019-2020, STMicroelectronics - All Rights Reserved
Yann Gautier3edc7c32019-05-20 19:17:08 +02003 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 */
6
7#include <platform_def.h>
8
9#include <common/debug.h>
10#include <drivers/st/bsec.h>
11#include <drivers/st/stpmic1.h>
12#include <lib/mmio.h>
13
14#include <stm32mp_dt.h>
15#include <stm32mp1_private.h>
16
17/*
18 * SYSCFG REGISTER OFFSET (base relative)
19 */
20#define SYSCFG_BOOTR 0x00U
21#define SYSCFG_IOCTRLSETR 0x18U
22#define SYSCFG_ICNR 0x1CU
23#define SYSCFG_CMPCR 0x20U
24#define SYSCFG_CMPENSETR 0x24U
25
26/*
27 * SYSCFG_BOOTR Register
28 */
29#define SYSCFG_BOOTR_BOOT_MASK GENMASK(2, 0)
30#define SYSCFG_BOOTR_BOOTPD_MASK GENMASK(6, 4)
31#define SYSCFG_BOOTR_BOOTPD_SHIFT 4
32/*
33 * SYSCFG_IOCTRLSETR Register
34 */
35#define SYSCFG_IOCTRLSETR_HSLVEN_TRACE BIT(0)
36#define SYSCFG_IOCTRLSETR_HSLVEN_QUADSPI BIT(1)
37#define SYSCFG_IOCTRLSETR_HSLVEN_ETH BIT(2)
38#define SYSCFG_IOCTRLSETR_HSLVEN_SDMMC BIT(3)
39#define SYSCFG_IOCTRLSETR_HSLVEN_SPI BIT(4)
40
41/*
42 * SYSCFG_ICNR Register
43 */
44#define SYSCFG_ICNR_AXI_M9 BIT(9)
45
46/*
47 * SYSCFG_CMPCR Register
48 */
49#define SYSCFG_CMPCR_SW_CTRL BIT(1)
50#define SYSCFG_CMPCR_READY BIT(8)
51#define SYSCFG_CMPCR_RANSRC GENMASK(19, 16)
52#define SYSCFG_CMPCR_RANSRC_SHIFT 16
53#define SYSCFG_CMPCR_RAPSRC GENMASK(23, 20)
54#define SYSCFG_CMPCR_ANSRC_SHIFT 24
55
56/*
57 * SYSCFG_CMPENSETR Register
58 */
59#define SYSCFG_CMPENSETR_MPU_EN BIT(0)
60
61void stm32mp1_syscfg_init(void)
62{
63 uint32_t bootr;
64 uint32_t otp = 0;
65 uint32_t vdd_voltage;
Yann Gautier3edc7c32019-05-20 19:17:08 +020066
67 /*
68 * Interconnect update : select master using the port 1.
69 * LTDC = AXI_M9.
70 */
Yann Gautiera18f61b2020-05-05 17:58:40 +020071 mmio_write_32(SYSCFG_BASE + SYSCFG_ICNR, SYSCFG_ICNR_AXI_M9);
Yann Gautier3edc7c32019-05-20 19:17:08 +020072
73 /* Disable Pull-Down for boot pin connected to VDD */
Yann Gautiera18f61b2020-05-05 17:58:40 +020074 bootr = mmio_read_32(SYSCFG_BASE + SYSCFG_BOOTR) &
Yann Gautier3edc7c32019-05-20 19:17:08 +020075 SYSCFG_BOOTR_BOOT_MASK;
Yann Gautiera18f61b2020-05-05 17:58:40 +020076 mmio_clrsetbits_32(SYSCFG_BASE + SYSCFG_BOOTR, SYSCFG_BOOTR_BOOTPD_MASK,
Yann Gautier3edc7c32019-05-20 19:17:08 +020077 bootr << SYSCFG_BOOTR_BOOTPD_SHIFT);
78
79 /*
80 * High Speed Low Voltage Pad mode Enable for SPI, SDMMC, ETH, QSPI
81 * and TRACE. Needed above ~50MHz and conditioned by AFMUX selection.
82 * It could be disabled for low frequencies or if AFMUX is selected
83 * but the function is not used, typically for TRACE.
84 * If high speed low voltage pad mode is node enable, platform will
85 * over consume.
86 *
87 * WARNING:
88 * Enabling High Speed mode while VDD > 2.7V
89 * with the OTP product_below_2v5 (OTP 18, BIT 13)
90 * erroneously set to 1 can damage the SoC!
91 * => TF-A enables the low power mode only if VDD < 2.7V (in DT)
92 * but this value needs to be consistent with board design.
93 */
94 if (bsec_read_otp(&otp, HW2_OTP) != BSEC_OK) {
95 panic();
96 }
97
98 otp = otp & HW2_OTP_PRODUCT_BELOW_2V5;
99
100 /* Get VDD supply */
101 vdd_voltage = dt_get_pwr_vdd_voltage();
102
103 /* Check if VDD is Low Voltage */
104 if (vdd_voltage == 0U) {
105 WARN("VDD unknown");
106 } else if (vdd_voltage < 2700000U) {
Yann Gautiera18f61b2020-05-05 17:58:40 +0200107 mmio_write_32(SYSCFG_BASE + SYSCFG_IOCTRLSETR,
Yann Gautier3edc7c32019-05-20 19:17:08 +0200108 SYSCFG_IOCTRLSETR_HSLVEN_TRACE |
109 SYSCFG_IOCTRLSETR_HSLVEN_QUADSPI |
110 SYSCFG_IOCTRLSETR_HSLVEN_ETH |
111 SYSCFG_IOCTRLSETR_HSLVEN_SDMMC |
112 SYSCFG_IOCTRLSETR_HSLVEN_SPI);
113
114 if (otp == 0U) {
115 INFO("Product_below_2v5=0: HSLVEN protected by HW\n");
116 }
117 } else {
118 if (otp != 0U) {
119 ERROR("Product_below_2v5=1:\n");
120 ERROR("\tHSLVEN update is destructive,\n");
121 ERROR("\tno update as VDD > 2.7V\n");
122 panic();
123 }
124 }
125
126 stm32mp1_syscfg_enable_io_compensation();
127}
128
129void stm32mp1_syscfg_enable_io_compensation(void)
130{
Yann Gautier3edc7c32019-05-20 19:17:08 +0200131 /*
132 * Activate automatic I/O compensation.
133 * Warning: need to ensure CSI enabled and ready in clock driver.
134 * Enable non-secure clock, we assume non-secure is suspended.
135 */
136 stm32mp1_clk_enable_non_secure(SYSCFG);
137
Yann Gautiera18f61b2020-05-05 17:58:40 +0200138 mmio_setbits_32(SYSCFG_BASE + SYSCFG_CMPENSETR,
Yann Gautier3edc7c32019-05-20 19:17:08 +0200139 SYSCFG_CMPENSETR_MPU_EN);
140
Yann Gautiera18f61b2020-05-05 17:58:40 +0200141 while ((mmio_read_32(SYSCFG_BASE + SYSCFG_CMPCR) &
Yann Gautier3edc7c32019-05-20 19:17:08 +0200142 SYSCFG_CMPCR_READY) == 0U) {
143 ;
144 }
145
Yann Gautiera18f61b2020-05-05 17:58:40 +0200146 mmio_clrbits_32(SYSCFG_BASE + SYSCFG_CMPCR, SYSCFG_CMPCR_SW_CTRL);
Yann Gautier3edc7c32019-05-20 19:17:08 +0200147}
148
149void stm32mp1_syscfg_disable_io_compensation(void)
150{
Yann Gautier3edc7c32019-05-20 19:17:08 +0200151 uint32_t value;
152
153 /*
154 * Deactivate automatic I/O compensation.
155 * Warning: CSI is disabled automatically in STOP if not
156 * requested for other usages and always OFF in STANDBY.
157 * Disable non-secure SYSCFG clock, we assume non-secure is suspended.
158 */
Yann Gautiera18f61b2020-05-05 17:58:40 +0200159 value = mmio_read_32(SYSCFG_BASE + SYSCFG_CMPCR) >>
Yann Gautier3edc7c32019-05-20 19:17:08 +0200160 SYSCFG_CMPCR_ANSRC_SHIFT;
161
Yann Gautiera18f61b2020-05-05 17:58:40 +0200162 mmio_clrbits_32(SYSCFG_BASE + SYSCFG_CMPCR,
Yann Gautier3edc7c32019-05-20 19:17:08 +0200163 SYSCFG_CMPCR_RANSRC | SYSCFG_CMPCR_RAPSRC);
164
Yann Gautiera18f61b2020-05-05 17:58:40 +0200165 value = mmio_read_32(SYSCFG_BASE + SYSCFG_CMPCR) |
Yann Gautier3edc7c32019-05-20 19:17:08 +0200166 (value << SYSCFG_CMPCR_RANSRC_SHIFT);
167
Yann Gautiera18f61b2020-05-05 17:58:40 +0200168 mmio_write_32(SYSCFG_BASE + SYSCFG_CMPCR, value | SYSCFG_CMPCR_SW_CTRL);
Yann Gautier3edc7c32019-05-20 19:17:08 +0200169
Yann Gautiera18f61b2020-05-05 17:58:40 +0200170 mmio_clrbits_32(SYSCFG_BASE + SYSCFG_CMPENSETR,
Yann Gautier3edc7c32019-05-20 19:17:08 +0200171 SYSCFG_CMPENSETR_MPU_EN);
172
173 stm32mp1_clk_disable_non_secure(SYSCFG);
174}