Re: [PATCH 07/13] KVM: SVM: Add intercept checks for descriptor table accesses

2011-03-28 Thread Avi Kivity

On 03/28/2011 12:46 PM, Joerg Roedel wrote:

This patch add intercept checks into the KVM instruction
emulator to check for the 8 instructions that access the
descriptor table addresses.

+static struct opcode group6[] = {
+   DI(ModRM,sldt),
+   DI(ModRM,str),
+   DI(ModRM | Priv, lldt),
+   DI(ModRM | Priv, ltr),
+   N, N, N, N,
+};
+
  static struct group_dual group7 = { {
-   N, N, DI(ModRM | SrcMem | Priv, lgdt), DI(ModRM | SrcMem | Priv, lidt),
+   DI(ModRM | DstMem | Priv, sgdt), DI(ModRM | DstMem | Priv, sidt),
+   DI(ModRM | SrcMem | Priv, lgdt), DI(ModRM | SrcMem | Priv, lidt),


| Mov, to avoid RMW for SIDT, for example.  Also need to indicate the 
operand size correctly.



diff --git a/arch/x86/kvm/svm.c b/arch/x86/kvm/svm.c
index 381b038..485a09f 100644
--- a/arch/x86/kvm/svm.c
+++ b/arch/x86/kvm/svm.c
@@ -3871,6 +3871,10 @@ static void svm_fpu_deactivate(struct kvm_vcpu *vcpu)
  #define POST_EX(exit) { .exit_code = (exit), \
.stage = X86_ICPT_POST_EXCEPT, \
.valid = true }
+#define POST_MEM(exit) { .exit_code = (exit), \
+.stage = X86_ICPT_POST_MEMACCESS, \
+.valid = true }
+

  static struct __x86_intercept {
u32 exit_code;
@@ -3884,9 +3888,18 @@ static struct __x86_intercept {
[x86_intercept_smsw]= POST_EX(SVM_EXIT_READ_CR0),
[x86_intercept_dr_read] = POST_EX(SVM_EXIT_READ_DR0),
[x86_intercept_dr_write]= POST_EX(SVM_EXIT_WRITE_DR0),
+   [x86_intercept_sldt]= POST_MEM(SVM_EXIT_LDTR_READ),
+   [x86_intercept_str] = POST_MEM(SVM_EXIT_TR_READ),
+   [x86_intercept_lldt]= POST_MEM(SVM_EXIT_LDTR_WRITE),
+   [x86_intercept_ltr] = POST_MEM(SVM_EXIT_TR_WRITE),
+   [x86_intercept_sgdt]= POST_MEM(SVM_EXIT_GDTR_READ),
+   [x86_intercept_sidt]= POST_MEM(SVM_EXIT_IDTR_READ),
+   [x86_intercept_lgdt]= POST_MEM(SVM_EXIT_GDTR_WRITE),
+   [x86_intercept_lidt]= POST_MEM(SVM_EXIT_IDTR_WRITE),
  };


Spec says POST_EX()?



  #undef POST_EX
+#undef POST_MEM

  static int svm_check_intercept(struct kvm_vcpu *vcpu,
   struct x86_instruction_info *info,



--
error compiling committee.c: too many arguments to function

--
To unsubscribe from this list: send the line unsubscribe kvm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH 07/13] KVM: SVM: Add intercept checks for descriptor table accesses

2011-03-28 Thread Roedel, Joerg
On Mon, Mar 28, 2011 at 08:35:54AM -0400, Avi Kivity wrote:
 On 03/28/2011 12:46 PM, Joerg Roedel wrote:
  This patch add intercept checks into the KVM instruction
  emulator to check for the 8 instructions that access the
  descriptor table addresses.
 
  +static struct opcode group6[] = {
  +   DI(ModRM,sldt),
  +   DI(ModRM,str),
  +   DI(ModRM | Priv, lldt),
  +   DI(ModRM | Priv, ltr),
  +   N, N, N, N,
  +};
  +
static struct group_dual group7 = { {
  -   N, N, DI(ModRM | SrcMem | Priv, lgdt), DI(ModRM | SrcMem | Priv, lidt),
  +   DI(ModRM | DstMem | Priv, sgdt), DI(ModRM | DstMem | Priv, sidt),
  +   DI(ModRM | SrcMem | Priv, lgdt), DI(ModRM | SrcMem | Priv, lidt),
 
 | Mov, to avoid RMW for SIDT, for example.  Also need to indicate the 
 operand size correctly.
 
  diff --git a/arch/x86/kvm/svm.c b/arch/x86/kvm/svm.c
  index 381b038..485a09f 100644
  --- a/arch/x86/kvm/svm.c
  +++ b/arch/x86/kvm/svm.c
  @@ -3871,6 +3871,10 @@ static void svm_fpu_deactivate(struct kvm_vcpu *vcpu)
#define POST_EX(exit) { .exit_code = (exit), \
  .stage = X86_ICPT_POST_EXCEPT, \
  .valid = true }
  +#define POST_MEM(exit) { .exit_code = (exit), \
  +.stage = X86_ICPT_POST_MEMACCESS, \
  +.valid = true }
  +
 
static struct __x86_intercept {
  u32 exit_code;
  @@ -3884,9 +3888,18 @@ static struct __x86_intercept {
  [x86_intercept_smsw]= POST_EX(SVM_EXIT_READ_CR0),
  [x86_intercept_dr_read] = POST_EX(SVM_EXIT_READ_DR0),
  [x86_intercept_dr_write]= POST_EX(SVM_EXIT_WRITE_DR0),
  +   [x86_intercept_sldt]= POST_MEM(SVM_EXIT_LDTR_READ),
  +   [x86_intercept_str] = POST_MEM(SVM_EXIT_TR_READ),
  +   [x86_intercept_lldt]= POST_MEM(SVM_EXIT_LDTR_WRITE),
  +   [x86_intercept_ltr] = POST_MEM(SVM_EXIT_TR_WRITE),
  +   [x86_intercept_sgdt]= POST_MEM(SVM_EXIT_GDTR_READ),
  +   [x86_intercept_sidt]= POST_MEM(SVM_EXIT_IDTR_READ),
  +   [x86_intercept_lgdt]= POST_MEM(SVM_EXIT_GDTR_WRITE),
  +   [x86_intercept_lidt]= POST_MEM(SVM_EXIT_IDTR_WRITE),
};
 
 Spec says POST_EX()?

Well, not entirely clear. Spec says that #GP takes precedence before the
intercept and the intruction reference says the #GP fires if the
supplied address is not within segment limits or the segment itself is
not valid, which, in my interpretation, made them POST_MEM.

Joerg

-- 
AMD Operating System Research Center

Advanced Micro Devices GmbH Einsteinring 24 85609 Dornach
General Managers: Alberto Bozzo, Andrew Bowd
Registration: Dornach, Landkr. Muenchen; Registerger. Muenchen, HRB Nr. 43632

--
To unsubscribe from this list: send the line unsubscribe kvm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH 07/13] KVM: SVM: Add intercept checks for descriptor table accesses

2011-03-28 Thread Avi Kivity

On 03/28/2011 03:56 PM, Roedel, Joerg wrote:

On Mon, Mar 28, 2011 at 08:35:54AM -0400, Avi Kivity wrote:
  On 03/28/2011 12:46 PM, Joerg Roedel wrote:
This patch add intercept checks into the KVM instruction
emulator to check for the 8 instructions that access the
descriptor table addresses.
  
+static struct opcode group6[] = {
+   DI(ModRM,sldt),
+   DI(ModRM,str),
+   DI(ModRM | Priv, lldt),
+   DI(ModRM | Priv, ltr),
+   N, N, N, N,
+};
+
  static struct group_dual group7 = { {
-   N, N, DI(ModRM | SrcMem | Priv, lgdt), DI(ModRM | SrcMem | Priv, 
lidt),
+   DI(ModRM | DstMem | Priv, sgdt), DI(ModRM | DstMem | Priv, sidt),
+   DI(ModRM | SrcMem | Priv, lgdt), DI(ModRM | SrcMem | Priv, lidt),

  | Mov, to avoid RMW for SIDT, for example.  Also need to indicate the
  operand size correctly.

diff --git a/arch/x86/kvm/svm.c b/arch/x86/kvm/svm.c
index 381b038..485a09f 100644
--- a/arch/x86/kvm/svm.c
+++ b/arch/x86/kvm/svm.c
@@ -3871,6 +3871,10 @@ static void svm_fpu_deactivate(struct kvm_vcpu 
*vcpu)
  #define POST_EX(exit) { .exit_code = (exit), \
.stage = X86_ICPT_POST_EXCEPT, \
.valid = true }
+#define POST_MEM(exit) { .exit_code = (exit), \
+.stage = X86_ICPT_POST_MEMACCESS, \
+.valid = true }
+
  
  static struct __x86_intercept {
u32 exit_code;
@@ -3884,9 +3888,18 @@ static struct __x86_intercept {
[x86_intercept_smsw]= POST_EX(SVM_EXIT_READ_CR0),
[x86_intercept_dr_read] = POST_EX(SVM_EXIT_READ_DR0),
[x86_intercept_dr_write]= POST_EX(SVM_EXIT_WRITE_DR0),
+   [x86_intercept_sldt]= POST_MEM(SVM_EXIT_LDTR_READ),
+   [x86_intercept_str] = POST_MEM(SVM_EXIT_TR_READ),
+   [x86_intercept_lldt]= POST_MEM(SVM_EXIT_LDTR_WRITE),
+   [x86_intercept_ltr] = POST_MEM(SVM_EXIT_TR_WRITE),
+   [x86_intercept_sgdt]= POST_MEM(SVM_EXIT_GDTR_READ),
+   [x86_intercept_sidt]= POST_MEM(SVM_EXIT_IDTR_READ),
+   [x86_intercept_lgdt]= POST_MEM(SVM_EXIT_GDTR_WRITE),
+   [x86_intercept_lidt]= POST_MEM(SVM_EXIT_IDTR_WRITE),
  };

  Spec says POST_EX()?

Well, not entirely clear. Spec says that #GP takes precedence before the
intercept and the intruction reference says the #GP fires if the
supplied address is not within segment limits or the segment itself is
not valid, which, in my interpretation, made them POST_MEM.


My interpretation would be that a #GP(0) due to CPL check takes 
precedence over the intercept, which takes precedence over a 
#GP(selector) due to the actual memory reference.


--
error compiling committee.c: too many arguments to function

--
To unsubscribe from this list: send the line unsubscribe kvm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH 07/13] KVM: SVM: Add intercept checks for descriptor table accesses

2011-03-26 Thread Avi Kivity

On 03/25/2011 11:29 AM, Joerg Roedel wrote:

This patch add intercept checks into the KVM instruction
emulator to check for the 8 instructions that access the
descriptor table addresses.


+static struct opcode group6[] = {
+   DI(ModRM,sldt),
+   DI(ModRM,str),
+   DI(ModRM | Priv, lldt),
+   DI(ModRM | Priv, ltr),
+   N, N, N, N,
+};
+
  static struct group_dual group7 = { {
-   N, N, DI(ModRM | SrcMem | Priv, lgdt), DI(ModRM | SrcMem | Priv, lidt),
+   DI(ModRM | DstMem | Priv, sgdt), DI(ModRM | DstMem | Priv, sidt),
+   DI(ModRM | SrcMem | Priv, lgdt), DI(ModRM | SrcMem | Priv, lidt),
DI(SrcNone | ModRM | DstMem | Mov, smsw), N,
DI(SrcMem16 | ModRM | Mov | Priv, lmsw),
DI(SrcMem | ModRM | ByteOp | Priv | NoAccess, invlpg),


You're adding decode info for instructions that aren't emulated.  Safe 
AFAICT because of 'default: goto cannot_emulate', I guess.


--
I have a truly marvellous patch that fixes the bug which this
signature is too narrow to contain.

--
To unsubscribe from this list: send the line unsubscribe kvm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH 07/13] KVM: SVM: Add intercept checks for descriptor table accesses

2011-03-26 Thread Joerg Roedel
On Sat, Mar 26, 2011 at 11:43:47AM +0200, Avi Kivity wrote:
 On 03/25/2011 11:29 AM, Joerg Roedel wrote:
 This patch add intercept checks into the KVM instruction
 emulator to check for the 8 instructions that access the
 descriptor table addresses.


 +static struct opcode group6[] = {
 +DI(ModRM,sldt),
 +DI(ModRM,str),
 +DI(ModRM | Priv, lldt),
 +DI(ModRM | Priv, ltr),
 +N, N, N, N,
 +};
 +
   static struct group_dual group7 = { {
 -N, N, DI(ModRM | SrcMem | Priv, lgdt), DI(ModRM | SrcMem | Priv, lidt),
 +DI(ModRM | DstMem | Priv, sgdt), DI(ModRM | DstMem | Priv, sidt),
 +DI(ModRM | SrcMem | Priv, lgdt), DI(ModRM | SrcMem | Priv, lidt),
  DI(SrcNone | ModRM | DstMem | Mov, smsw), N,
  DI(SrcMem16 | ModRM | Mov | Priv, lmsw),
  DI(SrcMem | ModRM | ByteOp | Priv | NoAccess, invlpg),

 You're adding decode info for instructions that aren't emulated.  Safe  
 AFAICT because of 'default: goto cannot_emulate', I guess.

Right, all that can happen is that the nested guest shoot itself in the
foot by getting an #UD. Same for the SVM instructions.

Joerg
--
To unsubscribe from this list: send the line unsubscribe kvm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html