From: Joelle van Dyne <j@getutm.app>
To: qemu-devel@nongnu.org
Cc: Joelle van Dyne <j@getutm.app>,
Stefan Berger <stefanb@linux.ibm.com>,
Stefan Berger <stefanb@linux.vnet.ibm.com>
Subject: [PATCH v2 01/11] tpm_crb: refactor common code
Date: Fri, 14 Jul 2023 00:09:17 -0700 [thread overview]
Message-ID: <20230714070931.23476-2-j@getutm.app> (raw)
In-Reply-To: <20230714070931.23476-1-j@getutm.app>
In preparation for the SysBus variant, we move common code styled
after the TPM TIS devices.
To maintain compatibility, we do not rename the existing tpm-crb
device.
Signed-off-by: Joelle van Dyne <j@getutm.app>
Reviewed-by: Stefan Berger <stefanb@linux.ibm.com>
---
docs/specs/tpm.rst | 1 +
hw/tpm/tpm_crb.h | 76 +++++++++++
hw/tpm/tpm_crb.c | 270 ++++++----------------------------------
hw/tpm/tpm_crb_common.c | 218 ++++++++++++++++++++++++++++++++
hw/tpm/meson.build | 1 +
hw/tpm/trace-events | 2 +-
6 files changed, 333 insertions(+), 235 deletions(-)
create mode 100644 hw/tpm/tpm_crb.h
create mode 100644 hw/tpm/tpm_crb_common.c
diff --git a/docs/specs/tpm.rst b/docs/specs/tpm.rst
index efe124a148..2bc29c9804 100644
--- a/docs/specs/tpm.rst
+++ b/docs/specs/tpm.rst
@@ -45,6 +45,7 @@ operating system.
QEMU files related to TPM CRB interface:
- ``hw/tpm/tpm_crb.c``
+ - ``hw/tpm/tpm_crb_common.c``
SPAPR interface
---------------
diff --git a/hw/tpm/tpm_crb.h b/hw/tpm/tpm_crb.h
new file mode 100644
index 0000000000..da3a0cf256
--- /dev/null
+++ b/hw/tpm/tpm_crb.h
@@ -0,0 +1,76 @@
+/*
+ * tpm_crb.h - QEMU's TPM CRB interface emulator
+ *
+ * Copyright (c) 2018 Red Hat, Inc.
+ *
+ * Authors:
+ * Marc-André Lureau <marcandre.lureau@redhat.com>
+ *
+ * This work is licensed under the terms of the GNU GPL, version 2 or later.
+ * See the COPYING file in the top-level directory.
+ *
+ * tpm_crb is a device for TPM 2.0 Command Response Buffer (CRB) Interface
+ * as defined in TCG PC Client Platform TPM Profile (PTP) Specification
+ * Family “2.0” Level 00 Revision 01.03 v22
+ */
+#ifndef TPM_TPM_CRB_H
+#define TPM_TPM_CRB_H
+
+#include "exec/memory.h"
+#include "hw/acpi/tpm.h"
+#include "sysemu/tpm_backend.h"
+#include "tpm_ppi.h"
+
+#define CRB_CTRL_CMD_SIZE (TPM_CRB_ADDR_SIZE - A_CRB_DATA_BUFFER)
+
+typedef struct TPMCRBState {
+ TPMBackend *tpmbe;
+ TPMBackendCmd cmd;
+ uint32_t regs[TPM_CRB_R_MAX];
+ MemoryRegion mmio;
+ MemoryRegion cmdmem;
+
+ size_t be_buffer_size;
+
+ bool ppi_enabled;
+ TPMPPI ppi;
+} TPMCRBState;
+
+#define CRB_INTF_TYPE_CRB_ACTIVE 0b1
+#define CRB_INTF_VERSION_CRB 0b1
+#define CRB_INTF_CAP_LOCALITY_0_ONLY 0b0
+#define CRB_INTF_CAP_IDLE_FAST 0b0
+#define CRB_INTF_CAP_XFER_SIZE_64 0b11
+#define CRB_INTF_CAP_FIFO_NOT_SUPPORTED 0b0
+#define CRB_INTF_CAP_CRB_SUPPORTED 0b1
+#define CRB_INTF_IF_SELECTOR_CRB 0b1
+
+enum crb_loc_ctrl {
+ CRB_LOC_CTRL_REQUEST_ACCESS = BIT(0),
+ CRB_LOC_CTRL_RELINQUISH = BIT(1),
+ CRB_LOC_CTRL_SEIZE = BIT(2),
+ CRB_LOC_CTRL_RESET_ESTABLISHMENT_BIT = BIT(3),
+};
+
+enum crb_ctrl_req {
+ CRB_CTRL_REQ_CMD_READY = BIT(0),
+ CRB_CTRL_REQ_GO_IDLE = BIT(1),
+};
+
+enum crb_start {
+ CRB_START_INVOKE = BIT(0),
+};
+
+enum crb_cancel {
+ CRB_CANCEL_INVOKE = BIT(0),
+};
+
+#define TPM_CRB_NO_LOCALITY 0xff
+
+void tpm_crb_request_completed(TPMCRBState *s, int ret);
+enum TPMVersion tpm_crb_get_version(TPMCRBState *s);
+int tpm_crb_pre_save(TPMCRBState *s);
+void tpm_crb_reset(TPMCRBState *s, uint64_t baseaddr);
+void tpm_crb_init_memory(Object *obj, TPMCRBState *s, Error **errp);
+
+#endif /* TPM_TPM_CRB_H */
diff --git a/hw/tpm/tpm_crb.c b/hw/tpm/tpm_crb.c
index ea930da545..3ef4977fb5 100644
--- a/hw/tpm/tpm_crb.c
+++ b/hw/tpm/tpm_crb.c
@@ -31,257 +31,62 @@
#include "tpm_ppi.h"
#include "trace.h"
#include "qom/object.h"
+#include "tpm_crb.h"
struct CRBState {
DeviceState parent_obj;
- TPMBackend *tpmbe;
- TPMBackendCmd cmd;
- uint32_t regs[TPM_CRB_R_MAX];
- MemoryRegion mmio;
- MemoryRegion cmdmem;
-
- size_t be_buffer_size;
-
- bool ppi_enabled;
- TPMPPI ppi;
+ TPMCRBState state;
};
typedef struct CRBState CRBState;
DECLARE_INSTANCE_CHECKER(CRBState, CRB,
TYPE_TPM_CRB)
-#define CRB_INTF_TYPE_CRB_ACTIVE 0b1
-#define CRB_INTF_VERSION_CRB 0b1
-#define CRB_INTF_CAP_LOCALITY_0_ONLY 0b0
-#define CRB_INTF_CAP_IDLE_FAST 0b0
-#define CRB_INTF_CAP_XFER_SIZE_64 0b11
-#define CRB_INTF_CAP_FIFO_NOT_SUPPORTED 0b0
-#define CRB_INTF_CAP_CRB_SUPPORTED 0b1
-#define CRB_INTF_IF_SELECTOR_CRB 0b1
-
-#define CRB_CTRL_CMD_SIZE (TPM_CRB_ADDR_SIZE - A_CRB_DATA_BUFFER)
-
-enum crb_loc_ctrl {
- CRB_LOC_CTRL_REQUEST_ACCESS = BIT(0),
- CRB_LOC_CTRL_RELINQUISH = BIT(1),
- CRB_LOC_CTRL_SEIZE = BIT(2),
- CRB_LOC_CTRL_RESET_ESTABLISHMENT_BIT = BIT(3),
-};
-
-enum crb_ctrl_req {
- CRB_CTRL_REQ_CMD_READY = BIT(0),
- CRB_CTRL_REQ_GO_IDLE = BIT(1),
-};
-
-enum crb_start {
- CRB_START_INVOKE = BIT(0),
-};
-
-enum crb_cancel {
- CRB_CANCEL_INVOKE = BIT(0),
-};
-
-#define TPM_CRB_NO_LOCALITY 0xff
-
-static uint64_t tpm_crb_mmio_read(void *opaque, hwaddr addr,
- unsigned size)
-{
- CRBState *s = CRB(opaque);
- void *regs = (void *)&s->regs + (addr & ~3);
- unsigned offset = addr & 3;
- uint32_t val = *(uint32_t *)regs >> (8 * offset);
-
- switch (addr) {
- case A_CRB_LOC_STATE:
- val |= !tpm_backend_get_tpm_established_flag(s->tpmbe);
- break;
- }
-
- trace_tpm_crb_mmio_read(addr, size, val);
-
- return val;
-}
-
-static uint8_t tpm_crb_get_active_locty(CRBState *s)
-{
- if (!ARRAY_FIELD_EX32(s->regs, CRB_LOC_STATE, locAssigned)) {
- return TPM_CRB_NO_LOCALITY;
- }
- return ARRAY_FIELD_EX32(s->regs, CRB_LOC_STATE, activeLocality);
-}
-
-static void tpm_crb_mmio_write(void *opaque, hwaddr addr,
- uint64_t val, unsigned size)
-{
- CRBState *s = CRB(opaque);
- uint8_t locty = addr >> 12;
-
- trace_tpm_crb_mmio_write(addr, size, val);
-
- switch (addr) {
- case A_CRB_CTRL_REQ:
- switch (val) {
- case CRB_CTRL_REQ_CMD_READY:
- ARRAY_FIELD_DP32(s->regs, CRB_CTRL_STS,
- tpmIdle, 0);
- break;
- case CRB_CTRL_REQ_GO_IDLE:
- ARRAY_FIELD_DP32(s->regs, CRB_CTRL_STS,
- tpmIdle, 1);
- break;
- }
- break;
- case A_CRB_CTRL_CANCEL:
- if (val == CRB_CANCEL_INVOKE &&
- s->regs[R_CRB_CTRL_START] & CRB_START_INVOKE) {
- tpm_backend_cancel_cmd(s->tpmbe);
- }
- break;
- case A_CRB_CTRL_START:
- if (val == CRB_START_INVOKE &&
- !(s->regs[R_CRB_CTRL_START] & CRB_START_INVOKE) &&
- tpm_crb_get_active_locty(s) == locty) {
- void *mem = memory_region_get_ram_ptr(&s->cmdmem);
-
- s->regs[R_CRB_CTRL_START] |= CRB_START_INVOKE;
- s->cmd = (TPMBackendCmd) {
- .in = mem,
- .in_len = MIN(tpm_cmd_get_size(mem), s->be_buffer_size),
- .out = mem,
- .out_len = s->be_buffer_size,
- };
-
- tpm_backend_deliver_request(s->tpmbe, &s->cmd);
- }
- break;
- case A_CRB_LOC_CTRL:
- switch (val) {
- case CRB_LOC_CTRL_RESET_ESTABLISHMENT_BIT:
- /* not loc 3 or 4 */
- break;
- case CRB_LOC_CTRL_RELINQUISH:
- ARRAY_FIELD_DP32(s->regs, CRB_LOC_STATE,
- locAssigned, 0);
- ARRAY_FIELD_DP32(s->regs, CRB_LOC_STS,
- Granted, 0);
- break;
- case CRB_LOC_CTRL_REQUEST_ACCESS:
- ARRAY_FIELD_DP32(s->regs, CRB_LOC_STS,
- Granted, 1);
- ARRAY_FIELD_DP32(s->regs, CRB_LOC_STS,
- beenSeized, 0);
- ARRAY_FIELD_DP32(s->regs, CRB_LOC_STATE,
- locAssigned, 1);
- break;
- }
- break;
- }
-}
-
-static const MemoryRegionOps tpm_crb_memory_ops = {
- .read = tpm_crb_mmio_read,
- .write = tpm_crb_mmio_write,
- .endianness = DEVICE_LITTLE_ENDIAN,
- .valid = {
- .min_access_size = 1,
- .max_access_size = 4,
- },
-};
-
-static void tpm_crb_request_completed(TPMIf *ti, int ret)
+static void tpm_crb_none_request_completed(TPMIf *ti, int ret)
{
CRBState *s = CRB(ti);
- s->regs[R_CRB_CTRL_START] &= ~CRB_START_INVOKE;
- if (ret != 0) {
- ARRAY_FIELD_DP32(s->regs, CRB_CTRL_STS,
- tpmSts, 1); /* fatal error */
- }
- memory_region_set_dirty(&s->cmdmem, 0, CRB_CTRL_CMD_SIZE);
+ tpm_crb_request_completed(&s->state, ret);
}
-static enum TPMVersion tpm_crb_get_version(TPMIf *ti)
+static enum TPMVersion tpm_crb_none_get_version(TPMIf *ti)
{
CRBState *s = CRB(ti);
- return tpm_backend_get_tpm_version(s->tpmbe);
+ return tpm_crb_get_version(&s->state);
}
-static int tpm_crb_pre_save(void *opaque)
+static int tpm_crb_none_pre_save(void *opaque)
{
CRBState *s = opaque;
- tpm_backend_finish_sync(s->tpmbe);
-
- return 0;
+ return tpm_crb_pre_save(&s->state);
}
-static const VMStateDescription vmstate_tpm_crb = {
+static const VMStateDescription vmstate_tpm_crb_none = {
.name = "tpm-crb",
- .pre_save = tpm_crb_pre_save,
+ .pre_save = tpm_crb_none_pre_save,
.fields = (VMStateField[]) {
- VMSTATE_UINT32_ARRAY(regs, CRBState, TPM_CRB_R_MAX),
+ VMSTATE_UINT32_ARRAY(state.regs, CRBState, TPM_CRB_R_MAX),
VMSTATE_END_OF_LIST(),
}
};
-static Property tpm_crb_properties[] = {
- DEFINE_PROP_TPMBE("tpmdev", CRBState, tpmbe),
- DEFINE_PROP_BOOL("ppi", CRBState, ppi_enabled, true),
+static Property tpm_crb_none_properties[] = {
+ DEFINE_PROP_TPMBE("tpmdev", CRBState, state.tpmbe),
+ DEFINE_PROP_BOOL("ppi", CRBState, state.ppi_enabled, true),
DEFINE_PROP_END_OF_LIST(),
};
-static void tpm_crb_reset(void *dev)
+static void tpm_crb_none_reset(void *dev)
{
CRBState *s = CRB(dev);
- if (s->ppi_enabled) {
- tpm_ppi_reset(&s->ppi);
- }
- tpm_backend_reset(s->tpmbe);
-
- memset(s->regs, 0, sizeof(s->regs));
-
- ARRAY_FIELD_DP32(s->regs, CRB_LOC_STATE,
- tpmRegValidSts, 1);
- ARRAY_FIELD_DP32(s->regs, CRB_CTRL_STS,
- tpmIdle, 1);
- ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
- InterfaceType, CRB_INTF_TYPE_CRB_ACTIVE);
- ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
- InterfaceVersion, CRB_INTF_VERSION_CRB);
- ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
- CapLocality, CRB_INTF_CAP_LOCALITY_0_ONLY);
- ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
- CapCRBIdleBypass, CRB_INTF_CAP_IDLE_FAST);
- ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
- CapDataXferSizeSupport, CRB_INTF_CAP_XFER_SIZE_64);
- ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
- CapFIFO, CRB_INTF_CAP_FIFO_NOT_SUPPORTED);
- ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
- CapCRB, CRB_INTF_CAP_CRB_SUPPORTED);
- ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
- InterfaceSelector, CRB_INTF_IF_SELECTOR_CRB);
- ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
- RID, 0b0000);
- ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID2,
- VID, PCI_VENDOR_ID_IBM);
-
- s->regs[R_CRB_CTRL_CMD_SIZE] = CRB_CTRL_CMD_SIZE;
- s->regs[R_CRB_CTRL_CMD_LADDR] = TPM_CRB_ADDR_BASE + A_CRB_DATA_BUFFER;
- s->regs[R_CRB_CTRL_RSP_SIZE] = CRB_CTRL_CMD_SIZE;
- s->regs[R_CRB_CTRL_RSP_ADDR] = TPM_CRB_ADDR_BASE + A_CRB_DATA_BUFFER;
-
- s->be_buffer_size = MIN(tpm_backend_get_buffer_size(s->tpmbe),
- CRB_CTRL_CMD_SIZE);
-
- if (tpm_backend_startup_tpm(s->tpmbe, s->be_buffer_size) < 0) {
- exit(1);
- }
+ return tpm_crb_reset(&s->state, TPM_CRB_ADDR_BASE);
}
-static void tpm_crb_realize(DeviceState *dev, Error **errp)
+static void tpm_crb_none_realize(DeviceState *dev, Error **errp)
{
CRBState *s = CRB(dev);
@@ -289,64 +94,61 @@ static void tpm_crb_realize(DeviceState *dev, Error **errp)
error_setg(errp, "at most one TPM device is permitted");
return;
}
- if (!s->tpmbe) {
+ if (!s->state.tpmbe) {
error_setg(errp, "'tpmdev' property is required");
return;
}
- memory_region_init_io(&s->mmio, OBJECT(s), &tpm_crb_memory_ops, s,
- "tpm-crb-mmio", sizeof(s->regs));
- memory_region_init_ram(&s->cmdmem, OBJECT(s),
- "tpm-crb-cmd", CRB_CTRL_CMD_SIZE, errp);
+ tpm_crb_init_memory(OBJECT(s), &s->state, errp);
memory_region_add_subregion(get_system_memory(),
- TPM_CRB_ADDR_BASE, &s->mmio);
+ TPM_CRB_ADDR_BASE, &s->state.mmio);
memory_region_add_subregion(get_system_memory(),
- TPM_CRB_ADDR_BASE + sizeof(s->regs), &s->cmdmem);
+ TPM_CRB_ADDR_BASE + sizeof(s->state.regs), &s->state.cmdmem);
- if (s->ppi_enabled) {
- tpm_ppi_init(&s->ppi, get_system_memory(),
+ if (s->state.ppi_enabled) {
+ tpm_ppi_init(&s->state.ppi, get_system_memory(),
TPM_PPI_ADDR_BASE, OBJECT(s));
}
if (xen_enabled()) {
- tpm_crb_reset(dev);
+ tpm_crb_none_reset(dev);
} else {
- qemu_register_reset(tpm_crb_reset, dev);
+ qemu_register_reset(tpm_crb_none_reset, dev);
}
}
-static void tpm_crb_class_init(ObjectClass *klass, void *data)
+static void tpm_crb_none_class_init(ObjectClass *klass, void *data)
{
DeviceClass *dc = DEVICE_CLASS(klass);
TPMIfClass *tc = TPM_IF_CLASS(klass);
- dc->realize = tpm_crb_realize;
- device_class_set_props(dc, tpm_crb_properties);
- dc->vmsd = &vmstate_tpm_crb;
+ dc->realize = tpm_crb_none_realize;
+ device_class_set_props(dc, tpm_crb_none_properties);
+ dc->vmsd = &vmstate_tpm_crb_none;
dc->user_creatable = true;
tc->model = TPM_MODEL_TPM_CRB;
- tc->get_version = tpm_crb_get_version;
- tc->request_completed = tpm_crb_request_completed;
+ tc->get_version = tpm_crb_none_get_version;
+ tc->request_completed = tpm_crb_none_request_completed;
set_bit(DEVICE_CATEGORY_MISC, dc->categories);
}
-static const TypeInfo tpm_crb_info = {
+static const TypeInfo tpm_crb_none_info = {
.name = TYPE_TPM_CRB,
/* could be TYPE_SYS_BUS_DEVICE (or LPC etc) */
.parent = TYPE_DEVICE,
.instance_size = sizeof(CRBState),
- .class_init = tpm_crb_class_init,
+ .class_init = tpm_crb_none_class_init,
.interfaces = (InterfaceInfo[]) {
{ TYPE_TPM_IF },
{ }
}
};
-static void tpm_crb_register(void)
+static void tpm_crb_none_register(void)
{
- type_register_static(&tpm_crb_info);
+ type_register_static(&tpm_crb_none_info);
}
-type_init(tpm_crb_register)
+type_init(tpm_crb_none_register)
diff --git a/hw/tpm/tpm_crb_common.c b/hw/tpm/tpm_crb_common.c
new file mode 100644
index 0000000000..4c173affb6
--- /dev/null
+++ b/hw/tpm/tpm_crb_common.c
@@ -0,0 +1,218 @@
+/*
+ * tpm_crb.c - QEMU's TPM CRB interface emulator
+ *
+ * Copyright (c) 2018 Red Hat, Inc.
+ *
+ * Authors:
+ * Marc-André Lureau <marcandre.lureau@redhat.com>
+ *
+ * This work is licensed under the terms of the GNU GPL, version 2 or later.
+ * See the COPYING file in the top-level directory.
+ *
+ * tpm_crb is a device for TPM 2.0 Command Response Buffer (CRB) Interface
+ * as defined in TCG PC Client Platform TPM Profile (PTP) Specification
+ * Family “2.0” Level 00 Revision 01.03 v22
+ */
+
+#include "qemu/osdep.h"
+
+#include "qemu/module.h"
+#include "qapi/error.h"
+#include "exec/address-spaces.h"
+#include "hw/qdev-properties.h"
+#include "hw/pci/pci_ids.h"
+#include "hw/acpi/tpm.h"
+#include "migration/vmstate.h"
+#include "sysemu/tpm_backend.h"
+#include "sysemu/tpm_util.h"
+#include "sysemu/reset.h"
+#include "sysemu/xen.h"
+#include "tpm_prop.h"
+#include "tpm_ppi.h"
+#include "trace.h"
+#include "qom/object.h"
+#include "tpm_crb.h"
+
+static uint64_t tpm_crb_mmio_read(void *opaque, hwaddr addr,
+ unsigned size)
+{
+ TPMCRBState *s = opaque;
+ void *regs = (void *)&s->regs + (addr & ~3);
+ unsigned offset = addr & 3;
+ uint32_t val = *(uint32_t *)regs >> (8 * offset);
+
+ switch (addr) {
+ case A_CRB_LOC_STATE:
+ val |= !tpm_backend_get_tpm_established_flag(s->tpmbe);
+ break;
+ }
+
+ trace_tpm_crb_mmio_read(addr, size, val);
+
+ return val;
+}
+
+static uint8_t tpm_crb_get_active_locty(TPMCRBState *s)
+{
+ if (!ARRAY_FIELD_EX32(s->regs, CRB_LOC_STATE, locAssigned)) {
+ return TPM_CRB_NO_LOCALITY;
+ }
+ return ARRAY_FIELD_EX32(s->regs, CRB_LOC_STATE, activeLocality);
+}
+
+static void tpm_crb_mmio_write(void *opaque, hwaddr addr,
+ uint64_t val, unsigned size)
+{
+ TPMCRBState *s = opaque;
+ uint8_t locty = addr >> 12;
+
+ trace_tpm_crb_mmio_write(addr, size, val);
+
+ switch (addr) {
+ case A_CRB_CTRL_REQ:
+ switch (val) {
+ case CRB_CTRL_REQ_CMD_READY:
+ ARRAY_FIELD_DP32(s->regs, CRB_CTRL_STS,
+ tpmIdle, 0);
+ break;
+ case CRB_CTRL_REQ_GO_IDLE:
+ ARRAY_FIELD_DP32(s->regs, CRB_CTRL_STS,
+ tpmIdle, 1);
+ break;
+ }
+ break;
+ case A_CRB_CTRL_CANCEL:
+ if (val == CRB_CANCEL_INVOKE &&
+ s->regs[R_CRB_CTRL_START] & CRB_START_INVOKE) {
+ tpm_backend_cancel_cmd(s->tpmbe);
+ }
+ break;
+ case A_CRB_CTRL_START:
+ if (val == CRB_START_INVOKE &&
+ !(s->regs[R_CRB_CTRL_START] & CRB_START_INVOKE) &&
+ tpm_crb_get_active_locty(s) == locty) {
+ void *mem = memory_region_get_ram_ptr(&s->cmdmem);
+
+ s->regs[R_CRB_CTRL_START] |= CRB_START_INVOKE;
+ s->cmd = (TPMBackendCmd) {
+ .in = mem,
+ .in_len = MIN(tpm_cmd_get_size(mem), s->be_buffer_size),
+ .out = mem,
+ .out_len = s->be_buffer_size,
+ };
+
+ tpm_backend_deliver_request(s->tpmbe, &s->cmd);
+ }
+ break;
+ case A_CRB_LOC_CTRL:
+ switch (val) {
+ case CRB_LOC_CTRL_RESET_ESTABLISHMENT_BIT:
+ /* not loc 3 or 4 */
+ break;
+ case CRB_LOC_CTRL_RELINQUISH:
+ ARRAY_FIELD_DP32(s->regs, CRB_LOC_STATE,
+ locAssigned, 0);
+ ARRAY_FIELD_DP32(s->regs, CRB_LOC_STS,
+ Granted, 0);
+ break;
+ case CRB_LOC_CTRL_REQUEST_ACCESS:
+ ARRAY_FIELD_DP32(s->regs, CRB_LOC_STS,
+ Granted, 1);
+ ARRAY_FIELD_DP32(s->regs, CRB_LOC_STS,
+ beenSeized, 0);
+ ARRAY_FIELD_DP32(s->regs, CRB_LOC_STATE,
+ locAssigned, 1);
+ break;
+ }
+ break;
+ }
+}
+
+const MemoryRegionOps tpm_crb_memory_ops = {
+ .read = tpm_crb_mmio_read,
+ .write = tpm_crb_mmio_write,
+ .endianness = DEVICE_LITTLE_ENDIAN,
+ .valid = {
+ .min_access_size = 1,
+ .max_access_size = 4,
+ },
+};
+
+void tpm_crb_request_completed(TPMCRBState *s, int ret)
+{
+ s->regs[R_CRB_CTRL_START] &= ~CRB_START_INVOKE;
+ if (ret != 0) {
+ ARRAY_FIELD_DP32(s->regs, CRB_CTRL_STS,
+ tpmSts, 1); /* fatal error */
+ }
+ memory_region_set_dirty(&s->cmdmem, 0, CRB_CTRL_CMD_SIZE);
+}
+
+enum TPMVersion tpm_crb_get_version(TPMCRBState *s)
+{
+ return tpm_backend_get_tpm_version(s->tpmbe);
+}
+
+int tpm_crb_pre_save(TPMCRBState *s)
+{
+ tpm_backend_finish_sync(s->tpmbe);
+
+ return 0;
+}
+
+void tpm_crb_reset(TPMCRBState *s, uint64_t baseaddr)
+{
+ if (s->ppi_enabled) {
+ tpm_ppi_reset(&s->ppi);
+ }
+ tpm_backend_reset(s->tpmbe);
+
+ memset(s->regs, 0, sizeof(s->regs));
+
+ ARRAY_FIELD_DP32(s->regs, CRB_LOC_STATE,
+ tpmRegValidSts, 1);
+ ARRAY_FIELD_DP32(s->regs, CRB_CTRL_STS,
+ tpmIdle, 1);
+ ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
+ InterfaceType, CRB_INTF_TYPE_CRB_ACTIVE);
+ ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
+ InterfaceVersion, CRB_INTF_VERSION_CRB);
+ ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
+ CapLocality, CRB_INTF_CAP_LOCALITY_0_ONLY);
+ ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
+ CapCRBIdleBypass, CRB_INTF_CAP_IDLE_FAST);
+ ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
+ CapDataXferSizeSupport, CRB_INTF_CAP_XFER_SIZE_64);
+ ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
+ CapFIFO, CRB_INTF_CAP_FIFO_NOT_SUPPORTED);
+ ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
+ CapCRB, CRB_INTF_CAP_CRB_SUPPORTED);
+ ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
+ InterfaceSelector, CRB_INTF_IF_SELECTOR_CRB);
+ ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID,
+ RID, 0b0000);
+ ARRAY_FIELD_DP32(s->regs, CRB_INTF_ID2,
+ VID, PCI_VENDOR_ID_IBM);
+
+ baseaddr += A_CRB_DATA_BUFFER;
+ s->regs[R_CRB_CTRL_CMD_SIZE] = CRB_CTRL_CMD_SIZE;
+ s->regs[R_CRB_CTRL_CMD_LADDR] = (uint32_t)baseaddr;
+ s->regs[R_CRB_CTRL_CMD_HADDR] = (uint32_t)(baseaddr >> 32);
+ s->regs[R_CRB_CTRL_RSP_SIZE] = CRB_CTRL_CMD_SIZE;
+ s->regs[R_CRB_CTRL_RSP_ADDR] = (uint32_t)baseaddr;
+
+ s->be_buffer_size = MIN(tpm_backend_get_buffer_size(s->tpmbe),
+ CRB_CTRL_CMD_SIZE);
+
+ if (tpm_backend_startup_tpm(s->tpmbe, s->be_buffer_size) < 0) {
+ exit(1);
+ }
+}
+
+void tpm_crb_init_memory(Object *obj, TPMCRBState *s, Error **errp)
+{
+ memory_region_init_io(&s->mmio, obj, &tpm_crb_memory_ops, s,
+ "tpm-crb-mmio", sizeof(s->regs));
+ memory_region_init_ram(&s->cmdmem, obj,
+ "tpm-crb-cmd", CRB_CTRL_CMD_SIZE, errp);
+}
diff --git a/hw/tpm/meson.build b/hw/tpm/meson.build
index 6968e60b3f..cb8204d5bc 100644
--- a/hw/tpm/meson.build
+++ b/hw/tpm/meson.build
@@ -3,6 +3,7 @@ system_ss.add(when: 'CONFIG_TPM_TIS_ISA', if_true: files('tpm_tis_isa.c'))
system_ss.add(when: 'CONFIG_TPM_TIS_SYSBUS', if_true: files('tpm_tis_sysbus.c'))
system_ss.add(when: 'CONFIG_TPM_TIS_I2C', if_true: files('tpm_tis_i2c.c'))
system_ss.add(when: 'CONFIG_TPM_CRB', if_true: files('tpm_crb.c'))
+system_ss.add(when: 'CONFIG_TPM_CRB', if_true: files('tpm_crb_common.c'))
system_ss.add(when: 'CONFIG_TPM_TIS', if_true: files('tpm_ppi.c'))
system_ss.add(when: 'CONFIG_TPM_CRB', if_true: files('tpm_ppi.c'))
diff --git a/hw/tpm/trace-events b/hw/tpm/trace-events
index fa882dfefe..3ab1bdb97b 100644
--- a/hw/tpm/trace-events
+++ b/hw/tpm/trace-events
@@ -1,6 +1,6 @@
# See docs/devel/tracing.rst for syntax documentation.
-# tpm_crb.c
+# tpm_crb_common.c
tpm_crb_mmio_read(uint64_t addr, unsigned size, uint32_t val) "CRB read 0x%016" PRIx64 " len:%u val: 0x%" PRIx32
tpm_crb_mmio_write(uint64_t addr, unsigned size, uint32_t val) "CRB write 0x%016" PRIx64 " len:%u val: 0x%" PRIx32
--
2.39.2 (Apple Git-143)
next prev parent reply other threads:[~2023-07-14 7:10 UTC|newest]
Thread overview: 52+ messages / expand[flat|nested] mbox.gz Atom feed top
2023-07-14 7:09 [PATCH v2 00/11] tpm: introduce TPM CRB SysBus device Joelle van Dyne
2023-07-14 7:09 ` Joelle van Dyne [this message]
2023-07-14 7:09 ` [PATCH v2 02/11] tpm_crb: CTRL_RSP_ADDR is 64-bits wide Joelle van Dyne
2023-07-14 7:09 ` [PATCH v2 03/11] tpm_ppi: refactor memory space initialization Joelle van Dyne
2023-07-14 7:09 ` [PATCH v2 04/11] tpm_crb: use a single read-as-mem/write-as-mmio mapping Joelle van Dyne
2023-07-14 12:03 ` Stefan Berger
2023-07-14 7:09 ` [PATCH v2 05/11] tpm_crb: use the ISA bus Joelle van Dyne
2023-07-17 13:46 ` Igor Mammedov
2023-07-18 14:16 ` Stefan Berger
2023-08-01 1:46 ` Joelle van Dyne
2023-10-17 14:24 ` Alexander Graf
2023-07-14 7:09 ` [PATCH v2 06/11] tpm_crb: move ACPI table building to device interface Joelle van Dyne
2023-07-14 17:21 ` Stefan Berger
2023-07-17 13:42 ` Igor Mammedov
2023-08-01 3:02 ` Joelle van Dyne
2023-08-01 19:38 ` Stefan Berger
2023-08-07 10:20 ` Igor Mammedov
2023-07-14 7:09 ` [PATCH v2 07/11] hw/arm/virt: add plug handler for TPM on SysBus Joelle van Dyne
2023-07-14 12:11 ` Stefan Berger
2023-07-14 17:09 ` Joelle van Dyne
2023-07-17 14:00 ` Igor Mammedov
2023-07-14 7:09 ` [PATCH v2 08/11] hw/loongarch/virt: " Joelle van Dyne
2023-07-20 17:57 ` Stefan Berger
2023-08-03 11:35 ` Stefan Berger
2023-07-14 7:09 ` [PATCH v2 09/11] tpm_tis_sysbus: move DSDT AML generation to device Joelle van Dyne
2023-07-14 16:19 ` Stefan Berger
2023-07-14 17:29 ` Joelle van Dyne
2023-07-14 17:37 ` Stefan Berger
2023-07-14 17:39 ` Joelle van Dyne
2023-07-14 17:43 ` Stefan Berger
2023-07-14 17:46 ` Joelle van Dyne
2023-07-14 18:01 ` Stefan Berger
2023-07-14 18:15 ` Joelle van Dyne
2023-07-17 14:06 ` Igor Mammedov
2023-07-14 7:09 ` [PATCH v2 10/11] tpm_crb_sysbus: introduce TPM CRB SysBus device Joelle van Dyne
2023-07-14 14:27 ` Stefan Berger
2023-07-14 17:20 ` Joelle van Dyne
2023-07-14 17:52 ` Stefan Berger
2023-07-17 14:23 ` Igor Mammedov
2023-10-29 2:21 ` Joelle van Dyne
2023-07-14 7:09 ` [PATCH v2 11/11] tpm_crb: support restoring older vmstate Joelle van Dyne
2023-07-14 14:05 ` Stefan Berger
2023-07-14 14:51 ` Stefan Berger
2023-07-14 17:04 ` Joelle van Dyne
2023-07-14 18:22 ` Stefan Berger
2023-07-14 18:41 ` Stefan Berger
2023-07-14 18:49 ` Joelle van Dyne
2023-07-14 19:12 ` Stefan Berger
2023-07-14 19:44 ` Joelle van Dyne
2023-07-14 19:56 ` Stefan Berger
2023-07-17 14:40 ` Peter Maydell
2023-07-17 14:33 ` Igor Mammedov
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20230714070931.23476-2-j@getutm.app \
--to=j@getutm.app \
--cc=qemu-devel@nongnu.org \
--cc=stefanb@linux.ibm.com \
--cc=stefanb@linux.vnet.ibm.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.