hax: fix compiliation errors on Windows
[sdk/emulator/qemu.git] / target-i386 / hax-all.c
1 /*
2  * QEMU KVM support
3  *
4  * Copyright IBM, Corp. 2008
5  *           Red Hat, Inc. 2008
6  *
7  * Authors:
8  *  Anthony Liguori   <aliguori@us.ibm.com>
9  *  Glauber Costa     <gcosta@redhat.com>
10  *
11  * Copyright (c) 2011 Intel Corporation
12  *  Written by:
13  *  Jiang Yunhong<yunhong.jiang@intel.com>
14  *  Xin Xiaohui<xiaohui.xin@intel.com>
15  *  Zhang Xiantao<xiantao.zhang@intel.com>
16  *
17  * This work is licensed under the terms of the GNU GPL, version 2 or later.
18  * See the COPYING file in the top-level directory.
19  *
20  */
21
22 /*
23  * HAX common code for both windows and darwin
24  * some code from KVM side
25  */
26
27 #include "strings.h"
28 #include "hax-i386.h"
29 #include "sysemu/kvm.h"
30 #include "exec/address-spaces.h"
31 #include "qemu/main-loop.h"
32
33 #define HAX_EMUL_ONE    0x1
34 #define HAX_EMUL_REAL   0x2
35 #define HAX_EMUL_HLT    0x4
36 #define HAX_EMUL_EXITLOOP    0x5
37
38 #define HAX_EMULATE_STATE_MMIO  0x1
39 #define HAX_EMULATE_STATE_REAL  0x2
40 #define HAX_EMULATE_STATE_NONE  0x3
41 #define HAX_EMULATE_STATE_INITIAL       0x4
42
43 struct hax_state hax_global;
44 int ret_hax_init = 0;
45 static int hax_disabled = 1;
46
47 int hax_support = -1;
48
49 /* Called after hax_init */
50 int hax_enabled(void)
51 {
52     return (!hax_disabled && hax_support);
53 }
54
55 void hax_disable(int disable)
56 {
57     hax_disabled = disable;
58 }
59
60 /* Currently non-PG modes are emulated by QEMU */
61 int hax_vcpu_emulation_mode(CPUArchState *env)
62 {
63     // Tcg is single-thread, so we need haxm to run smp.
64     // If the host has no UG, we always run tcg.
65
66     if (hax_enabled())
67         return 0;
68     else
69         return 1;
70 }
71
72 static int hax_prepare_emulation(CPUArchState *env)
73 {
74     /* Flush all emulation states */
75     tlb_flush(ENV_GET_CPU(env), 1);
76     tb_flush(env);
77     /* Sync the vcpu state from hax kernel module */
78     hax_vcpu_sync_state(env, 0);
79     return 0;
80 }
81
82 /*
83  * Check whether to break the translation block loop
84  * break tbloop after one MMIO emulation, or after finish emulation mode
85  */
86 static int hax_stop_tbloop(CPUArchState *env)
87 {
88     CPUState *cpu = ENV_GET_CPU(env);
89     switch (cpu->hax_vcpu->emulation_state)
90     {
91     case HAX_EMULATE_STATE_MMIO:
92         if (cpu->hax_vcpu->resync) {
93             hax_prepare_emulation(env);     
94             cpu->hax_vcpu->resync = 0;
95             return 0;
96         }
97         return 1;
98         break;
99     case HAX_EMULATE_STATE_INITIAL:
100     case HAX_EMULATE_STATE_REAL:
101         if (!hax_vcpu_emulation_mode(env))
102             return 1;
103         break;
104     default:
105         dprint("Invalid emulation state in hax_sto_tbloop state %x\n",
106         cpu->hax_vcpu->emulation_state);
107         break;
108     }
109
110     return 0;
111 }
112
113 int hax_stop_emulation(CPUArchState *env)
114 {
115     CPUState *cpu = ENV_GET_CPU(env);
116     if (hax_stop_tbloop(env))
117     {
118         cpu->hax_vcpu->emulation_state =  HAX_EMULATE_STATE_NONE;
119         /*
120          * QEMU emulation changes vcpu state,
121          * Sync the vcpu state to HAX kernel module
122          */
123         hax_vcpu_sync_state(env, 1);
124         return 1;
125     }
126
127     return 0;
128 }
129
130 int hax_stop_translate(CPUArchState *env)
131 {
132     struct hax_vcpu_state *vstate;
133
134     vstate = ENV_GET_CPU(env)->hax_vcpu;
135     assert(vstate->emulation_state);
136     if (vstate->emulation_state == HAX_EMULATE_STATE_MMIO )
137         return 1;
138
139     return 0;
140 }
141
142 int valid_hax_tunnel_size(uint16_t size)
143 {
144     return size >= sizeof(struct hax_tunnel);
145 }
146
147 hax_fd hax_vcpu_get_fd(CPUArchState *env)
148 {
149     struct hax_vcpu_state *vcpu = ENV_GET_CPU(env)->hax_vcpu;
150     if (!vcpu)
151         return HAX_INVALID_FD;
152     return vcpu->fd;
153 }
154
155 /* Current version */
156 uint32_t hax_cur_version = 0x2; // ver 2.0: support fast mmio
157 /* Least HAX kernel version */
158 uint32_t hax_lest_version = 0x1;
159
160 static int hax_get_capability(struct hax_state *hax)
161 {
162     int ret;
163     struct hax_capabilityinfo capinfo, *cap = &capinfo;
164
165     ret = hax_capability(hax, cap);
166     if (ret)
167         return ret;
168
169     if ( ((cap->wstatus & HAX_CAP_WORKSTATUS_MASK) ==
170         HAX_CAP_STATUS_NOTWORKING ))
171     {
172         if (cap->winfo & HAX_CAP_FAILREASON_VT)
173             dprint("VTX feature is not enabled. which will cause HAX driver not working.\n");
174         else if (cap->winfo & HAX_CAP_FAILREASON_NX)
175             dprint("NX feature is not enabled, which will cause HAX driver not working.\n");
176         return -ENXIO;
177     }
178
179     if (!(cap->winfo & HAX_CAP_UG))
180     {
181         dprint("UG feature is not available on platform needed to support HAXM.\n");
182         return -ENXIO;
183     }
184
185     if (cap->wstatus & HAX_CAP_MEMQUOTA)
186     {
187         if (cap->mem_quota < hax->mem_quota)
188         {
189             dprint("The memory needed by this VM exceeds the driver limit.\n");
190             return -ENOSPC;
191         }
192     }
193     return 0;
194 }
195
196 static int hax_version_support(struct hax_state *hax)
197 {
198     int ret;
199     struct hax_module_version version;
200
201     ret = hax_mod_version(hax, &version);
202     if (ret < 0)
203         return 0;
204
205     if ( (hax_lest_version > version.cur_version) ||
206          (hax_cur_version < version.compat_version) )
207         return 0;
208
209     return 1;
210 }
211
212 int hax_vcpu_create(int id)
213 {
214     struct hax_vcpu_state *vcpu = NULL;
215     int ret;
216
217     if (!hax_global.vm)
218     {
219         dprint("vcpu %x created failed, vm is null\n", id);
220         return -1;
221     }
222
223     if (hax_global.vm->vcpus[id])
224     {
225         dprint("vcpu %x allocated already\n", id);
226         return 0;
227     }
228
229     vcpu = g_malloc(sizeof(struct hax_vcpu_state));
230     if (!vcpu)
231     {
232         dprint("Failed to alloc vcpu state\n");
233         return -ENOMEM;
234     }
235
236     memset(vcpu, 0, sizeof(struct hax_vcpu_state));
237
238     ret = hax_host_create_vcpu(hax_global.vm->fd, id);
239     if (ret)
240     {
241         dprint("Failed to create vcpu %x\n", id);
242         goto error;
243     }
244
245     vcpu->vcpu_id = id;
246     vcpu->fd = hax_host_open_vcpu(hax_global.vm->id, id);
247     if (hax_invalid_fd(vcpu->fd))
248     {
249         dprint("Failed to open the vcpu\n");
250         ret = -ENODEV;
251         goto error;
252     }
253
254     hax_global.vm->vcpus[id] = vcpu;
255
256     ret = hax_host_setup_vcpu_channel(vcpu);
257     if (ret)
258     {
259         dprint("Invalid hax tunnel size \n");
260         ret = -EINVAL;
261         goto error;
262     }
263     return 0;
264
265 error:
266     /* vcpu and tunnel will be closed automatically */
267     if (vcpu && !hax_invalid_fd(vcpu->fd))
268         hax_close_fd(vcpu->fd);
269
270     hax_global.vm->vcpus[id] = NULL;
271     g_free(vcpu);
272     return -1;
273 }
274
275 int hax_vcpu_destroy(CPUArchState *env)
276 {
277     struct hax_vcpu_state *vcpu = ENV_GET_CPU(env)->hax_vcpu;
278
279     if (!hax_global.vm)
280     {
281         dprint("vcpu %x destroy failed, vm is null\n", vcpu->vcpu_id);
282         return -1;
283     }
284
285     if (!vcpu)
286         return 0;
287
288     /*
289      * 1. The hax_tunnel is also destroied when vcpu destroy
290      * 2. close fd will cause hax module vcpu be cleaned
291      */
292     hax_close_fd(vcpu->fd);
293     hax_global.vm->vcpus[vcpu->vcpu_id] = NULL;
294     g_free(vcpu);
295     return 0;
296 }
297
298 int hax_init_vcpu(CPUArchState *env)
299 {
300     int ret;
301     CPUState *cpu = ENV_GET_CPU(env);
302
303     ret = hax_vcpu_create(cpu->cpu_index);
304     if (ret < 0)
305     {
306         dprint("Failed to create HAX vcpu\n");
307         exit(-1);
308     }
309
310     cpu->hax_vcpu = hax_global.vm->vcpus[cpu->cpu_index];
311     cpu->hax_vcpu->emulation_state = HAX_EMULATE_STATE_INITIAL;
312     cpu->hax_vcpu_dirty = 1;
313     qemu_register_reset(hax_reset_vcpu_state, env);
314
315     return ret;
316 }
317
318 struct hax_vm *hax_vm_create(struct hax_state *hax)
319 {
320     struct hax_vm *vm;
321     int vm_id = 0, ret;
322     char *vm_name = NULL;
323
324     if (hax_invalid_fd(hax->fd))
325         return NULL;
326
327     if (hax->vm)
328         return hax->vm;
329
330     vm = g_malloc(sizeof(struct hax_vm));
331     if (!vm)
332         return NULL;
333     memset(vm, 0, sizeof(struct hax_vm));
334     ret = hax_host_create_vm(hax, &vm_id);
335     if (ret) {
336         dprint("Failed to create vm %x\n", ret);
337         goto error;
338     }
339     vm->id = vm_id;
340     vm->fd = hax_host_open_vm(hax, vm_id);
341     if (hax_invalid_fd(vm->fd))
342     {
343         dprint("Open the vm devcie error:%s\n", vm_name);
344         goto error;
345     }
346
347     hax->vm = vm;
348     dprint("End of VM create, id %d\n", vm->id);
349     return vm;
350
351 error:
352     g_free(vm);
353     hax->vm = NULL;
354     return NULL;
355 }
356
357 int hax_vm_destroy(struct hax_vm *vm)
358 {
359     int i;
360
361     for (i = 0; i < HAX_MAX_VCPU; i++)
362         if (vm->vcpus[i])
363         {
364             dprint("VCPU should be cleaned before vm clean\n");
365             return -1;
366         }
367     hax_close_fd(vm->fd);
368     g_free(vm);
369     hax_global.vm = NULL;
370     return 0;
371 }
372
373 static void
374 hax_region_add(MemoryListener *listener, MemoryRegionSection *section)
375 {
376     hax_set_phys_mem(section);
377 }
378
379 static void
380 hax_region_del(MemoryListener *listener, MemoryRegionSection *section)
381 {
382     hax_set_phys_mem(section);
383 }
384
385
386 /* currently we fake the dirty bitmap sync, always dirty */
387 // avoid implicit declaration warning on Windows
388 int ffsl(long value);
389 static void hax_log_sync(MemoryListener *listener, MemoryRegionSection *section)
390 {
391     MemoryRegion *mr = section->mr;
392     unsigned long c;
393     unsigned int len = ((int128_get64(section->size) / TARGET_PAGE_SIZE) + HOST_LONG_BITS - 1) /
394                         HOST_LONG_BITS;
395     unsigned long bitmap[len];
396     int i, j;
397
398     for (i = 0; i < len; i++) {
399         bitmap[i] = 1;
400         c = leul_to_cpu(bitmap[i]);
401         do {
402             j = ffsl(c) - 1;
403             c &= ~(1ul << j);
404             memory_region_set_dirty(mr, (i * HOST_LONG_BITS + j) *
405                 TARGET_PAGE_SIZE, TARGET_PAGE_SIZE);
406         } while (c != 0);
407     }
408 }
409
410 static void hax_log_global_start(struct MemoryListener *listener)
411 {
412 }
413
414 static void hax_log_global_stop(struct MemoryListener *listener)
415 {
416 }
417
418 static void hax_log_start(MemoryListener *listener,
419                            MemoryRegionSection *section)
420 {
421 }
422
423 static void hax_log_stop(MemoryListener *listener,
424                           MemoryRegionSection *section)
425 {
426 }
427
428 static void hax_begin(MemoryListener *listener)
429 {
430 }
431
432 static void hax_commit(MemoryListener *listener)
433 {
434 }
435
436 static void hax_region_nop(MemoryListener *listener,
437                         MemoryRegionSection *section)
438 {
439 }
440
441 static MemoryListener hax_memory_listener = {
442     .begin = hax_begin,
443     .commit = hax_commit,
444     .region_add = hax_region_add,
445     .region_del = hax_region_del,
446     .region_nop = hax_region_nop,
447     .log_start = hax_log_start,
448     .log_stop = hax_log_stop,
449     .log_sync = hax_log_sync,
450     .log_global_start = hax_log_global_start,
451     .log_global_stop = hax_log_global_stop,
452 };
453
454 static void hax_handle_interrupt(CPUState *cpu, int mask)
455 {
456     cpu->interrupt_request |= mask;
457
458     if (!qemu_cpu_is_self(cpu)) {
459         qemu_cpu_kick(cpu);
460     }
461 }
462
463 int hax_pre_init(uint64_t ram_size)
464 {
465     struct hax_state *hax = NULL;
466
467     dprint("hax_disabled %d\n", hax_disabled);
468     if (hax_disabled)
469         return 0;
470     hax = &hax_global;
471     memset(hax, 0, sizeof(struct hax_state));
472     hax->mem_quota = ram_size;
473     dprint("ram_size %lx\n", ram_size);
474
475     return 0;
476 }
477
478 static int hax_init(void)
479 {
480     struct hax_state *hax = NULL;
481     struct hax_qemu_version qversion;
482     int ret;
483
484     hax_support = 0;
485
486     hax = &hax_global;
487
488
489     hax->fd = hax_mod_open();
490     if (hax_invalid_fd(hax->fd))
491     {
492         hax->fd = 0;
493         ret = -ENODEV;
494         goto error;
495     }
496
497     ret = hax_get_capability(hax);
498
499     if (ret)
500     {
501         if (ret != -ENOSPC)
502             ret = -EINVAL;
503         goto error;
504     }
505
506     if (!hax_version_support(hax))
507     {
508         dprint("Incompat Hax version. Qemu current version %x ", hax_cur_version );
509         dprint("requires least HAX version %x\n", hax_lest_version);
510         ret = -EINVAL;
511         goto error;
512     }
513
514     hax->vm = hax_vm_create(hax);
515     if (!hax->vm)
516     {
517         dprint("Failed to create HAX VM\n");
518         ret = -EINVAL;
519         goto error;
520     }
521
522     memory_listener_register(&hax_memory_listener, &address_space_memory);
523
524     qversion.cur_version = hax_cur_version;
525     qversion.least_version = hax_lest_version;
526     hax_notify_qemu_version(hax->vm->fd, &qversion);
527     cpu_interrupt_handler = hax_handle_interrupt;
528     hax_support = 1;
529
530     return ret;
531 error:
532     if (hax->vm)
533         hax_vm_destroy(hax->vm);
534     if (hax->fd)
535         hax_mod_close(hax);
536
537     return ret;
538 }
539
540 int hax_accel_init(void)
541 {
542     if (hax_disabled) {
543         dprint("HAX is disabled and emulator runs in emulation mode.\n");
544         return 0;
545     }
546
547     ret_hax_init = hax_init();
548     if (ret_hax_init && (ret_hax_init != -ENOSPC)) {
549         dprint("No accelerator found.\n");
550         return ret_hax_init;
551     } else {
552         dprint("HAX is %s and emulator runs in %s mode.\n",
553         !ret_hax_init ? "working" : "not working",
554         !ret_hax_init ? "fast virt" : "emulation");
555         return 0;
556     }
557 }
558
559 int hax_handle_fastmmio(CPUArchState *env, struct hax_fastmmio *hft)
560 {
561     uint64_t buf = 0;
562     /*
563      * With fast MMIO, QEMU need not sync vCPU state with HAXM
564      * driver because it will only invoke MMIO handler
565      * However, some MMIO operations utilize virtual address like qemu_pipe
566      * Thus we need to sync the CR0, CR3 and CR4 so that QEMU
567      * can translate the guest virtual address to guest physical
568      * address
569      */
570     env->cr[0] = hft->_cr0;
571     env->cr[2] = hft->_cr2;
572     env->cr[3] = hft->_cr3;
573     env->cr[4] = hft->_cr4;
574
575     buf = hft->value;
576
577     cpu_physical_memory_rw(hft->gpa, (uint8_t *)&buf, hft->size, hft->direction);
578     if (hft->direction == 0)
579         hft->value = buf;
580
581     return 0;
582 }
583
584 int hax_handle_io(CPUArchState *env, uint32_t df, uint16_t port, int direction,
585   int size, int count, void *buffer)
586 {
587     uint8_t *ptr;
588     int i;
589
590     if (!df)
591         ptr = (uint8_t *)buffer;
592     else
593         ptr = buffer + size * count - size;
594     for (i = 0; i < count; i++)
595     {
596         if (direction == HAX_EXIT_IO_IN) {
597             switch (size) {
598                 case 1:
599                     stb_p(ptr, cpu_inb(port));
600                     break;
601                 case 2:
602                     stw_p(ptr, cpu_inw(port));
603                     break;
604                 case 4:
605                     stl_p(ptr, cpu_inl(port));
606                     break;
607             }
608         } else {
609             switch (size) {
610                 case 1:
611                     cpu_outb(port, ldub_p(ptr));
612                     break;
613                 case 2:
614                     cpu_outw(port, lduw_p(ptr));
615                     break;
616                 case 4:
617                     cpu_outl(port, ldl_p(ptr));
618                     break;
619             }
620         }
621         if (!df)
622             ptr += size;
623         else
624             ptr -= size;
625     }
626
627     return 0;
628 }
629
630 static int hax_vcpu_interrupt(CPUArchState *env)
631 {
632     CPUState *cpu = ENV_GET_CPU(env);
633     struct hax_vcpu_state *vcpu = cpu->hax_vcpu;
634     struct hax_tunnel *ht = vcpu->tunnel;
635
636     /*
637      * Try to inject an interrupt if the guest can accept it
638      * Unlike KVM, HAX kernel check for the eflags, instead of qemu
639      */
640     if (ht->ready_for_interrupt_injection /*&&
641       (cpu->interrupt_request & CPU_INTERRUPT_HARD)*/)
642     {
643         int irq;
644
645         cpu->interrupt_request &= ~CPU_INTERRUPT_HARD;
646         irq = cpu_get_pic_interrupt(env);
647         if (irq >= 0) {
648             hax_inject_interrupt(env, irq);
649         }
650     }
651
652     /* If we have an interrupt but the guest is not ready to receive an
653      * interrupt, request an interrupt window exit.  This will
654      * cause a return to userspace as soon as the guest is ready to
655      * receive interrupts. */
656     if ((cpu->interrupt_request & CPU_INTERRUPT_HARD))
657         ht->request_interrupt_window = 1;
658     else
659         ht->request_interrupt_window = 0;
660     return 0;
661 }
662
663 void hax_raise_event(CPUArchState *env)
664 {
665     struct hax_vcpu_state *vcpu = ENV_GET_CPU(env)->hax_vcpu;
666
667     if (!vcpu)
668         return;
669     vcpu->tunnel->user_event_pending = 1;
670 }
671
672 /*
673  * Ask hax kernel module to run the CPU for us till:
674  * 1. Guest crash or shutdown
675  * 2. Need QEMU's emulation like guest execute MMIO instruction or guest
676  *    enter emulation mode (non-PG mode)
677  * 3. Guest execute HLT
678  * 4. Qemu have Signal/event pending
679  * 5. An unknown VMX exit happens
680  */
681 extern void qemu_system_reset_request(void);
682 static int hax_vcpu_hax_exec(CPUArchState *env)
683 {
684     int ret = 0;
685     CPUState *cpu = ENV_GET_CPU(env);
686     X86CPU *x86_cpu = X86_CPU(cpu);
687     struct hax_vcpu_state *vcpu = cpu->hax_vcpu;
688     struct hax_tunnel *ht = vcpu->tunnel;
689
690     if (hax_vcpu_emulation_mode(env))
691     {
692         dprint("Trying to vcpu execute at eip:%lx\n", env->eip);
693         return  HAX_EMUL_EXITLOOP;
694     }
695
696     if (cpu->interrupt_request & CPU_INTERRUPT_INIT) {
697         fprintf(stderr, "\nhax_vcpu_hax_exec: handling INIT for %d \n", cpu->cpu_index);
698         do_cpu_init(x86_cpu);
699         hax_vcpu_sync_state(env, 1);
700     }
701     if (cpu->interrupt_request & CPU_INTERRUPT_SIPI) {
702         fprintf(stderr, "hax_vcpu_hax_exec: handling SIPI for %d \n", cpu->cpu_index);
703         hax_vcpu_sync_state(env, 0);
704         do_cpu_sipi(x86_cpu);
705         hax_vcpu_sync_state(env, 1);
706     }
707
708     //hax_cpu_synchronize_state(env);
709
710     do {
711         int hax_ret;
712
713         if (cpu->exit_request) {
714             ret = HAX_EMUL_EXITLOOP ;
715             break;
716         }
717
718 #if 0
719         if (env->hax_vcpu_dirty) {
720                 hax_vcpu_sync_state(env, 1);
721                 env->hax_vcpu_dirty = 0;
722         }
723 #endif
724
725         hax_vcpu_interrupt(env);
726         qemu_mutex_unlock_iothread();
727         hax_ret = hax_vcpu_run(vcpu);
728         qemu_mutex_lock_iothread();
729
730 #ifdef CONFIG_DARWIN
731         current_cpu = cpu;
732 #endif
733         /* Simply continue the vcpu_run if system call interrupted */
734         if (hax_ret == -EINTR || hax_ret == -EAGAIN) {
735             dprint("io window interrupted\n");
736             continue;
737         }
738
739         if (hax_ret < 0)
740         {
741             dprint("vcpu run failed for vcpu  %x\n", vcpu->vcpu_id);
742             abort();
743         }
744         switch (ht->_exit_status)
745         {
746             case HAX_EXIT_IO:
747                 {
748                       ret = hax_handle_io(env, ht->pio._df, ht->pio._port,
749                       ht->pio._direction,
750                       ht->pio._size, ht->pio._count, vcpu->iobuf);
751                 }
752                 break;
753             case HAX_EXIT_MMIO:
754                 ret = HAX_EMUL_ONE;
755                 break;
756             case HAX_EXIT_FAST_MMIO:
757                 ret = hax_handle_fastmmio(env,
758                         (struct hax_fastmmio *)vcpu->iobuf);
759                 break;
760             case HAX_EXIT_REAL:
761                 ret = HAX_EMUL_REAL;
762                 break;
763                 /* Guest state changed, currently only for shutdown */
764             case HAX_EXIT_STATECHANGE:
765                 dprint("VCPU shutdown request\n");
766                 qemu_system_reset_request();
767                 hax_prepare_emulation(env);
768                 cpu_dump_state(cpu, stderr, fprintf, 0);
769                 ret = HAX_EMUL_EXITLOOP;
770                 break;
771             case HAX_EXIT_UNKNOWN_VMEXIT:
772                 dprint("Unknown VMX exit %x from guest\n", ht->_exit_reason);
773                 qemu_system_reset_request();
774                 hax_prepare_emulation(env);
775                 cpu_dump_state(cpu, stderr, fprintf, 0);
776                 ret = HAX_EMUL_EXITLOOP;
777                 break;
778             case HAX_EXIT_HLT:
779                 if (!(cpu->interrupt_request & CPU_INTERRUPT_HARD) &&
780                   !(cpu->interrupt_request & CPU_INTERRUPT_NMI)) {
781                     /* hlt instruction with interrupt disabled is shutdown */
782                     env->eflags |= IF_MASK;
783                     cpu->halted = 1;
784                     cpu->exception_index = EXCP_HLT;
785                     ret = HAX_EMUL_HLT;
786                 }
787                 break;
788                 /* these situation will continue to hax module */
789             case HAX_EXIT_INTERRUPT:
790             case HAX_EXIT_PAUSED:
791                 break;
792             default:
793                 dprint("Unknow exit %x from hax\n", ht->_exit_status);
794                 qemu_system_reset_request();
795                 hax_prepare_emulation(env);
796                 cpu_dump_state(cpu, stderr, fprintf, 0);
797                 ret = HAX_EMUL_EXITLOOP;
798                 break;
799         }
800     }while (!ret);
801
802     if (cpu->exit_request) {
803         cpu->exit_request = 0;
804         cpu->exception_index = EXCP_INTERRUPT;
805     }
806     return ret;
807 }
808
809 #if 0
810 static void do_hax_cpu_synchronize_state(void *_env)
811 {
812     CPUArchState *env = _env;
813     CPUState *cpu = ENV_GET_CPU(env);
814     if (!cpu->hax_vcpu_dirty) {
815         hax_vcpu_sync_state(env, 0);
816         cpu->hax_vcpu_dirty = 1;
817     }
818 }
819
820 void hax_cpu_synchronize_state(CPUState *cpu)
821 {
822     if (!cpu->hax_vcpu_dirty) {
823         run_on_cpu(cpu, do_hax_cpu_synchronize_state, cpu);
824     }
825 }
826 #endif
827
828 void hax_cpu_synchronize_post_reset(CPUArchState *env)
829 {
830     hax_vcpu_sync_state(env, 1);
831     ENV_GET_CPU(env)->hax_vcpu_dirty = 0;
832 }
833
834 void hax_cpu_synchronize_post_init(CPUArchState *env)
835 {
836     hax_vcpu_sync_state(env, 1);
837     ENV_GET_CPU(env)->hax_vcpu_dirty = 0;
838 }
839
840 /*
841  * return 1 when need emulate, 0 when need exit loop
842  */
843 int hax_vcpu_exec(CPUArchState *env)
844 {
845     int next = 0, ret = 0;
846     struct hax_vcpu_state *vcpu;
847     CPUState *cpu = ENV_GET_CPU(env);
848
849     if (cpu->hax_vcpu->emulation_state != HAX_EMULATE_STATE_NONE)
850         return 1;
851
852     vcpu = cpu->hax_vcpu;
853     next = hax_vcpu_hax_exec(env);
854     switch (next)
855     {
856         case HAX_EMUL_ONE:
857             ret = 1;
858             vcpu->emulation_state = HAX_EMULATE_STATE_MMIO;
859             hax_prepare_emulation(env);
860             break;
861         case HAX_EMUL_REAL:
862             ret = 1;
863             vcpu->emulation_state =
864               HAX_EMULATE_STATE_REAL;
865             hax_prepare_emulation(env);
866             break;
867         case HAX_EMUL_HLT:
868         case HAX_EMUL_EXITLOOP:
869             break;
870         default:
871             dprint("Unknown hax vcpu exec return %x\n", next);
872             abort();
873     }
874
875     return ret;
876 }
877
878 int hax_smp_cpu_exec(CPUArchState *env)
879 {
880     CPUState *cpu = ENV_GET_CPU(env);
881     int why;
882     int ret;
883
884     while (1) {
885         if (cpu->exception_index >= EXCP_INTERRUPT) {
886             ret = cpu->exception_index;
887             cpu->exception_index = -1;
888             break;
889         }
890
891         why = hax_vcpu_hax_exec(env);
892
893         if ((why != HAX_EMUL_HLT) && (why != HAX_EMUL_EXITLOOP))
894         {
895             dprint("Unknown hax vcpu return %x\n", why);
896             abort();
897         }
898     }
899
900     return ret;
901 }
902
903 #define HAX_RAM_INFO_ROM 0x1
904
905 static void set_v8086_seg(struct segment_desc_t *lhs, const SegmentCache *rhs)
906 {
907     memset(lhs, 0, sizeof(struct segment_desc_t ));
908     lhs->selector = rhs->selector;
909     lhs->base = rhs->base;
910     lhs->limit = rhs->limit;
911     lhs->type = 3;
912     lhs->present = 1;
913     lhs->dpl = 3;
914     lhs->operand_size = 0;
915     lhs->desc = 1;
916     lhs->long_mode = 0;
917     lhs->granularity = 0;
918     lhs->available = 0;
919 }
920
921 static void get_seg(SegmentCache *lhs, const struct segment_desc_t *rhs)
922 {
923     lhs->selector = rhs->selector;
924     lhs->base = rhs->base;
925     lhs->limit = rhs->limit;
926     lhs->flags =
927       (rhs->type << DESC_TYPE_SHIFT)
928       | (rhs->present * DESC_P_MASK)
929       | (rhs->dpl << DESC_DPL_SHIFT)
930       | (rhs->operand_size << DESC_B_SHIFT)
931       | (rhs->desc * DESC_S_MASK)
932       | (rhs->long_mode << DESC_L_SHIFT)
933       | (rhs->granularity * DESC_G_MASK)
934       | (rhs->available * DESC_AVL_MASK);
935 }
936
937 static void set_seg(struct segment_desc_t *lhs, const SegmentCache *rhs)
938 {
939     unsigned flags = rhs->flags;
940
941     memset(lhs, 0, sizeof(struct segment_desc_t));
942     lhs->selector = rhs->selector;
943     lhs->base = rhs->base;
944     lhs->limit = rhs->limit;
945     lhs->type = (flags >> DESC_TYPE_SHIFT) & 15;
946     lhs->present = (flags & DESC_P_MASK) != 0;
947     lhs->dpl = rhs->selector & 3;
948     lhs->operand_size = (flags >> DESC_B_SHIFT) & 1;
949     lhs->desc = (flags & DESC_S_MASK) != 0;
950     lhs->long_mode = (flags >> DESC_L_SHIFT) & 1;
951     lhs->granularity = (flags & DESC_G_MASK) != 0;
952     lhs->available = (flags & DESC_AVL_MASK) != 0;
953 }
954
955 static void hax_getput_reg(uint64_t *hax_reg, target_ulong *qemu_reg, int set)
956 {
957     target_ulong reg = *hax_reg;
958
959     if (set)
960         *hax_reg = *qemu_reg;
961     else
962         *qemu_reg = reg;
963 }
964
965 /* The sregs has been synced with HAX kernel already before this call */
966 static int hax_get_segments(CPUArchState *env, struct vcpu_state_t *sregs)
967 {
968     get_seg(&env->segs[R_CS], &sregs->_cs);
969     get_seg(&env->segs[R_DS], &sregs->_ds);
970     get_seg(&env->segs[R_ES], &sregs->_es);
971     get_seg(&env->segs[R_FS], &sregs->_fs);
972     get_seg(&env->segs[R_GS], &sregs->_gs);
973     get_seg(&env->segs[R_SS], &sregs->_ss);
974
975     get_seg(&env->tr, &sregs->_tr);
976     get_seg(&env->ldt, &sregs->_ldt);
977     env->idt.limit = sregs->_idt.limit;
978     env->idt.base = sregs->_idt.base;
979     env->gdt.limit = sregs->_gdt.limit;
980     env->gdt.base = sregs->_gdt.base;
981     return 0;
982 }
983
984 static int hax_set_segments(CPUArchState *env, struct vcpu_state_t *sregs)
985 {
986     if ((env->eflags & VM_MASK)) {
987         set_v8086_seg(&sregs->_cs, &env->segs[R_CS]);
988         set_v8086_seg(&sregs->_ds, &env->segs[R_DS]);
989         set_v8086_seg(&sregs->_es, &env->segs[R_ES]);
990         set_v8086_seg(&sregs->_fs, &env->segs[R_FS]);
991         set_v8086_seg(&sregs->_gs, &env->segs[R_GS]);
992         set_v8086_seg(&sregs->_ss, &env->segs[R_SS]);
993     } else {
994         set_seg(&sregs->_cs, &env->segs[R_CS]);
995         set_seg(&sregs->_ds, &env->segs[R_DS]);
996         set_seg(&sregs->_es, &env->segs[R_ES]);
997         set_seg(&sregs->_fs, &env->segs[R_FS]);
998         set_seg(&sregs->_gs, &env->segs[R_GS]);
999         set_seg(&sregs->_ss, &env->segs[R_SS]);
1000
1001         if (env->cr[0] & CR0_PE_MASK) {
1002             /* force ss cpl to cs cpl */
1003             sregs->_ss.selector = (sregs->_ss.selector & ~3) |
1004               (sregs->_cs.selector & 3);
1005             sregs->_ss.dpl = sregs->_ss.selector & 3;
1006         }
1007     }
1008
1009     set_seg(&sregs->_tr, &env->tr);
1010     set_seg(&sregs->_ldt, &env->ldt);
1011     sregs->_idt.limit = env->idt.limit;
1012     sregs->_idt.base = env->idt.base;
1013     sregs->_gdt.limit = env->gdt.limit;
1014     sregs->_gdt.base = env->gdt.base;
1015     return 0;
1016 }
1017
1018 /*
1019  * After get the state from the kernel module, some
1020  * qemu emulator state need be updated also
1021  */
1022 static int hax_setup_qemu_emulator(CPUArchState *env)
1023 {
1024
1025 #define HFLAG_COPY_MASK ~( \
1026   HF_CPL_MASK | HF_PE_MASK | HF_MP_MASK | HF_EM_MASK | \
1027   HF_TS_MASK | HF_TF_MASK | HF_VM_MASK | HF_IOPL_MASK | \
1028   HF_OSFXSR_MASK | HF_LMA_MASK | HF_CS32_MASK | \
1029   HF_SS32_MASK | HF_CS64_MASK | HF_ADDSEG_MASK)
1030
1031     uint32_t hflags;
1032
1033     hflags = (env->segs[R_CS].flags >> DESC_DPL_SHIFT) & HF_CPL_MASK;
1034     hflags |= (env->cr[0] & CR0_PE_MASK) << (HF_PE_SHIFT - CR0_PE_SHIFT);
1035     hflags |= (env->cr[0] << (HF_MP_SHIFT - CR0_MP_SHIFT)) &
1036       (HF_MP_MASK | HF_EM_MASK | HF_TS_MASK);
1037     hflags |= (env->eflags & (HF_TF_MASK | HF_VM_MASK | HF_IOPL_MASK));
1038     hflags |= (env->cr[4] & CR4_OSFXSR_MASK) <<
1039       (HF_OSFXSR_SHIFT - CR4_OSFXSR_SHIFT);
1040
1041     if (env->efer & MSR_EFER_LMA) {
1042         hflags |= HF_LMA_MASK;
1043     }
1044
1045     if ((hflags & HF_LMA_MASK) && (env->segs[R_CS].flags & DESC_L_MASK)) {
1046         hflags |= HF_CS32_MASK | HF_SS32_MASK | HF_CS64_MASK;
1047     } else {
1048         hflags |= (env->segs[R_CS].flags & DESC_B_MASK) >>
1049           (DESC_B_SHIFT - HF_CS32_SHIFT);
1050         hflags |= (env->segs[R_SS].flags & DESC_B_MASK) >>
1051           (DESC_B_SHIFT - HF_SS32_SHIFT);
1052         if (!(env->cr[0] & CR0_PE_MASK) ||
1053           (env->eflags & VM_MASK) ||
1054           !(hflags & HF_CS32_MASK)) {
1055             hflags |= HF_ADDSEG_MASK;
1056         } else {
1057             hflags |= ((env->segs[R_DS].base |
1058                   env->segs[R_ES].base |
1059                   env->segs[R_SS].base) != 0) <<
1060               HF_ADDSEG_SHIFT;
1061         }
1062     }
1063     env->hflags = (env->hflags & HFLAG_COPY_MASK) | hflags;
1064     return 0;
1065 }
1066
1067 static int hax_sync_vcpu_register(CPUArchState *env, int set)
1068 {
1069     struct vcpu_state_t regs;
1070     int ret;
1071     memset(&regs, 0, sizeof(struct vcpu_state_t));
1072
1073     if (!set)
1074     {
1075         ret = hax_sync_vcpu_state(env, &regs, 0);
1076         if (ret < 0)
1077             return -1;
1078     }
1079
1080     /*generic register */
1081     hax_getput_reg(&regs._rax, &env->regs[R_EAX], set);
1082     hax_getput_reg(&regs._rbx, &env->regs[R_EBX], set);
1083     hax_getput_reg(&regs._rcx, &env->regs[R_ECX], set);
1084     hax_getput_reg(&regs._rdx, &env->regs[R_EDX], set);
1085     hax_getput_reg(&regs._rsi, &env->regs[R_ESI], set);
1086     hax_getput_reg(&regs._rdi, &env->regs[R_EDI], set);
1087     hax_getput_reg(&regs._rsp, &env->regs[R_ESP], set);
1088     hax_getput_reg(&regs._rbp, &env->regs[R_EBP], set);
1089
1090     hax_getput_reg(&regs._rflags, &env->eflags, set);
1091     hax_getput_reg(&regs._rip, &env->eip, set);
1092
1093     if (set)
1094     {
1095
1096         regs._cr0 = env->cr[0];
1097         regs._cr2 = env->cr[2];
1098         regs._cr3 = env->cr[3];
1099         regs._cr4 = env->cr[4];
1100         hax_set_segments(env, &regs);
1101     }
1102     else
1103     {
1104         env->cr[0] = regs._cr0;
1105         env->cr[2] = regs._cr2;
1106         env->cr[3] = regs._cr3;
1107         env->cr[4] = regs._cr4;
1108         hax_get_segments(env, &regs);
1109     }
1110
1111     if (set)
1112     {
1113         ret = hax_sync_vcpu_state(env, &regs, 1);
1114         if (ret < 0)
1115             return -1;
1116     }
1117     if (!set)
1118         hax_setup_qemu_emulator(env);
1119     return 0;
1120 }
1121
1122 static void hax_msr_entry_set(struct vmx_msr *item,
1123   uint32_t index, uint64_t value)
1124 {
1125     item->entry = index;
1126     item->value = value;
1127 }
1128
1129 static int hax_get_msrs(CPUArchState *env)
1130 {
1131     struct hax_msr_data md;
1132     struct vmx_msr *msrs = md.entries;
1133     int ret, i, n;
1134
1135     n = 0;
1136     msrs[n++].entry = MSR_IA32_SYSENTER_CS;
1137     msrs[n++].entry = MSR_IA32_SYSENTER_ESP;
1138     msrs[n++].entry = MSR_IA32_SYSENTER_EIP;
1139     msrs[n++].entry = MSR_IA32_TSC;
1140     md.nr_msr = n;
1141     ret = hax_sync_msr(env, &md, 0);
1142     if (ret < 0)
1143         return ret;
1144
1145     for (i = 0; i < md.done; i++) {
1146         switch (msrs[i].entry) {
1147             case MSR_IA32_SYSENTER_CS:
1148                 env->sysenter_cs = msrs[i].value;
1149                 break;
1150             case MSR_IA32_SYSENTER_ESP:
1151                 env->sysenter_esp = msrs[i].value;
1152                 break;
1153             case MSR_IA32_SYSENTER_EIP:
1154                 env->sysenter_eip = msrs[i].value;
1155                 break;
1156             case MSR_IA32_TSC:
1157                 env->tsc = msrs[i].value;
1158                 break;
1159         }
1160     }
1161
1162     return 0;
1163 }
1164
1165 static int hax_set_msrs(CPUArchState *env)
1166 {
1167     struct hax_msr_data md;
1168     struct vmx_msr *msrs;
1169     msrs = md.entries;
1170     int n = 0;
1171
1172     memset(&md, 0, sizeof(struct hax_msr_data));
1173     hax_msr_entry_set(&msrs[n++], MSR_IA32_SYSENTER_CS, env->sysenter_cs);
1174     hax_msr_entry_set(&msrs[n++], MSR_IA32_SYSENTER_ESP, env->sysenter_esp);
1175     hax_msr_entry_set(&msrs[n++], MSR_IA32_SYSENTER_EIP, env->sysenter_eip);
1176     hax_msr_entry_set(&msrs[n++], MSR_IA32_TSC, env->tsc);
1177     md.nr_msr = n;
1178     md.done = 0;
1179
1180     return hax_sync_msr(env, &md, 1);
1181
1182 }
1183
1184 static int hax_get_fpu(CPUArchState *env)
1185 {
1186     struct fx_layout fpu;
1187     int i, ret;
1188
1189     ret = hax_sync_fpu(env, &fpu, 0);
1190     if (ret < 0)
1191         return ret;
1192
1193     env->fpstt = (fpu.fsw >> 11) & 7;
1194     env->fpus = fpu.fsw;
1195     env->fpuc = fpu.fcw;
1196     for (i = 0; i < 8; ++i)
1197         env->fptags[i] = !((fpu.ftw >> i) & 1);
1198     memcpy(env->fpregs, fpu.st_mm, sizeof(env->fpregs));
1199
1200     memcpy(env->xmm_regs, fpu.mmx_1, sizeof(fpu.mmx_1));
1201     memcpy((XMMReg *)(env->xmm_regs) + 8, fpu.mmx_2, sizeof(fpu.mmx_2));
1202     env->mxcsr = fpu.mxcsr;
1203
1204     return 0;
1205 }
1206
1207 static int hax_set_fpu(CPUArchState *env)
1208 {
1209     struct fx_layout fpu;
1210     int i;
1211
1212     memset(&fpu, 0, sizeof(fpu));
1213     fpu.fsw = env->fpus & ~(7 << 11);
1214     fpu.fsw |= (env->fpstt & 7) << 11;
1215     fpu.fcw = env->fpuc;
1216
1217     for (i = 0; i < 8; ++i)
1218         fpu.ftw |= (!env->fptags[i]) << i;
1219
1220     memcpy(fpu.st_mm, env->fpregs, sizeof (env->fpregs));
1221     memcpy(fpu.mmx_1, env->xmm_regs, sizeof (fpu.mmx_1));
1222     memcpy(fpu.mmx_2, (XMMReg *)(env->xmm_regs) + 8, sizeof (fpu.mmx_2));
1223
1224     fpu.mxcsr = env->mxcsr;
1225
1226     return hax_sync_fpu(env, &fpu, 1);
1227 }
1228
1229 int hax_arch_get_registers(CPUArchState *env)
1230 {
1231     int ret;
1232
1233     ret = hax_sync_vcpu_register(env, 0);
1234     if (ret < 0)
1235         return ret;
1236
1237     ret = hax_get_fpu(env);
1238     if (ret < 0)
1239         return ret;
1240
1241     ret = hax_get_msrs(env);
1242     if (ret < 0)
1243         return ret;
1244
1245     return 0;
1246 }
1247
1248 static int hax_arch_set_registers(CPUArchState *env)
1249 {
1250     int ret;
1251     ret = hax_sync_vcpu_register(env, 1);
1252
1253     if (ret < 0)
1254     {
1255         dprint("Failed to sync vcpu reg\n");
1256         return ret;
1257     }
1258     ret = hax_set_fpu(env);
1259     if (ret < 0)
1260     {
1261         dprint("FPU failed\n");
1262         return ret;
1263     }
1264     ret = hax_set_msrs(env);
1265     if (ret < 0)
1266     {
1267         dprint("MSR failed\n");
1268         return ret;
1269     }
1270
1271     return 0;
1272 }
1273
1274 void hax_vcpu_sync_state(CPUArchState *env, int modified)
1275 {
1276     if (hax_enabled()) {
1277         if (modified)
1278             hax_arch_set_registers(env);
1279         else
1280             hax_arch_get_registers(env);
1281     }
1282 }
1283
1284 /*
1285  * much simpler than kvm, at least in first stage because:
1286  * We don't need consider the device pass-through, we don't need
1287  * consider the framebuffer, and we may even remove the bios at all
1288  */
1289 int hax_sync_vcpus(void)
1290 {
1291     if (hax_enabled())
1292     {
1293         CPUState *cpu;
1294
1295         cpu = first_cpu;
1296         if (!cpu)
1297             return 0;
1298
1299         for (; cpu != NULL; cpu = CPU_NEXT(cpu)) {
1300             int ret;
1301
1302             ret = hax_arch_set_registers(cpu->env_ptr);
1303             if (ret < 0)
1304             {
1305                 dprint("Failed to sync HAX vcpu context\n");
1306                 exit(1);
1307             }
1308         }
1309     }
1310
1311     return 0;
1312 }
1313 void hax_reset_vcpu_state(void *opaque)
1314 {
1315     CPUState *cpu;
1316     for (cpu = first_cpu; cpu != NULL; cpu = CPU_NEXT(cpu))
1317     {
1318         dprint("*********ReSet hax_vcpu->emulation_state \n");
1319         cpu->hax_vcpu->emulation_state  = HAX_EMULATE_STATE_INITIAL;
1320         cpu->hax_vcpu->tunnel->user_event_pending = 0;
1321         cpu->hax_vcpu->tunnel->ready_for_interrupt_injection = 0;
1322     }
1323 }
1324