<p>Patrick Rudolph has uploaded this change for <strong>review</strong>.</p><p><a href="https://review.coreboot.org/25402">View Change</a></p><pre style="font-family: monospace,monospace; white-space: pre-wrap;">[WIP]util/intemetool: Add P2SB interface support<br><br>Try to unhide HECI using P2SB interface.<br>Tests showed that it's not possible to toggle HECI after<br>the interface has been locked. Maybe some other bits need<br>to be toggled first.<br><br>TODO: Needs test on hardware that hides the interface.<br><br>Change-Id: I6e67238095856d9937f8f392b8113d99af4cd186<br>Signed-off-by: Patrick Rudolph <patrick.rudolph@9elements.com><br>---<br>M util/intelmetool/Makefile<br>M util/intelmetool/intelmetool.c<br>A util/intelmetool/p2sb.c<br>A util/intelmetool/p2sb.h<br>4 files changed, 255 insertions(+), 1 deletion(-)<br><br></pre><pre style="font-family: monospace,monospace; white-space: pre-wrap;">git pull ssh://review.coreboot.org:29418/coreboot refs/changes/02/25402/1</pre><pre style="font-family: monospace,monospace; white-space: pre-wrap;"><span>diff --git a/util/intelmetool/Makefile b/util/intelmetool/Makefile</span><br><span>index b455a0e..850c46b 100644</span><br><span>--- a/util/intelmetool/Makefile</span><br><span>+++ b/util/intelmetool/Makefile</span><br><span>@@ -18,9 +18,10 @@</span><br><span> INSTALL ?= /usr/bin/install</span><br><span> PREFIX ?= /usr/local</span><br><span> CFLAGS ?= -O0 -g -Wall -W -Wno-unused-parameter -Wno-sign-compare -Wno-unused-function</span><br><span style="color: hsl(120, 100%, 40%);">+CFLAGS += -I../../src/commonlib/include</span><br><span> LDFLAGS += -lpci -lz</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">-OBJS = intelmetool.o me.o me_status.o mmap.o rcba.o msr.o</span><br><span style="color: hsl(120, 100%, 40%);">+OBJS = intelmetool.o me.o me_status.o mmap.o rcba.o msr.o p2sb.o</span><br><span> </span><br><span> OS_ARCH = $(shell uname)</span><br><span> ifeq ($(OS_ARCH), Darwin)</span><br><span>diff --git a/util/intelmetool/intelmetool.c b/util/intelmetool/intelmetool.c</span><br><span>index 0e75a50..34a8012 100644</span><br><span>--- a/util/intelmetool/intelmetool.c</span><br><span>+++ b/util/intelmetool/intelmetool.c</span><br><span>@@ -28,11 +28,13 @@</span><br><span> #include "mmap.h"</span><br><span> #include "msr.h"</span><br><span> #include "rcba.h"</span><br><span style="color: hsl(120, 100%, 40%);">+#include "p2sb.h"</span><br><span> </span><br><span> extern int fd_mem;</span><br><span> int debug = 0;</span><br><span> </span><br><span> static uint32_t fd2 = 0;</span><br><span style="color: hsl(120, 100%, 40%);">+static uint32_t psfx_t0_shdw_pcien = 0;</span><br><span> static int ME_major_ver = 0;</span><br><span> static int ME_minor_ver = 0;</span><br><span> </span><br><span>@@ -176,6 +178,11 @@</span><br><span> return 0;</span><br><span> }</span><br><span> </span><br><span style="color: hsl(120, 100%, 40%);">+#define PSF_BASE_ADDRESS 0xA00</span><br><span style="color: hsl(120, 100%, 40%);">+#define PCR_PSFX_T0_SHDW_PCIEN 0x1C</span><br><span style="color: hsl(120, 100%, 40%);">+#define PCR_PSFX_T0_SHDW_PCIEN_FUNDIS (1 << 8)</span><br><span style="color: hsl(120, 100%, 40%);">+#define PID_PSF1 0xBA</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span> static int activate_me(void)</span><br><span> {</span><br><span> const uint32_t rcba = get_rcba_phys();</span><br><span>@@ -194,6 +201,21 @@</span><br><span> printf("MEI was hidden on PCI, now unlocked\n");</span><br><span> else if (debug)</span><br><span> printf("MEI not hidden on PCI, checking if visible\n");</span><br><span style="color: hsl(120, 100%, 40%);">+ } else {</span><br><span style="color: hsl(120, 100%, 40%);">+ const uint64_t p2sb = get_p2sb_phys();</span><br><span style="color: hsl(120, 100%, 40%);">+ if (debug)</span><br><span style="color: hsl(120, 100%, 40%);">+ printf("P2SB bar: 0x%" PRIx64 "\n", p2sb);</span><br><span style="color: hsl(120, 100%, 40%);">+ if (p2sb > 0) {</span><br><span style="color: hsl(120, 100%, 40%);">+ if (pcr_read32(PID_PSF1, PSF_BASE_ADDRESS +</span><br><span style="color: hsl(120, 100%, 40%);">+ PCR_PSFX_T0_SHDW_PCIEN,</span><br><span style="color: hsl(120, 100%, 40%);">+ &psfx_t0_shdw_pcien))</span><br><span style="color: hsl(120, 100%, 40%);">+ printf("Error reading PCR\n");</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ if (pcr_and32(PID_PSF1, PSF_BASE_ADDRESS +</span><br><span style="color: hsl(120, 100%, 40%);">+ PCR_PSFX_T0_SHDW_PCIEN,</span><br><span style="color: hsl(120, 100%, 40%);">+ ~PCR_PSFX_T0_SHDW_PCIEN_FUNDIS))</span><br><span style="color: hsl(120, 100%, 40%);">+ printf("Error writing PCR\n");</span><br><span style="color: hsl(120, 100%, 40%);">+ }</span><br><span> }</span><br><span> </span><br><span> return 0;</span><br><span>@@ -217,6 +239,15 @@</span><br><span> if (debug)</span><br><span> printf("done\n");</span><br><span> }</span><br><span style="color: hsl(120, 100%, 40%);">+ } else {</span><br><span style="color: hsl(120, 100%, 40%);">+ const uint64_t p2sb = get_p2sb_phys();</span><br><span style="color: hsl(120, 100%, 40%);">+ if (p2sb > 0 &&</span><br><span style="color: hsl(120, 100%, 40%);">+ (psfx_t0_shdw_pcien & PCR_PSFX_T0_SHDW_PCIEN_FUNDIS)) {</span><br><span style="color: hsl(120, 100%, 40%);">+ if (pcr_or32(PID_PSF1, PSF_BASE_ADDRESS +</span><br><span style="color: hsl(120, 100%, 40%);">+ PCR_PSFX_T0_SHDW_PCIEN,</span><br><span style="color: hsl(120, 100%, 40%);">+ PCR_PSFX_T0_SHDW_PCIEN_FUNDIS))</span><br><span style="color: hsl(120, 100%, 40%);">+ printf("Error writing PCR\n");</span><br><span style="color: hsl(120, 100%, 40%);">+ }</span><br><span> }</span><br><span> }</span><br><span> </span><br><span>diff --git a/util/intelmetool/p2sb.c b/util/intelmetool/p2sb.c</span><br><span>new file mode 100644</span><br><span>index 0000000..28ce46f</span><br><span>--- /dev/null</span><br><span>+++ b/util/intelmetool/p2sb.c</span><br><span>@@ -0,0 +1,204 @@</span><br><span style="color: hsl(120, 100%, 40%);">+/*</span><br><span style="color: hsl(120, 100%, 40%);">+ * Copyright (C) 2014 Damien Zammit <damien@zamaudio.com></span><br><span style="color: hsl(120, 100%, 40%);">+ * Copyright (C) 2017 Patrick Rudolph <siro@das-labor.org></span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * This program is free software; you can redistribute it and/or modify</span><br><span style="color: hsl(120, 100%, 40%);">+ * it under the terms of the GNU General Public License as published by</span><br><span style="color: hsl(120, 100%, 40%);">+ * the Free Software Foundation; version 2 of the License.</span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * This program is distributed in the hope that it will be useful,</span><br><span style="color: hsl(120, 100%, 40%);">+ * but WITHOUT ANY WARRANTY; without even the implied warranty of</span><br><span style="color: hsl(120, 100%, 40%);">+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the</span><br><span style="color: hsl(120, 100%, 40%);">+ * GNU General Public License for more details.</span><br><span style="color: hsl(120, 100%, 40%);">+ */</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+#include <stdio.h></span><br><span style="color: hsl(120, 100%, 40%);">+#include <inttypes.h></span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+#include "intelmetool.h"</span><br><span style="color: hsl(120, 100%, 40%);">+#include "mmap.h"</span><br><span style="color: hsl(120, 100%, 40%);">+#include "p2sb.h"</span><br><span style="color: hsl(120, 100%, 40%);">+#include "assert.h"</span><br><span style="color: hsl(120, 100%, 40%);">+#include "commonlib/helpers.h"</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+static const int size = 0x1000000;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+/* Returns the physical P2SB base address or zero on error. */</span><br><span style="color: hsl(120, 100%, 40%);">+u64 get_p2sb_phys(void)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+ struct pci_access *pacc;</span><br><span style="color: hsl(120, 100%, 40%);">+ struct pci_dev *sb;</span><br><span style="color: hsl(120, 100%, 40%);">+ uint64_t p2sb_phys = 0;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ pacc = pci_alloc();</span><br><span style="color: hsl(120, 100%, 40%);">+ pacc->method = PCI_ACCESS_I386_TYPE1;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ pci_init(pacc);</span><br><span style="color: hsl(120, 100%, 40%);">+ pci_scan_bus(pacc);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ sb = pci_get_dev(pacc, 0, 0, 0x1f, 1);</span><br><span style="color: hsl(120, 100%, 40%);">+ if (!sb) {</span><br><span style="color: hsl(120, 100%, 40%);">+ printf("Uh oh, southbridge not on BDF(0:31:1), please report "</span><br><span style="color: hsl(120, 100%, 40%);">+ "this error, exiting.\n");</span><br><span style="color: hsl(120, 100%, 40%);">+ pci_cleanup(pacc);</span><br><span style="color: hsl(120, 100%, 40%);">+ return 0;</span><br><span style="color: hsl(120, 100%, 40%);">+ }</span><br><span style="color: hsl(120, 100%, 40%);">+ pci_fill_info(sb, PCI_FILL_IDENT | PCI_FILL_BASES | PCI_FILL_SIZES |</span><br><span style="color: hsl(120, 100%, 40%);">+ PCI_FILL_CLASS);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ const u8 reg8 = pci_read_byte(sb, 0xe1);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ if (pci_read_byte(sb, 0xe2) & 2) {</span><br><span style="color: hsl(120, 100%, 40%);">+ static int once;</span><br><span style="color: hsl(120, 100%, 40%);">+ if (!once)</span><br><span style="color: hsl(120, 100%, 40%);">+ printf("Warning: Endpoint Mask Lock Bit set !\n");</span><br><span style="color: hsl(120, 100%, 40%);">+ once = 1;</span><br><span style="color: hsl(120, 100%, 40%);">+ }</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ /* Make device visible */</span><br><span style="color: hsl(120, 100%, 40%);">+ pci_write_byte(sb, 0xe1, 0);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ /* someone home ? */</span><br><span style="color: hsl(120, 100%, 40%);">+ if (pci_read_word(sb, 0) == 0x0000 ||</span><br><span style="color: hsl(120, 100%, 40%);">+ pci_read_word(sb, 0) == 0xffff)</span><br><span style="color: hsl(120, 100%, 40%);">+ goto out;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ /* Probe for memory bar */</span><br><span style="color: hsl(120, 100%, 40%);">+ if (pci_read_long(sb, 0x10) & 1)</span><br><span style="color: hsl(120, 100%, 40%);">+ goto out;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ /* Get Sideband Register Access address */</span><br><span style="color: hsl(120, 100%, 40%);">+ if ((pci_read_long(sb, 0x10) & 0x6) == 0x0)</span><br><span style="color: hsl(120, 100%, 40%);">+ p2sb_phys = pci_read_long(sb, 0x10) & 0xfffffff8UL;</span><br><span style="color: hsl(120, 100%, 40%);">+ else if ((pci_read_long(sb, 0x10) & 0x6) == 0x4)</span><br><span style="color: hsl(120, 100%, 40%);">+ p2sb_phys = (pci_read_long(sb, 0x10) & 0xfffffff8UL) |</span><br><span style="color: hsl(120, 100%, 40%);">+ (((unsigned long long)pci_read_long(sb, 0x14)) << 32);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+out:</span><br><span style="color: hsl(120, 100%, 40%);">+ /* Make device invisible */</span><br><span style="color: hsl(120, 100%, 40%);">+ pci_write_byte(sb, 0xe1, reg8 | 1);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ pci_free_dev(sb);</span><br><span style="color: hsl(120, 100%, 40%);">+ pci_cleanup(pacc);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ return p2sb_phys;</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+/*</span><br><span style="color: hsl(120, 100%, 40%);">+ * Writes 'val' to P2SB register at address 'addr'.</span><br><span style="color: hsl(120, 100%, 40%);">+ * Returns 1 on error and 0 on success.</span><br><span style="color: hsl(120, 100%, 40%);">+ */</span><br><span style="color: hsl(120, 100%, 40%);">+static int write_p2sb32(uint32_t addr, uint32_t val)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+ volatile uint8_t *p2sb;</span><br><span style="color: hsl(120, 100%, 40%);">+ const uint64_t p2sb_phys = get_p2sb_phys();</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ if (!p2sb_phys) {</span><br><span style="color: hsl(120, 100%, 40%);">+ printf("Could not get P2SB address\n");</span><br><span style="color: hsl(120, 100%, 40%);">+ return 1;</span><br><span style="color: hsl(120, 100%, 40%);">+ }</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ p2sb = map_physical((off_t)p2sb_phys, size);</span><br><span style="color: hsl(120, 100%, 40%);">+ if (p2sb == NULL) {</span><br><span style="color: hsl(120, 100%, 40%);">+ printf("Could not map P2SB\n");</span><br><span style="color: hsl(120, 100%, 40%);">+ return 1;</span><br><span style="color: hsl(120, 100%, 40%);">+ }</span><br><span style="color: hsl(120, 100%, 40%);">+ *(uint32_t *)(p2sb + addr) = val;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ munmap((void *)p2sb, size);</span><br><span style="color: hsl(120, 100%, 40%);">+ return 0;</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+/*</span><br><span style="color: hsl(120, 100%, 40%);">+ * Reads P2SB register at address 'addr' and stores it in 'val'.</span><br><span style="color: hsl(120, 100%, 40%);">+ * Returns 1 on error and 0 on success.</span><br><span style="color: hsl(120, 100%, 40%);">+ */</span><br><span style="color: hsl(120, 100%, 40%);">+static int read_p2sb32(uint32_t addr, uint32_t *val)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+ volatile uint8_t *p2sb;</span><br><span style="color: hsl(120, 100%, 40%);">+ const uint64_t p2sb_phys = get_p2sb_phys();</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ if (!p2sb_phys) {</span><br><span style="color: hsl(120, 100%, 40%);">+ printf("Could not get P2SB address\n");</span><br><span style="color: hsl(120, 100%, 40%);">+ return 1;</span><br><span style="color: hsl(120, 100%, 40%);">+ }</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ p2sb = map_physical((off_t)p2sb_phys, size);</span><br><span style="color: hsl(120, 100%, 40%);">+ if (p2sb == NULL) {</span><br><span style="color: hsl(120, 100%, 40%);">+ printf("Could not map P2SB\n");</span><br><span style="color: hsl(120, 100%, 40%);">+ return 1;</span><br><span style="color: hsl(120, 100%, 40%);">+ }</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ *val = *(uint32_t *)(p2sb + addr);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ munmap((void *)p2sb, size);</span><br><span style="color: hsl(120, 100%, 40%);">+ return 0;</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+/* Port Id lives in bits 23:16 and register offset lives in 15:0 of address. */</span><br><span style="color: hsl(120, 100%, 40%);">+#define PCR_PORTID_SHIFT 16</span><br><span style="color: hsl(120, 100%, 40%);">+#define PCR_OFFSET_SHIFT 0</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+static uint32_t __pcr_reg_address(uint8_t pid, uint16_t offset)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+ return (pid << PCR_PORTID_SHIFT) | (offset << PCR_OFFSET_SHIFT);</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+int pcr_read32(uint8_t pid, uint16_t offset, uint32_t *val)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+ /* Ensure the PCR offset is corretcly aligned. */</span><br><span style="color: hsl(120, 100%, 40%);">+ assert(IS_ALIGNED(offset, sizeof(uint32_t)));</span><br><span style="color: hsl(120, 100%, 40%);">+ return read_p2sb32(__pcr_reg_address(pid, offset), val);</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+/*</span><br><span style="color: hsl(120, 100%, 40%);">+ * After every write one needs to perform a read an innocuous register to</span><br><span style="color: hsl(120, 100%, 40%);">+ * ensure the writes are completed for certain ports. This is done for</span><br><span style="color: hsl(120, 100%, 40%);">+ * all ports so that the callers don't need the per-port knowledge for</span><br><span style="color: hsl(120, 100%, 40%);">+ * each transaction.</span><br><span style="color: hsl(120, 100%, 40%);">+ */</span><br><span style="color: hsl(120, 100%, 40%);">+static inline int write_completion(uint8_t pid, uint16_t offset)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+ uint32_t reg32;</span><br><span style="color: hsl(120, 100%, 40%);">+ uint32_t a = __pcr_reg_address(pid, ALIGN_DOWN(offset, sizeof(uint32_t)));</span><br><span style="color: hsl(120, 100%, 40%);">+ return read_p2sb32(a, ®32);</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+int pcr_write32(uint8_t pid, uint16_t offset, uint32_t indata)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+ /* Ensure the PCR offset is corretcly aligned. */</span><br><span style="color: hsl(120, 100%, 40%);">+ assert(IS_ALIGNED(offset, sizeof(indata)));</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ if (write_p2sb32(__pcr_reg_address(pid, offset), indata))</span><br><span style="color: hsl(120, 100%, 40%);">+ return 1;</span><br><span style="color: hsl(120, 100%, 40%);">+ /* Ensure the writes complete. */</span><br><span style="color: hsl(120, 100%, 40%);">+ if (write_completion(pid, offset))</span><br><span style="color: hsl(120, 100%, 40%);">+ return 1;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ return 0;</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+int pcr_or32(uint8_t pid, uint16_t offset, uint32_t ordata)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+ uint32_t data32;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ if (pcr_read32(pid, offset, &data32))</span><br><span style="color: hsl(120, 100%, 40%);">+ return 1;</span><br><span style="color: hsl(120, 100%, 40%);">+ data32 |= ordata;</span><br><span style="color: hsl(120, 100%, 40%);">+ if (pcr_write32(pid, offset, data32))</span><br><span style="color: hsl(120, 100%, 40%);">+ return 1;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ return 0;</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+int pcr_and32(uint8_t pid, uint16_t offset, uint32_t anddata)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+ uint32_t data32;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ if (pcr_read32(pid, offset, &data32))</span><br><span style="color: hsl(120, 100%, 40%);">+ return 1;</span><br><span style="color: hsl(120, 100%, 40%);">+ data32 &= anddata;</span><br><span style="color: hsl(120, 100%, 40%);">+ if (pcr_write32(pid, offset, data32))</span><br><span style="color: hsl(120, 100%, 40%);">+ return 1;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ return 0;</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span>diff --git a/util/intelmetool/p2sb.h b/util/intelmetool/p2sb.h</span><br><span>new file mode 100644</span><br><span>index 0000000..f5c8515</span><br><span>--- /dev/null</span><br><span>+++ b/util/intelmetool/p2sb.h</span><br><span>@@ -0,0 +1,18 @@</span><br><span style="color: hsl(120, 100%, 40%);">+/*</span><br><span style="color: hsl(120, 100%, 40%);">+ * Copyright (C) 2017 Patrick Rudolph <siro@das-labor.org></span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * This program is free software; you can redistribute it and/or modify</span><br><span style="color: hsl(120, 100%, 40%);">+ * it under the terms of the GNU General Public License as published by</span><br><span style="color: hsl(120, 100%, 40%);">+ * the Free Software Foundation; version 2 of the License.</span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * This program is distributed in the hope that it will be useful,</span><br><span style="color: hsl(120, 100%, 40%);">+ * but WITHOUT ANY WARRANTY; without even the implied warranty of</span><br><span style="color: hsl(120, 100%, 40%);">+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the</span><br><span style="color: hsl(120, 100%, 40%);">+ * GNU General Public License for more details.</span><br><span style="color: hsl(120, 100%, 40%);">+ */</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+int pcr_read32(uint8_t pid, uint16_t offset, uint32_t *val);</span><br><span style="color: hsl(120, 100%, 40%);">+int pcr_write32(uint8_t pid, uint16_t offset, uint32_t indata);</span><br><span style="color: hsl(120, 100%, 40%);">+int pcr_or32(uint8_t pid, uint16_t offset, uint32_t ordata);</span><br><span style="color: hsl(120, 100%, 40%);">+int pcr_and32(uint8_t pid, uint16_t offset, uint32_t anddata);</span><br><span style="color: hsl(120, 100%, 40%);">+u64 get_p2sb_phys(void);</span><br><span></span><br></pre><p>To view, visit <a href="https://review.coreboot.org/25402">change 25402</a>. To unsubscribe, or for help writing mail filters, visit <a href="https://review.coreboot.org/settings">settings</a>.</p><div itemscope itemtype="http://schema.org/EmailMessage"><div itemscope itemprop="action" itemtype="http://schema.org/ViewAction"><link itemprop="url" href="https://review.coreboot.org/25402"/><meta itemprop="name" content="View Change"/></div></div>
<div style="display:none"> Gerrit-Project: coreboot </div>
<div style="display:none"> Gerrit-Branch: master </div>
<div style="display:none"> Gerrit-MessageType: newchange </div>
<div style="display:none"> Gerrit-Change-Id: I6e67238095856d9937f8f392b8113d99af4cd186 </div>
<div style="display:none"> Gerrit-Change-Number: 25402 </div>
<div style="display:none"> Gerrit-PatchSet: 1 </div>
<div style="display:none"> Gerrit-Owner: Patrick Rudolph <patrick.rudolph@9elements.com> </div>