mirror of
https://review.coreboot.org/flashrom.git
synced 2025-04-27 07:02:34 +02:00
ichspi.c: Add support for region 9 and beyond in Meteor Lake
Since Meteor Lake, configuring region access for FREG9 and higher is necessary. This configuration is determined using BIOS_BM registers: BIOS_BM_RAP (Offset 0x118): BIOS Master Read Access Permissions. Each bit [15:0] corresponds to a region [15:0]. A set bit grants BIOS master read access. BIOS_BM_WAP (Offset 0x11c): BIOS Master Write Access Permissions. Each bit [15:0] corresponds to a region [15:0]. A set bit grants BIOS master write/erase access. Move CHIPSET_METEOR_LAKE to the bottom of the ich_chipset list to ensure that all the newer chipsets in the future will use BIOS_BM check by default. BUG=b:319773700, b:304439294 BUG=b:319336080 TEST=On MTL, use flashrom -VV to see correct FREG9 access TEST=On ADL, use flashrom -VV to see not break anything TEST=On APL, use flashrom -VV to see not break anything Change-Id: I1e06e7b3d470423a6014e623826d9234fdebfbf9 Signed-off-by: Hsuan Ting Chen <roccochen@chromium.org> Reviewed-on: https://review.coreboot.org/c/flashrom/+/81357 Reviewed-by: Jamie Ryu <jamie.m.ryu@intel.com> Reviewed-by: Nikolai Artemiev <nartemiev@google.com> Reviewed-by: Anastasia Klimchuk <aklm@chromium.org> Tested-by: build bot (Jenkins) <no-reply@coreboot.org>
This commit is contained in:
parent
3b3e25f1ca
commit
85b977151b
84
ichspi.c
84
ichspi.c
@ -153,6 +153,9 @@
|
|||||||
#define ICH9_FADDR_FLA 0x01ffffff
|
#define ICH9_FADDR_FLA 0x01ffffff
|
||||||
#define ICH9_REG_FDATA0 0x10 /* 64 Bytes */
|
#define ICH9_REG_FDATA0 0x10 /* 64 Bytes */
|
||||||
|
|
||||||
|
#define ICH_REG_BIOS_BM_RAP 0x118 /* 16 Bits BIOS Master Read Access Permissions */
|
||||||
|
#define ICH_REG_BIOS_BM_WAP 0x11c /* 16 Bits BIOS Master Write Access Permissions */
|
||||||
|
|
||||||
#define ICH9_REG_FRAP 0x50 /* 32 Bytes Flash Region Access Permissions */
|
#define ICH9_REG_FRAP 0x50 /* 32 Bytes Flash Region Access Permissions */
|
||||||
#define ICH9_REG_FREG0 0x54 /* 32 Bytes Flash Region 0 */
|
#define ICH9_REG_FREG0 0x54 /* 32 Bytes Flash Region 0 */
|
||||||
|
|
||||||
@ -1834,8 +1837,52 @@ static const char *const access_names[] = {
|
|||||||
"read-write", "write-only", "read-only", "locked"
|
"read-write", "write-only", "read-only", "locked"
|
||||||
};
|
};
|
||||||
|
|
||||||
static enum ich_access_protection ich9_handle_frap(struct fd_region *fd_regions,
|
static void ich_get_bios_region_access(uint16_t *region_read_access,
|
||||||
uint32_t frap, unsigned int i)
|
uint16_t *region_write_access)
|
||||||
|
{
|
||||||
|
uint32_t tmp;
|
||||||
|
*region_read_access = 0;
|
||||||
|
*region_write_access = 0;
|
||||||
|
|
||||||
|
if (ich_generation >= CHIPSET_METEOR_LAKE) {
|
||||||
|
/*
|
||||||
|
* Starting from Meteor Lake, we need to fetch the region
|
||||||
|
* read/write access permissions from the BIOS_BM registers
|
||||||
|
* because we need to support FREG9 or above.
|
||||||
|
*/
|
||||||
|
*region_read_access = mmio_readw(ich_spibar + ICH_REG_BIOS_BM_RAP);
|
||||||
|
*region_write_access = mmio_readw(ich_spibar + ICH_REG_BIOS_BM_WAP);
|
||||||
|
msg_pdbg("0x118: 0x%04"PRIx16" (BIOS_BM_RAP)\n", *region_read_access);
|
||||||
|
msg_pdbg("0x11a: 0x%04"PRIx16" (BIOS_BM_WAP)\n", *region_write_access);
|
||||||
|
} else {
|
||||||
|
/*
|
||||||
|
* FRAP - Flash Regions Access Permissions Register
|
||||||
|
* Bit Descriptions:
|
||||||
|
* 31:24 BIOS Master Write Access Grant (BMWAG)
|
||||||
|
* 23:16 BIOS Master Read Access Grant (BMRAG)
|
||||||
|
* 15:8 BIOS Region Write Access (BRWA)
|
||||||
|
* 7:0 BIOS Region Read Access (BRRA)
|
||||||
|
*/
|
||||||
|
tmp = mmio_readl(ich_spibar + ICH9_REG_FRAP);
|
||||||
|
msg_pdbg("0x50: 0x%08"PRIx32" (FRAP)\n", tmp);
|
||||||
|
msg_pdbg("BMWAG 0x%02"PRIx32", ", ICH_BMWAG(tmp));
|
||||||
|
msg_pdbg("BMRAG 0x%02"PRIx32", ", ICH_BMRAG(tmp));
|
||||||
|
msg_pdbg("BRWA 0x%02"PRIx32", ", ICH_BRWA(tmp));
|
||||||
|
msg_pdbg("BRRA 0x%02"PRIx32"\n", ICH_BRRA(tmp));
|
||||||
|
|
||||||
|
*region_read_access = (uint16_t)ICH_BRRA(tmp);
|
||||||
|
*region_write_access = (uint16_t)ICH_BRWA(tmp);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static unsigned int ich_get_defined_region_count(void) {
|
||||||
|
return (ich_generation >= CHIPSET_METEOR_LAKE) ? 16 : 8;
|
||||||
|
}
|
||||||
|
|
||||||
|
static enum ich_access_protection ich9_handle_region_access(struct fd_region *fd_regions,
|
||||||
|
uint16_t region_read_access,
|
||||||
|
uint16_t region_write_access,
|
||||||
|
unsigned int i)
|
||||||
{
|
{
|
||||||
static const char *const region_names[] = {
|
static const char *const region_names[] = {
|
||||||
"Flash Descriptor", "BIOS", "Management Engine",
|
"Flash Descriptor", "BIOS", "Management Engine",
|
||||||
@ -1863,12 +1910,12 @@ static enum ich_access_protection ich9_handle_frap(struct fd_region *fd_regions,
|
|||||||
}
|
}
|
||||||
msg_pdbg("0x%02X: 0x%08"PRIx32" ", offset, freg);
|
msg_pdbg("0x%02X: 0x%08"PRIx32" ", offset, freg);
|
||||||
|
|
||||||
if (i < 8) {
|
if (i < ich_get_defined_region_count()) {
|
||||||
rwperms_idx = (((ICH_BRWA(frap) >> i) & 1) << 1) |
|
rwperms_idx = (((region_write_access >> i) & 1) << 1) |
|
||||||
(((ICH_BRRA(frap) >> i) & 1) << 0);
|
(((region_read_access >> i) & 1) << 0);
|
||||||
rwperms = access_perms_to_protection[rwperms_idx];
|
rwperms = access_perms_to_protection[rwperms_idx];
|
||||||
} else {
|
} else {
|
||||||
/* Datasheets don't define any access bits for regions > 7. We
|
/* Datasheets might not define all the access bits for regions. We
|
||||||
can't rely on the actual descriptor settings either as there
|
can't rely on the actual descriptor settings either as there
|
||||||
are several overrides for them (those by other masters are
|
are several overrides for them (those by other masters are
|
||||||
not even readable by us, *shrug*). */
|
not even readable by us, *shrug*). */
|
||||||
@ -2059,11 +2106,11 @@ static void init_chipset_properties(struct swseq_data *swseq, struct hwseq_data
|
|||||||
case CHIPSET_400_SERIES_COMET_POINT:
|
case CHIPSET_400_SERIES_COMET_POINT:
|
||||||
case CHIPSET_500_SERIES_TIGER_POINT:
|
case CHIPSET_500_SERIES_TIGER_POINT:
|
||||||
case CHIPSET_600_SERIES_ALDER_POINT:
|
case CHIPSET_600_SERIES_ALDER_POINT:
|
||||||
case CHIPSET_METEOR_LAKE:
|
|
||||||
case CHIPSET_APOLLO_LAKE:
|
case CHIPSET_APOLLO_LAKE:
|
||||||
case CHIPSET_GEMINI_LAKE:
|
case CHIPSET_GEMINI_LAKE:
|
||||||
case CHIPSET_JASPER_LAKE:
|
case CHIPSET_JASPER_LAKE:
|
||||||
case CHIPSET_ELKHART_LAKE:
|
case CHIPSET_ELKHART_LAKE:
|
||||||
|
case CHIPSET_METEOR_LAKE:
|
||||||
*num_pr = 6; /* Includes GPR0 */
|
*num_pr = 6; /* Includes GPR0 */
|
||||||
*reg_pr0 = PCH100_REG_FPR0;
|
*reg_pr0 = PCH100_REG_FPR0;
|
||||||
swseq->reg_ssfsc = PCH100_REG_SSFSC;
|
swseq->reg_ssfsc = PCH100_REG_SSFSC;
|
||||||
@ -2099,11 +2146,11 @@ static void init_chipset_properties(struct swseq_data *swseq, struct hwseq_data
|
|||||||
case CHIPSET_400_SERIES_COMET_POINT:
|
case CHIPSET_400_SERIES_COMET_POINT:
|
||||||
case CHIPSET_500_SERIES_TIGER_POINT:
|
case CHIPSET_500_SERIES_TIGER_POINT:
|
||||||
case CHIPSET_600_SERIES_ALDER_POINT:
|
case CHIPSET_600_SERIES_ALDER_POINT:
|
||||||
case CHIPSET_METEOR_LAKE:
|
|
||||||
case CHIPSET_APOLLO_LAKE:
|
case CHIPSET_APOLLO_LAKE:
|
||||||
case CHIPSET_GEMINI_LAKE:
|
case CHIPSET_GEMINI_LAKE:
|
||||||
case CHIPSET_JASPER_LAKE:
|
case CHIPSET_JASPER_LAKE:
|
||||||
case CHIPSET_ELKHART_LAKE:
|
case CHIPSET_ELKHART_LAKE:
|
||||||
|
case CHIPSET_METEOR_LAKE:
|
||||||
*num_freg = 16;
|
*num_freg = 16;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
@ -2161,11 +2208,11 @@ static int init_ich_default(const struct programmer_cfg *cfg, void *spibar, enum
|
|||||||
case CHIPSET_400_SERIES_COMET_POINT:
|
case CHIPSET_400_SERIES_COMET_POINT:
|
||||||
case CHIPSET_500_SERIES_TIGER_POINT:
|
case CHIPSET_500_SERIES_TIGER_POINT:
|
||||||
case CHIPSET_600_SERIES_ALDER_POINT:
|
case CHIPSET_600_SERIES_ALDER_POINT:
|
||||||
case CHIPSET_METEOR_LAKE:
|
|
||||||
case CHIPSET_APOLLO_LAKE:
|
case CHIPSET_APOLLO_LAKE:
|
||||||
case CHIPSET_GEMINI_LAKE:
|
case CHIPSET_GEMINI_LAKE:
|
||||||
case CHIPSET_JASPER_LAKE:
|
case CHIPSET_JASPER_LAKE:
|
||||||
case CHIPSET_ELKHART_LAKE:
|
case CHIPSET_ELKHART_LAKE:
|
||||||
|
case CHIPSET_METEOR_LAKE:
|
||||||
tmp = mmio_readl(spibar + PCH100_REG_DLOCK);
|
tmp = mmio_readl(spibar + PCH100_REG_DLOCK);
|
||||||
msg_pdbg("0x0c: 0x%08"PRIx32" (DLOCK)\n", tmp);
|
msg_pdbg("0x0c: 0x%08"PRIx32" (DLOCK)\n", tmp);
|
||||||
prettyprint_pch100_reg_dlock(tmp);
|
prettyprint_pch100_reg_dlock(tmp);
|
||||||
@ -2175,16 +2222,15 @@ static int init_ich_default(const struct programmer_cfg *cfg, void *spibar, enum
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (desc_valid) {
|
if (desc_valid) {
|
||||||
tmp = mmio_readl(spibar + ICH9_REG_FRAP);
|
/* Get the region access data from FRAP/BIOS_BM */
|
||||||
msg_pdbg("0x50: 0x%08"PRIx32" (FRAP)\n", tmp);
|
uint16_t region_read_access, region_write_access;
|
||||||
msg_pdbg("BMWAG 0x%02"PRIx32", ", ICH_BMWAG(tmp));
|
ich_get_bios_region_access(®ion_read_access, ®ion_write_access);
|
||||||
msg_pdbg("BMRAG 0x%02"PRIx32", ", ICH_BMRAG(tmp));
|
|
||||||
msg_pdbg("BRWA 0x%02"PRIx32", ", ICH_BRWA(tmp));
|
|
||||||
msg_pdbg("BRRA 0x%02"PRIx32"\n", ICH_BRRA(tmp));
|
|
||||||
|
|
||||||
/* Handle FREGx and FRAP registers */
|
/* Handle FREGx and region access registers */
|
||||||
for (i = 0; i < num_freg; i++)
|
for (i = 0; i < num_freg; i++)
|
||||||
ich_spi_rw_restricted |= ich9_handle_frap(hwseq_data.fd_regions, tmp, i);
|
ich_spi_rw_restricted |= ich9_handle_region_access(hwseq_data.fd_regions,
|
||||||
|
region_read_access,
|
||||||
|
region_write_access, i);
|
||||||
if (ich_spi_rw_restricted)
|
if (ich_spi_rw_restricted)
|
||||||
msg_pinfo("Not all flash regions are freely accessible by flashrom. This is "
|
msg_pinfo("Not all flash regions are freely accessible by flashrom. This is "
|
||||||
"most likely\ndue to an active ME. Please see "
|
"most likely\ndue to an active ME. Please see "
|
||||||
@ -2242,12 +2288,12 @@ static int init_ich_default(const struct programmer_cfg *cfg, void *spibar, enum
|
|||||||
case CHIPSET_400_SERIES_COMET_POINT:
|
case CHIPSET_400_SERIES_COMET_POINT:
|
||||||
case CHIPSET_500_SERIES_TIGER_POINT:
|
case CHIPSET_500_SERIES_TIGER_POINT:
|
||||||
case CHIPSET_600_SERIES_ALDER_POINT:
|
case CHIPSET_600_SERIES_ALDER_POINT:
|
||||||
case CHIPSET_METEOR_LAKE:
|
|
||||||
case CHIPSET_APOLLO_LAKE:
|
case CHIPSET_APOLLO_LAKE:
|
||||||
case CHIPSET_GEMINI_LAKE:
|
case CHIPSET_GEMINI_LAKE:
|
||||||
case CHIPSET_JASPER_LAKE:
|
case CHIPSET_JASPER_LAKE:
|
||||||
case CHIPSET_BAYTRAIL:
|
case CHIPSET_BAYTRAIL:
|
||||||
case CHIPSET_ELKHART_LAKE:
|
case CHIPSET_ELKHART_LAKE:
|
||||||
|
case CHIPSET_METEOR_LAKE:
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
ichspi_bbar = mmio_readl(spibar + ICH9_REG_BBAR);
|
ichspi_bbar = mmio_readl(spibar + ICH9_REG_BBAR);
|
||||||
@ -2282,11 +2328,11 @@ static int init_ich_default(const struct programmer_cfg *cfg, void *spibar, enum
|
|||||||
case CHIPSET_400_SERIES_COMET_POINT:
|
case CHIPSET_400_SERIES_COMET_POINT:
|
||||||
case CHIPSET_500_SERIES_TIGER_POINT:
|
case CHIPSET_500_SERIES_TIGER_POINT:
|
||||||
case CHIPSET_600_SERIES_ALDER_POINT:
|
case CHIPSET_600_SERIES_ALDER_POINT:
|
||||||
case CHIPSET_METEOR_LAKE:
|
|
||||||
case CHIPSET_APOLLO_LAKE:
|
case CHIPSET_APOLLO_LAKE:
|
||||||
case CHIPSET_GEMINI_LAKE:
|
case CHIPSET_GEMINI_LAKE:
|
||||||
case CHIPSET_JASPER_LAKE:
|
case CHIPSET_JASPER_LAKE:
|
||||||
case CHIPSET_ELKHART_LAKE:
|
case CHIPSET_ELKHART_LAKE:
|
||||||
|
case CHIPSET_METEOR_LAKE:
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
tmp = mmio_readl(spibar + ICH9_REG_FPB);
|
tmp = mmio_readl(spibar + ICH9_REG_FPB);
|
||||||
|
@ -357,11 +357,12 @@ enum ich_chipset {
|
|||||||
CHIPSET_400_SERIES_COMET_POINT,
|
CHIPSET_400_SERIES_COMET_POINT,
|
||||||
CHIPSET_500_SERIES_TIGER_POINT,
|
CHIPSET_500_SERIES_TIGER_POINT,
|
||||||
CHIPSET_600_SERIES_ALDER_POINT,
|
CHIPSET_600_SERIES_ALDER_POINT,
|
||||||
CHIPSET_METEOR_LAKE,
|
|
||||||
CHIPSET_APOLLO_LAKE,
|
CHIPSET_APOLLO_LAKE,
|
||||||
CHIPSET_GEMINI_LAKE,
|
CHIPSET_GEMINI_LAKE,
|
||||||
CHIPSET_JASPER_LAKE,
|
CHIPSET_JASPER_LAKE,
|
||||||
CHIPSET_ELKHART_LAKE,
|
CHIPSET_ELKHART_LAKE,
|
||||||
|
/* All chipsets after METEOR_LAKE should support checking BIOS_BM to get read/write access to of FREG0~15 */
|
||||||
|
CHIPSET_METEOR_LAKE,
|
||||||
};
|
};
|
||||||
|
|
||||||
/* ichspi.c */
|
/* ichspi.c */
|
||||||
|
Loading…
x
Reference in New Issue
Block a user