blob: 0afed728b220faca3ab25f8b3fdb9dfaadf037bc [file] [log] [blame]
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +00001/*
2 * This file is part of the flashrom project.
3 *
4 * Copyright (C) 2009 Carl-Daniel Hailfinger
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; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
19 */
20
21#include <stdint.h>
22#include <string.h>
23#include <stdlib.h>
24#include <fcntl.h>
25#include <sys/types.h>
26#include <sys/stat.h>
27#include <errno.h>
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +000028#include "flash.h"
29
Carl-Daniel Hailfinger66ef4e52009-12-13 22:28:00 +000030#if NEED_PCI == 1
Christian Ruppert0cdb0312009-05-14 18:57:26 +000031struct pci_dev *pci_dev_find_filter(struct pci_filter filter)
32{
33 struct pci_dev *temp;
34
35 for (temp = pacc->devices; temp; temp = temp->next)
36 if (pci_filter_match(&filter, temp))
37 return temp;
38
39 return NULL;
40}
41
Carl-Daniel Hailfinger9f46cfc2009-11-15 17:13:29 +000042struct pci_dev *pci_dev_find_vendorclass(uint16_t vendor, uint16_t class)
43{
44 struct pci_dev *temp;
45 struct pci_filter filter;
46 uint16_t tmp2;
47
48 pci_filter_init(NULL, &filter);
49 filter.vendor = vendor;
50
51 for (temp = pacc->devices; temp; temp = temp->next)
52 if (pci_filter_match(&filter, temp)) {
53 /* Read PCI class */
54 tmp2 = pci_read_word(temp, 0x0a);
55 if (tmp2 == class)
56 return temp;
57 }
58
59 return NULL;
60}
61
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +000062struct pci_dev *pci_dev_find(uint16_t vendor, uint16_t device)
63{
64 struct pci_dev *temp;
65 struct pci_filter filter;
66
67 pci_filter_init(NULL, &filter);
68 filter.vendor = vendor;
69 filter.device = device;
70
71 for (temp = pacc->devices; temp; temp = temp->next)
72 if (pci_filter_match(&filter, temp))
73 return temp;
74
75 return NULL;
76}
77
78struct pci_dev *pci_card_find(uint16_t vendor, uint16_t device,
79 uint16_t card_vendor, uint16_t card_device)
80{
81 struct pci_dev *temp;
82 struct pci_filter filter;
83
84 pci_filter_init(NULL, &filter);
85 filter.vendor = vendor;
86 filter.device = device;
87
88 for (temp = pacc->devices; temp; temp = temp->next)
89 if (pci_filter_match(&filter, temp)) {
90 if ((card_vendor ==
91 pci_read_word(temp, PCI_SUBSYSTEM_VENDOR_ID))
92 && (card_device ==
93 pci_read_word(temp, PCI_SUBSYSTEM_ID)))
94 return temp;
95 }
96
97 return NULL;
98}
Carl-Daniel Hailfinger66ef4e52009-12-13 22:28:00 +000099#endif
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000100
Carl-Daniel Hailfinger66ef4e52009-12-13 22:28:00 +0000101#if INTERNAL_SUPPORT == 1
Carl-Daniel Hailfinger14e100c2009-12-22 23:42:04 +0000102struct superio superio = {};
Michael Karcher0bdc0922010-02-28 01:33:48 +0000103int force_boardenable = 0;
Carl-Daniel Hailfinger14e100c2009-12-22 23:42:04 +0000104
105void probe_superio(void)
106{
107 superio = probe_superio_ite();
108#if 0 /* Winbond SuperI/O code is not yet available. */
109 if (superio.vendor == SUPERIO_VENDOR_NONE)
110 superio = probe_superio_winbond();
111#endif
112}
113
Michael Karcher8c1df282010-02-26 09:51:20 +0000114int is_laptop;
115
Uwe Hermanna0869322009-05-14 20:41:57 +0000116int internal_init(void)
117{
118 int ret = 0;
119
Michael Karcher0bdc0922010-02-28 01:33:48 +0000120 if (programmer_param && !strlen(programmer_param)) {
121 free(programmer_param);
122 programmer_param = NULL;
123 }
124 if (programmer_param) {
125 char *arg;
126 arg = extract_param(&programmer_param, "boardenable=", ",:");
127 if (arg && !strcmp(arg,"force"))
128 force_boardenable = 1;
129 else if (arg)
130 msg_perr("Unknown argument for boardenable: %s\n", arg);
131 free(arg);
132
133 if (strlen(programmer_param))
134 msg_perr("Unhandled programmer parameters: %s\n",
135 programmer_param);
136 free(programmer_param);
137 programmer_param = NULL;
138 }
Carl-Daniel Hailfinger3b7e75a2009-05-14 21:41:10 +0000139 get_io_perms();
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000140
141 /* Initialize PCI access for flash enables */
142 pacc = pci_alloc(); /* Get the pci_access structure */
143 /* Set all options you want -- here we stick with the defaults */
144 pci_init(pacc); /* Initialize the PCI library */
145 pci_scan_bus(pacc); /* We want to get the list of devices */
146
147 /* We look at the lbtable first to see if we need a
148 * mainboard specific flash enable sequence.
149 */
150 coreboot_init();
Michael Karcher6701ee82010-01-20 14:14:11 +0000151 dmi_init();
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000152
Carl-Daniel Hailfinger14e100c2009-12-22 23:42:04 +0000153 /* Probe for the SuperI/O chip and fill global struct superio. */
154 probe_superio();
155
Michael Karcher8c1df282010-02-26 09:51:20 +0000156 /* Warn if a laptop is detected */
157 if (is_laptop)
158 printf("========================================================================\n"
159 "WARNING! You seem to be running flashrom on a laptop.\n"
160 "Laptops, notebooks and netbooks are difficult to support and we recommend\n"
161 "to use the vendor flashing utility. The embedded controller (EC) in these\n"
162 "machines often interacts badly with flashing\n"
163 "See http://www.flashrom.org/Laptops\n"
164 "========================================================================\n");
165
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000166 /* try to enable it. Failure IS an option, since not all motherboards
167 * really need this to be done, etc., etc.
168 */
169 ret = chipset_flash_enable();
170 if (ret == -2) {
171 printf("WARNING: No chipset found. Flash detection "
172 "will most likely fail.\n");
173 }
174
175 board_flash_enable(lb_vendor, lb_part);
176
Carl-Daniel Hailfinger9246ff42009-09-02 13:43:56 +0000177 /* Even if chipset init returns an error code, we don't want to abort.
178 * The error code might have been a warning only.
179 * Besides that, we don't check the board enable return code either.
180 */
181 return 0;
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000182}
183
184int internal_shutdown(void)
185{
Carl-Daniel Hailfingerdb41c592009-08-09 21:50:24 +0000186 release_io_perms();
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000187
188 return 0;
189}
Carl-Daniel Hailfinger66ef4e52009-12-13 22:28:00 +0000190#endif
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000191
Carl-Daniel Hailfinger5820f422009-05-16 21:22:56 +0000192void internal_chip_writeb(uint8_t val, chipaddr addr)
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000193{
Carl-Daniel Hailfinger78185dc2009-05-17 15:49:24 +0000194 mmio_writeb(val, (void *) addr);
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000195}
196
Carl-Daniel Hailfinger5820f422009-05-16 21:22:56 +0000197void internal_chip_writew(uint16_t val, chipaddr addr)
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000198{
Carl-Daniel Hailfinger78185dc2009-05-17 15:49:24 +0000199 mmio_writew(val, (void *) addr);
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000200}
201
Carl-Daniel Hailfinger5820f422009-05-16 21:22:56 +0000202void internal_chip_writel(uint32_t val, chipaddr addr)
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000203{
Carl-Daniel Hailfinger78185dc2009-05-17 15:49:24 +0000204 mmio_writel(val, (void *) addr);
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000205}
206
Carl-Daniel Hailfinger5820f422009-05-16 21:22:56 +0000207uint8_t internal_chip_readb(const chipaddr addr)
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000208{
Carl-Daniel Hailfinger78185dc2009-05-17 15:49:24 +0000209 return mmio_readb((void *) addr);
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000210}
211
Carl-Daniel Hailfinger5820f422009-05-16 21:22:56 +0000212uint16_t internal_chip_readw(const chipaddr addr)
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000213{
Carl-Daniel Hailfinger78185dc2009-05-17 15:49:24 +0000214 return mmio_readw((void *) addr);
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000215}
216
Carl-Daniel Hailfinger5820f422009-05-16 21:22:56 +0000217uint32_t internal_chip_readl(const chipaddr addr)
Carl-Daniel Hailfinger702218d2009-05-08 17:43:22 +0000218{
Carl-Daniel Hailfinger78185dc2009-05-17 15:49:24 +0000219 return mmio_readl((void *) addr);
220}
221
Carl-Daniel Hailfinger0bd2a2b2009-06-05 18:32:07 +0000222void internal_chip_readn(uint8_t *buf, const chipaddr addr, size_t len)
223{
224 memcpy(buf, (void *)addr, len);
225 return;
226}