Palacios Public Git Repository

To checkout Palacios execute

  git clone http://v3vee.org/palacios/palacios.web/palacios.git
This will give you the master branch. You probably want the devel branch or one of the release branches. To switch to the devel branch, simply execute
  cd palacios
  git checkout --track -b devel origin/devel
The other branches are similar.


added irq initial setup
[palacios.git] / palacios / src / palacios / svm_handler.c
1 #include <palacios/svm_handler.h>
2 #include <palacios/vmm.h>
3 #include <palacios/vm_guest_mem.h>
4 #include <palacios/vmm_emulate.h>
5 #include <palacios/svm_ctrl_regs.h>
6 #include <palacios/svm_io.h>
7 #include <palacios/vmm_intr.h>
8
9 extern struct vmm_os_hooks * os_hooks;
10
11
12 int handle_svm_exit(struct guest_info * info) {
13   vmcb_ctrl_t * guest_ctrl = 0;
14   vmcb_saved_state_t * guest_state = 0;
15   ulong_t exit_code = 0;
16   
17   guest_ctrl = GET_VMCB_CTRL_AREA((vmcb_t*)(info->vmm_data));
18   guest_state = GET_VMCB_SAVE_STATE_AREA((vmcb_t*)(info->vmm_data));
19   
20
21   // Update the high level state 
22   info->rip = guest_state->rip;
23   info->vm_regs.rsp = guest_state->rsp;
24   info->vm_regs.rax = guest_state->rax;
25   info->vm_regs.rsp = guest_state->rsp;  
26
27
28   exit_code = guest_ctrl->exit_code;
29  
30   // PrintDebugVMCB((vmcb_t*)(info->vmm_data));
31
32
33   // PrintDebug("SVM Returned:(VMCB=%x)\n", info->vmm_data); 
34   //PrintDebug("RIP: %x\n", guest_state->rip);
35
36   
37   //PrintDebug("SVM Returned: Exit Code: %x\n",exit_code); 
38   
39   if (exit_code == VMEXIT_IOIO) {
40     struct svm_io_info * io_info = (struct svm_io_info *)&(guest_ctrl->exit_info1);
41     
42     if (io_info->type == 0) {
43       if (io_info->str) {
44         if (handle_svm_io_outs(info) == -1 ) {
45           return -1;
46         }
47       } else {
48         if (handle_svm_io_out(info) == -1) {
49           return -1;
50         }
51       }
52     } else {
53       if (io_info->str) {
54         if (handle_svm_io_ins(info) == -1) {
55           return -1;
56         }
57       } else {
58         if (handle_svm_io_in(info) == -1) {
59           return -1;
60         }
61       }
62     }
63   } else if (exit_code == VMEXIT_CR0_WRITE) {
64     PrintDebug("CR0 Write\n");
65
66     if (handle_cr0_write(info) == -1) {
67       return -1;
68     }
69     /*
70   } else if (( (exit_code == VMEXIT_CR3_READ)  ||
71                (exit_code == VMEXIT_CR3_WRITE) ||
72                (exit_code == VMEXIT_INVLPG)    ||
73                (exit_code == VMEXIT_INVLPGA)   || 
74                (exit_code == VMEXIT_EXCP14)) && 
75              (info->page_mode == SHADOW_PAGING)) {
76     handle_shadow_paging(info);
77     */
78
79   } else if (exit_code == VMEXIT_INTR) {
80
81     //    handle_svm_intr(info);
82
83   } else if (exit_code == VMEXIT_HLT) {
84     PrintDebug("Guest halted\n");
85     return -1;
86   } else {
87     addr_t rip_addr = get_addr_linear(info, guest_state->rip, guest_state->cs.selector);
88     char buf[15];
89     addr_t host_addr;
90
91
92     PrintDebug("SVM Returned:(VMCB=%x)\n", info->vmm_data); 
93     PrintDebug("RIP: %x\n", guest_state->rip);
94     PrintDebug("RIP Linear: %x\n", rip_addr);
95     
96     PrintDebug("SVM Returned: Exit Code: %x\n",exit_code); 
97     
98     PrintDebug("io_info1 low = 0x%.8x\n", *(uint_t*)&(guest_ctrl->exit_info1));
99     PrintDebug("io_info1 high = 0x%.8x\n", *(uint_t *)(((uchar_t *)&(guest_ctrl->exit_info1)) + 4));
100     
101     PrintDebug("io_info2 low = 0x%.8x\n", *(uint_t*)&(guest_ctrl->exit_info2));
102     PrintDebug("io_info2 high = 0x%.8x\n", *(uint_t *)(((uchar_t *)&(guest_ctrl->exit_info2)) + 4));
103
104     
105
106     if (guest_pa_to_host_pa(info, guest_state->rip, &host_addr) == -1) {
107       PrintDebug("Could not translate guest_state->rip to host address\n");
108       return -1;
109     }
110
111     PrintDebug("Host Address of rip = 0x%x\n", host_addr);
112
113     memset(buf, 0, 15);
114     
115     PrintDebug("Reading from 0x%x in guest\n", rip_addr);
116     
117     read_guest_pa_memory(info, rip_addr, 15, buf);
118
119     PrintTraceMemDump(buf, 15);
120
121     while(1);
122
123   }
124
125
126   // Update the low level state
127
128   if (intr_pending(&(info->intr_state))) {
129     guest_ctrl->EVENTINJ.vector = get_intr_number(&(info->intr_state));
130     guest_ctrl->EVENTINJ.valid = 1;
131  
132     switch (get_intr_type(&(info->intr_state))) {
133     case EXTERNAL_IRQ:
134       guest_ctrl->EVENTINJ.type = SVM_INJECTION_EXTERNAL_INTR;
135       break;
136     case NMI:
137       guest_ctrl->EVENTINJ.type = SVM_INJECTION_NMI;
138       break;
139     case EXCEPTION:
140       guest_ctrl->EVENTINJ.type = SVM_INJECTION_EXCEPTION;
141       guest_ctrl->EVENTINJ.error_code = info->intr_state.excp_error_code;
142       break;
143     case SOFTWARE:
144       guest_ctrl->EVENTINJ.type = SVM_INJECTION_SOFT_INTR;
145       break;
146     case VIRTUAL:
147       guest_ctrl->EVENTINJ.type = SVM_INJECTION_VIRTUAL_INTR;
148       break;
149
150     case INVALID_INTR: 
151     default:
152       PrintDebug("Attempted to issue an invalid interrupt\n");
153       return -1;
154     }
155
156     // IMPORTANT TODO
157     // We need to figure out stack parameters....
158
159     //EVENTINJ.error_code
160
161   }
162
163   guest_state->rax = info->vm_regs.rax;
164   guest_state->rip = info->rip;
165   guest_state->rsp = info->vm_regs.rsp;
166
167   return 0;
168 }
169
170
171
172
173 int handle_shadow_paging(struct guest_info * info) {
174   vmcb_ctrl_t * guest_ctrl = GET_VMCB_CTRL_AREA((vmcb_t*)(info->vmm_data));
175   //  vmcb_saved_state_t * guest_state = GET_VMCB_SAVE_STATE_AREA((vmcb_t*)(info->vmm_data));
176
177   if (guest_ctrl->exit_code == VMEXIT_CR3_READ) {
178
179   }
180
181   return 0;
182 }
183
184
185
186 int handle_svm_intr(struct guest_info * info) {
187   vmcb_ctrl_t * guest_ctrl = GET_VMCB_CTRL_AREA((vmcb_t*)(info->vmm_data));
188   // vmcb_saved_state_t * guest_state = GET_VMCB_SAVE_STATE_AREA((vmcb_t*)(info->vmm_data));
189
190   //struct Interrupt_Info * int_info = &(guest_ctrl->exit_int_info);
191
192   //struct vmm_irq_hook * get_irq_hook(&(info->irq_map), int_info->vector);
193
194   PrintDebug("SVM Returned: Exit Code: %x\n",guest_ctrl->exit_code); 
195   PrintDebug("V_INTR_VECTOR: 0x%x\n", guest_ctrl->guest_ctrl.V_INTR_VECTOR);
196   
197
198
199
200   while(1);
201
202                                      
203
204
205
206   
207  
208  
209     
210   return 0;
211 }