From patchwork Wed Nov 19 15:43:10 2014 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Nadav Amit X-Patchwork-Id: 5338271 Return-Path: X-Original-To: patchwork-kvm@patchwork.kernel.org Delivered-To: patchwork-parsemail@patchwork1.web.kernel.org Received: from mail.kernel.org (mail.kernel.org [198.145.19.201]) by patchwork1.web.kernel.org (Postfix) with ESMTP id 854769F2F1 for ; Wed, 19 Nov 2014 15:44:19 +0000 (UTC) Received: from mail.kernel.org (localhost [127.0.0.1]) by mail.kernel.org (Postfix) with ESMTP id B5A0A20176 for ; Wed, 19 Nov 2014 15:44:18 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.kernel.org (Postfix) with ESMTP id 1DD9020172 for ; Wed, 19 Nov 2014 15:44:16 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1756008AbaKSPoL (ORCPT ); Wed, 19 Nov 2014 10:44:11 -0500 Received: from mailgw12.technion.ac.il ([132.68.225.12]:9092 "EHLO mailgw12.technion.ac.il" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1754559AbaKSPoL (ORCPT ); Wed, 19 Nov 2014 10:44:11 -0500 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AjACANq5bFSERCABjGdsb2JhbABahDzTXgKBBxYBAQEBAQEQAQEBJ0KEAwEFJ1IQUVcZiEHOG4V5AQEBBwIBH5EIBxaENQWGRqUqjWlrgQgkgR8BAQE X-IPAS-Result: AjACANq5bFSERCABjGdsb2JhbABahDzTXgKBBxYBAQEBAQEQAQEBJ0KEAwEFJ1IQUVcZiEHOG4V5AQEBBwIBH5EIBxaENQWGRqUqjWlrgQgkgR8BAQE X-IronPort-AV: E=Sophos;i="5.07,417,1413234000"; d="scan'208";a="130100398" Received: from csa.cs.technion.ac.il ([132.68.32.1]) by mailgw12.technion.ac.il with ESMTP; 19 Nov 2014 17:44:08 +0200 Received: from csn.cs.technion.ac.il (csn.cs.technion.ac.il [132.68.32.15]) by csa.cs.technion.ac.il (Postfix) with ESMTP id 0D53D14003E; Wed, 19 Nov 2014 17:44:08 +0200 (IST) Received: from csl-tapuz20.cs.technion.ac.il (csl-tapuz20.cs.technion.ac.il [132.68.206.58]) by csn.cs.technion.ac.il (Postfix) with ESMTPSA id EEAEEA1C49; Wed, 19 Nov 2014 17:44:07 +0200 (IST) From: Nadav Amit To: pbonzini@redhat.com Cc: kvm@vger.kernel.org, Nadav Amit Subject: [PATCH 3/6] KVM: x86: Emulator performs privilege checks on __linearize Date: Wed, 19 Nov 2014 17:43:10 +0200 Message-Id: <1416411793-22244-4-git-send-email-namit@cs.technion.ac.il> X-Mailer: git-send-email 1.9.1 In-Reply-To: <1416411793-22244-1-git-send-email-namit@cs.technion.ac.il> References: <1416411793-22244-1-git-send-email-namit@cs.technion.ac.il> Sender: kvm-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: kvm@vger.kernel.org X-Spam-Status: No, score=-6.9 required=5.0 tests=BAYES_00, RCVD_IN_DNSWL_HI, T_RP_MATCHES_RCVD, UNPARSEABLE_RELAY autolearn=unavailable version=3.3.1 X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on mail.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP When segment is accessed, real hardware does not perform any privilege level checks. In contrast, KVM emulator does. This causes some discrepencies from real hardware. For instance, reading from readable code segment may fail due to incorrect segment checks. In addition, it introduces unnecassary overhead. To reference Intel SDM 5.5 ("Privilege Levels"): "Privilege levels are checked when the segment selector of a segment descriptor is loaded into a segment register." The SDM never mentions privilege level checks during memory access, except for loading far pointers in section 5.10 ("Pointer Validation"). Those are actually segment selector loads and are emulated in the similarily (i.e., regardless to __linearize checks). This behavior was also checked using sysexit. A data-segment whose DPL=0 was loaded, and after sysexit (CPL=3) it is still accessible. Therefore, all the privilege level checks in __linearize are removed. Signed-off-by: Nadav Amit --- arch/x86/kvm/emulate.c | 15 --------------- 1 file changed, 15 deletions(-) diff --git a/arch/x86/kvm/emulate.c b/arch/x86/kvm/emulate.c index 1317560..d9461e4 100644 --- a/arch/x86/kvm/emulate.c +++ b/arch/x86/kvm/emulate.c @@ -663,7 +663,6 @@ static __always_inline int __linearize(struct x86_emulate_ctxt *ctxt, ulong la; u32 lim; u16 sel; - unsigned cpl; la = seg_base(ctxt, addr.seg) + addr.ea; *max_size = 0; @@ -705,20 +704,6 @@ static __always_inline int __linearize(struct x86_emulate_ctxt *ctxt, } if (size > *max_size) goto bad; - cpl = ctxt->ops->cpl(ctxt); - if (!fetch) { - /* data segment or readable code segment */ - if (cpl > desc.dpl) - goto bad; - } else if ((desc.type & 8) && !(desc.type & 4)) { - /* nonconforming code segment */ - if (cpl != desc.dpl) - goto bad; - } else if ((desc.type & 8) && (desc.type & 4)) { - /* conforming code segment */ - if (cpl < desc.dpl) - goto bad; - } break; } if (ctxt->mode != X86EMUL_MODE_PROT64)