Re: [PATCH kvm-unit-tests 4/4] x86/taskswitch_vm86: Task switches into/out of VM86

2012-01-24 Thread Gleb Natapov
On Tue, Jan 24, 2012 at 11:14:23AM +0100, Kevin Wolf wrote:
> Am 23.01.2012 17:42, schrieb Gleb Natapov:
> > On Mon, Jan 23, 2012 at 05:32:59PM +0100, Kevin Wolf wrote:
> >> Am 23.01.2012 17:22, schrieb Gleb Natapov:
> >>> On Mon, Jan 23, 2012 at 05:20:22PM +0100, Kevin Wolf wrote:
>  Am 23.01.2012 17:10, schrieb Gleb Natapov:
> > On Mon, Jan 23, 2012 at 05:07:13PM +0100, Kevin Wolf wrote:
> >> This adds a test case that jumps into VM86 by iret-ing to a TSS and 
> >> back
> >> to Protected Mode using a task gate in the IDT.
> >>
> > Can you add the test case to taskswitch2.c?
> 
> >>> Running one test to check all aspects of taskswitch emulation.
> >>
> >> (We all know that top-posting is disliked, but middle-posting looks even
> >> crazier!)
> >>
> > Inserting replies 
> 
> Very true!
> 
:)

> > at random places is a new cool thing!
> > 
> >> Does having one test provide any value in and of itself? It's just an
> >> implementation detail of the test suite. When testing the KVM patches I
> >> ran all three test cases with './run_tests.sh -g task', which is
> >> hopefully easy enough.
> >>
> > I think it does. I do not have to use external script to combine tests
> > on the same topic or even remember that such script exists. We do not
> > create separate tests to test each instruction emulation either. And I
> > usually run qemu not on the same machine I compile it on, so I need
> > special tricks to make those test script work. Of course if putting this
> > code into existing test file is hard separate test is OK, but is this
> > really the case here?
> 
> I haven't really checked whether they interfere. I guess I would have to
> move the GDT indexes for my manually created TSSes and I would have to
> hope that nobody else needs the memory I'm overwriting with the real
> mode code (there doesn't seem to be memory management for < 1 MB).
> 
You can add function alloc_vpage_low(). Other tests may find it useful.

> Should taskswitch.c and taskswitch2.c be merged as well then? Or is
> there a reason why they must stay separate? One file or three files
> makes sense to me for three tests, but two not so much.
> 
taskswitch.c should be removed. It tests nothing that taskswitch2.c does
not check as far as I see.

--
Gleb.
--
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 kvm-unit-tests 4/4] x86/taskswitch_vm86: Task switches into/out of VM86

2012-01-24 Thread Kevin Wolf
Am 23.01.2012 17:42, schrieb Gleb Natapov:
> On Mon, Jan 23, 2012 at 05:32:59PM +0100, Kevin Wolf wrote:
>> Am 23.01.2012 17:22, schrieb Gleb Natapov:
>>> On Mon, Jan 23, 2012 at 05:20:22PM +0100, Kevin Wolf wrote:
 Am 23.01.2012 17:10, schrieb Gleb Natapov:
> On Mon, Jan 23, 2012 at 05:07:13PM +0100, Kevin Wolf wrote:
>> This adds a test case that jumps into VM86 by iret-ing to a TSS and back
>> to Protected Mode using a task gate in the IDT.
>>
> Can you add the test case to taskswitch2.c?

>>> Running one test to check all aspects of taskswitch emulation.
>>
>> (We all know that top-posting is disliked, but middle-posting looks even
>> crazier!)
>>
> Inserting replies 

Very true!

> at random places is a new cool thing!
> 
>> Does having one test provide any value in and of itself? It's just an
>> implementation detail of the test suite. When testing the KVM patches I
>> ran all three test cases with './run_tests.sh -g task', which is
>> hopefully easy enough.
>>
> I think it does. I do not have to use external script to combine tests
> on the same topic or even remember that such script exists. We do not
> create separate tests to test each instruction emulation either. And I
> usually run qemu not on the same machine I compile it on, so I need
> special tricks to make those test script work. Of course if putting this
> code into existing test file is hard separate test is OK, but is this
> really the case here?

I haven't really checked whether they interfere. I guess I would have to
move the GDT indexes for my manually created TSSes and I would have to
hope that nobody else needs the memory I'm overwriting with the real
mode code (there doesn't seem to be memory management for < 1 MB).

Should taskswitch.c and taskswitch2.c be merged as well then? Or is
there a reason why they must stay separate? One file or three files
makes sense to me for three tests, but two not so much.

Kevin
--
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 kvm-unit-tests 4/4] x86/taskswitch_vm86: Task switches into/out of VM86

2012-01-23 Thread Gleb Natapov
On Mon, Jan 23, 2012 at 05:32:59PM +0100, Kevin Wolf wrote:
> Am 23.01.2012 17:22, schrieb Gleb Natapov:
> > On Mon, Jan 23, 2012 at 05:20:22PM +0100, Kevin Wolf wrote:
> >> Am 23.01.2012 17:10, schrieb Gleb Natapov:
> >>> On Mon, Jan 23, 2012 at 05:07:13PM +0100, Kevin Wolf wrote:
>  This adds a test case that jumps into VM86 by iret-ing to a TSS and back
>  to Protected Mode using a task gate in the IDT.
> 
> >>> Can you add the test case to taskswitch2.c?
> >>
> > Running one test to check all aspects of taskswitch emulation.
> 
> (We all know that top-posting is disliked, but middle-posting looks even
> crazier!)
> 
Inserting replies at random places is a new cool thing!

