blob: 039df20c437daccf7eb447b0fb4a62f5da0cc090 [file] [log] [blame]
Kyösti Mälkkie8b4da22014-10-21 18:22:32 +03001/*
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
17 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
18 */
19
20#ifndef _HUDSON_EARLY_SETUP_C_
21#define _HUDSON_EARLY_SETUP_C_
22
23#include <stdint.h>
24#include <arch/io.h>
25#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
32void 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
77void 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. */
90 dev = PCI_DEV(0, 0x14, 3);
91 byte = pci_read_config8(dev, 0x4a);
92 byte |= 1 << 5; /* enable port 80 */
93 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
126#if CONFIG_HAVE_ACPI_RESUME
127int acpi_get_sleep_type(void)
128{
129 u16 tmp = inw(ACPI_PM1_CNT_BLK);
130 tmp = ((tmp & (7 << 10)) >> 10);
131 /* printk(BIOS_DEBUG, "SLP_TYP type was %x\n", tmp); */
132 return (int)tmp;
133}
134#endif
135
136#if CONFIG_HAVE_ACPI_RESUME
137int acpi_is_wakeup_early(void)
138{
139 return (acpi_get_sleep_type() == 3);
140}
141#endif
142
143unsigned long get_top_of_ram(void)
144{
145 uint32_t xdata = 0;
146 int xnvram_pos = 0xf8, xi;
147 for (xi = 0; xi<4; xi++) {
148 outb(xnvram_pos, BIOSRAM_INDEX);
149 xdata &= ~(0xff << (xi * 8));
150 xdata |= inb(BIOSRAM_DATA) << (xi *8);
151 xnvram_pos++;
152 }
153 return (unsigned long) xdata;
154}
155
156#endif