summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--util/inteltool/inteltool.c38
-rw-r--r--util/inteltool/inteltool.h22
-rw-r--r--util/inteltool/lpc.c40
-rw-r--r--util/inteltool/memory.c16
-rw-r--r--util/inteltool/spi.c106
5 files changed, 217 insertions, 5 deletions
diff --git a/util/inteltool/inteltool.c b/util/inteltool/inteltool.c
index 9a4ab89b9f..b7dbd62223 100644
--- a/util/inteltool/inteltool.c
+++ b/util/inteltool/inteltool.c
@@ -204,6 +204,30 @@ static const struct {
"14th generation (Meteor Lake P family) Core Processor"},
{ PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_CORE_MTL_ID_P_5,
"14th generation (Meteor Lake P family) Core Processor"},
+
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ELKHART_LAKE_1,
+ "Elkhart Lake Processor" },
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ELKHART_LAKE_2,
+ "Elkhart Lake Processor" },
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ELKHART_LAKE_3,
+ "Elkhart Lake Processor" },
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ELKHART_LAKE_4,
+ "Elkhart Lake Processor" },
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ELKHART_LAKE_5,
+ "Elkhart Lake Processor" },
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ELKHART_LAKE_6,
+ "Elkhart Lake Processor" },
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ELKHART_LAKE_7,
+ "Elkhart Lake Processor" },
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ELKHART_LAKE_8,
+ "Elkhart Lake Processor" },
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ELKHART_LAKE_9,
+ "Elkhart Lake Processor" },
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ELKHART_LAKE_10,
+ "Elkhart Lake Processor" },
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ELKHART_LAKE_11,
+ "Elkhart Lake Processor" },
+
/* Southbridges (LPC controllers) */
{ PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82371XX, "371AB/EB/MB" },
{ PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ICH10, "ICH10" },
@@ -613,6 +637,18 @@ static const struct {
"Intel(R) MeteorLake-P GT2" },
{ PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_MTL_P_GT2_4,
"Intel(R) MeteorLake-P GT2" },
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_EHL_GT1_1,
+ "Intel(R) Elkhart Lake GT1" },
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_EHL_GT1_2,
+ "Intel(R) Elkhart Lake GT1" },
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_EHL_GT1_3,
+ "Intel(R) Elkhart Lake GT1" },
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_EHL_GT1_4,
+ "Intel(R) Elkhart Lake GT1" },
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_EHL_GT1_5,
+ "Intel(R) Elkhart Lake GT1" },
+ { PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_EHL_GT1_6,
+ "Intel(R) Elkhart Lake GT1" },
};
#ifndef __DARWIN__
@@ -1053,7 +1089,7 @@ int main(int argc, char *argv[])
print_ambs(nb, pacc);
if (dump_spi)
- print_spi(sb);
+ print_spi(sb, pacc);
if (dump_gfx)
print_gfx(gfx);
diff --git a/util/inteltool/inteltool.h b/util/inteltool/inteltool.h
index 9ed958c736..f44c79c5fc 100644
--- a/util/inteltool/inteltool.h
+++ b/util/inteltool/inteltool.h
@@ -344,6 +344,19 @@ static inline uint32_t inl(unsigned port)
#define PCI_DEVICE_ID_INTEL_DNV_LPC 0x19dc
#define PCI_DEVICE_ID_INTEL_GLK_LPC 0x31E8
+/* Elkhart Lake */
+#define PCI_DEVICE_ID_INTEL_ELKHART_LAKE_1 0x4514
+#define PCI_DEVICE_ID_INTEL_ELKHART_LAKE_2 0x4516
+#define PCI_DEVICE_ID_INTEL_ELKHART_LAKE_3 0x4518
+#define PCI_DEVICE_ID_INTEL_ELKHART_LAKE_4 0x451a
+#define PCI_DEVICE_ID_INTEL_ELKHART_LAKE_5 0x4528
+#define PCI_DEVICE_ID_INTEL_ELKHART_LAKE_6 0x452a
+#define PCI_DEVICE_ID_INTEL_ELKHART_LAKE_7 0x452c
+#define PCI_DEVICE_ID_INTEL_ELKHART_LAKE_8 0x452e
+#define PCI_DEVICE_ID_INTEL_ELKHART_LAKE_9 0x4532
+#define PCI_DEVICE_ID_INTEL_ELKHART_LAKE_10 0x4534
+#define PCI_DEVICE_ID_INTEL_ELKHART_LAKE_11 0x4536
+
/* Intel starts counting these generations with the integration of the DRAM controller */
#define PCI_DEVICE_ID_INTEL_CORE_0TH_GEN 0xd132 /* Nehalem */
#define PCI_DEVICE_ID_INTEL_CORE_1ST_GEN_D 0x0040 /* Clarkdale (Westmere Desktop) */
@@ -486,6 +499,13 @@ static inline uint32_t inl(unsigned port)
#define PCI_DEVICE_ID_INTEL_TGL_GT1_2 0x9A68
#define PCI_DEVICE_ID_INTEL_TGL_GT2_ULT_1 0x9A78
#define PCI_DEVICE_ID_INTEL_TGL_GT2_ULT_2 0x9A70
+/* Elkhart Lake */
+#define PCI_DEVICE_ID_INTEL_EHL_GT1_1 0x4541
+#define PCI_DEVICE_ID_INTEL_EHL_GT1_2 0x4551
+#define PCI_DEVICE_ID_INTEL_EHL_GT1_3 0x4555
+#define PCI_DEVICE_ID_INTEL_EHL_GT1_4 0x4557
+#define PCI_DEVICE_ID_INTEL_EHL_GT1_5 0x4570
+#define PCI_DEVICE_ID_INTEL_EHL_GT1_6 0x4571
#define PCI_DEVICE_ID_INTEL_ADL_S_GT1 0x4680
#define PCI_DEVICE_ID_INTEL_ADL_S_GT1_2 0x4682
#define PCI_DEVICE_ID_INTEL_ADL_S_GT1_3 0x4690
@@ -538,7 +558,7 @@ int print_epbar(struct pci_dev *nb);
int print_dmibar(struct pci_dev *nb);
int print_pciexbar(struct pci_dev *nb);
int print_ambs(struct pci_dev *nb, struct pci_access *pacc);
-int print_spi(struct pci_dev *sb);
+int print_spi(struct pci_dev *sb, struct pci_access *pacc);
int print_gfx(struct pci_dev *gfx);
int print_ahci(struct pci_dev *ahci);
int print_sgx(void);
diff --git a/util/inteltool/lpc.c b/util/inteltool/lpc.c
index 8e171e3afb..4ce06ae5b9 100644
--- a/util/inteltool/lpc.c
+++ b/util/inteltool/lpc.c
@@ -77,6 +77,28 @@ static const io_register_t alderlake_espi_cfg_registers[] = {
{0xDC, 4, "ESPI_BC"},
};
+static const io_register_t elkhart_espi_cfg_registers[] = {
+ {0x00, 4, "ESPI_DID_VID"},
+ {0x04, 4, "ESPI_STS_CMD"},
+ {0x08, 4, "ESPI_CC_RID"},
+ {0x0C, 4, "ESPI_BIST_HTYPE_PLT_CLS"},
+ {0x2C, 4, "ESPI_SS"},
+ {0x34, 4, "ESPI_CAPP"},
+ {0x80, 4, "ESPI_IOD_IOE"},
+ {0x84, 4, "ESPI_LGIR1"},
+ {0x88, 4, "ESPI_LGIR2"},
+ {0x8C, 4, "ESPI_LGIR3"},
+ {0x90, 4, "ESPI_LGIR4"},
+ {0x94, 4, "ESPI_ULKMC"},
+ {0xA0, 4, "ESPI_CS1IORE"},
+ {0xA4, 4, "ESPI_CS1GIR1"},
+ {0xA8, 4, "ESPI_CS1GMR1"},
+ {0xD0, 4, "ESPI_FS1"},
+ {0xD4, 4, "ESPI_FS2"},
+ {0xD8, 4, "ESPI_BDE"},
+ {0xDC, 4, "ESPI_BC"},
+};
+
int print_lpc(struct pci_dev *sb, struct pci_access *pacc)
{
size_t i, cfg_registers_size = 0;
@@ -138,6 +160,24 @@ int print_lpc(struct pci_dev *sb, struct pci_access *pacc)
cfg_registers = alderlake_espi_cfg_registers;
cfg_registers_size = ARRAY_SIZE(alderlake_espi_cfg_registers);
break;
+ case PCI_DEVICE_ID_INTEL_EHL:
+ dev = pci_get_dev(pacc, sb->domain, sb->bus, sb->dev, 0);
+ if (!dev) {
+ printf("LPC/eSPI interface not found.\n");
+ return 1;
+ }
+ bc = pci_read_long(dev, SUNRISE_LPC_BC);
+ if (bc & (1 << 2)) {
+ printf("Device 0:1f.0 is eSPI (BC.LPC_ESPI=1)\n\n");
+ cfg_registers = elkhart_espi_cfg_registers;
+ cfg_registers_size = ARRAY_SIZE(elkhart_espi_cfg_registers);
+
+ } else {
+ printf("Device 0:1f.0 is LPC (BC.LPC_ESPI=0)\n\n");
+ cfg_registers = sunrise_lpc_cfg_registers;
+ cfg_registers_size = ARRAY_SIZE(sunrise_lpc_cfg_registers);
+ }
+ break;
default:
printf("Error: Dumping LPC/eSPI on this southbridge is not (yet) supported.\n");
return 1;
diff --git a/util/inteltool/memory.c b/util/inteltool/memory.c
index ae25494b13..bb7ad60617 100644
--- a/util/inteltool/memory.c
+++ b/util/inteltool/memory.c
@@ -240,6 +240,22 @@ int print_mchbar(struct pci_dev *nb, struct pci_access *pacc, const char *dump_s
mchbar_phys &= 0x0000007fffff0000UL; /* 38:16 */
size = 32768;
break;
+ case PCI_DEVICE_ID_INTEL_ELKHART_LAKE_1:
+ case PCI_DEVICE_ID_INTEL_ELKHART_LAKE_2:
+ case PCI_DEVICE_ID_INTEL_ELKHART_LAKE_3:
+ case PCI_DEVICE_ID_INTEL_ELKHART_LAKE_4:
+ case PCI_DEVICE_ID_INTEL_ELKHART_LAKE_5:
+ case PCI_DEVICE_ID_INTEL_ELKHART_LAKE_6:
+ case PCI_DEVICE_ID_INTEL_ELKHART_LAKE_7:
+ case PCI_DEVICE_ID_INTEL_ELKHART_LAKE_8:
+ case PCI_DEVICE_ID_INTEL_ELKHART_LAKE_9:
+ case PCI_DEVICE_ID_INTEL_ELKHART_LAKE_10:
+ case PCI_DEVICE_ID_INTEL_ELKHART_LAKE_11:
+ mchbar_phys = pci_read_long(nb, 0x48);
+ mchbar_phys |= ((uint64_t)pci_read_long(nb, 0x4c)) << 32;
+ mchbar_phys &= 0x0000007fffff0000UL; /* 38:16 */
+ size = 65536;
+ break;
default:
printf("Error: Dumping MCHBAR on this northbridge is not (yet) supported.\n");
printf("Error: Unknown PCI id: %04x/%04x\n", nb->vendor_id, nb->device_id);
diff --git a/util/inteltool/spi.c b/util/inteltool/spi.c
index f2f345784d..cba43ed10e 100644
--- a/util/inteltool/spi.c
+++ b/util/inteltool/spi.c
@@ -42,6 +42,21 @@ static const io_register_t adl_pch_bios_cntl_registers[] = {
{ 0x12, 19, "Reserved" },
};
+static const io_register_t elkhart_bios_cntl_registers[] = {
+ { 0x0, 1, "BIOSWE - write enable" },
+ { 0x1, 1, "BLE - lock enable" },
+ { 0x2, 1, "ESPI - eSPI Enable Pin Strap" },
+ { 0x3, 1, "Reserved" },
+ { 0x4, 1, "TS - TopSwapStatus" },
+ { 0x5, 1, "EISS - Enable InSMM.STS" },
+ { 0x6, 1, "BBS - Boot BIOS Strap" },
+ { 0x7, 1, "BILD - BIOS Interface Lock-Down" },
+ { 0x8, 1, "BWPDS - BIOS Write Protect Disable Status" },
+ { 0x9, 1, "Reserved" },
+ { 0xa, 1, "BWRS - BIOS Write Status" },
+ { 0xb, 1, "BWRE - BIOS Write Reporting (Async-SMI) Enable" },
+};
+
#define ICH9_SPIBAR 0x3800
#define ICH78_SPIBAR 0x3020
@@ -95,6 +110,66 @@ static const io_register_t ich7_spi_bar_registers[] = {
{ 0x68, 4, "PBR2 Protected BIOS Range 2" },
};
+/*
+ * Intel Atom x6000E Series, and Intel Pentium and Celeron N and J Series Processors for IoT Applications
+ * February 2023,
+ * Document number 636722
+ */
+static const io_register_t elkhart_spi_bar_registers[] = {
+ { 0x00, 4, "BFPR - BIOS Flash primary region" },
+ { 0x04, 2, "HSFSTS - Hardware Sequencing Flash Status" },
+ { 0x06, 2, "HSFCTL - Hardware Sequencing Flash Control" },
+ { 0x08, 4, "FADDR - Flash Address" },
+ { 0x0c, 4, "BIOS_DLOCK - Discrete Lock Bits" },
+ { 0x10, 4, "FDATA0" },
+ /* 0x10 .. 0x4f are filled with data */
+ { 0x50, 4, "FRACC - Flash Region Access Permissions" },
+ { 0x54, 4, "Flash Region 0" },
+ { 0x58, 4, "Flash Region 1" },
+ { 0x5c, 4, "Flash Region 2" },
+ { 0x60, 4, "Flash Region 3" },
+ { 0x64, 4, "Flash Region 4" },
+ { 0x68, 4, "Flash Region 5" },
+ { 0x6c, 4, "Flash Region 6" },
+ { 0x70, 4, "Flash Region 7" },
+ { 0x74, 4, "Flash Region 8" },
+ { 0x78, 4, "Flash Region 9" },
+ { 0x7c, 4, "Flash Region 10" },
+ { 0x80, 4, "Flash Region 11" },
+ { 0x84, 4, "FPR0 - Flash Protected Range 0" },
+ { 0x88, 4, "FPR0 - Flash Protected Range 1" },
+ { 0x8c, 4, "FPR0 - Flash Protected Range 2" },
+ { 0x90, 4, "FPR0 - Flash Protected Range 3" },
+ { 0x94, 4, "FPR0 - Flash Protected Range 4" },
+ { 0x98, 4, "GPR0 - Global Protected Range 0" },
+ { 0xa0, 4, "SSFSTS - Software Sequencing Flash Status" },
+ { 0xa4, 2, "PREOP - Prefix opcode Configuration" },
+ { 0xa6, 2, "OPTYPE - Opcode Type Configuration" },
+ { 0xa8, 4, "OPMENU0 - Opcode Menu Configuration" },
+ { 0xac, 4, "OPMENU1 - Opcode Menu Configuration" },
+ { 0xb0, 4, "SFRACC - Secondary Flash Region Access Permissions" },
+ { 0xb4, 4, "FDOC - Flash Descriptor Observability Control" },
+ { 0xb8, 4, "FDOD - Flash Descriptor Observability Data" },
+ { 0xc0, 4, "AFC - Additional Flash Control" },
+ { 0xc4, 4, "SFDP0_VSCC0 - Vendor Specific Component Capabilities" },
+ { 0xc8, 4, "SFDP0_VSCC1 - Vendor Specific Component Capabilities" },
+ { 0xcc, 4, "PTINX - Parameter Table Index" },
+ { 0xd0, 4, "PTDATA - Parameter Table Data" },
+ { 0xd4, 4, "SBRS - SPI Bus Requester Status" },
+ { 0xe0, 4, "FREG12 - Flash Region" },
+ { 0xe4, 4, "FREG13 - Flash Region" },
+ { 0xe8, 4, "FREG14 - Flash Region" },
+ { 0xec, 4, "FREG15 - Flash Region" },
+ { 0x118, 4, "BM_WAP - BIOS Master Read Access Permissions (BIOS_BM_RAP)" },
+ { 0x11c, 4, "BM_WAP - BIOS Master Write Access Permissions (BIOS_BM_WAP)" },
+ { 0x184, 4, "CSXE_PR0 - CSXE Flash Protected Range" },
+ { 0x188, 4, "CSXE_PR1 - CSXE Flash Protected Range" },
+ { 0x18c, 4, "CSXE_PR2 - CSXE Flash Protected Range" },
+ { 0x190, 4, "CSXE_PR3 - CSXE Flash Protected Range" },
+ { 0x194, 4, "CSXE_PR4 - CSXE Flash Protected Range" },
+ { 0x198, 4, "CSXE_PR0 - CSXE Flash Protected Range" },
+ { 0x198, 4, "CSXE_WPR0 - Write Protected Range 0" },
+};
static int print_bioscntl(struct pci_dev *sb)
{
@@ -232,6 +307,11 @@ static int print_bioscntl(struct pci_dev *sb)
bios_cntl_register = adl_pch_bios_cntl_registers;
size = ARRAY_SIZE(adl_pch_bios_cntl_registers);
break;
+ case PCI_DEVICE_ID_INTEL_EHL:
+ bios_cntl = pci_read_byte(sb, 0xdc);
+ bios_cntl_register = elkhart_bios_cntl_registers;
+ size = ARRAY_SIZE(elkhart_bios_cntl_registers);
+ break;
default:
printf("Error: Dumping SPI on this southbridge is not (yet) supported.\n");
return 1;
@@ -250,12 +330,13 @@ static int print_bioscntl(struct pci_dev *sb)
return 0;
}
-static int print_spibar(struct pci_dev *sb) {
+static int print_spibar(struct pci_dev *sb, struct pci_access *pacc) {
int i, size = 0, rcba_size = 0x4000;
volatile uint8_t *rcba;
uint32_t rcba_phys;
const io_register_t *spi_register = NULL;
uint32_t spibaroffset;
+ struct pci_dev *spidev;
printf("\n============= SPI Bar ==============\n\n");
@@ -378,6 +459,25 @@ static int print_spibar(struct pci_dev *sb) {
size = ARRAY_SIZE(spi_bar_registers);
spi_register = spi_bar_registers;
break;
+ case PCI_DEVICE_ID_INTEL_EHL:
+ /* the southbridge is the eSPI controller, we need to get the SPI flash controller */
+ if (!(spidev = pci_get_dev(pacc, sb->domain, sb->bus, sb->dev, 5))) {
+ perror("Error: no spi device 0:31.5\n");
+ return 1;
+ }
+
+ rcba_phys = ((uint64_t)pci_read_long(spidev, 0x10) & 0xfffff000);
+ rcba_size = 4096;
+ if (!rcba_phys) {
+ fprintf(stderr, "Error: no valid bar 0 of device 0:31.5 found %x %x\n", rcba_phys, rcba_size);
+ return 1;
+ }
+
+ /* this is not rcba, but we keep it to use common code */
+ spibaroffset = 0;
+ spi_register = elkhart_spi_bar_registers;
+ size = ARRAY_SIZE(elkhart_spi_bar_registers);
+ break;
case PCI_DEVICE_ID_INTEL_ICH:
case PCI_DEVICE_ID_INTEL_ICH0:
case PCI_DEVICE_ID_INTEL_ICH2:
@@ -420,6 +520,6 @@ static int print_spibar(struct pci_dev *sb) {
return 0;
}
-int print_spi(struct pci_dev *sb) {
- return (print_bioscntl(sb) || print_spibar(sb));
+int print_spi(struct pci_dev *sb, struct pci_access *pacc) {
+ return (print_bioscntl(sb) || print_spibar(sb, pacc));
}