blob: cb0104601046a5d14ceb23e8a67fb7378a68301b [file] [log] [blame]
Stefan Reinauer36a22682008-10-29 04:52:57 +00001/*
2 * This file is part of the coreboot project.
Stefan Reinauer14e22772010-04-27 06:56:47 +00003 *
Stefan Reinauerde3206a2010-02-22 06:09:43 +00004 * Copyright (C) 2007-2010 coresystems GmbH
Stefan Reinauer36a22682008-10-29 04:52:57 +00005 *
Uwe Hermann2bb4acf2010-03-01 17:19:55 +00006 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; version 2 of the License.
Stefan Reinauer36a22682008-10-29 04:52:57 +00009 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
Stefan Reinauer36a22682008-10-29 04:52:57 +000014 */
15
Stefan Reinauer36a22682008-10-29 04:52:57 +000016#include <stdint.h>
Elyes HAOUASd07048a2019-04-21 20:17:11 +020017#include <cf9_reset.h>
Elyes HAOUAS5d4cf362018-08-06 09:58:28 +020018#include <console/console.h>
Kyösti Mälkkicd7a70f2019-08-17 20:51:08 +030019#include <arch/romstage.h>
Elyes HAOUAS5d4cf362018-08-06 09:58:28 +020020#include <cpu/x86/lapic.h>
Stefan Reinauer36a22682008-10-29 04:52:57 +000021#include <device/pci_def.h>
Kyösti Mälkkif1b58b72019-03-01 13:43:02 +020022#include <device/pci_ops.h>
Kyösti Mälkki3855c012019-03-03 08:45:19 +020023#include <device/pnp_ops.h>
Stefan Reinauer36a22682008-10-29 04:52:57 +000024#include <device/pnp_def.h>
Edwin Beasanteb50c7d2010-07-06 21:05:04 +000025#include <pc80/mc146818rtc.h>
Edward O'Callaghan77757c22015-01-04 21:33:39 +110026#include <northbridge/intel/i945/i945.h>
27#include <northbridge/intel/i945/raminit.h>
28#include <southbridge/intel/i82801gx/i82801gx.h>
Patrick Rudolph425e75a2019-03-24 15:06:17 +010029#include <southbridge/intel/common/pmclib.h>
Elyes HAOUAS5d4cf362018-08-06 09:58:28 +020030#include <superio/winbond/common/winbond.h>
31#include <superio/winbond/w83627thg/w83627thg.h>
32
33#include "option_table.h"
Patrick Georgid0835952010-10-05 09:07:10 +000034
Uwe Hermann57b2ff82010-11-21 17:29:59 +000035#define SERIAL_DEV PNP_DEV(0x2e, W83627THG_SP1)
36
Arthur Heymansfecf7772019-11-09 14:19:04 +010037/* Override the default lpc decode ranges */
38static void mb_lpc_decode(void)
Stefan Reinauer36a22682008-10-29 04:52:57 +000039{
Patrick Georgia4700192011-01-27 07:39:38 +000040 int lpt_en = 0;
Arthur Heymansb451df22017-08-15 20:59:09 +020041 if (read_option(lpt, 0) != 0)
42 lpt_en = LPT_LPC_EN; /* enable LPT */
43
Arthur Heymansfecf7772019-11-09 14:19:04 +010044 pci_update_config16(PCI_DEV(0, 0x1f, 0), LPC_EN, ~LPT_LPC_EN, lpt_en);
Stefan Reinauer36a22682008-10-29 04:52:57 +000045}
46
Stefan Reinauer36a22682008-10-29 04:52:57 +000047/* This box has two superios, so enabling serial becomes slightly excessive.
48 * We disable a lot of stuff to make sure that there are no conflicts between
49 * the two. Also set up the GPIOs from the beginning. This is the "no schematic
50 * but safe anyways" method.
51 */
52static void early_superio_config_w83627thg(void)
53{
Antonello Dettori9ec11232016-11-08 18:44:46 +010054 pnp_devfn_t dev;
Stefan Reinauer14e22772010-04-27 06:56:47 +000055
Elyes HAOUAS531b87a2016-09-19 09:46:33 -060056 dev = PNP_DEV(0x2e, W83627THG_SP1);
Elyes HAOUAS5d4cf362018-08-06 09:58:28 +020057 pnp_enter_conf_state(dev);
Stefan Reinauer36a22682008-10-29 04:52:57 +000058
Elyes HAOUASf10b5ff2016-10-06 19:49:55 +020059 pnp_write_config(dev, 0x24, 0xc6); /* PNPCSV */
Stefan Reinaueraca6ec62009-10-26 17:12:21 +000060
Elyes HAOUASf10b5ff2016-10-06 19:49:55 +020061 pnp_write_config(dev, 0x29, 0x43); /* GPIO settings */
62 pnp_write_config(dev, 0x2a, 0x40); /* GPIO settings */
Stefan Reinaueraca6ec62009-10-26 17:12:21 +000063
Elyes HAOUAS531b87a2016-09-19 09:46:33 -060064 dev = PNP_DEV(0x2e, W83627THG_SP1);
Stefan Reinauer36a22682008-10-29 04:52:57 +000065 pnp_set_logical_device(dev);
66 pnp_set_enable(dev, 0);
67 pnp_set_iobase(dev, PNP_IDX_IO0, 0x3f8);
68 pnp_set_irq(dev, PNP_IDX_IRQ0, 4);
69 pnp_set_enable(dev, 1);
70
Elyes HAOUAS531b87a2016-09-19 09:46:33 -060071 dev = PNP_DEV(0x2e, W83627THG_SP2);
Stefan Reinauer36a22682008-10-29 04:52:57 +000072 pnp_set_logical_device(dev);
73 pnp_set_enable(dev, 0);
74 pnp_set_iobase(dev, PNP_IDX_IO0, 0x2f8);
75 pnp_set_irq(dev, PNP_IDX_IRQ0, 3);
Stefan Reinauer36a22682008-10-29 04:52:57 +000076 pnp_set_enable(dev, 1);
77
Elyes HAOUAS531b87a2016-09-19 09:46:33 -060078 dev = PNP_DEV(0x2e, W83627THG_KBC);
Stefan Reinauer36a22682008-10-29 04:52:57 +000079 pnp_set_logical_device(dev);
80 pnp_set_enable(dev, 0);
81 pnp_set_iobase(dev, PNP_IDX_IO0, 0x60);
82 pnp_set_iobase(dev, PNP_IDX_IO1, 0x64);
Stefan Reinauer36a22682008-10-29 04:52:57 +000083 pnp_set_enable(dev, 1);
84
Elyes HAOUAS531b87a2016-09-19 09:46:33 -060085 dev = PNP_DEV(0x2e, W83627THG_GAME_MIDI_GPIO1);
Stefan Reinauer36a22682008-10-29 04:52:57 +000086 pnp_set_logical_device(dev);
87 pnp_set_enable(dev, 0);
Elyes HAOUASf10b5ff2016-10-06 19:49:55 +020088 pnp_write_config(dev, 0xf5, 0xff); /* invert all GPIOs */
Stefan Reinauer36a22682008-10-29 04:52:57 +000089 pnp_set_enable(dev, 1);
90
Elyes HAOUAS531b87a2016-09-19 09:46:33 -060091 dev = PNP_DEV(0x2e, W83627THG_GPIO2);
Stefan Reinauer36a22682008-10-29 04:52:57 +000092 pnp_set_logical_device(dev);
Elyes HAOUASf10b5ff2016-10-06 19:49:55 +020093 pnp_set_enable(dev, 1); /* Just enable it */
Stefan Reinauer36a22682008-10-29 04:52:57 +000094
Elyes HAOUAS531b87a2016-09-19 09:46:33 -060095 dev = PNP_DEV(0x2e, W83627THG_GPIO3);
Stefan Reinauer36a22682008-10-29 04:52:57 +000096 pnp_set_logical_device(dev);
97 pnp_set_enable(dev, 0);
Elyes HAOUASf10b5ff2016-10-06 19:49:55 +020098 pnp_write_config(dev, 0xf0, 0xfb); /* GPIO bit 2 is output */
99 pnp_write_config(dev, 0xf1, 0x00); /* GPIO bit 2 is 0 */
100 pnp_write_config(dev, 0x30, 0x03); /* Enable GPIO3+4. pnp_set_enable is not sufficient */
Stefan Reinauer36a22682008-10-29 04:52:57 +0000101
Elyes HAOUAS531b87a2016-09-19 09:46:33 -0600102 dev = PNP_DEV(0x2e, W83627THG_FDC);
Stefan Reinauer36a22682008-10-29 04:52:57 +0000103 pnp_set_logical_device(dev);
104 pnp_set_enable(dev, 0);
105
Elyes HAOUAS531b87a2016-09-19 09:46:33 -0600106 dev = PNP_DEV(0x2e, W83627THG_PP);
Stefan Reinauer36a22682008-10-29 04:52:57 +0000107 pnp_set_logical_device(dev);
108 pnp_set_enable(dev, 0);
109
Stefan Reinauer54309d62009-01-20 22:53:10 +0000110 /* Enable HWM */
Elyes HAOUAS531b87a2016-09-19 09:46:33 -0600111 dev = PNP_DEV(0x2e, W83627THG_HWM);
Stefan Reinauer54309d62009-01-20 22:53:10 +0000112 pnp_set_logical_device(dev);
113 pnp_set_enable(dev, 0);
114 pnp_set_iobase(dev, PNP_IDX_IO0, 0xa00);
115 pnp_set_enable(dev, 1);
116
Elyes HAOUAS5d4cf362018-08-06 09:58:28 +0200117 pnp_exit_conf_state(dev);
Stefan Reinauer36a22682008-10-29 04:52:57 +0000118
Elyes HAOUAS531b87a2016-09-19 09:46:33 -0600119 dev = PNP_DEV(0x4e, W83627THG_SP1);
Elyes HAOUAS5d4cf362018-08-06 09:58:28 +0200120 pnp_enter_conf_state(dev);
Stefan Reinauer36a22682008-10-29 04:52:57 +0000121
Elyes HAOUASf10b5ff2016-10-06 19:49:55 +0200122 pnp_set_logical_device(dev); /* Set COM3 to sane non-conflicting values */
Stefan Reinauer36a22682008-10-29 04:52:57 +0000123 pnp_set_enable(dev, 0);
124 pnp_set_iobase(dev, PNP_IDX_IO0, 0x3e8);
125 pnp_set_irq(dev, PNP_IDX_IRQ0, 11);
126 pnp_set_enable(dev, 1);
127
Elyes HAOUAS531b87a2016-09-19 09:46:33 -0600128 dev = PNP_DEV(0x4e, W83627THG_SP2);
Elyes HAOUASf10b5ff2016-10-06 19:49:55 +0200129 pnp_set_logical_device(dev); /* Set COM4 to sane non-conflicting values */
Stefan Reinauer36a22682008-10-29 04:52:57 +0000130 pnp_set_enable(dev, 0);
131 pnp_set_iobase(dev, PNP_IDX_IO0, 0x2e8);
132 pnp_set_irq(dev, PNP_IDX_IRQ0, 10);
133 pnp_set_enable(dev, 1);
134
Elyes HAOUAS531b87a2016-09-19 09:46:33 -0600135 dev = PNP_DEV(0x4e, W83627THG_FDC);
Stefan Reinauer36a22682008-10-29 04:52:57 +0000136 pnp_set_logical_device(dev);
137 pnp_set_enable(dev, 0);
138
Elyes HAOUAS531b87a2016-09-19 09:46:33 -0600139 dev = PNP_DEV(0x4e, W83627THG_PP);
Stefan Reinauer36a22682008-10-29 04:52:57 +0000140 pnp_set_logical_device(dev);
141 pnp_set_enable(dev, 0);
142
Elyes HAOUAS531b87a2016-09-19 09:46:33 -0600143 dev = PNP_DEV(0x4e, W83627THG_KBC);
Stefan Reinauer36a22682008-10-29 04:52:57 +0000144 pnp_set_logical_device(dev);
145 pnp_set_enable(dev, 0);
146 pnp_set_iobase(dev, PNP_IDX_IO0, 0x00);
147 pnp_set_iobase(dev, PNP_IDX_IO1, 0x00);
148
Elyes HAOUAS5d4cf362018-08-06 09:58:28 +0200149 pnp_exit_conf_state(dev);
Stefan Reinauer36a22682008-10-29 04:52:57 +0000150}
151
152static void rcba_config(void)
153{
154 /* Set up virtual channel 0 */
Stefan Reinauer36a22682008-10-29 04:52:57 +0000155
156 /* Device 1f interrupt pin register */
Arthur Heymansb451df22017-08-15 20:59:09 +0200157 RCBA32(D31IP) = 0x00042210;
Stefan Reinauer36a22682008-10-29 04:52:57 +0000158 /* Device 1d interrupt pin register */
Arthur Heymansb451df22017-08-15 20:59:09 +0200159 RCBA32(D28IP) = 0x00214321;
Stefan Reinauer36a22682008-10-29 04:52:57 +0000160
161 /* dev irq route register */
Arthur Heymansb451df22017-08-15 20:59:09 +0200162 RCBA16(D31IR) = 0x0132;
163 RCBA16(D30IR) = 0x3241;
164 RCBA16(D29IR) = 0x0237;
165 RCBA16(D28IR) = 0x3210;
166 RCBA16(D27IR) = 0x3210;
Stefan Reinauer36a22682008-10-29 04:52:57 +0000167
168 /* Enable IOAPIC */
Arthur Heymansb451df22017-08-15 20:59:09 +0200169 RCBA8(OIC) = 0x03;
Stefan Reinauer36a22682008-10-29 04:52:57 +0000170
Stefan Reinauer36a22682008-10-29 04:52:57 +0000171 /* Enable PCIe Root Port Clock Gate */
Elyes HAOUASf10b5ff2016-10-06 19:49:55 +0200172
Stefan Reinauer36a22682008-10-29 04:52:57 +0000173}
174
175static void early_ich7_init(void)
176{
177 uint8_t reg8;
178 uint32_t reg32;
179
Elyes HAOUASf10b5ff2016-10-06 19:49:55 +0200180 /* program secondary mlt XXX byte? */
Elyes HAOUAS6df210b2019-10-25 14:05:17 +0200181 pci_write_config8(PCI_DEV(0, 0x1e, 0), SMLT, 0x20);
Stefan Reinauer36a22682008-10-29 04:52:57 +0000182
Elyes HAOUASf10b5ff2016-10-06 19:49:55 +0200183 /* reset rtc power status */
Elyes HAOUAS6df210b2019-10-25 14:05:17 +0200184 reg8 = pci_read_config8(PCI_DEV(0, 0x1f, 0), GEN_PMCON_3);
185 reg8 &= ~RTC_BATTERY_DEAD;
186 pci_write_config8(PCI_DEV(0, 0x1f, 0), GEN_PMCON_3, reg8);
Stefan Reinauer36a22682008-10-29 04:52:57 +0000187
Elyes HAOUASf10b5ff2016-10-06 19:49:55 +0200188 /* usb transient disconnect */
Stefan Reinauer36a22682008-10-29 04:52:57 +0000189 reg8 = pci_read_config8(PCI_DEV(0, 0x1f, 0), 0xad);
190 reg8 |= (3 << 0);
191 pci_write_config8(PCI_DEV(0, 0x1f, 0), 0xad, reg8);
192
193 reg32 = pci_read_config32(PCI_DEV(0, 0x1d, 7), 0xfc);
194 reg32 |= (1 << 29) | (1 << 17);
195 pci_write_config32(PCI_DEV(0, 0x1d, 7), 0xfc, reg32);
196
197 reg32 = pci_read_config32(PCI_DEV(0, 0x1d, 7), 0xdc);
198 reg32 |= (1 << 31) | (1 << 27);
199 pci_write_config32(PCI_DEV(0, 0x1d, 7), 0xdc, reg32);
200
Arthur Heymans2437fe92019-10-04 13:59:29 +0200201 ich7_setup_cir();
Stefan Reinauer36a22682008-10-29 04:52:57 +0000202}
203
Kyösti Mälkki157b1892019-08-16 14:02:25 +0300204void mainboard_romstage_entry(void)
Stefan Reinauer36a22682008-10-29 04:52:57 +0000205{
Vladimir Serbinenko55601882014-10-15 20:17:51 +0200206 int s3resume = 0;
Stefan Reinauer36a22682008-10-29 04:52:57 +0000207
Kyösti Mälkki157b1892019-08-16 14:02:25 +0300208 enable_lapic();
Stefan Reinauer36a22682008-10-29 04:52:57 +0000209
Arthur Heymansfecf7772019-11-09 14:19:04 +0100210 i82801gx_lpc_setup();
211 mb_lpc_decode();
Stefan Reinauer36a22682008-10-29 04:52:57 +0000212 early_superio_config_w83627thg();
213
214 /* Set up the console */
Stefan Reinauer36a22682008-10-29 04:52:57 +0000215 console_init();
216
Stefan Reinauer36a22682008-10-29 04:52:57 +0000217 if (MCHBAR16(SSKPD) == 0xCAFE) {
Elyes HAOUASd07048a2019-04-21 20:17:11 +0200218 system_reset();
Stefan Reinauer36a22682008-10-29 04:52:57 +0000219 }
220
221 /* Perform some early chipset initialization required
222 * before RAM initialization can work
223 */
224 i945_early_initialization();
225
Vladimir Serbinenko55601882014-10-15 20:17:51 +0200226 s3resume = southbridge_detect_s3_resume();
Stefan Reinauera5fdadf2009-07-21 21:58:20 +0000227
Stefan Reinauer36a22682008-10-29 04:52:57 +0000228 /* Enable SPD ROMs and DDR-II DRAM */
229 enable_smbus();
Stefan Reinauer14e22772010-04-27 06:56:47 +0000230
Kyösti Mälkki346d2012019-03-23 10:07:16 +0200231 if (CONFIG(DEBUG_RAM_SETUP))
232 dump_spd_registers();
Stefan Reinauer36a22682008-10-29 04:52:57 +0000233
Vladimir Serbinenko55601882014-10-15 20:17:51 +0200234 sdram_initialize(s3resume ? 2 : 0, NULL);
Stefan Reinauer36a22682008-10-29 04:52:57 +0000235
236 /* Perform some initialization that must run before stage2 */
237 early_ich7_init();
238
Stefan Reinauer14e22772010-04-27 06:56:47 +0000239 /* This should probably go away. Until now it is required
240 * and mainboard specific
Stefan Reinauer36a22682008-10-29 04:52:57 +0000241 */
242 rcba_config();
243
244 /* Chipset Errata! */
245 fixup_i945_errata();
246
247 /* Initialize the internal PCIe links before we go into stage2 */
Vladimir Serbinenko55601882014-10-15 20:17:51 +0200248 i945_late_initialization(s3resume);
Stefan Reinauer36a22682008-10-29 04:52:57 +0000249}