From nobody Thu May 16 06:32:47 2024 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=pass(p=reject dis=none) header.from=linux.ibm.com ARC-Seal: i=1; a=rsa-sha256; t=1671127410; cv=none; d=zohomail.com; s=zohoarc; b=fQuKEeJHV5z4I+oe1cQYdAyRyjd+cf2ToyCi0wNW3z4h4z9BSqPeS2mM4aUfgz+MYTHTMm3q2wmyBQpJ8zcgBvmM1DhISuusLrbYRtZnLSza3zAwYIBVGKK6dqIxZBQYQA20oJLOaRSjfx1mcK69yoQT/BN+o2H2zP638EN8hOg= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1671127410; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Post:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:References:Sender:Subject:To; bh=12L1pASwqTFXDrs8A/uM0W+tdTpOCev9fz+ELuWxkMY=; b=Oju/MU2MSjwAFm8z+L+O+4F5nxRUITwz70MIZiJGwcOWheJ3l5gD91GEstD28C9kK8r5qUuQRjltLK2PvHTTuC93FiO7aqxr5RAdwp5F+9Shg/8h2NDUdtzpd8bOJskIX6GSuzgIzpln4CcT/lkVVmw4I1B1I8gUY/Cz27G1z3I= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=pass header.from= (p=reject dis=none) Return-Path: Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 1671127410879217.1104560308653; Thu, 15 Dec 2022 10:03:30 -0800 (PST) Received: from localhost ([::1] helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1p5sZN-0001zx-78; Thu, 15 Dec 2022 13:02:57 -0500 Received: from eggs.gnu.org ([2001:470:142:3::10]) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1p5sZH-0001wn-KK for qemu-devel@nongnu.org; Thu, 15 Dec 2022 13:02:51 -0500 Received: from mx0a-001b2d01.pphosted.com ([148.163.156.1]) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1p5sZF-0000Ur-6G for qemu-devel@nongnu.org; Thu, 15 Dec 2022 13:02:51 -0500 Received: from pps.filterd (m0098409.ppops.net [127.0.0.1]) by mx0a-001b2d01.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 2BFHl6h2022863 for ; Thu, 15 Dec 2022 18:02:47 GMT Received: from pps.reinject (localhost [127.0.0.1]) by mx0a-001b2d01.pphosted.com (PPS) with ESMTPS id 3mg7b29wmn-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT) for ; Thu, 15 Dec 2022 18:02:46 +0000 Received: from m0098409.ppops.net (m0098409.ppops.net [127.0.0.1]) by pps.reinject (8.17.1.5/8.17.1.5) with ESMTP id 2BFHHXSk001455 for ; Thu, 15 Dec 2022 18:02:46 GMT Received: from ppma04wdc.us.ibm.com (1a.90.2fa9.ip4.static.sl-reverse.com [169.47.144.26]) by mx0a-001b2d01.pphosted.com (PPS) with ESMTPS id 3mg7b29wkh-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Thu, 15 Dec 2022 18:02:46 +0000 Received: from pps.filterd (ppma04wdc.us.ibm.com [127.0.0.1]) by ppma04wdc.us.ibm.com (8.17.1.19/8.17.1.19) with ESMTP id 2BFGqRYg017876; Thu, 15 Dec 2022 18:02:44 GMT Received: from smtprelay04.wdc07v.mail.ibm.com ([9.208.129.114]) by ppma04wdc.us.ibm.com (PPS) with ESMTPS id 3meyqkms98-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Thu, 15 Dec 2022 18:02:44 +0000 Received: from smtpav06.dal12v.mail.ibm.com (smtpav06.dal12v.mail.ibm.com [10.241.53.105]) by smtprelay04.wdc07v.mail.ibm.com (8.14.9/8.14.9/NCO v10.0) with ESMTP id 2BFI2hDi23200494 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK); Thu, 15 Dec 2022 18:02:43 GMT Received: from smtpav06.dal12v.mail.ibm.com (unknown [127.0.0.1]) by IMSVA (Postfix) with ESMTP id 6831E58059; Thu, 15 Dec 2022 18:02:43 +0000 (GMT) Received: from smtpav06.dal12v.mail.ibm.com (unknown [127.0.0.1]) by IMSVA (Postfix) with ESMTP id 93B9158043; Thu, 15 Dec 2022 18:02:42 +0000 (GMT) Received: from lingrow.int.hansenpartnership.com (unknown [9.163.9.130]) by smtpav06.dal12v.mail.ibm.com (Postfix) with ESMTP; Thu, 15 Dec 2022 18:02:42 +0000 (GMT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ibm.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding; s=pp1; bh=12L1pASwqTFXDrs8A/uM0W+tdTpOCev9fz+ELuWxkMY=; b=Msy4A/v4fWCmfAStsSJK2v2okyM4ZvWvH9x7XSMJljw8oHVqdJvNC9ExZYjkc/OqxrQV Twb3+0wSI1Z/EpAXJoRT6YsEn8FIh7gNyCIY5Kk9XTeJcYhSGWS1aHRl69DolMM75N1Q HtVPEgECw6OQiQjt7Z89F0VVVqs5fv4wbYmzjJAE3MaHcbirH7ncy1eKkiGhsCo6b1nD MqdORZl6ExnX32y2ds7Rc+XCBLF+nELax1RtnCH7jRigIbul2NiQVLNFdNXIMbGLI4Sf JMd93DsSua915IG4lHE3pJqT9OjDEpRxITJ3yLjhtgZJoJo2D26LlGHVpqEkET7g0lKq bQ== From: James Bottomley To: qemu-devel@nongnu.org Cc: Stefan Berger , =?UTF-8?q?Daniel=20P=20=2E=20Berrang=C3=A9?= , Markus Armbruster Subject: [PATCH 1/2] tpm: convert tpmdev options processing to new visitor format Date: Thu, 15 Dec 2022 13:01:24 -0500 Message-Id: <20221215180125.24632-2-jejb@linux.ibm.com> X-Mailer: git-send-email 2.35.3 In-Reply-To: <20221215180125.24632-1-jejb@linux.ibm.com> References: <20221215180125.24632-1-jejb@linux.ibm.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-TM-AS-GCONF: 00 X-Proofpoint-ORIG-GUID: wQKJWHkeTwtIvBL7nlMh8uYNSE4Pl4aw X-Proofpoint-GUID: 118agujBfwtr7T_oIoWpue3a6KcHWJ1u X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.205,Aquarius:18.0.923,Hydra:6.0.545,FMLib:17.11.122.1 definitions=2022-12-15_10,2022-12-15_02,2022-06-22_01 X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0 adultscore=0 clxscore=1015 priorityscore=1501 malwarescore=0 lowpriorityscore=0 bulkscore=0 mlxlogscore=999 impostorscore=0 spamscore=0 suspectscore=0 mlxscore=0 phishscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.12.0-2212070000 definitions=main-2212150145 Received-SPF: pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) client-ip=209.51.188.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Received-SPF: pass client-ip=148.163.156.1; envelope-from=jejb@linux.ibm.com; helo=mx0a-001b2d01.pphosted.com X-Spam_score_int: -19 X-Spam_score: -2.0 X-Spam_bar: -- X-Spam_report: (-2.0 / 5.0 requ) BAYES_00=-1.9, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_EF=-0.1, RCVD_IN_MSPIKE_H2=-0.001, SPF_HELO_NONE=0.001, SPF_PASS=-0.001 autolearn=ham autolearn_force=no X-Spam_action: no action X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: qemu-devel-bounces+importer=patchew.org@nongnu.org X-ZohoMail-DKIM: pass (identity @ibm.com) X-ZM-MESSAGEID: 1671127413029100008 Content-Type: text/plain; charset="utf-8" From: James Bottomley Instead of processing the tpmdev options using the old qemu options, convert to the new visitor format which also allows the passing of json on the command line. Signed-off-by: James Bottomley --- backends/tpm/tpm_emulator.c | 35 ++++++-------- backends/tpm/tpm_passthrough.c | 37 +++++---------- include/sysemu/tpm.h | 2 +- include/sysemu/tpm_backend.h | 2 +- monitor/hmp-cmds.c | 4 +- qapi/tpm.json | 26 ++--------- softmmu/tpm.c | 84 +++++++++++++++------------------- softmmu/vl.c | 4 +- 8 files changed, 71 insertions(+), 123 deletions(-) diff --git a/backends/tpm/tpm_emulator.c b/backends/tpm/tpm_emulator.c index 49cc3d749d..82988a2986 100644 --- a/backends/tpm/tpm_emulator.c +++ b/backends/tpm/tpm_emulator.c @@ -69,7 +69,7 @@ typedef struct TPMBlobBuffers { struct TPMEmulator { TPMBackend parent; =20 - TPMEmulatorOptions *options; + TpmTypeOptions *options; CharBackend ctrl_chr; QIOChannel *data_ioc; TPMVersion tpm_version; @@ -584,33 +584,28 @@ err_exit: return -1; } =20 -static int tpm_emulator_handle_device_opts(TPMEmulator *tpm_emu, QemuOpts = *opts) +static int tpm_emulator_handle_device_opts(TPMEmulator *tpm_emu, TpmTypeOp= tions *opts) { - const char *value; Error *err =3D NULL; Chardev *dev; =20 - value =3D qemu_opt_get(opts, "chardev"); - if (!value) { - error_report("tpm-emulator: parameter 'chardev' is missing"); - goto err; - } + tpm_emu->options =3D opts; + tpm_emu->data_ioc =3D NULL; =20 - dev =3D qemu_chr_find(value); + dev =3D qemu_chr_find(opts->u.emulator.chardev); if (!dev) { - error_report("tpm-emulator: tpm chardev '%s' not found", value); + error_report("tpm-emulator: tpm chardev '%s' not found", + opts->u.emulator.chardev); goto err; } =20 if (!qemu_chr_fe_init(&tpm_emu->ctrl_chr, dev, &err)) { error_prepend(&err, "tpm-emulator: No valid chardev found at '%s':= ", - value); + opts->u.emulator.chardev); error_report_err(err); goto err; } =20 - tpm_emu->options->chardev =3D g_strdup(value); - if (tpm_emulator_prepare_data_fd(tpm_emu) < 0) { goto err; } @@ -621,7 +616,7 @@ static int tpm_emulator_handle_device_opts(TPMEmulator = *tpm_emu, QemuOpts *opts) if (tpm_util_test_tpmdev(QIO_CHANNEL_SOCKET(tpm_emu->data_ioc)->fd, &tpm_emu->tpm_version)) { error_report("'%s' is not emulating TPM device. Error: %s", - tpm_emu->options->chardev, strerror(errno)); + tpm_emu->options->u.emulator.chardev, strerror(errno= )); goto err; } =20 @@ -649,7 +644,7 @@ err: return -1; } =20 -static TPMBackend *tpm_emulator_create(QemuOpts *opts) +static TPMBackend *tpm_emulator_create(TpmTypeOptions *opts) { TPMBackend *tb =3D TPM_BACKEND(object_new(TYPE_TPM_EMULATOR)); =20 @@ -664,10 +659,9 @@ static TPMBackend *tpm_emulator_create(QemuOpts *opts) static TpmTypeOptions *tpm_emulator_get_tpm_options(TPMBackend *tb) { TPMEmulator *tpm_emu =3D TPM_EMULATOR(tb); - TpmTypeOptions *options =3D g_new0(TpmTypeOptions, 1); + TpmTypeOptions *options; =20 - options->type =3D TPM_TYPE_EMULATOR; - options->u.emulator.data =3D QAPI_CLONE(TPMEmulatorOptions, tpm_emu->o= ptions); + options =3D QAPI_CLONE(TpmTypeOptions, tpm_emu->options); =20 return options; } @@ -972,7 +966,6 @@ static void tpm_emulator_inst_init(Object *obj) =20 trace_tpm_emulator_inst_init(); =20 - tpm_emu->options =3D g_new0(TPMEmulatorOptions, 1); tpm_emu->cur_locty_number =3D ~0; qemu_mutex_init(&tpm_emu->mutex); tpm_emu->vmstate =3D @@ -990,7 +983,7 @@ static void tpm_emulator_shutdown(TPMEmulator *tpm_emu) { ptm_res res; =20 - if (!tpm_emu->options->chardev) { + if (!tpm_emu->data_ioc) { /* was never properly initialized */ return; } @@ -1015,7 +1008,7 @@ static void tpm_emulator_inst_finalize(Object *obj) =20 qemu_chr_fe_deinit(&tpm_emu->ctrl_chr, false); =20 - qapi_free_TPMEmulatorOptions(tpm_emu->options); + qapi_free_TpmTypeOptions(tpm_emu->options); =20 if (tpm_emu->migration_blocker) { migrate_del_blocker(tpm_emu->migration_blocker); diff --git a/backends/tpm/tpm_passthrough.c b/backends/tpm/tpm_passthrough.c index 5a2f74db1b..2ce39b2167 100644 --- a/backends/tpm/tpm_passthrough.c +++ b/backends/tpm/tpm_passthrough.c @@ -41,7 +41,7 @@ OBJECT_DECLARE_SIMPLE_TYPE(TPMPassthruState, TPM_PASSTHRO= UGH) struct TPMPassthruState { TPMBackend parent; =20 - TPMPassthroughOptions *options; + TpmTypeOptions *options; const char *tpm_dev; int tpm_fd; bool tpm_executing; @@ -214,8 +214,8 @@ static int tpm_passthrough_open_sysfs_cancel(TPMPassthr= uState *tpm_pt) char *dev; char path[PATH_MAX]; =20 - if (tpm_pt->options->cancel_path) { - fd =3D qemu_open_old(tpm_pt->options->cancel_path, O_WRONLY); + if (tpm_pt->options->u.passthrough.cancel_path) { + fd =3D qemu_open_old(tpm_pt->options->u.passthrough.cancel_path, O= _WRONLY); if (fd < 0) { error_report("tpm_passthrough: Could not open TPM cancel path:= %s", strerror(errno)); @@ -245,30 +245,18 @@ static int tpm_passthrough_open_sysfs_cancel(TPMPasst= hruState *tpm_pt) if (fd < 0) { error_report("tpm_passthrough: Could not guess TPM cancel path"); } else { - tpm_pt->options->cancel_path =3D g_strdup(path); + tpm_pt->options->u.passthrough.cancel_path =3D g_strdup(path); } =20 return fd; } =20 static int -tpm_passthrough_handle_device_opts(TPMPassthruState *tpm_pt, QemuOpts *opt= s) +tpm_passthrough_handle_device_opts(TPMPassthruState *tpm_pt, TpmTypeOption= s *opts) { - const char *value; + tpm_pt->options =3D opts; =20 - value =3D qemu_opt_get(opts, "cancel-path"); - if (value) { - tpm_pt->options->cancel_path =3D g_strdup(value); - tpm_pt->options->has_cancel_path =3D true; - } - - value =3D qemu_opt_get(opts, "path"); - if (value) { - tpm_pt->options->has_path =3D true; - tpm_pt->options->path =3D g_strdup(value); - } - - tpm_pt->tpm_dev =3D value ? value : TPM_PASSTHROUGH_DEFAULT_DEVICE; + tpm_pt->tpm_dev =3D opts->u.passthrough.has_path ? opts->u.passthrough= .path : TPM_PASSTHROUGH_DEFAULT_DEVICE; tpm_pt->tpm_fd =3D qemu_open_old(tpm_pt->tpm_dev, O_RDWR); if (tpm_pt->tpm_fd < 0) { error_report("Cannot access TPM device using '%s': %s", @@ -290,11 +278,11 @@ tpm_passthrough_handle_device_opts(TPMPassthruState *= tpm_pt, QemuOpts *opts) return 0; } =20 -static TPMBackend *tpm_passthrough_create(QemuOpts *opts) +static TPMBackend *tpm_passthrough_create(TpmTypeOptions *tto) { Object *obj =3D object_new(TYPE_TPM_PASSTHROUGH); =20 - if (tpm_passthrough_handle_device_opts(TPM_PASSTHROUGH(obj), opts)) { + if (tpm_passthrough_handle_device_opts(TPM_PASSTHROUGH(obj), tto)) { object_unref(obj); return NULL; } @@ -320,9 +308,7 @@ static TpmTypeOptions *tpm_passthrough_get_tpm_options(= TPMBackend *tb) { TpmTypeOptions *options =3D g_new0(TpmTypeOptions, 1); =20 - options->type =3D TPM_TYPE_PASSTHROUGH; - options->u.passthrough.data =3D QAPI_CLONE(TPMPassthroughOptions, - TPM_PASSTHROUGH(tb)->options); + options =3D QAPI_CLONE(TpmTypeOptions, TPM_PASSTHROUGH(tb)->options); =20 return options; } @@ -346,7 +332,6 @@ static void tpm_passthrough_inst_init(Object *obj) { TPMPassthruState *tpm_pt =3D TPM_PASSTHROUGH(obj); =20 - tpm_pt->options =3D g_new0(TPMPassthroughOptions, 1); tpm_pt->tpm_fd =3D -1; tpm_pt->cancel_fd =3D -1; } @@ -363,7 +348,7 @@ static void tpm_passthrough_inst_finalize(Object *obj) if (tpm_pt->cancel_fd >=3D 0) { qemu_close(tpm_pt->cancel_fd); } - qapi_free_TPMPassthroughOptions(tpm_pt->options); + qapi_free_TpmTypeOptions(tpm_pt->options); } =20 static void tpm_passthrough_class_init(ObjectClass *klass, void *data) diff --git a/include/sysemu/tpm.h b/include/sysemu/tpm.h index fb40e30ff6..55a789ce63 100644 --- a/include/sysemu/tpm.h +++ b/include/sysemu/tpm.h @@ -18,7 +18,7 @@ #ifdef CONFIG_TPM =20 int tpm_config_parse(QemuOptsList *opts_list, const char *optarg); -int tpm_init(void); +void tpm_init(void); void tpm_cleanup(void); =20 typedef enum TPMVersion { diff --git a/include/sysemu/tpm_backend.h b/include/sysemu/tpm_backend.h index 8fd3269c11..bcef275688 100644 --- a/include/sysemu/tpm_backend.h +++ b/include/sysemu/tpm_backend.h @@ -57,7 +57,7 @@ struct TPMBackendClass { /* get a descriptive text of the backend to display to the user */ const char *desc; =20 - TPMBackend *(*create)(QemuOpts *opts); + TPMBackend *(*create)(TpmTypeOptions *tto); =20 /* start up the TPM on the backend - optional */ int (*startup_tpm)(TPMBackend *t, size_t buffersize); diff --git a/monitor/hmp-cmds.c b/monitor/hmp-cmds.c index 01b789a79e..e99447ad68 100644 --- a/monitor/hmp-cmds.c +++ b/monitor/hmp-cmds.c @@ -863,7 +863,7 @@ void hmp_info_tpm(Monitor *mon, const QDict *qdict) =20 switch (ti->options->type) { case TPM_TYPE_PASSTHROUGH: - tpo =3D ti->options->u.passthrough.data; + tpo =3D &ti->options->u.passthrough; monitor_printf(mon, "%s%s%s%s", tpo->has_path ? ",path=3D" : "", tpo->has_path ? tpo->path : "", @@ -871,7 +871,7 @@ void hmp_info_tpm(Monitor *mon, const QDict *qdict) tpo->has_cancel_path ? tpo->cancel_path : ""); break; case TPM_TYPE_EMULATOR: - teo =3D ti->options->u.emulator.data; + teo =3D &ti->options->u.emulator; monitor_printf(mon, ",chardev=3D%s", teo->chardev); break; case TPM_TYPE__MAX: diff --git a/qapi/tpm.json b/qapi/tpm.json index 4e2ea9756a..d8cbd5ea0e 100644 --- a/qapi/tpm.json +++ b/qapi/tpm.json @@ -99,39 +99,23 @@ { 'struct': 'TPMEmulatorOptions', 'data': { 'chardev' : 'str' }, 'if': 'CONFIG_TPM' } =20 -## -# @TPMPassthroughOptionsWrapper: -# -# Since: 1.5 -## -{ 'struct': 'TPMPassthroughOptionsWrapper', - 'data': { 'data': 'TPMPassthroughOptions' }, - 'if': 'CONFIG_TPM' } - -## -# @TPMEmulatorOptionsWrapper: -# -# Since: 2.11 -## -{ 'struct': 'TPMEmulatorOptionsWrapper', - 'data': { 'data': 'TPMEmulatorOptions' }, - 'if': 'CONFIG_TPM' } - ## # @TpmTypeOptions: # # A union referencing different TPM backend types' configuration options # +# @id: identifier of the backend # @type: - 'passthrough' The configuration options for the TPM passthrough= type # - 'emulator' The configuration options for TPM emulator backend t= ype # # Since: 1.5 ## { 'union': 'TpmTypeOptions', - 'base': { 'type': 'TpmType' }, + 'base': { 'type': 'TpmType', + 'id': 'str' }, 'discriminator': 'type', - 'data': { 'passthrough' : 'TPMPassthroughOptionsWrapper', - 'emulator': 'TPMEmulatorOptionsWrapper' }, + 'data': { 'passthrough' : 'TPMPassthroughOptions', + 'emulator': 'TPMEmulatorOptions' }, 'if': 'CONFIG_TPM' } =20 ## diff --git a/softmmu/tpm.c b/softmmu/tpm.c index 578563f05a..22ddfbaaed 100644 --- a/softmmu/tpm.c +++ b/softmmu/tpm.c @@ -17,14 +17,26 @@ #include "qapi/error.h" #include "qapi/qapi-commands-tpm.h" #include "qapi/qmp/qerror.h" +#include "qapi/qobject-input-visitor.h" +#include "qapi/qapi-visit-tpm.h" #include "sysemu/tpm_backend.h" #include "sysemu/tpm.h" #include "qemu/config-file.h" #include "qemu/error-report.h" +#include "qemu/help_option.h" =20 static QLIST_HEAD(, TPMBackend) tpm_backends =3D QLIST_HEAD_INITIALIZER(tpm_backends); =20 +typedef struct TpmTypeOptionsQueueEntry { + TpmTypeOptions *tto; + QSIMPLEQ_ENTRY(TpmTypeOptionsQueueEntry) entry; +} TpmTypeOptionsQueueEntry; + +typedef QSIMPLEQ_HEAD(, TpmTypeOptionsQueueEntry) TpmTypeOptionsQueue; + +static TpmTypeOptionsQueue tto_queue =3D QSIMPLEQ_HEAD_INITIALIZER(tto_que= ue); + static const TPMBackendClass * tpm_be_find_by_type(enum TpmType type) { @@ -84,63 +96,36 @@ TPMBackend *qemu_find_tpm_be(const char *id) return NULL; } =20 -static int tpm_init_tpmdev(void *dummy, QemuOpts *opts, Error **errp) +static void tpm_init_tpmdev(TpmTypeOptions *tto) { - /* - * Use of error_report() in a function with an Error ** parameter - * is suspicious. It is okay here. The parameter only exists to - * make the function usable with qemu_opts_foreach(). It is not - * actually used. - */ - const char *value; - const char *id; const TPMBackendClass *be; TPMBackend *drv; - Error *local_err =3D NULL; - int i; =20 if (!QLIST_EMPTY(&tpm_backends)) { error_report("Only one TPM is allowed."); - return 1; + exit(1); } =20 - id =3D qemu_opts_id(opts); - if (id =3D=3D NULL) { + if (!tto->id) { error_report(QERR_MISSING_PARAMETER, "id"); - return 1; + exit(1); } =20 - value =3D qemu_opt_get(opts, "type"); - if (!value) { - error_report(QERR_MISSING_PARAMETER, "type"); - tpm_display_backend_drivers(); - return 1; - } - - i =3D qapi_enum_parse(&TpmType_lookup, value, -1, NULL); - be =3D i >=3D 0 ? tpm_be_find_by_type(i) : NULL; + be =3D tto->type >=3D 0 ? tpm_be_find_by_type(tto->type) : NULL; if (be =3D=3D NULL) { error_report(QERR_INVALID_PARAMETER_VALUE, "type", "a TPM backend type"); tpm_display_backend_drivers(); - return 1; - } - - /* validate backend specific opts */ - if (!qemu_opts_validate(opts, be->opts, &local_err)) { - error_report_err(local_err); - return 1; + exit(1); } =20 - drv =3D be->create(opts); + drv =3D be->create(tto); if (!drv) { - return 1; + exit(1); } =20 - drv->id =3D g_strdup(id); + drv->id =3D g_strdup(tto->id); QLIST_INSERT_HEAD(&tpm_backends, drv, list); - - return 0; } =20 /* @@ -161,14 +146,15 @@ void tpm_cleanup(void) * Initialize the TPM. Process the tpmdev command line options describing = the * TPM backend. */ -int tpm_init(void) +void tpm_init(void) { - if (qemu_opts_foreach(qemu_find_opts("tpmdev"), - tpm_init_tpmdev, NULL, NULL)) { - return -1; - } + while (!QSIMPLEQ_EMPTY(&tto_queue)) { + TpmTypeOptionsQueueEntry *ttoqe =3D QSIMPLEQ_FIRST(&tto_queue); =20 - return 0; + QSIMPLEQ_REMOVE_HEAD(&tto_queue, entry); + tpm_init_tpmdev(ttoqe->tto); + g_free(ttoqe); + } } =20 /* @@ -177,16 +163,18 @@ int tpm_init(void) */ int tpm_config_parse(QemuOptsList *opts_list, const char *optarg) { - QemuOpts *opts; + Visitor *v; + TpmTypeOptionsQueueEntry *toqe; =20 - if (!strcmp(optarg, "help")) { + if (is_help_option(optarg)) { tpm_display_backend_drivers(); return -1; } - opts =3D qemu_opts_parse_noisily(opts_list, optarg, true); - if (!opts) { - return -1; - } + v =3D qobject_input_visitor_new_str(optarg, "type", &error_fatal); + toqe =3D g_new(TpmTypeOptionsQueueEntry, 1); + visit_type_TpmTypeOptions(v, NULL, &toqe->tto, &error_fatal); + visit_free(v); + QSIMPLEQ_INSERT_TAIL(&tto_queue, toqe, entry); return 0; } =20 diff --git a/softmmu/vl.c b/softmmu/vl.c index 5115221efe..773add75cf 100644 --- a/softmmu/vl.c +++ b/softmmu/vl.c @@ -1934,9 +1934,7 @@ static void qemu_create_late_backends(void) =20 object_option_foreach_add(object_create_late); =20 - if (tpm_init() < 0) { - exit(1); - } + tpm_init(); =20 qemu_opts_foreach(qemu_find_opts("mon"), mon_init_func, NULL, &error_fatal); --=20 2.35.3 From nobody Thu May 16 06:32:47 2024 Delivered-To: importer@patchew.org Authentication-Results: mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=pass(p=reject dis=none) header.from=linux.ibm.com ARC-Seal: i=1; a=rsa-sha256; t=1671127410; cv=none; d=zohomail.com; s=zohoarc; b=h2yEcf2ZaEf2fNu1PZI4QA25ODyWe9WTYHPXp8S+yNtQH2u0/+k7/AD/3O7u+D4GKzKQkTWxHNW/UugR8enhfzaoQXdJNxEIYWENN9Sp4uHWAHGELTJt+7q54VVXdFjpZy/DzKYTU7KzG7Ug49qrIWChwW8Og+TW2SkfqTLuLy4= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zohomail.com; s=zohoarc; t=1671127410; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Post:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:References:Sender:Subject:To; bh=zEiXSN6gMyRh6ROguTddLyqrOPXbLHt7InD49x5z1mM=; b=mzwgM3L55XOxWjTNieY14n2LO7BZRUKbHk8Atp1hvHEgYJll7zkbmdwLwWlww+eBP9YzGT1MUwfHPPGHiAg9te/L2vyiHEYxSbHy4Y6xPL66t9FIO2PzrmmF28HfVPikMC5htcnsGlopKwDsqrFEG+yR1E1u4DQ4QJuXX2GHfeU= ARC-Authentication-Results: i=1; mx.zohomail.com; dkim=pass; spf=pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=pass header.from= (p=reject dis=none) Return-Path: Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 167112741084092.44015586625721; Thu, 15 Dec 2022 10:03:30 -0800 (PST) Received: from localhost ([::1] helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1p5sZj-0002KW-PP; Thu, 15 Dec 2022 13:03:19 -0500 Received: from eggs.gnu.org ([2001:470:142:3::10]) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1p5sZd-00029x-Pd for qemu-devel@nongnu.org; Thu, 15 Dec 2022 13:03:14 -0500 Received: from mx0b-001b2d01.pphosted.com ([148.163.158.5] helo=mx0a-001b2d01.pphosted.com) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1p5sZb-0000YU-9u for qemu-devel@nongnu.org; Thu, 15 Dec 2022 13:03:13 -0500 Received: from pps.filterd (m0098419.ppops.net [127.0.0.1]) by mx0b-001b2d01.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 2BFHhei7007111 for ; Thu, 15 Dec 2022 18:03:10 GMT Received: from pps.reinject (localhost [127.0.0.1]) by mx0b-001b2d01.pphosted.com (PPS) with ESMTPS id 3mg87vghde-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT) for ; Thu, 15 Dec 2022 18:03:09 +0000 Received: from m0098419.ppops.net (m0098419.ppops.net [127.0.0.1]) by pps.reinject (8.17.1.5/8.17.1.5) with ESMTP id 2BFHox8i013682 for ; Thu, 15 Dec 2022 18:03:09 GMT Received: from ppma03dal.us.ibm.com (b.bd.3ea9.ip4.static.sl-reverse.com [169.62.189.11]) by mx0b-001b2d01.pphosted.com (PPS) with ESMTPS id 3mg87vghcr-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Thu, 15 Dec 2022 18:03:09 +0000 Received: from pps.filterd (ppma03dal.us.ibm.com [127.0.0.1]) by ppma03dal.us.ibm.com (8.17.1.19/8.17.1.19) with ESMTP id 2BFHHfjB005722; Thu, 15 Dec 2022 18:03:08 GMT Received: from smtprelay01.wdc07v.mail.ibm.com ([9.208.129.119]) by ppma03dal.us.ibm.com (PPS) with ESMTPS id 3meyfe01sk-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Thu, 15 Dec 2022 18:03:07 +0000 Received: from smtpav06.dal12v.mail.ibm.com (smtpav06.dal12v.mail.ibm.com [10.241.53.105]) by smtprelay01.wdc07v.mail.ibm.com (8.14.9/8.14.9/NCO v10.0) with ESMTP id 2BFI36vR36372974 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK); Thu, 15 Dec 2022 18:03:06 GMT Received: from smtpav06.dal12v.mail.ibm.com (unknown [127.0.0.1]) by IMSVA (Postfix) with ESMTP id 296BD58059; Thu, 15 Dec 2022 18:03:06 +0000 (GMT) Received: from smtpav06.dal12v.mail.ibm.com (unknown [127.0.0.1]) by IMSVA (Postfix) with ESMTP id 77BE558055; Thu, 15 Dec 2022 18:03:05 +0000 (GMT) Received: from lingrow.int.hansenpartnership.com (unknown [9.163.9.130]) by smtpav06.dal12v.mail.ibm.com (Postfix) with ESMTP; Thu, 15 Dec 2022 18:03:05 +0000 (GMT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ibm.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : content-transfer-encoding : mime-version; s=pp1; bh=zEiXSN6gMyRh6ROguTddLyqrOPXbLHt7InD49x5z1mM=; b=o8aWmmBVgf54+5f2/sGLX3W4SSpmrahLRT9t3GkvxbB6Sc9uDo9u7t+hXcJcdeJpXuIM BpxNiHLj0KmSZmX36iS7Mzh5CsbzRmQzMVe2WYMsZVAk613HKd/WJun9HvcM+t0bXfF/ 0AZ/5Gznb8fWNmE6PZni7DTTzj9dCBvJeFtVI6YdVKuqW1rUMorlXmG4r13ELDE21Cfc CRRZJ64mUTvjipHQWQFVZ/zGakJEhRrNaeDUDJKMXAHEMCuPS+IC4aFKP7D8qEJ2YNLb nglPgFk1Pypm81PZtR0plflgknqNR/Ye0c/pr0IRFuc3HbGsjo/VFNNeynTYxlEEpgyS hA== From: James Bottomley To: qemu-devel@nongnu.org Cc: Stefan Berger , =?UTF-8?q?Daniel=20P=20=2E=20Berrang=C3=A9?= , Markus Armbruster Subject: [PATCH 2/2] tpm: add backend for mssim Date: Thu, 15 Dec 2022 13:01:25 -0500 Message-Id: <20221215180125.24632-3-jejb@linux.ibm.com> X-Mailer: git-send-email 2.35.3 In-Reply-To: <20221215180125.24632-1-jejb@linux.ibm.com> References: <20221215180125.24632-1-jejb@linux.ibm.com> X-TM-AS-GCONF: 00 X-Proofpoint-GUID: TIzUCddTtefbKOw2d1e7oe0ym5wvHrTi X-Proofpoint-ORIG-GUID: k-xQ8KcZU8EeYL8f-taBVaujFTCaAnFd Content-Transfer-Encoding: quoted-printable X-Proofpoint-UnRewURL: 0 URL was un-rewritten MIME-Version: 1.0 X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.205,Aquarius:18.0.923,Hydra:6.0.545,FMLib:17.11.122.1 definitions=2022-12-15_10,2022-12-15_02,2022-06-22_01 X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0 impostorscore=0 mlxlogscore=999 clxscore=1015 lowpriorityscore=0 spamscore=0 adultscore=0 bulkscore=0 phishscore=0 malwarescore=0 suspectscore=0 priorityscore=1501 mlxscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.12.0-2212070000 definitions=main-2212150145 Received-SPF: pass (zohomail.com: domain of gnu.org designates 209.51.188.17 as permitted sender) client-ip=209.51.188.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Received-SPF: pass client-ip=148.163.158.5; envelope-from=jejb@linux.ibm.com; helo=mx0a-001b2d01.pphosted.com X-Spam_score_int: -19 X-Spam_score: -2.0 X-Spam_bar: -- X-Spam_report: (-2.0 / 5.0 requ) BAYES_00=-1.9, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_EF=-0.1, RCVD_IN_MSPIKE_H2=-0.001, SPF_HELO_NONE=0.001, SPF_PASS=-0.001 autolearn=ham autolearn_force=no X-Spam_action: no action X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: qemu-devel-bounces+importer=patchew.org@nongnu.org X-ZohoMail-DKIM: pass (identity @ibm.com) X-ZM-MESSAGEID: 1671127413889100011 Content-Type: text/plain; charset="utf-8" From: James Bottomley The Microsoft Simulator (mssim) is the reference emulation platform for the TCG TPM 2.0 specification. https://github.com/Microsoft/ms-tpm-20-ref.git It exports a fairly simple network socket baset protocol on two sockets, one for command (default 2321) and one for control (default 2322). This patch adds a simple backend that can speak the mssim protocol over the network. It also allows the host, and two ports to be specified on the qemu command line. The benefits are twofold: firstly it gives us a backend that actually speaks a standard TPM emulation protocol instead of the linux specific TPM driver format of the current emulated TPM backend and secondly, using the microsoft protocol, the end point of the emulator can be anywhere on the network, facilitating the cloud use case where a central TPM service can be used over a control network. The implementation does basic control commands like power off/on, but doesn't implement cancellation or startup. The former because cancellation is pretty much useless on a fast operating TPM emulator and the latter because this emulator is designed to be used with OVMF which itself does TPM startup and I wanted to validate that. To run this, simply download an emulator based on the MS specification (package ibmswtpm2 on openSUSE) and run it, then add these two lines to the qemu command and it will use the emulator. -tpmdev mssim,id=3Dtpm0 \ -device tpm-crb,tpmdev=3Dtpm0 \ to use a remote emulator replace the first line with -tpmdev "{'type':'mssim','id':'tpm0','command':{'type':inet,'host':'rem= ote','port':'2321'}}" tpm-tis also works as the backend. Signed-off-by: James Bottomley --- v2: convert to SocketAddr json and use qio_channel_socket_connect_sync() --- MAINTAINERS | 5 + backends/tpm/Kconfig | 5 + backends/tpm/meson.build | 1 + backends/tpm/tpm_mssim.c | 251 +++++++++++++++++++++++++++++++++++++++ backends/tpm/tpm_mssim.h | 43 +++++++ monitor/hmp-cmds.c | 7 ++ qapi/tpm.json | 25 +++- 7 files changed, 334 insertions(+), 3 deletions(-) create mode 100644 backends/tpm/tpm_mssim.c create mode 100644 backends/tpm/tpm_mssim.h diff --git a/MAINTAINERS b/MAINTAINERS index 6966490c94..a4a3bf9ab4 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -3046,6 +3046,11 @@ F: backends/tpm/ F: tests/qtest/*tpm* T: git https://github.com/stefanberger/qemu-tpm.git tpm-next =20 +MSSIM TPM Backend +M: James Bottomley +S: Maintained +F: backends/tpm/tpm_mssim.* + Checkpatch S: Odd Fixes F: scripts/checkpatch.pl diff --git a/backends/tpm/Kconfig b/backends/tpm/Kconfig index 5d91eb89c2..d6d6fa53e9 100644 --- a/backends/tpm/Kconfig +++ b/backends/tpm/Kconfig @@ -12,3 +12,8 @@ config TPM_EMULATOR bool default y depends on TPM_BACKEND + +config TPM_MSSIM + bool + default y + depends on TPM_BACKEND diff --git a/backends/tpm/meson.build b/backends/tpm/meson.build index 7f2503f84e..c7c3c79125 100644 --- a/backends/tpm/meson.build +++ b/backends/tpm/meson.build @@ -3,4 +3,5 @@ if have_tpm softmmu_ss.add(files('tpm_util.c')) softmmu_ss.add(when: 'CONFIG_TPM_PASSTHROUGH', if_true: files('tpm_passt= hrough.c')) softmmu_ss.add(when: 'CONFIG_TPM_EMULATOR', if_true: files('tpm_emulator= .c')) + softmmu_ss.add(when: 'CONFIG_TPM_MSSIM', if_true: files('tpm_mssim.c')) endif diff --git a/backends/tpm/tpm_mssim.c b/backends/tpm/tpm_mssim.c new file mode 100644 index 0000000000..7c10ce2944 --- /dev/null +++ b/backends/tpm/tpm_mssim.c @@ -0,0 +1,251 @@ +/* + * Emulator TPM driver which connects over the mssim protocol + * SPDX-License-Identifier: GPL-2.0-or-later + * + * Copyright (c) 2022 + * Author: James Bottomley + */ + +#include "qemu/osdep.h" +#include "qemu/error-report.h" +#include "qemu/sockets.h" + +#include "qapi/clone-visitor.h" +#include "qapi/qapi-visit-tpm.h" + +#include "io/channel-socket.h" + +#include "sysemu/tpm_backend.h" +#include "sysemu/tpm_util.h" + +#include "qom/object.h" + +#include "tpm_int.h" +#include "tpm_mssim.h" + +#define ERROR_PREFIX "TPM mssim Emulator: " + +#define TYPE_TPM_MSSIM "tpm-mssim" +OBJECT_DECLARE_SIMPLE_TYPE(TPMmssim, TPM_MSSIM) + +struct TPMmssim { + TPMBackend parent; + + TpmTypeOptions *opts; + + QIOChannelSocket *cmd_qc, *ctrl_qc; +}; + +static int tpm_send_ctrl(TPMmssim *t, uint32_t cmd, Error **errp) +{ + int ret; + + cmd =3D htonl(cmd); + ret =3D qio_channel_write_all(QIO_CHANNEL(t->ctrl_qc), (char *)&cmd, s= izeof(cmd), errp); + if (ret !=3D 0) + return ret; + ret =3D qio_channel_read_all(QIO_CHANNEL(t->ctrl_qc), (char *)&cmd, si= zeof(cmd), errp); + if (ret !=3D 0) + return ret; + if (cmd !=3D 0) { + error_setg(errp, ERROR_PREFIX "Incorrect ACK recieved on control c= hannel 0x%x\n", cmd); + return -1; + } + return 0; +} + +static void tpm_mssim_instance_init(Object *obj) +{ +} + +static void tpm_mssim_instance_finalize(Object *obj) +{ + TPMmssim *t =3D TPM_MSSIM(obj); + + if (t->ctrl_qc) + tpm_send_ctrl(t, TPM_SIGNAL_POWER_OFF, NULL); + + object_unref(OBJECT(t->ctrl_qc)); + object_unref(OBJECT(t->cmd_qc)); +} + +static void tpm_mssim_cancel_cmd(TPMBackend *tb) +{ + return; +} + +static TPMVersion tpm_mssim_get_version(TPMBackend *tb) +{ + return TPM_VERSION_2_0; +} + +static size_t tpm_mssim_get_buffer_size(TPMBackend *tb) +{ + /* TCG standard profile max buffer size */ + return 4096; +} + +static TpmTypeOptions *tpm_mssim_get_opts(TPMBackend *tb) +{ + TPMmssim *t =3D TPM_MSSIM(tb); + TpmTypeOptions *opts; + + opts =3D QAPI_CLONE(TpmTypeOptions, t->opts); + + return opts; +} + +static void tpm_mssim_handle_request(TPMBackend *tb, TPMBackendCmd *cmd, + Error **errp) +{ + TPMmssim *t =3D TPM_MSSIM(tb); + uint32_t header, len; + uint8_t locality =3D cmd->locty; + struct iovec iov[4]; + int ret; + + header =3D htonl(TPM_SEND_COMMAND); + len =3D htonl(cmd->in_len); + + iov[0].iov_base =3D &header; + iov[0].iov_len =3D sizeof(header); + iov[1].iov_base =3D &locality; + iov[1].iov_len =3D sizeof(locality); + iov[2].iov_base =3D &len; + iov[2].iov_len =3D sizeof(len); + iov[3].iov_base =3D (void *)cmd->in; + iov[3].iov_len =3D cmd->in_len; + + ret =3D qio_channel_writev_all(QIO_CHANNEL(t->cmd_qc), iov, 4, errp); + if (ret !=3D 0) + goto fail; + + ret =3D qio_channel_read_all(QIO_CHANNEL(t->cmd_qc), (char *)&len, siz= eof(len), errp); + if (ret !=3D 0) + goto fail; + len =3D ntohl(len); + if (len > cmd->out_len) { + error_setg(errp, "receive size is too large"); + goto fail; + } + ret =3D qio_channel_read_all(QIO_CHANNEL(t->cmd_qc), (char *)cmd->out,= len, errp); + if (ret !=3D 0) + goto fail; + /* ACK packet */ + ret =3D qio_channel_read_all(QIO_CHANNEL(t->cmd_qc), (char *)&header, = sizeof(header), errp); + if (ret !=3D 0) + goto fail; + if (header !=3D 0) { + error_setg(errp, "incorrect ACK received on command channel 0x%x",= len); + goto fail; + } + + return; + + fail: + error_prepend(errp, ERROR_PREFIX); + tpm_util_write_fatal_error_response(cmd->out, cmd->out_len); +} + +static TPMBackend *tpm_mssim_create(TpmTypeOptions *opts) +{ + TPMBackend *be =3D TPM_BACKEND(object_new(TYPE_TPM_MSSIM)); + TPMmssim *t =3D TPM_MSSIM(be); + int sock; + Error *errp =3D NULL; + TPMmssimOptions *mo =3D &opts->u.mssim; + + t->opts =3D opts; + if (!mo->has_command) { + mo->has_command =3D true; + mo->command =3D g_new0(SocketAddress, 1); + mo->command->type =3D SOCKET_ADDRESS_TYPE_INET; + mo->command->u.inet.host =3D g_strdup("localhost"); + mo->command->u.inet.port =3D g_strdup("2321"); + } + if (!mo->has_control) { + mo->has_control =3D true; + mo->control =3D g_new0(SocketAddress, 1); + mo->control->type =3D SOCKET_ADDRESS_TYPE_INET; + mo->control->u.inet.host =3D g_strdup(mo->command->u.inet.host= ); + mo->control->u.inet.port =3D g_strdup("2322"); + } + + t->cmd_qc =3D qio_channel_socket_new(); + t->ctrl_qc =3D qio_channel_socket_new(); + + if (qio_channel_socket_connect_sync(t->cmd_qc, mo->command, &errp) < 0) + goto fail; + + if (qio_channel_socket_connect_sync(t->ctrl_qc, mo->control, &errp) < = 0) + goto fail; + + /* reset the TPM using a power cycle sequence, in case someone + * has previously powered it up */ + sock =3D tpm_send_ctrl(t, TPM_SIGNAL_POWER_OFF, &errp); + if (sock !=3D 0) + goto fail; + sock =3D tpm_send_ctrl(t, TPM_SIGNAL_POWER_ON, &errp); + if (sock !=3D 0) + goto fail; + sock =3D tpm_send_ctrl(t, TPM_SIGNAL_NV_ON, &errp); + if (sock !=3D 0) + goto fail; + + return be; + + fail: + object_unref(OBJECT(t->ctrl_qc)); + object_unref(OBJECT(t->cmd_qc)); + t->ctrl_qc =3D NULL; + error_prepend(&errp, ERROR_PREFIX); + error_report_err(errp); + object_unref(OBJECT(be)); + + return NULL; +} + +static const QemuOptDesc tpm_mssim_cmdline_opts[] =3D { + TPM_STANDARD_CMDLINE_OPTS, + { + .name =3D "command", + .type =3D QEMU_OPT_STRING, + .help =3D "Command socket (default localhost:2321)", + }, + { + .name =3D "control", + .type =3D QEMU_OPT_STRING, + .help =3D "control socket (default localhost:2322)", + }, +}; + +static void tpm_mssim_class_init(ObjectClass *klass, void *data) +{ + TPMBackendClass *cl =3D TPM_BACKEND_CLASS(klass); + + cl->type =3D TPM_TYPE_MSSIM; + cl->opts =3D tpm_mssim_cmdline_opts; + cl->desc =3D "TPM mssim emulator backend driver"; + cl->create =3D tpm_mssim_create; + cl->cancel_cmd =3D tpm_mssim_cancel_cmd; + cl->get_tpm_version =3D tpm_mssim_get_version; + cl->get_buffer_size =3D tpm_mssim_get_buffer_size; + cl->get_tpm_options =3D tpm_mssim_get_opts; + cl->handle_request =3D tpm_mssim_handle_request; +} + +static const TypeInfo tpm_mssim_info =3D { + .name =3D TYPE_TPM_MSSIM, + .parent =3D TYPE_TPM_BACKEND, + .instance_size =3D sizeof(TPMmssim), + .class_init =3D tpm_mssim_class_init, + .instance_init =3D tpm_mssim_instance_init, + .instance_finalize =3D tpm_mssim_instance_finalize, +}; + +static void tpm_mssim_register(void) +{ + type_register_static(&tpm_mssim_info); +} + +type_init(tpm_mssim_register) diff --git a/backends/tpm/tpm_mssim.h b/backends/tpm/tpm_mssim.h new file mode 100644 index 0000000000..04a270338a --- /dev/null +++ b/backends/tpm/tpm_mssim.h @@ -0,0 +1,43 @@ +/* + * SPDX-License-Identifier: BSD-2-Clause + * + * The code below is copied from the Microsoft/TCG Reference implementation + * + * https://github.com/Microsoft/ms-tpm-20-ref.git + * + * In file TPMCmd/Simulator/include/TpmTcpProtocol.h + */ + +#define TPM_SIGNAL_POWER_ON 1 +#define TPM_SIGNAL_POWER_OFF 2 +#define TPM_SIGNAL_PHYS_PRES_ON 3 +#define TPM_SIGNAL_PHYS_PRES_OFF 4 +#define TPM_SIGNAL_HASH_START 5 +#define TPM_SIGNAL_HASH_DATA 6 + // {uint32_t BufferSize, uint8_t[BufferSize] Buffer} +#define TPM_SIGNAL_HASH_END 7 +#define TPM_SEND_COMMAND 8 + // {uint8_t Locality, uint32_t InBufferSize, uint8_t[InBufferSize]= InBuffer} -> + // {uint32_t OutBufferSize, uint8_t[OutBufferSize] OutBuffer} + +#define TPM_SIGNAL_CANCEL_ON 9 +#define TPM_SIGNAL_CANCEL_OFF 10 +#define TPM_SIGNAL_NV_ON 11 +#define TPM_SIGNAL_NV_OFF 12 +#define TPM_SIGNAL_KEY_CACHE_ON 13 +#define TPM_SIGNAL_KEY_CACHE_OFF 14 + +#define TPM_REMOTE_HANDSHAKE 15 +#define TPM_SET_ALTERNATIVE_RESULT 16 + +#define TPM_SIGNAL_RESET 17 +#define TPM_SIGNAL_RESTART 18 + +#define TPM_SESSION_END 20 +#define TPM_STOP 21 + +#define TPM_GET_COMMAND_RESPONSE_SIZES 25 + +#define TPM_ACT_GET_SIGNALED 26 + +#define TPM_TEST_FAILURE_MODE 30 diff --git a/monitor/hmp-cmds.c b/monitor/hmp-cmds.c index e99447ad68..319f9eeeb6 100644 --- a/monitor/hmp-cmds.c +++ b/monitor/hmp-cmds.c @@ -841,6 +841,7 @@ void hmp_info_tpm(Monitor *mon, const QDict *qdict) unsigned int c =3D 0; TPMPassthroughOptions *tpo; TPMEmulatorOptions *teo; + TPMmssimOptions *tmo; =20 info_list =3D qmp_query_tpm(&err); if (err) { @@ -874,6 +875,12 @@ void hmp_info_tpm(Monitor *mon, const QDict *qdict) teo =3D &ti->options->u.emulator; monitor_printf(mon, ",chardev=3D%s", teo->chardev); break; + case TPM_TYPE_MSSIM: + tmo =3D &ti->options->u.mssim; + monitor_printf(mon, ",command=3D%s:%s,control=3D%s:%s", + tmo->command->u.inet.host, tmo->command->u.inet= .port, + tmo->control->u.inet.host, tmo->control->u.inet= .port); + break; case TPM_TYPE__MAX: break; } diff --git a/qapi/tpm.json b/qapi/tpm.json index d8cbd5ea0e..b773bde2ff 100644 --- a/qapi/tpm.json +++ b/qapi/tpm.json @@ -5,6 +5,7 @@ ## # =3D TPM (trusted platform module) devices ## +{ 'include': 'sockets.json' } =20 ## # @TpmModel: @@ -49,7 +50,7 @@ # # Since: 1.5 ## -{ 'enum': 'TpmType', 'data': [ 'passthrough', 'emulator' ], +{ 'enum': 'TpmType', 'data': [ 'passthrough', 'emulator', 'mssim' ], 'if': 'CONFIG_TPM' } =20 ## @@ -64,7 +65,7 @@ # Example: # # -> { "execute": "query-tpm-types" } -# <- { "return": [ "passthrough", "emulator" ] } +# <- { "return": [ "passthrough", "emulator", "mssim" ] } # ## { 'command': 'query-tpm-types', 'returns': ['TpmType'], @@ -99,6 +100,22 @@ { 'struct': 'TPMEmulatorOptions', 'data': { 'chardev' : 'str' }, 'if': 'CONFIG_TPM' } =20 +## +# @TPMmssimOptions: +# +# Information for the mssim emulator connection +# +# @command: command socket for the TPM emulator +# @control: control socket for the TPM emulator +# +# Since: 7.2.0 +## +{ 'struct': 'TPMmssimOptions', + 'data': { + '*command': 'SocketAddress', + '*control': 'SocketAddress' }, + 'if': 'CONFIG_TPM' } + ## # @TpmTypeOptions: # @@ -107,6 +124,7 @@ # @id: identifier of the backend # @type: - 'passthrough' The configuration options for the TPM passthrough= type # - 'emulator' The configuration options for TPM emulator backend t= ype +# - 'mssim' The configuration options for TPM emulator mssim type # # Since: 1.5 ## @@ -115,7 +133,8 @@ 'id': 'str' }, 'discriminator': 'type', 'data': { 'passthrough' : 'TPMPassthroughOptions', - 'emulator': 'TPMEmulatorOptions' }, + 'emulator': 'TPMEmulatorOptions', + 'mssim': 'TPMmssimOptions' }, 'if': 'CONFIG_TPM' } =20 ## --=20 2.35.3