From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1752671AbdLEBJu (ORCPT ); Mon, 4 Dec 2017 20:09:50 -0500 Received: from mail-by2nam03on0083.outbound.protection.outlook.com ([104.47.42.83]:22016 "EHLO NAM03-BY2-obe.outbound.protection.outlook.com" rhost-flags-OK-OK-OK-FAIL) by vger.kernel.org with ESMTP id S1751852AbdLEBFx (ORCPT ); Mon, 4 Dec 2017 20:05:53 -0500 Authentication-Results: spf=none (sender IP is ) smtp.mailfrom=brijesh.singh@amd.com; From: Brijesh Singh To: kvm@vger.kernel.org, linux-kernel@vger.kernel.org, x86@kernel.org Cc: bp@alien8.de, Brijesh Singh , Thomas Gleixner , Ingo Molnar , "H. Peter Anvin" , Paolo Bonzini , =?UTF-8?q?Radim=20Kr=C4=8Dm=C3=A1=C5=99?= , Joerg Roedel , Borislav Petkov , Tom Lendacky Subject: [Part2 PATCH v9 27/38] KVM: SVM: Add support for KVM_SEV_LAUNCH_START command Date: Mon, 4 Dec 2017 19:04:27 -0600 Message-Id: <20171205010438.5773-28-brijesh.singh@amd.com> X-Mailer: git-send-email 2.9.5 In-Reply-To: <20171205010438.5773-1-brijesh.singh@amd.com> References: <20171205010438.5773-1-brijesh.singh@amd.com> MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-Originating-IP: [165.204.78.1] X-ClientProxiedBy: CY4PR0601CA0087.namprd06.prod.outlook.com (52.132.96.156) To CY1PR12MB0149.namprd12.prod.outlook.com (10.161.173.19) X-MS-PublicTrafficType: Email X-MS-Office365-Filtering-Correlation-Id: 645605ad-1109-4947-0c7c-08d53b7c40f4 X-MS-Office365-Filtering-HT: Tenant X-Microsoft-Antispam: UriScan:;BCL:0;PCL:0;RULEID:(5600026)(4604075)(4534020)(4602075)(4627115)(201703031133081)(201702281549075)(48565401081)(2017052603286);SRVR:CY1PR12MB0149; X-Microsoft-Exchange-Diagnostics: 1;CY1PR12MB0149;3:AcWKxi16uERdKVxQujgnvrdZx9H2xI8LyvukCmwsylwIdO4TNaizqEKw/sT75MYCpNfOw5yt63lFjLXzEYWAErLX6Hat+xrHR+el40ocRH4J51u5XVZtt/5/HuoTzPjKn9LvcDZJYsMNX5uW4FrSWRTIUc7aEPnTgEB8sxrQk0Oavw9PsM4gjywq8cR9oj/W+eTgNx1nvluz6kpJimY7LHBqFRHAgQcDZ4vG9x5VzuzVafvgtG0Ex5ZjqKjal/ZZ;25:1cZh3vsjfI2UVzLIpFlt6wKkLfpD6sD4tFeJ2zhxqVxl4U4a/nZdaqjI3occq9VilxOZ6Z4vpdxTNM28uRNE3MwmnRROJ+8TRtQdHTKYnpIqse3jY4sF/r1KztlF3yx46uzBXpMjyH/cJRsfjTZJOamrOZdmac9puAUiVF7w65GbvhP5fDwvIi+1XPsO8k21VZXwBY++Rul+yALdxOYjdIuocsn2fiC38wWFT7r1uG05CsqcnsRvas43/RlJdNbOSeAcvbc4pgPnhbMTALk738ZFl//zHsM/aVeyFMBfNhxis+n7UhI7Fyvf4/g69gVaCWjaAKzAQW3GOG8kuX+85g==;31:hBT6MUkWehrfAKzaM0uD8HVcM3h2NcxEPCimcuWF2acgYV/lfSXofgYs2xbi9x80J3nMlhoENwDSdNDOUL66Ape2Sjggyjd7y6qfGl7NSynSiXuSE/EDNCKgMiCLb7YfusxZVmPHUKVL7cCTzXxNXuTpUFAs17G5Na6w36+d4zJrtuNK8F2cIpJNdguiUploxOaZq0+/TMhuhT6VSmbc2xDumlp4rnM45YA2oRF+ZY8= X-MS-TrafficTypeDiagnostic: CY1PR12MB0149: X-Microsoft-Exchange-Diagnostics: 1;CY1PR12MB0149;20:YKpK5hPq/wnw+QZWhMH6N89Kb/T7Nwn4E0voq/oQD2Hkxtcsz4rRZoml0ubC2Kma5HeOdKh9Vl6qTtKHX0MeTmLcuDzNSIRE+FO/MNHy/9JZyBDFho8pqfbXK08NfnN78q7CM3NWx6sRQS/n1SLeJ15HwWlzGDewPRf/kWkXrD8W6WSadHqVxDQnP2yqa1n5Xd73j/XIXuornpUUu+csGqTHmS+RNgW8ozd6rzxxkqda3X1lGtK7/Cnu5a3b9WGBWeoD9seyfZdjpIAo02GVG+cvhxlf4lmKsIffWgad+d9mqF7lyrVdm8/Y7SqNJ63r0/Wes3CR7UFoH+Re0wchLIUme7kgRdPUO5cq0wJl1vkQSsPBqyY/b31460MDJzNreHU1KRRqWwVgdWVZYdxqTjfHRiObGrwELdPfC4ZNJuS36lf4rNzB9NvNwS/yUhsqNHx3jkfpHePx7+RXbXeVBIvpF/Etn4H/IpwBawGl54347JAGE+SPwencqXuILcE4;4:oPxXOZijFuA8aU9DNP2kG8/XhrllN9OAgzQsRuz+SO7gY7PnvANphKUyENyNBNOIgCr4s34MBqwYBNAYKOAlb4HHjtcKqfT8QGhlwTIFnhPJY2uzj6QZxY8Z8DdE55FN0ixqaGlG6A7aPEmq2pLWPnDsqMZpq05wb2YIawmXT4Ukwim2vkgmFDJkN9QA7CptQ8T9YZvXQA6lZY5C0O4hyVcoQT0lKyLE7t8jLJRBtOaRK1NW+LNP6XfRxqWr23alRoAMgvlcexoer63oFZf9nLcmpRS1F9cb5N02thxvE8tbDUZeoI0qrxp9Na6jwS9NLRxTYbFrsKFanCgSNEofdg== X-Microsoft-Antispam-PRVS: X-Exchange-Antispam-Report-Test: UriScan:(9452136761055)(767451399110); X-Exchange-Antispam-Report-CFA-Test: BCL:0;PCL:0;RULEID:(6040450)(2401047)(5005006)(8121501046)(93006095)(93001095)(10201501046)(3002001)(3231022)(6055026)(6041248)(20161123558100)(20161123555025)(20161123562025)(20161123564025)(201703131423075)(201702281528075)(201703061421075)(201703061406153)(20161123560025)(6072148)(201708071742011);SRVR:CY1PR12MB0149;BCL:0;PCL:0;RULEID:(100000803101)(100110400095);SRVR:CY1PR12MB0149; X-Forefront-PRVS: 0512CC5201 X-Forefront-Antispam-Report: SFV:NSPM;SFS:(10009020)(6009001)(366004)(39860400002)(346002)(376002)(189002)(199003)(16526018)(189998001)(106356001)(478600001)(7416002)(2870700001)(101416001)(23676004)(52116002)(97736004)(86362001)(7696005)(33646002)(54906003)(25786009)(105586002)(76176011)(316002)(2950100002)(6666003)(7736002)(2906002)(6486002)(50226002)(81166006)(81156014)(8936002)(53936002)(8676002)(4326008)(1076002)(305945005)(66066001)(6116002)(53416004)(5660300001)(47776003)(68736007)(3846002)(50466002)(36756003);DIR:OUT;SFP:1101;SCL:1;SRVR:CY1PR12MB0149;H:wsp141597wss.amd.com;FPR:;SPF:None;PTR:InfoNoRecords;MX:1;A:1;LANG:en; X-Microsoft-Exchange-Diagnostics: =?utf-8?B?MTtDWTFQUjEyTUIwMTQ5OzIzOmxFSGRodWQrZ2dZYk5lNGJxbUdoeWFUYWtE?= =?utf-8?B?cHBCck55elFiYnB3SXpwRWFDcGVFeVZsV3h0SlNyOU5oYlBTUkljTk42Vys2?= =?utf-8?B?eUg1NUZvMitDNFpQZ05meTNtNFN3ZFJhRjREQXI1MVhjZm4zS1BRRzZFV0pC?= =?utf-8?B?L05MNXNFSmpHaWx5eWlQNUVTZlJSdWQ5S2xERUsyS0RTSGd4OVRkZjNtL0NS?= =?utf-8?B?RG5aV0JtajJCNGtXUVRPVlBkSjR1Wlo3K3p6K1BPdzNlV1V5NndrM3BRYTlx?= =?utf-8?B?SUFLeVI5YWZRS3Q0M281U3VIZ0FRQ1hjZ1RBOVNIdmJoM3RSYUMvdWFCRUJ5?= =?utf-8?B?b1VZc1oyU29VY1ZwNTJEQ2Npdk1CZXlBOEtYU3l1TmI2UURVb0QvOXFyK1E0?= =?utf-8?B?ZmhTdU00eUxVU3VjTFJUTjh1WVFCYy8vM3BNMFB0ZXRQMnRyS3VFdTNnRE50?= =?utf-8?B?NGM5em5uQmJuM3FORURGU0N6dGJlcElZUG9iNWgwbGdvT0gwcTN4ZDdaWGpk?= =?utf-8?B?NTIvaG5WYWdQb2JNQTc4UDZnUUVOYW9qMmxHWnF1dDRlTkhpVEVMMWNJa0lZ?= =?utf-8?B?YTJKSjVsZ3dWVUcyeVdqdXpXLzErdjhDUUViNU04RkVHYm1oUUs4cDNGTHg0?= =?utf-8?B?bjEyM05qZDBQbVlBSTN1RDFzYVZvMU1KZ3FvRmgvWEhLY2lBaVlYMWZ2RnVD?= =?utf-8?B?TjQyQXBwdWF2cHE3WnVJUStvWkRycmpWcjgvYWsySlJvQXFIcVdmc1pWZzVR?= =?utf-8?B?bksxZjQ3ckJabUN1dlE3ZGRpT2JJeE5LWmV0ZGhPbWhYT3R0eTJwWmhFdGd6?= =?utf-8?B?NHd6cllNMTZHTjd3QjlwY01PN1hMZEtyNmxiUFU4d0tPMFp3OTdOVHBJb2RK?= =?utf-8?B?YlIwWnRtVWYyRERTRHJnUjNIT0sxbUNnUmg4OVp2L1ZjTDNSUkcvcEMzVlp4?= =?utf-8?B?U1VGdTRTTTZ4cGtrNklMOHVXVXQxV1d1UFhCM0MrM2F1c0RzdmxLTkpHNi9k?= =?utf-8?B?NytzYVgvVVRPV3FSSzE0TURKZUhJVkxBWmtGdnJERkVhUmxzandqZ1BvS1VD?= =?utf-8?B?TVM4aTJvN0ljWWVQT0VBMkZmZ3owRExKWnRNRU9PWXIzZkc5Qm9maUs2Qi9q?= =?utf-8?B?NnpEcmY5TUZmMjRhOFMxeUp4SXo3dFVHQ250ZEFXWGNWWGlGdXRjVzFuYU9Y?= =?utf-8?B?eStLZ3l2V2YrS1Z4QlA0TkZtYlMyQVFnMnUySFJhV0J3bkJkMU8zb0Z4eXVy?= =?utf-8?B?TkVSbXh1Vy85TkF6bU4vYnA0TjVQdGlzaUg2ZWtlVFdpcys2OUJ5RmtabWFr?= =?utf-8?B?bXVoNkloQVV4SDNvRC90S2YzNnNxTVZvMnFYWjVWZ0xHR2NtaURsN0lDYm9F?= =?utf-8?B?bm1uMGdIMktFZnlVYmVodlZUTVRTODhjdXFHREpLN2xjUXUrdXppMWs4T0gx?= =?utf-8?B?UDJ0cFk1YUdPRHlIN1YxZ3NGV1NlOEVLdy9GRHBkTFQ1VlJJdEZkTEVuRS9F?= =?utf-8?Q?tflpVBKlQLdAIXkzTiHektO4U=3D?= X-Microsoft-Exchange-Diagnostics: 1;CY1PR12MB0149;6:Won9ISLvdN0ZWqUNuQsehqjJtPLrMyvE2Rq5xv9PSAu3JX2DyQaAerhbWhBCRmBEmAIsLCq9fpKa++b2bExv4NPoPdvfW8mOJS8kDWGu3N+TXC/GcrUquBxWnctvk2RH5wsgmV5DZ0uR9XS1c00/fDPJheflVE2PD2xT1oKyAI5V7cvXj+qJG0Zg1RoeAOhcyysdwWmcAKWySa56nBMln9orJf/9orAe+i3P6hSikxqMNwO4sqbbbKghQqA9IEi1TaUoWW88hLIUSGNXDuepqmJbKGoCMgCTxT0ubitvL0ht0RC5H2xgnhcZnT44ZupvICRuc32CHTVYTqY37K4WHYmnbCDP/TEtSA5RFp2lxVA=;5:+LbXZYrSSpGM7qfMR6C8/3S4qZvY3fmj5yT40ObgjD7H+uagf/V2H7MkYlyhWzrbEhjwIImqUCE8UvKKr13vb4fOQ0msZvg2aEQ1GX7pvUE5wf3cpoO9bhoxJ1VYjzQDGVZOozFdpxFvCGtbdoImfs3xUVDh/BWOUe23cxOo7OA=;24:i1zTsYzA3DPhMmjK/J+e2Nne8iEfS5wf4zM29x/43cjnrA7LPj4xR9OVW4ypg+TU41Ul4cIi58oJes9+VwvPPqeRJdmx8SDzkB9xWKjJC58=;7:s9IC+T3hTUUHu1uIUtdOMnlOEEPhNHD5ENsYQqJ0c5x18J9BZ4lpAdZQsvEBi+ud5U73+Cbj7GVht7Sxw2uuSrA0mvRq7hdpKpz/xY3DHMtRxm+beLrNdopsuv1aezpNJOMfG6bfat27foLiMgmZIStxcR+vObhvMUflkpFYkKuEh1ySMNUgH7W0+T1dKkcrjac1WpLfOlkEfMNxfsK2iYehG5deiT4KlXmQtZFG8mLKhcrE3korsB4wwwyi87rS SpamDiagnosticOutput: 1:99 SpamDiagnosticMetadata: NSPM X-Microsoft-Exchange-Diagnostics: 1;CY1PR12MB0149;20:9qEdhu2/noZCnfCgQ1PH3LK11i8neYtfOuWyV6oimmiNbnnbmcLCWkR1ttst5UsUEoTkSq3vChNgV8MihOJa/jXztZwsrtfuSpPOC5HE+K+ZtbMLjeZkOSP82FGxDRx13zCJbZg65ejD+7CSULjfYYIIWpYvkLBs069+WWaaMdEegkRmyhP9CV9xEqF8plYlvOAtmdhT5OA1Tw4T3ZFw0cgxxLUG5gBPIZFIRMA8TKxLgvOa0o1zKiTpPPDk7P6o X-OriginatorOrg: amd.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 05 Dec 2017 01:05:18.8262 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: 645605ad-1109-4947-0c7c-08d53b7c40f4 X-MS-Exchange-CrossTenant-FromEntityHeader: Hosted X-MS-Exchange-CrossTenant-Id: 3dd8961f-e488-4e60-8e11-a82d994e183d X-MS-Exchange-Transport-CrossTenantHeadersStamped: CY1PR12MB0149 Sender: linux-kernel-owner@vger.kernel.org List-ID: X-Mailing-List: linux-kernel@vger.kernel.org The KVM_SEV_LAUNCH_START command is used to create a memory encryption context within the SEV firmware. In order to do so, the guest owner should provide the guest's policy, its public Diffie-Hellman (PDH) key and session information. The command implements the LAUNCH_START flow defined in SEV spec Section 6.2. Cc: Thomas Gleixner Cc: Ingo Molnar Cc: "H. Peter Anvin" Cc: Paolo Bonzini Cc: "Radim Krčmář" Cc: Joerg Roedel Cc: Borislav Petkov Cc: Tom Lendacky Cc: x86@kernel.org Cc: kvm@vger.kernel.org Cc: linux-kernel@vger.kernel.org Improvements-by: Borislav Petkov Signed-off-by: Brijesh Singh Reviewed-by: Borislav Petkov --- arch/x86/include/asm/kvm_host.h | 2 + arch/x86/kvm/svm.c | 153 ++++++++++++++++++++++++++++++++++++++++ 2 files changed, 155 insertions(+) diff --git a/arch/x86/include/asm/kvm_host.h b/arch/x86/include/asm/kvm_host.h index 384dcfda43cc..0ea890375532 100644 --- a/arch/x86/include/asm/kvm_host.h +++ b/arch/x86/include/asm/kvm_host.h @@ -750,6 +750,8 @@ enum kvm_irqchip_mode { struct kvm_sev_info { bool active; /* SEV enabled guest */ unsigned int asid; /* ASID used for this guest */ + unsigned int handle; /* SEV firmware handle */ + int fd; /* SEV device fd */ }; struct kvm_arch { diff --git a/arch/x86/kvm/svm.c b/arch/x86/kvm/svm.c index cdbdc86d7aee..e5b712e55186 100644 --- a/arch/x86/kvm/svm.c +++ b/arch/x86/kvm/svm.c @@ -1538,11 +1538,45 @@ static void sev_asid_free(struct kvm *kvm) __sev_asid_free(sev->asid); } +static void sev_unbind_asid(struct kvm *kvm, unsigned int handle) +{ + struct sev_data_decommission *decommission; + struct sev_data_deactivate *data; + + if (!handle) + return; + + data = kzalloc(sizeof(*data), GFP_KERNEL); + if (!data) + return; + + /* deactivate handle */ + data->handle = handle; + sev_guest_deactivate(data, NULL); + + wbinvd_on_all_cpus(); + sev_guest_df_flush(NULL); + kfree(data); + + decommission = kzalloc(sizeof(*decommission), GFP_KERNEL); + if (!decommission) + return; + + /* decommission handle */ + decommission->handle = handle; + sev_guest_decommission(decommission, NULL); + + kfree(decommission); +} + static void sev_vm_destroy(struct kvm *kvm) { + struct kvm_sev_info *sev = &kvm->arch.sev_info; + if (!sev_guest(kvm)) return; + sev_unbind_asid(kvm, sev->handle); sev_asid_free(kvm); } @@ -5708,6 +5742,122 @@ static int sev_guest_init(struct kvm *kvm, struct kvm_sev_cmd *argp) return ret; } +static int sev_bind_asid(struct kvm *kvm, unsigned int handle, int *error) +{ + struct sev_data_activate *data; + int asid = sev_get_asid(kvm); + int ret; + + wbinvd_on_all_cpus(); + + ret = sev_guest_df_flush(error); + if (ret) + return ret; + + data = kzalloc(sizeof(*data), GFP_KERNEL); + if (!data) + return -ENOMEM; + + /* activate ASID on the given handle */ + data->handle = handle; + data->asid = asid; + ret = sev_guest_activate(data, error); + kfree(data); + + return ret; +} + +static int sev_issue_cmd(int fd, int id, void *data, int *error) +{ + struct fd f; + int ret; + + f = fdget(fd); + if (!f.file) + return -EBADF; + + ret = sev_issue_cmd_external_user(f.file, id, data, error); + + fdput(f); + return ret; +} + +static int sev_launch_start(struct kvm *kvm, struct kvm_sev_cmd *argp) +{ + struct kvm_sev_info *sev = &kvm->arch.sev_info; + struct sev_data_launch_start *start; + struct kvm_sev_launch_start params; + void *dh_blob, *session_blob; + int *error = &argp->error; + int ret; + + if (!sev_guest(kvm)) + return -ENOTTY; + + if (copy_from_user(¶ms, (void __user *)(uintptr_t)argp->data, sizeof(params))) + return -EFAULT; + + start = kzalloc(sizeof(*start), GFP_KERNEL); + if (!start) + return -ENOMEM; + + dh_blob = NULL; + if (params.dh_uaddr) { + dh_blob = psp_copy_user_blob(params.dh_uaddr, params.dh_len); + if (IS_ERR(dh_blob)) { + ret = PTR_ERR(dh_blob); + goto e_free; + } + + start->dh_cert_address = __sme_set(__pa(dh_blob)); + start->dh_cert_len = params.dh_len; + } + + session_blob = NULL; + if (params.session_uaddr) { + session_blob = psp_copy_user_blob(params.session_uaddr, params.session_len); + if (IS_ERR(session_blob)) { + ret = PTR_ERR(session_blob); + goto e_free_dh; + } + + start->session_address = __sme_set(__pa(session_blob)); + start->session_len = params.session_len; + } + + start->handle = params.handle; + start->policy = params.policy; + + /* create memory encryption context */ + ret = sev_issue_cmd(argp->sev_fd, SEV_CMD_LAUNCH_START, start, error); + if (ret) + goto e_free_session; + + /* Bind ASID to this guest */ + ret = sev_bind_asid(kvm, start->handle, error); + if (ret) + goto e_free_session; + + /* return handle to userspace */ + params.handle = start->handle; + if (copy_to_user((void __user *)(uintptr_t)argp->data, ¶ms, sizeof(params))) { + sev_unbind_asid(kvm, start->handle); + ret = -EFAULT; + goto e_free_session; + } + + sev->handle = start->handle; + sev->fd = argp->sev_fd; + +e_free_session: + kfree(session_blob); +e_free_dh: + kfree(dh_blob); +e_free: + kfree(start); + return ret; +} + static int svm_mem_enc_op(struct kvm *kvm, void __user *argp) { struct kvm_sev_cmd sev_cmd; @@ -5725,6 +5875,9 @@ static int svm_mem_enc_op(struct kvm *kvm, void __user *argp) case KVM_SEV_INIT: r = sev_guest_init(kvm, &sev_cmd); break; + case KVM_SEV_LAUNCH_START: + r = sev_launch_start(kvm, &sev_cmd); + break; default: r = -EINVAL; goto out; -- 2.9.5