blob: 1f038f61f1c2b17dc9d56762876c663f42bd3272 [file] [log] [blame]
Felix Held2d020e12021-12-15 20:52:10 +01001/* SPDX-License-Identifier: GPL-2.0-only */
2
3#include <amdblocks/acpimmio.h>
4#include <amdblocks/lpc.h>
5#include <amdblocks/pmlib.h>
6#include <amdblocks/reset.h>
7#include <amdblocks/smbus.h>
8#include <amdblocks/spi.h>
9#include <soc/southbridge.h>
10#include <types.h>
11
12static void sb_enable_lpc(void)
13{
14 u8 byte;
15
16 /* Enable LPC controller */
17 byte = pm_io_read8(PM_LPC_GATING);
18 byte |= PM_LPC_ENABLE;
19 pm_io_write8(PM_LPC_GATING, byte);
20}
21
22static void sb_lpc_decode(void)
23{
24 u32 tmp = 0;
25
26 /* Enable I/O decode to LPC bus */
27 tmp = DECODE_ENABLE_PARALLEL_PORT0 | DECODE_ENABLE_PARALLEL_PORT2
28 | DECODE_ENABLE_PARALLEL_PORT4 | DECODE_ENABLE_SERIAL_PORT0
29 | DECODE_ENABLE_SERIAL_PORT1 | DECODE_ENABLE_SERIAL_PORT2
30 | DECODE_ENABLE_SERIAL_PORT3 | DECODE_ENABLE_SERIAL_PORT4
31 | DECODE_ENABLE_SERIAL_PORT5 | DECODE_ENABLE_SERIAL_PORT6
32 | DECODE_ENABLE_SERIAL_PORT7 | DECODE_ENABLE_AUDIO_PORT0
33 | DECODE_ENABLE_AUDIO_PORT1 | DECODE_ENABLE_AUDIO_PORT2
34 | DECODE_ENABLE_AUDIO_PORT3 | DECODE_ENABLE_MSS_PORT2
35 | DECODE_ENABLE_MSS_PORT3 | DECODE_ENABLE_FDC_PORT0
36 | DECODE_ENABLE_FDC_PORT1 | DECODE_ENABLE_GAME_PORT
37 | DECODE_ENABLE_KBC_PORT | DECODE_ENABLE_ACPIUC_PORT
38 | DECODE_ENABLE_ADLIB_PORT;
39
40 /* Decode SIOs at 2E/2F and 4E/4F */
41 if (CONFIG(STONEYRIDGE_LEGACY_FREE))
42 tmp |= DECODE_ALTERNATE_SIO_ENABLE | DECODE_SIO_ENABLE;
43
44 lpc_enable_decode(tmp);
45}
46
47static void setup_spread_spectrum(int *reboot)
48{
49 uint16_t rstcfg = pm_read16(PWR_RESET_CFG);
50
51 rstcfg &= ~TOGGLE_ALL_PWR_GOOD;
52 pm_write16(PWR_RESET_CFG, rstcfg);
53
54 uint32_t cntl1 = misc_read32(MISC_CLK_CNTL1);
55
56 if (cntl1 & CG1PLL_FBDIV_TEST) {
57 printk(BIOS_DEBUG, "Spread spectrum is ready\n");
58 misc_write32(MISC_CGPLL_CONFIG1,
59 misc_read32(MISC_CGPLL_CONFIG1) |
60 CG1PLL_SPREAD_SPECTRUM_ENABLE);
61
62 return;
63 }
64
65 printk(BIOS_DEBUG, "Setting up spread spectrum\n");
66
67 uint32_t cfg6 = misc_read32(MISC_CGPLL_CONFIG6);
68 cfg6 &= ~CG1PLL_LF_MODE_MASK;
69 cfg6 |= (0x0f8 << CG1PLL_LF_MODE_SHIFT) & CG1PLL_LF_MODE_MASK;
70 misc_write32(MISC_CGPLL_CONFIG6, cfg6);
71
72 uint32_t cfg3 = misc_read32(MISC_CGPLL_CONFIG3);
73 cfg3 &= ~CG1PLL_REFDIV_MASK;
74 cfg3 |= (0x003 << CG1PLL_REFDIV_SHIFT) & CG1PLL_REFDIV_MASK;
75 cfg3 &= ~CG1PLL_FBDIV_MASK;
76 cfg3 |= (0x04b << CG1PLL_FBDIV_SHIFT) & CG1PLL_FBDIV_MASK;
77 misc_write32(MISC_CGPLL_CONFIG3, cfg3);
78
79 uint32_t cfg5 = misc_read32(MISC_CGPLL_CONFIG5);
80 cfg5 &= ~SS_AMOUNT_NFRAC_SLIP_MASK;
81 cfg5 |= (0x2 << SS_AMOUNT_NFRAC_SLIP_SHIFT) & SS_AMOUNT_NFRAC_SLIP_MASK;
82 misc_write32(MISC_CGPLL_CONFIG5, cfg5);
83
84 uint32_t cfg4 = misc_read32(MISC_CGPLL_CONFIG4);
85 cfg4 &= ~SS_AMOUNT_DSFRAC_MASK;
86 cfg4 |= (0xd000 << SS_AMOUNT_DSFRAC_SHIFT) & SS_AMOUNT_DSFRAC_MASK;
87 cfg4 &= ~SS_STEP_SIZE_DSFRAC_MASK;
88 cfg4 |= (0x02d5 << SS_STEP_SIZE_DSFRAC_SHIFT)
89 & SS_STEP_SIZE_DSFRAC_MASK;
90 misc_write32(MISC_CGPLL_CONFIG4, cfg4);
91
92 rstcfg |= TOGGLE_ALL_PWR_GOOD;
93 pm_write16(PWR_RESET_CFG, rstcfg);
94
95 cntl1 |= CG1PLL_FBDIV_TEST;
96 misc_write32(MISC_CLK_CNTL1, cntl1);
97
98 *reboot = 1;
99}
100
101static void setup_misc(int *reboot)
102{
103 /* Undocumented register */
104 uint32_t reg = misc_read32(0x50);
105 if (!(reg & BIT(16))) {
106 reg |= BIT(16);
107
108 misc_write32(0x50, reg);
109 *reboot = 1;
110 }
111}
112
113/* Before console init */
114void bootblock_fch_early_init(void)
115{
116 int reboot = 0;
117
118 /* Enable_acpimmio_decode_pm04 to enable the ACPIMMIO decode which is needed to access
119 the GPIO registers. */
120 enable_acpimmio_decode_pm04();
121 lpc_enable_rom();
122 sb_enable_lpc();
123 lpc_enable_port80();
124 sb_lpc_decode();
125 /* Make sure the base address is predictable */
126 lpc_set_spibase(SPI_BASE_ADDRESS);
127 fch_spi_early_init();
128 fch_smbus_init();
129 fch_enable_cf9_io();
130 setup_spread_spectrum(&reboot);
131 setup_misc(&reboot);
132
133 if (reboot)
134 warm_reset();
135
136 fch_enable_legacy_io();
137 enable_aoac_devices();
138
139 /* disable the keyboard reset function before mainboard GPIO setup */
140 if (CONFIG(DISABLE_KEYBOARD_RESET_PIN))
141 fch_disable_kb_rst();
142}
143
144/* After console init */
145void bootblock_fch_init(void)
146{
147 pm_set_power_failure_state();
148 fch_print_pmxc0_status();
149 show_spi_speeds_and_modes();
150}
151
152void fch_clk_output_48Mhz(u32 osc)
153{
154 u32 ctrl;
155
156 /*
157 * Clear the disable for OSCOUT1 (signal typically named XnnM_25M_48M)
158 * or OSCOUT2 (USBCLK/25M_48M_OSC). The frequency defaults to 48MHz.
159 */
160 ctrl = misc_read32(MISC_CLK_CNTL1);
161
162 switch (osc) {
163 case 1:
164 ctrl &= ~OSCOUT1_CLK_OUTPUT_ENB;
165 break;
166 case 2:
167 ctrl &= ~OSCOUT2_CLK_OUTPUT_ENB;
168 break;
169 default:
170 return; /* do nothing if invalid */
171 }
172 misc_write32(MISC_CLK_CNTL1, ctrl);
173}