> Does having one test provide any value in and of itself? It's just an
> implementation detail of the test suite. When testing the KVM patches I
> ran all three test cases with './run_tests.sh -g task', which is
> hopefully easy enough.
> 
I think it does. I do not have to use external script to combine tests
on the same topic or even remember that such script exists. We do not
create separate tests to test each instruction emulation either. And I
usually run qemu not on the same machine I compile it on, so I need
special tricks to make those test script work. Of course if putting this
code into existing test file is hard separate test is OK, but is this
really the case here?

> Kevin
> 
> > 
> >> That's actually what I intended to do at first, but there's nothing to
> >> share and having a clean environment that can't interfere with other
> >> tests feels nicer.
> >>
> >> What would we gain from merging the files?
> >>
> >> Kevin
> >>
> >>
> >>>
>  Signed-off-by: Kevin Wolf 
>  ---
>   config-i386.mak   |3 +-
>   lib/x86/desc.c|   37 +-
>   lib/x86/desc.h|   36 +
>   lib/x86/vm.c  |4 +-
>   lib/x86/vm.h  |1 +
>   x86/taskswitch_vm86.c |   59 
>  +
>   x86/unittests.cfg |6 +
>   7 files changed, 107 insertions(+), 39 deletions(-)
>   create mode 100644 x86/taskswitch_vm86.c
> 
>  diff --git a/config-i386.mak b/config-i386.mak
>  index de52f3d..b5c3b9c 100644
>  --- a/config-i386.mak
>  +++ b/config-i386.mak
>  @@ -5,9 +5,10 @@ ldarch = elf32-i386
>   CFLAGS += -D__i386__
>   CFLAGS += -I $(KERNELDIR)/include
>   
>  -tests = $(TEST_DIR)/taskswitch.flat $(TEST_DIR)/taskswitch2.flat
>  +tests = $(TEST_DIR)/taskswitch.flat $(TEST_DIR)/taskswitch2.flat 
>  $(TEST_DIR)/taskswitch_vm86.flat
>   
>   include config-x86-common.mak
>   
>   $(TEST_DIR)/taskswitch.elf: $(cstart.o) $(TEST_DIR)/taskswitch.o
>   $(TEST_DIR)/taskswitch2.elf: $(cstart.o) $(TEST_DIR)/taskswitch2.o
>  +$(TEST_DIR)/taskswitch_vm86.elf: $(cstart.o) 
>  $(TEST_DIR)/taskswitch_vm86.o
>  diff --git a/lib/x86/desc.c b/lib/x86/desc.c
>  index 770c250..c4a3607 100644
>  --- a/lib/x86/desc.c
>  +++ b/lib/x86/desc.c
>  @@ -27,41 +27,6 @@ typedef struct {
>   u8 base_high;
>   } gdt_entry_t;
>   
>  -typedef struct {
>  -u16 prev;
>  -u16 res1;
>  -u32 esp0;
>  -u16 ss0;
>  -u16 res2;
>  -u32 esp1;
>  -u16 ss1;
>  -u16 res3;
>  -u32 esp2;
>  -u16 ss2;
>  -u16 res4;
>  -u32 cr3;
>  -u32 eip;
>  -u32 eflags;
>  -u32 eax, ecx, edx, ebx, esp, ebp, esi, edi;
>  -u16 es;
>  -u16 res5;
>  -u16 cs;
>  -u16 res6;
>  -u16 ss;
>  -u16 res7;
>  -u16 ds;
>  -u16 res8;
>  -u16 fs;
>  -u16 res9;
>  -u16 gs;
>  -u16 res10;
>  -u16 ldt;
>  -u16 res11;
>  -u16 t:1;
>  -u16 res12:15;
>  -u16 iomap_base;
>  -} tss32_t;
>  -
>   extern idt_entry_t boot_idt[256];
>   
>   void set_idt_entry(int vec, void *addr, int dpl)
>  @@ -327,7 +292,7 @@ void setup_gdt(void)
> ".Lflush2: "::"r"(0x10));
>   }
>   
>  -static void set_idt_task_gate(int vec, u16 sel)
>  +void set_idt_task_gate(int vec, u16 sel)
>   {
>   idt_entry_t *e = &boot_idt[vec];
>   
>  diff --git a/lib/x86/desc.h b/lib/x86/desc.h
>  index 0b4897c..f819452 100644
>  --- a/lib/x86/desc.h
>  +++ b/lib/x86/desc.h
>  @@ -24,6 +24,41 @@ struct ex_regs {
>   unsigned long rflags;
>   };
>   
>  +typedef struct {
>  +u16 prev;
>  +u16 res1;
>  +u32 esp0;
>  +u16 ss0;
>  +u16 res2;
>  +u32 esp1;
>  +u16 ss1;
>  +u16 r

Re: [PATCH kvm-unit-tests 4/4] x86/taskswitch_vm86: Task switches into/out of VM86

2012-01-23 Thread Kevin Wolf
Am 23.01.2012 17:22, schrieb Gleb Natapov:
> On Mon, Jan 23, 2012 at 05:20:22PM +0100, Kevin Wolf wrote:
>> Am 23.01.2012 17:10, schrieb Gleb Natapov:
>>> On Mon, Jan 23, 2012 at 05:07:13PM +0100, Kevin Wolf wrote:
 This adds a test case that jumps into VM86 by iret-ing to a TSS and back
 to Protected Mode using a task gate in the IDT.

>>> Can you add the test case to taskswitch2.c?
>>
> Running one test to check all aspects of taskswitch emulation.

(We all know that top-posting is disliked, but middle-posting looks even
crazier!)

Does having one test provide any value in and of itself? It's just an
implementation detail of the test suite. When testing the KVM patches I
ran all three test cases with './run_tests.sh -g task', which is
hopefully easy enough.

Kevin

> 
>> That's actually what I intended to do at first, but there's nothing to
>> share and having a clean environment that can't interfere with other
>> tests feels nicer.
>>
>> What would we gain from merging the files?
>>
>> Kevin
>>
>>
>>>
 Signed-off-by: Kevin Wolf 
 ---
  config-i386.mak   |3 +-
  lib/x86/desc.c|   37 +-
  lib/x86/desc.h|   36 +
  lib/x86/vm.c  |4 +-
  lib/x86/vm.h  |1 +
  x86/taskswitch_vm86.c |   59 
 +
  x86/unittests.cfg |6 +
  7 files changed, 107 insertions(+), 39 deletions(-)
  create mode 100644 x86/taskswitch_vm86.c

 diff --git a/config-i386.mak b/config-i386.mak
 index de52f3d..b5c3b9c 100644
 --- a/config-i386.mak
 +++ b/config-i386.mak
 @@ -5,9 +5,10 @@ ldarch = elf32-i386
  CFLAGS += -D__i386__
  CFLAGS += -I $(KERNELDIR)/include
  
 -tests = $(TEST_DIR)/taskswitch.flat $(TEST_DIR)/taskswitch2.flat
 +tests = $(TEST_DIR)/taskswitch.flat $(TEST_DIR)/taskswitch2.flat 
 $(TEST_DIR)/taskswitch_vm86.flat
  
  include config-x86-common.mak
  
  $(TEST_DIR)/taskswitch.elf: $(cstart.o) $(TEST_DIR)/taskswitch.o
  $(TEST_DIR)/taskswitch2.elf: $(cstart.o) $(TEST_DIR)/taskswitch2.o
 +$(TEST_DIR)/taskswitch_vm86.elf: $(cstart.o) $(TEST_DIR)/taskswitch_vm86.o
 diff --git a/lib/x86/desc.c b/lib/x86/desc.c
 index 770c250..c4a3607 100644
 --- a/lib/x86/desc.c
 +++ b/lib/x86/desc.c
 @@ -27,41 +27,6 @@ typedef struct {
u8 base_high;
  } gdt_entry_t;
  
 -typedef struct {
 -  u16 prev;
 -  u16 res1;
 -  u32 esp0;
 -  u16 ss0;
 -  u16 res2;
 -  u32 esp1;
 -  u16 ss1;
 -  u16 res3;
 -  u32 esp2;
 -  u16 ss2;
 -  u16 res4;
 -  u32 cr3;
 -  u32 eip;
 -  u32 eflags;
 -  u32 eax, ecx, edx, ebx, esp, ebp, esi, edi;
 -  u16 es;
 -  u16 res5;
 -  u16 cs;
 -  u16 res6;
 -  u16 ss;
 -  u16 res7;
 -  u16 ds;
 -  u16 res8;
 -  u16 fs;
 -  u16 res9;
 -  u16 gs;
 -  u16 res10;
 -  u16 ldt;
 -  u16 res11;
 -  u16 t:1;
 -  u16 res12:15;
 -  u16 iomap_base;
 -} tss32_t;
 -
  extern idt_entry_t boot_idt[256];
  
  void set_idt_entry(int vec, void *addr, int dpl)
 @@ -327,7 +292,7 @@ void setup_gdt(void)
  ".Lflush2: "::"r"(0x10));
  }
  
 -static void set_idt_task_gate(int vec, u16 sel)
 +void set_idt_task_gate(int vec, u16 sel)
  {
  idt_entry_t *e = &boot_idt[vec];
  
 diff --git a/lib/x86/desc.h b/lib/x86/desc.h
 index 0b4897c..f819452 100644
 --- a/lib/x86/desc.h
 +++ b/lib/x86/desc.h
 @@ -24,6 +24,41 @@ struct ex_regs {
  unsigned long rflags;
  };
  
 +typedef struct {
 +  u16 prev;
 +  u16 res1;
 +  u32 esp0;
 +  u16 ss0;
 +  u16 res2;
 +  u32 esp1;
 +  u16 ss1;
 +  u16 res3;
 +  u32 esp2;
 +  u16 ss2;
 +  u16 res4;
 +  u32 cr3;
 +  u32 eip;
 +  u32 eflags;
 +  u32 eax, ecx, edx, ebx, esp, ebp, esi, edi;
 +  u16 es;
 +  u16 res5;
 +  u16 cs;
 +  u16 res6;
 +  u16 ss;
 +  u16 res7;
 +  u16 ds;
 +  u16 res8;
 +  u16 fs;
 +  u16 res9;
 +  u16 gs;
 +  u16 res10;
 +  u16 ldt;
 +  u16 res11;
 +  u16 t:1;
 +  u16 res12:15;
 +  u16 iomap_base;
 +} tss32_t;
 +
  #define ASM_TRY(catch)  \
  "movl $0, %%gs:4 \n\t"  \
  ".pushsection .data.ex \n\t"\
 @@ -44,6 +79,7 @@ unsigned exception_error_code(void);
  void set_idt_entry(int vec, void *addr, int dpl);
  void set_idt_sel(int vec, u16 sel);
  void set_gdt_entry(int num, u32 base,  u32 limit, u8 access, u8 gran);
 +void set_idt_task_gate(int vec, u16 sel);
  void set_intr_task_gate(int e, void *fn);
  void print_current_tss_info(void);
  void handle_exception(u8 v, v

Re: [PATCH kvm-unit-tests 4/4] x86/taskswitch_vm86: Task switches into/out of VM86

2012-01-23 Thread Gleb Natapov
On Mon, Jan 23, 2012 at 05:20:22PM +0100, Kevin Wolf wrote:
> Am 23.01.2012 17:10, schrieb Gleb Natapov:
> > On Mon, Jan 23, 2012 at 05:07:13PM +0100, Kevin Wolf wrote:
> >> This adds a test case that jumps into VM86 by iret-ing to a TSS and back
> >> to Protected Mode using a task gate in the IDT.
> >>
> > Can you add the test case to taskswitch2.c?
> 
Running one test to check all aspects of taskswitch emulation.

> That's actually what I intended to do at first, but there's nothing to
> share and having a clean environment that can't interfere with other
> tests feels nicer.
> 
> What would we gain from merging the files?
> 
> Kevin
> 
> 
> > 
> >> Signed-off-by: Kevin Wolf 
> >> ---
> >>  config-i386.mak   |3 +-
> >>  lib/x86/desc.c|   37 +-
> >>  lib/x86/desc.h|   36 +
> >>  lib/x86/vm.c  |4 +-
> >>  lib/x86/vm.h  |1 +
> >>  x86/taskswitch_vm86.c |   59 
> >> +
> >>  x86/unittests.cfg |6 +
> >>  7 files changed, 107 insertions(+), 39 deletions(-)
> >>  create mode 100644 x86/taskswitch_vm86.c
> >>
> >> diff --git a/config-i386.mak b/config-i386.mak
> >> index de52f3d..b5c3b9c 100644
> >> --- a/config-i386.mak
> >> +++ b/config-i386.mak
> >> @@ -5,9 +5,10 @@ ldarch = elf32-i386
> >>  CFLAGS += -D__i386__
> >>  CFLAGS += -I $(KERNELDIR)/include
> >>  
> >> -tests = $(TEST_DIR)/taskswitch.flat $(TEST_DIR)/taskswitch2.flat
> >> +tests = $(TEST_DIR)/taskswitch.flat $(TEST_DIR)/taskswitch2.flat 
> >> $(TEST_DIR)/taskswitch_vm86.flat
> >>  
> >>  include config-x86-common.mak
> >>  
> >>  $(TEST_DIR)/taskswitch.elf: $(cstart.o) $(TEST_DIR)/taskswitch.o
> >>  $(TEST_DIR)/taskswitch2.elf: $(cstart.o) $(TEST_DIR)/taskswitch2.o
> >> +$(TEST_DIR)/taskswitch_vm86.elf: $(cstart.o) $(TEST_DIR)/taskswitch_vm86.o
> >> diff --git a/lib/x86/desc.c b/lib/x86/desc.c
> >> index 770c250..c4a3607 100644
> >> --- a/lib/x86/desc.c
> >> +++ b/lib/x86/desc.c
> >> @@ -27,41 +27,6 @@ typedef struct {
> >>u8 base_high;
> >>  } gdt_entry_t;
> >>  
> >> -typedef struct {
> >> -  u16 prev;
> >> -  u16 res1;
> >> -  u32 esp0;
> >> -  u16 ss0;
> >> -  u16 res2;
> >> -  u32 esp1;
> >> -  u16 ss1;
> >> -  u16 res3;
> >> -  u32 esp2;
> >> -  u16 ss2;
> >> -  u16 res4;
> >> -  u32 cr3;
> >> -  u32 eip;
> >> -  u32 eflags;
> >> -  u32 eax, ecx, edx, ebx, esp, ebp, esi, edi;
> >> -  u16 es;
> >> -  u16 res5;
> >> -  u16 cs;
> >> -  u16 res6;
> >> -  u16 ss;
> >> -  u16 res7;
> >> -  u16 ds;
> >> -  u16 res8;
> >> -  u16 fs;
> >> -  u16 res9;
> >> -  u16 gs;
> >> -  u16 res10;
> >> -  u16 ldt;
> >> -  u16 res11;
> >> -  u16 t:1;
> >> -  u16 res12:15;
> >> -  u16 iomap_base;
> >> -} tss32_t;
> >> -
> >>  extern idt_entry_t boot_idt[256];
> >>  
> >>  void set_idt_entry(int vec, void *addr, int dpl)
> >> @@ -327,7 +292,7 @@ void setup_gdt(void)
> >>  ".Lflush2: "::"r"(0x10));
> >>  }
> >>  
> >> -static void set_idt_task_gate(int vec, u16 sel)
> >> +void set_idt_task_gate(int vec, u16 sel)
> >>  {
> >>  idt_entry_t *e = &boot_idt[vec];
> >>  
> >> diff --git a/lib/x86/desc.h b/lib/x86/desc.h
> >> index 0b4897c..f819452 100644
> >> --- a/lib/x86/desc.h
> >> +++ b/lib/x86/desc.h
> >> @@ -24,6 +24,41 @@ struct ex_regs {
> >>  unsigned long rflags;
> >>  };
> >>  
> >> +typedef struct {
> >> +  u16 prev;
> >> +  u16 res1;
> >> +  u32 esp0;
> >> +  u16 ss0;
> >> +  u16 res2;
> >> +  u32 esp1;
> >> +  u16 ss1;
> >> +  u16 res3;
> >> +  u32 esp2;
> >> +  u16 ss2;
> >> +  u16 res4;
> >> +  u32 cr3;
> >> +  u32 eip;
> >> +  u32 eflags;
> >> +  u32 eax, ecx, edx, ebx, esp, ebp, esi, edi;
> >> +  u16 es;
> >> +  u16 res5;
> >> +  u16 cs;
> >> +  u16 res6;
> >> +  u16 ss;
> >> +  u16 res7;
> >> +  u16 ds;
> >> +  u16 res8;
> >> +  u16 fs;
> >> +  u16 res9;
> >> +  u16 gs;
> >> +  u16 res10;
> >> +  u16 ldt;
> >> +  u16 res11;
> >> +  u16 t:1;
> >> +  u16 res12:15;
> >> +  u16 iomap_base;
> >> +} tss32_t;
> >> +
> >>  #define ASM_TRY(catch)  \
> >>  "movl $0, %%gs:4 \n\t"  \
> >>  ".pushsection .data.ex \n\t"\
> >> @@ -44,6 +79,7 @@ unsigned exception_error_code(void);
> >>  void set_idt_entry(int vec, void *addr, int dpl);
> >>  void set_idt_sel(int vec, u16 sel);
> >>  void set_gdt_entry(int num, u32 base,  u32 limit, u8 access, u8 gran);
> >> +void set_idt_task_gate(int vec, u16 sel);
> >>  void set_intr_task_gate(int e, void *fn);
> >>  void print_current_tss_info(void);
> >>  void handle_exception(u8 v, void (*func)(struct ex_regs *regs));
> >> diff --git a/lib/x86/vm.c b/lib/x86/vm.c
> >> index abbb0c9..aae044a 100644
> >> --- a/lib/x86/vm.c
> >> +++ b/lib/x86/vm.c
> >> @@ -108,14 +108,14 @@ void install_large_page(unsigned long *cr3,
> >>unsigned long phys,
> >>void *virt)
> >>  {
> >> -install_pte(cr3, 2,

Re: [PATCH kvm-unit-tests 4/4] x86/taskswitch_vm86: Task switches into/out of VM86

2012-01-23 Thread Kevin Wolf
Am 23.01.2012 17:10, schrieb Gleb Natapov:
> On Mon, Jan 23, 2012 at 05:07:13PM +0100, Kevin Wolf wrote:
>> This adds a test case that jumps into VM86 by iret-ing to a TSS and back
>> to Protected Mode using a task gate in the IDT.
>>
> Can you add the test case to taskswitch2.c?

That's actually what I intended to do at first, but there's nothing to
share and having a clean environment that can't interfere with other
tests feels nicer.

What would we gain from merging the files?

Kevin


> 
>> Signed-off-by: Kevin Wolf 
>> ---
>>  config-i386.mak   |3 +-
>>  lib/x86/desc.c|   37 +-
>>  lib/x86/desc.h|   36 +
>>  lib/x86/vm.c  |4 +-
>>  lib/x86/vm.h  |1 +
>>  x86/taskswitch_vm86.c |   59 
>> +
>>  x86/unittests.cfg |6 +
>>  7 files changed, 107 insertions(+), 39 deletions(-)
>>  create mode 100644 x86/taskswitch_vm86.c
>>
>> diff --git a/config-i386.mak b/config-i386.mak
>> index de52f3d..b5c3b9c 100644
>> --- a/config-i386.mak
>> +++ b/config-i386.mak
>> @@ -5,9 +5,10 @@ ldarch = elf32-i386
>>  CFLAGS += -D__i386__
>>  CFLAGS += -I $(KERNELDIR)/include
>>  
>> -tests = $(TEST_DIR)/taskswitch.flat $(TEST_DIR)/taskswitch2.flat
>> +tests = $(TEST_DIR)/taskswitch.flat $(TEST_DIR)/taskswitch2.flat 
>> $(TEST_DIR)/taskswitch_vm86.flat
>>  
>>  include config-x86-common.mak
>>  
>>  $(TEST_DIR)/taskswitch.elf: $(cstart.o) $(TEST_DIR)/taskswitch.o
>>  $(TEST_DIR)/taskswitch2.elf: $(cstart.o) $(TEST_DIR)/taskswitch2.o
>> +$(TEST_DIR)/taskswitch_vm86.elf: $(cstart.o) $(TEST_DIR)/taskswitch_vm86.o
>> diff --git a/lib/x86/desc.c b/lib/x86/desc.c
>> index 770c250..c4a3607 100644
>> --- a/lib/x86/desc.c
>> +++ b/lib/x86/desc.c
>> @@ -27,41 +27,6 @@ typedef struct {
>>  u8 base_high;
>>  } gdt_entry_t;
>>  
>> -typedef struct {
>> -u16 prev;
>> -u16 res1;
>> -u32 esp0;
>> -u16 ss0;
>> -u16 res2;
>> -u32 esp1;
>> -u16 ss1;
>> -u16 res3;
>> -u32 esp2;
>> -u16 ss2;
>> -u16 res4;
>> -u32 cr3;
>> -u32 eip;
>> -u32 eflags;
>> -u32 eax, ecx, edx, ebx, esp, ebp, esi, edi;
>> -u16 es;
>> -u16 res5;
>> -u16 cs;
>> -u16 res6;
>> -u16 ss;
>> -u16 res7;
>> -u16 ds;
>> -u16 res8;
>> -u16 fs;
>> -u16 res9;
>> -u16 gs;
>> -u16 res10;
>> -u16 ldt;
>> -u16 res11;
>> -u16 t:1;
>> -u16 res12:15;
>> -u16 iomap_base;
>> -} tss32_t;
>> -
>>  extern idt_entry_t boot_idt[256];
>>  
>>  void set_idt_entry(int vec, void *addr, int dpl)
>> @@ -327,7 +292,7 @@ void setup_gdt(void)
>>".Lflush2: "::"r"(0x10));
>>  }
>>  
>> -static void set_idt_task_gate(int vec, u16 sel)
>> +void set_idt_task_gate(int vec, u16 sel)
>>  {
>>  idt_entry_t *e = &boot_idt[vec];
>>  
>> diff --git a/lib/x86/desc.h b/lib/x86/desc.h
>> index 0b4897c..f819452 100644
>> --- a/lib/x86/desc.h
>> +++ b/lib/x86/desc.h
>> @@ -24,6 +24,41 @@ struct ex_regs {
>>  unsigned long rflags;
>>  };
>>  
>> +typedef struct {
>> +u16 prev;
>> +u16 res1;
>> +u32 esp0;
>> +u16 ss0;
>> +u16 res2;
>> +u32 esp1;
>> +u16 ss1;
>> +u16 res3;
>> +u32 esp2;
>> +u16 ss2;
>> +u16 res4;
>> +u32 cr3;
>> +u32 eip;
>> +u32 eflags;
>> +u32 eax, ecx, edx, ebx, esp, ebp, esi, edi;
>> +u16 es;
>> +u16 res5;
>> +u16 cs;
>> +u16 res6;
>> +u16 ss;
>> +u16 res7;
>> +u16 ds;
>> +u16 res8;
>> +u16 fs;
>> +u16 res9;
>> +u16 gs;
>> +u16 res10;
>> +u16 ldt;
>> +u16 res11;
>> +u16 t:1;
>> +u16 res12:15;
>> +u16 iomap_base;
>> +} tss32_t;
>> +
>>  #define ASM_TRY(catch)  \
>>  "movl $0, %%gs:4 \n\t"  \
>>  ".pushsection .data.ex \n\t"\
>> @@ -44,6 +79,7 @@ unsigned exception_error_code(void);
>>  void set_idt_entry(int vec, void *addr, int dpl);
>>  void set_idt_sel(int vec, u16 sel);
>>  void set_gdt_entry(int num, u32 base,  u32 limit, u8 access, u8 gran);
>> +void set_idt_task_gate(int vec, u16 sel);
>>  void set_intr_task_gate(int e, void *fn);
>>  void print_current_tss_info(void);
>>  void handle_exception(u8 v, void (*func)(struct ex_regs *regs));
>> diff --git a/lib/x86/vm.c b/lib/x86/vm.c
>> index abbb0c9..aae044a 100644
>> --- a/lib/x86/vm.c
>> +++ b/lib/x86/vm.c
>> @@ -108,14 +108,14 @@ void install_large_page(unsigned long *cr3,
>>unsigned long phys,
>>void *virt)
>>  {
>> -install_pte(cr3, 2, virt, phys | PTE_PRESENT | PTE_WRITE | PTE_PSE, 0);
>> +install_pte(cr3, 2, virt, phys | PTE_PRESENT | PTE_WRITE | PTE_USER | 
>> PTE_PSE, 0);
>>  }
>>  
>>  void install_page(unsigned long *cr3,
>>unsigned long phys,
>>void *virt)
>>  {
>> -install_pte(cr3, 1, virt, phys 

Re: [PATCH kvm-unit-tests 4/4] x86/taskswitch_vm86: Task switches into/out of VM86

2012-01-23 Thread Gleb Natapov
On Mon, Jan 23, 2012 at 05:07:13PM +0100, Kevin Wolf wrote:
> This adds a test case that jumps into VM86 by iret-ing to a TSS and back
> to Protected Mode using a task gate in the IDT.
> 
Can you add the test case to taskswitch2.c?

> Signed-off-by: Kevin Wolf 
> ---
>  config-i386.mak   |3 +-
>  lib/x86/desc.c|   37 +-
>  lib/x86/desc.h|   36 +
>  lib/x86/vm.c  |4 +-
>  lib/x86/vm.h  |1 +
>  x86/taskswitch_vm86.c |   59 
> +
>  x86/unittests.cfg |6 +
>  7 files changed, 107 insertions(+), 39 deletions(-)
>  create mode 100644 x86/taskswitch_vm86.c
> 
> diff --git a/config-i386.mak b/config-i386.mak
> index de52f3d..b5c3b9c 100644
> --- a/config-i386.mak
> +++ b/config-i386.mak
> @@ -5,9 +5,10 @@ ldarch = elf32-i386
>  CFLAGS += -D__i386__
>  CFLAGS += -I $(KERNELDIR)/include
>  
> -tests = $(TEST_DIR)/taskswitch.flat $(TEST_DIR)/taskswitch2.flat
> +tests = $(TEST_DIR)/taskswitch.flat $(TEST_DIR)/taskswitch2.flat 
> $(TEST_DIR)/taskswitch_vm86.flat
>  
>  include config-x86-common.mak
>  
>  $(TEST_DIR)/taskswitch.elf: $(cstart.o) $(TEST_DIR)/taskswitch.o
>  $(TEST_DIR)/taskswitch2.elf: $(cstart.o) $(TEST_DIR)/taskswitch2.o
> +$(TEST_DIR)/taskswitch_vm86.elf: $(cstart.o) $(TEST_DIR)/taskswitch_vm86.o
> diff --git a/lib/x86/desc.c b/lib/x86/desc.c
> index 770c250..c4a3607 100644
> --- a/lib/x86/desc.c
> +++ b/lib/x86/desc.c
> @@ -27,41 +27,6 @@ typedef struct {
>   u8 base_high;
>  } gdt_entry_t;
>  
> -typedef struct {
> - u16 prev;
> - u16 res1;
> - u32 esp0;
> - u16 ss0;
> - u16 res2;
> - u32 esp1;
> - u16 ss1;
> - u16 res3;
> - u32 esp2;
> - u16 ss2;
> - u16 res4;
> - u32 cr3;
> - u32 eip;
> - u32 eflags;
> - u32 eax, ecx, edx, ebx, esp, ebp, esi, edi;
> - u16 es;
> - u16 res5;
> - u16 cs;
> - u16 res6;
> - u16 ss;
> - u16 res7;
> - u16 ds;
> - u16 res8;
> - u16 fs;
> - u16 res9;
> - u16 gs;
> - u16 res10;
> - u16 ldt;
> - u16 res11;
> - u16 t:1;
> - u16 res12:15;
> - u16 iomap_base;
> -} tss32_t;
> -
>  extern idt_entry_t boot_idt[256];
>  
>  void set_idt_entry(int vec, void *addr, int dpl)
> @@ -327,7 +292,7 @@ void setup_gdt(void)
> ".Lflush2: "::"r"(0x10));
>  }
>  
> -static void set_idt_task_gate(int vec, u16 sel)
> +void set_idt_task_gate(int vec, u16 sel)
>  {
>  idt_entry_t *e = &boot_idt[vec];
>  
> diff --git a/lib/x86/desc.h b/lib/x86/desc.h
> index 0b4897c..f819452 100644
> --- a/lib/x86/desc.h
> +++ b/lib/x86/desc.h
> @@ -24,6 +24,41 @@ struct ex_regs {
>  unsigned long rflags;
>  };
>  
> +typedef struct {
> + u16 prev;
> + u16 res1;
> + u32 esp0;
> + u16 ss0;
> + u16 res2;
> + u32 esp1;
> + u16 ss1;
> + u16 res3;
> + u32 esp2;
> + u16 ss2;
> + u16 res4;
> + u32 cr3;
> + u32 eip;
> + u32 eflags;
> + u32 eax, ecx, edx, ebx, esp, ebp, esi, edi;
> + u16 es;
> + u16 res5;
> + u16 cs;
> + u16 res6;
> + u16 ss;
> + u16 res7;
> + u16 ds;
> + u16 res8;
> + u16 fs;
> + u16 res9;
> + u16 gs;
> + u16 res10;
> + u16 ldt;
> + u16 res11;
> + u16 t:1;
> + u16 res12:15;
> + u16 iomap_base;
> +} tss32_t;
> +
>  #define ASM_TRY(catch)  \
>  "movl $0, %%gs:4 \n\t"  \
>  ".pushsection .data.ex \n\t"\
> @@ -44,6 +79,7 @@ unsigned exception_error_code(void);
>  void set_idt_entry(int vec, void *addr, int dpl);
>  void set_idt_sel(int vec, u16 sel);
>  void set_gdt_entry(int num, u32 base,  u32 limit, u8 access, u8 gran);
> +void set_idt_task_gate(int vec, u16 sel);
>  void set_intr_task_gate(int e, void *fn);
>  void print_current_tss_info(void);
>  void handle_exception(u8 v, void (*func)(struct ex_regs *regs));
> diff --git a/lib/x86/vm.c b/lib/x86/vm.c
> index abbb0c9..aae044a 100644
> --- a/lib/x86/vm.c
> +++ b/lib/x86/vm.c
> @@ -108,14 +108,14 @@ void install_large_page(unsigned long *cr3,
>unsigned long phys,
>void *virt)
>  {
> -install_pte(cr3, 2, virt, phys | PTE_PRESENT | PTE_WRITE | PTE_PSE, 0);
> +install_pte(cr3, 2, virt, phys | PTE_PRESENT | PTE_WRITE | PTE_USER | 
> PTE_PSE, 0);
>  }
>  
>  void install_page(unsigned long *cr3,
>unsigned long phys,
>void *virt)
>  {
> -install_pte(cr3, 1, virt, phys | PTE_PRESENT | PTE_WRITE, 0);
> +install_pte(cr3, 1, virt, phys | PTE_PRESENT | PTE_WRITE | PTE_USER, 0);
>  }
>  
>  
> diff --git a/lib/x86/vm.h b/lib/x86/vm.h
> index bf8fd52..aebc5c3 100644
> --- a/lib/x86/vm.h
> +++ b/lib/x86/vm.h
> @@ -13,6 +13,7 @@
>  #define PTE_PRESENT (1ull << 0)
>  #define PTE_PSE (1ull << 7)
>  #define PTE_WRITE   

[PATCH kvm-unit-tests 4/4] x86/taskswitch_vm86: Task switches into/out of VM86

2012-01-23 Thread Kevin Wolf
This adds a test case that jumps into VM86 by iret-ing to a TSS and back
to Protected Mode using a task gate in the IDT.

Signed-off-by: Kevin Wolf 
---
 config-i386.mak   |3 +-
 lib/x86/desc.c|   37 +-
 lib/x86/desc.h|   36 +
 lib/x86/vm.c  |4 +-
 lib/x86/vm.h  |1 +
 x86/taskswitch_vm86.c |   59 +
 x86/unittests.cfg |6 +
 7 files changed, 107 insertions(+), 39 deletions(-)
 create mode 100644 x86/taskswitch_vm86.c

diff --git a/config-i386.mak b/config-i386.mak
index de52f3d..b5c3b9c 100644
--- a/config-i386.mak
+++ b/config-i386.mak
@@ -5,9 +5,10 @@ ldarch = elf32-i386
 CFLAGS += -D__i386__
 CFLAGS += -I $(KERNELDIR)/include
 
-tests = $(TEST_DIR)/taskswitch.flat $(TEST_DIR)/taskswitch2.flat
+tests = $(TEST_DIR)/taskswitch.flat $(TEST_DIR)/taskswitch2.flat 
$(TEST_DIR)/taskswitch_vm86.flat
 
 include config-x86-common.mak
 
 $(TEST_DIR)/taskswitch.elf: $(cstart.o) $(TEST_DIR)/taskswitch.o
 $(TEST_DIR)/taskswitch2.elf: $(cstart.o) $(TEST_DIR)/taskswitch2.o
+$(TEST_DIR)/taskswitch_vm86.elf: $(cstart.o) $(TEST_DIR)/taskswitch_vm86.o
diff --git a/lib/x86/desc.c b/lib/x86/desc.c
index 770c250..c4a3607 100644
--- a/lib/x86/desc.c
+++ b/lib/x86/desc.c
@@ -27,41 +27,6 @@ typedef struct {
u8 base_high;
 } gdt_entry_t;
 
-typedef struct {
-   u16 prev;
-   u16 res1;
-   u32 esp0;
-   u16 ss0;
-   u16 res2;
-   u32 esp1;
-   u16 ss1;
-   u16 res3;
-   u32 esp2;
-   u16 ss2;
-   u16 res4;
-   u32 cr3;
-   u32 eip;
-   u32 eflags;
-   u32 eax, ecx, edx, ebx, esp, ebp, esi, edi;
-   u16 es;
-   u16 res5;
-   u16 cs;
-   u16 res6;
-   u16 ss;
-   u16 res7;
-   u16 ds;
-   u16 res8;
-   u16 fs;
-   u16 res9;
-   u16 gs;
-   u16 res10;
-   u16 ldt;
-   u16 res11;
-   u16 t:1;
-   u16 res12:15;
-   u16 iomap_base;
-} tss32_t;
-
 extern idt_entry_t boot_idt[256];
 
 void set_idt_entry(int vec, void *addr, int dpl)
@@ -327,7 +292,7 @@ void setup_gdt(void)
  ".Lflush2: "::"r"(0x10));
 }
 
-static void set_idt_task_gate(int vec, u16 sel)
+void set_idt_task_gate(int vec, u16 sel)
 {
 idt_entry_t *e = &boot_idt[vec];
 
diff --git a/lib/x86/desc.h b/lib/x86/desc.h
index 0b4897c..f819452 100644
--- a/lib/x86/desc.h
+++ b/lib/x86/desc.h
@@ -24,6 +24,41 @@ struct ex_regs {
 unsigned long rflags;
 };
 
+typedef struct {
+   u16 prev;
+   u16 res1;
+   u32 esp0;
+   u16 ss0;
+   u16 res2;
+   u32 esp1;
+   u16 ss1;
+   u16 res3;
+   u32 esp2;
+   u16 ss2;
+   u16 res4;
+   u32 cr3;
+   u32 eip;
+   u32 eflags;
+   u32 eax, ecx, edx, ebx, esp, ebp, esi, edi;
+   u16 es;
+   u16 res5;
+   u16 cs;
+   u16 res6;
+   u16 ss;
+   u16 res7;
+   u16 ds;
+   u16 res8;
+   u16 fs;
+   u16 res9;
+   u16 gs;
+   u16 res10;
+   u16 ldt;
+   u16 res11;
+   u16 t:1;
+   u16 res12:15;
+   u16 iomap_base;
+} tss32_t;
+
 #define ASM_TRY(catch)  \
 "movl $0, %%gs:4 \n\t"  \
 ".pushsection .data.ex \n\t"\
@@ -44,6 +79,7 @@ unsigned exception_error_code(void);
 void set_idt_entry(int vec, void *addr, int dpl);
 void set_idt_sel(int vec, u16 sel);
 void set_gdt_entry(int num, u32 base,  u32 limit, u8 access, u8 gran);
+void set_idt_task_gate(int vec, u16 sel);
 void set_intr_task_gate(int e, void *fn);
 void print_current_tss_info(void);
 void handle_exception(u8 v, void (*func)(struct ex_regs *regs));
diff --git a/lib/x86/vm.c b/lib/x86/vm.c
index abbb0c9..aae044a 100644
--- a/lib/x86/vm.c
+++ b/lib/x86/vm.c
@@ -108,14 +108,14 @@ void install_large_page(unsigned long *cr3,
   unsigned long phys,
   void *virt)
 {
-install_pte(cr3, 2, virt, phys | PTE_PRESENT | PTE_WRITE | PTE_PSE, 0);
+install_pte(cr3, 2, virt, phys | PTE_PRESENT | PTE_WRITE | PTE_USER | 
PTE_PSE, 0);
 }
 
 void install_page(unsigned long *cr3,
   unsigned long phys,
   void *virt)
 {
-install_pte(cr3, 1, virt, phys | PTE_PRESENT | PTE_WRITE, 0);
+install_pte(cr3, 1, virt, phys | PTE_PRESENT | PTE_WRITE | PTE_USER, 0);
 }
 
 
diff --git a/lib/x86/vm.h b/lib/x86/vm.h
index bf8fd52..aebc5c3 100644
--- a/lib/x86/vm.h
+++ b/lib/x86/vm.h
@@ -13,6 +13,7 @@
 #define PTE_PRESENT (1ull << 0)
 #define PTE_PSE (1ull << 7)
 #define PTE_WRITE   (1ull << 1)
+#define PTE_USER(1ull << 2)
 #define PTE_ADDR(0xff000ull)
 
 void setup_vm();
diff --git a/x86/taskswitch_vm86.c b/x86/taskswitch_vm86.c
new file mode 100644
index 000..363cb00
--- /dev/null
+++ b/x86/taskswitch_vm86.c
@@ -0,0 +1,59 @@
+#include "libcflat.h"
+#include "desc.h"
+#inclu