sb/amd/{agesa,pi}/hudson: Explicitly enable LPC controller
[coreboot.git] / src / drivers / spi / boot_device_rw_nommap.c
blob5de9a71cebc7be6dae3140301858347cb7252bb9
1 /*
2 * This file is part of the coreboot project.
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; version 2 of the License.
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
14 #include <boot_device.h>
15 #include <spi_flash.h>
16 #include <spi-generic.h>
17 #include <stdint.h>
19 static struct spi_flash sfg;
20 static bool sfg_init_done;
22 static ssize_t spi_readat(const struct region_device *rd, void *b,
23 size_t offset, size_t size)
25 if (spi_flash_read(&sfg, offset, size, b))
26 return -1;
28 return size;
31 static ssize_t spi_writeat(const struct region_device *rd, const void *b,
32 size_t offset, size_t size)
34 if (spi_flash_write(&sfg, offset, size, b))
35 return -1;
37 return size;
40 static ssize_t spi_eraseat(const struct region_device *rd,
41 size_t offset, size_t size)
43 if (spi_flash_erase(&sfg, offset, size))
44 return -1;
46 return size;
49 static const struct region_device_ops spi_ops = {
50 .readat = spi_readat,
51 .writeat = spi_writeat,
52 .eraseat = spi_eraseat,
55 static const struct region_device spi_rw =
56 REGION_DEV_INIT(&spi_ops, 0, CONFIG_ROM_SIZE);
58 static void boot_device_rw_init(void)
60 const int bus = CONFIG_BOOT_DEVICE_SPI_FLASH_BUS;
61 const int cs = 0;
63 if (sfg_init_done == true)
64 return;
66 /* Ensure any necessary setup is performed by the drivers. */
67 spi_init();
69 if (!spi_flash_probe(bus, cs, &sfg))
70 sfg_init_done = true;
73 const struct region_device *boot_device_rw(void)
75 /* Probe for the SPI flash device if not already done. */
76 boot_device_rw_init();
78 if (sfg_init_done != true)
79 return NULL;
81 return &spi_rw;
84 const struct spi_flash *boot_device_spi_flash(void)
86 boot_device_rw_init();
88 if (sfg_init_done != true)
89 return NULL;
91 return &sfg;
94 int boot_device_wp_region(const struct region_device *rd,
95 const enum bootdev_prot_type type)
97 uint32_t ctrlr_pr;
99 /* Ensure boot device has been initialized at least once. */
100 boot_device_init();
102 const struct spi_flash *boot_dev = boot_device_spi_flash();
104 if (boot_dev == NULL)
105 return -1;
107 if (type == MEDIA_WP) {
108 if (spi_flash_is_write_protected(boot_dev,
109 region_device_region(rd)) != 1) {
110 return spi_flash_set_write_protected(boot_dev,
111 region_device_region(rd), true,
112 SPI_WRITE_PROTECTION_REBOOT);
115 /* Already write protected */
116 return 0;
119 switch (type) {
120 case CTRLR_WP:
121 ctrlr_pr = WRITE_PROTECT;
122 break;
123 case CTRLR_RP:
124 ctrlr_pr = READ_PROTECT;
125 break;
126 case CTRLR_RWP:
127 ctrlr_pr = READ_WRITE_PROTECT;
128 break;
129 default:
130 return -1;
133 return spi_flash_ctrlr_protect_region(boot_dev,
134 region_device_region(rd), ctrlr_pr);