blob: 1b9b6891e837910bbbdc55215958ba9a7a36c1b2 [file] [log] [blame]
zbao246e84b2012-07-13 18:47:03 +08001/*
2 * This file is part of the coreboot project.
3 *
4 * Copyright (C) 2010 Advanced Micro Devices, Inc.
5 *
6 * 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.
9 *
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.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
Paul Menzela46a7122013-02-23 18:37:27 +010017 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
zbao246e84b2012-07-13 18:47:03 +080018 */
19
Elyes HAOUAS65fa5982014-07-22 23:12:38 +020020#ifndef _HUDSON_EARLY_SETUP_C_
21#define _HUDSON_EARLY_SETUP_C_
zbao246e84b2012-07-13 18:47:03 +080022
23#include <stdint.h>
Stefan Reinauer24d1d4b2013-03-21 11:51:41 -070024#include <arch/io.h>
zbao246e84b2012-07-13 18:47:03 +080025#include <arch/acpi.h>
26#include <console/console.h>
27#include <reset.h>
28#include <arch/cpu.h>
29#include <cbmem.h>
30#include "hudson.h"
31
Idwer Volleringc18e5212014-01-06 21:57:56 +000032void hudson_pci_port80(void)
33{
34 u8 byte;
35 device_t dev;
36
37 /* P2P Bridge */
38 dev = PCI_DEV(0, 0x14, 4);
39
40 /* Chip Control: Enable subtractive decoding */
41 byte = pci_read_config8(dev, 0x40);
42 byte |= 1 << 5;
43 pci_write_config8(dev, 0x40, byte);
44
45 /* Misc Control: Enable subtractive decoding if 0x40 bit 5 is set */
46 byte = pci_read_config8(dev, 0x4B);
47 byte |= 1 << 7;
48 pci_write_config8(dev, 0x4B, byte);
49
50 /* The same IO Base and IO Limit here is meaningful because we set the
51 * bridge to be subtractive. During early setup stage, we have to make
52 * sure that data can go through port 0x80.
53 */
54 /* IO Base: 0xf000 */
55 byte = pci_read_config8(dev, 0x1C);
56 byte |= 0xF << 4;
57 pci_write_config8(dev, 0x1C, byte);
58
59 /* IO Limit: 0xf000 */
60 byte = pci_read_config8(dev, 0x1D);
61 byte |= 0xF << 4;
62 pci_write_config8(dev, 0x1D, byte);
63
64 /* PCI Command: Enable IO response */
65 byte = pci_read_config8(dev, 0x04);
66 byte |= 1 << 0;
67 pci_write_config8(dev, 0x04, byte);
68
69 /* LPC controller */
70 dev = PCI_DEV(0, 0x14, 3);
71
72 byte = pci_read_config8(dev, 0x4A);
73 byte &= ~(1 << 5); /* disable lpc port 80 */
74 pci_write_config8(dev, 0x4A, byte);
75}
76
zbao246e84b2012-07-13 18:47:03 +080077void hudson_lpc_port80(void)
78{
79 u8 byte;
80 device_t dev;
81
82 /* Enable LPC controller */
83 outb(0xEC, 0xCD6);
84 byte = inb(0xCD7);
85 byte |= 1;
86 outb(0xEC, 0xCD6);
87 outb(byte, 0xCD7);
88
89 /* Enable port 80 LPC decode in pci function 3 configuration space. */
Idwer Volleringc18e5212014-01-06 21:57:56 +000090 dev = PCI_DEV(0, 0x14, 3);
zbao246e84b2012-07-13 18:47:03 +080091 byte = pci_read_config8(dev, 0x4a);
Idwer Volleringc18e5212014-01-06 21:57:56 +000092 byte |= 1 << 5; /* enable port 80 */
zbao246e84b2012-07-13 18:47:03 +080093 pci_write_config8(dev, 0x4a, byte);
94}
95
96int s3_save_nvram_early(u32 dword, int size, int nvram_pos)
97{
98 int i;
99 printk(BIOS_DEBUG, "Writing %x of size %d to nvram pos: %d\n", dword, size, nvram_pos);
100
101 for (i = 0; i<size; i++) {
102 outb(nvram_pos, BIOSRAM_INDEX);
103 outb((dword >>(8 * i)) & 0xff , BIOSRAM_DATA);
104 nvram_pos++;
105 }
106
107 return nvram_pos;
108}
109
110int s3_load_nvram_early(int size, u32 *old_dword, int nvram_pos)
111{
112 u32 data = *old_dword;
113 int i;
114 for (i = 0; i<size; i++) {
115 outb(nvram_pos, BIOSRAM_INDEX);
116 data &= ~(0xff << (i * 8));
117 data |= inb(BIOSRAM_DATA) << (i *8);
118 nvram_pos++;
119 }
120 *old_dword = data;
121 printk(BIOS_DEBUG, "Loading %x of size %d to nvram pos:%d\n", *old_dword, size,
122 nvram_pos-size);
123 return nvram_pos;
124}
125
Edward O'Callaghan893a55e2014-12-02 17:44:47 +1100126#if IS_ENABLED(CONFIG_HAVE_ACPI_RESUME)
zbao246e84b2012-07-13 18:47:03 +0800127int acpi_get_sleep_type(void)
128{
Alexandru Gagniuccf1f9b62014-04-20 13:24:42 -0500129 u16 tmp = inw(ACPI_PM1_CNT_BLK);
zbao246e84b2012-07-13 18:47:03 +0800130 tmp = ((tmp & (7 << 10)) >> 10);
131 /* printk(BIOS_DEBUG, "SLP_TYP type was %x\n", tmp); */
132 return (int)tmp;
133}
zbao246e84b2012-07-13 18:47:03 +0800134
zbao246e84b2012-07-13 18:47:03 +0800135int acpi_is_wakeup_early(void)
136{
137 return (acpi_get_sleep_type() == 3);
138}
Edward O'Callaghan893a55e2014-12-02 17:44:47 +1100139#endif /* CONFIG_HAVE_ACPI_RESUME */
zbao246e84b2012-07-13 18:47:03 +0800140
Kyösti Mälkkibc90e152013-09-04 13:26:11 +0300141unsigned long get_top_of_ram(void)
zbao246e84b2012-07-13 18:47:03 +0800142{
143 uint32_t xdata = 0;
144 int xnvram_pos = 0xf8, xi;
145 for (xi = 0; xi<4; xi++) {
146 outb(xnvram_pos, BIOSRAM_INDEX);
147 xdata &= ~(0xff << (xi * 8));
148 xdata |= inb(BIOSRAM_DATA) << (xi *8);
149 xnvram_pos++;
150 }
Kyösti Mälkkibc90e152013-09-04 13:26:11 +0300151 return (unsigned long) xdata;
zbao246e84b2012-07-13 18:47:03 +0800152}
153
Edward O'Callaghan893a55e2014-12-02 17:44:47 +1100154#endif /* _HUDSON_EARLY_SETUP_C_ */