1 /* 2 * This program is free software; you can redistribute it and/or modify 3 * it under the terms of the GNU General Public License, version 2, as 4 * published by the Free Software Foundation. 5 * 6 * This program is distributed in the hope that it will be useful, 7 * but WITHOUT ANY WARRANTY; without even the implied warranty of 8 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 9 * GNU General Public License for more details. 10 * 11 * You should have received a copy of the GNU General Public License 12 * along with this program; if not, write to the Free Software 13 * Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 14 * 15 * Copyright IBM Corp. 2008 16 * Copyright 2011 Freescale Semiconductor, Inc. 17 * 18 * Authors: Hollis Blanchard <hollisb@us.ibm.com> 19 */ 20 21 #include <linux/kvm_host.h> 22 #include <asm/disassemble.h> 23 24 #include "booke.h" 25 26 #define OP_19_XOP_RFI 50 27 #define OP_19_XOP_RFCI 51 28 29 #define OP_31_XOP_MFMSR 83 30 #define OP_31_XOP_WRTEE 131 31 #define OP_31_XOP_MTMSR 146 32 #define OP_31_XOP_WRTEEI 163 33 34 static void kvmppc_emul_rfi(struct kvm_vcpu *vcpu) 35 { 36 vcpu->arch.pc = vcpu->arch.shared->srr0; 37 kvmppc_set_msr(vcpu, vcpu->arch.shared->srr1); 38 } 39 40 static void kvmppc_emul_rfci(struct kvm_vcpu *vcpu) 41 { 42 vcpu->arch.pc = vcpu->arch.csrr0; 43 kvmppc_set_msr(vcpu, vcpu->arch.csrr1); 44 } 45 46 int kvmppc_booke_emulate_op(struct kvm_run *run, struct kvm_vcpu *vcpu, 47 unsigned int inst, int *advance) 48 { 49 int emulated = EMULATE_DONE; 50 int rs = get_rs(inst); 51 int rt = get_rt(inst); 52 53 switch (get_op(inst)) { 54 case 19: 55 switch (get_xop(inst)) { 56 case OP_19_XOP_RFI: 57 kvmppc_emul_rfi(vcpu); 58 kvmppc_set_exit_type(vcpu, EMULATED_RFI_EXITS); 59 *advance = 0; 60 break; 61 62 case OP_19_XOP_RFCI: 63 kvmppc_emul_rfci(vcpu); 64 kvmppc_set_exit_type(vcpu, EMULATED_RFCI_EXITS); 65 *advance = 0; 66 break; 67 68 default: 69 emulated = EMULATE_FAIL; 70 break; 71 } 72 break; 73 74 case 31: 75 switch (get_xop(inst)) { 76 77 case OP_31_XOP_MFMSR: 78 kvmppc_set_gpr(vcpu, rt, vcpu->arch.shared->msr); 79 kvmppc_set_exit_type(vcpu, EMULATED_MFMSR_EXITS); 80 break; 81 82 case OP_31_XOP_MTMSR: 83 kvmppc_set_exit_type(vcpu, EMULATED_MTMSR_EXITS); 84 kvmppc_set_msr(vcpu, kvmppc_get_gpr(vcpu, rs)); 85 break; 86 87 case OP_31_XOP_WRTEE: 88 vcpu->arch.shared->msr = (vcpu->arch.shared->msr & ~MSR_EE) 89 | (kvmppc_get_gpr(vcpu, rs) & MSR_EE); 90 kvmppc_set_exit_type(vcpu, EMULATED_WRTEE_EXITS); 91 break; 92 93 case OP_31_XOP_WRTEEI: 94 vcpu->arch.shared->msr = (vcpu->arch.shared->msr & ~MSR_EE) 95 | (inst & MSR_EE); 96 kvmppc_set_exit_type(vcpu, EMULATED_WRTEE_EXITS); 97 break; 98 99 default: 100 emulated = EMULATE_FAIL; 101 } 102 103 break; 104 105 default: 106 emulated = EMULATE_FAIL; 107 } 108 109 return emulated; 110 } 111 112 /* 113 * NOTE: some of these registers are not emulated on BOOKE_HV (GS-mode). 114 * Their backing store is in real registers, and these functions 115 * will return the wrong result if called for them in another context 116 * (such as debugging). 117 */ 118 int kvmppc_booke_emulate_mtspr(struct kvm_vcpu *vcpu, int sprn, ulong spr_val) 119 { 120 int emulated = EMULATE_DONE; 121 122 switch (sprn) { 123 case SPRN_DEAR: 124 vcpu->arch.shared->dar = spr_val; 125 break; 126 case SPRN_ESR: 127 vcpu->arch.shared->esr = spr_val; 128 break; 129 case SPRN_CSRR0: 130 vcpu->arch.csrr0 = spr_val; 131 break; 132 case SPRN_CSRR1: 133 vcpu->arch.csrr1 = spr_val; 134 break; 135 case SPRN_DBCR0: 136 vcpu->arch.dbcr0 = spr_val; 137 break; 138 case SPRN_DBCR1: 139 vcpu->arch.dbcr1 = spr_val; 140 break; 141 case SPRN_DBSR: 142 vcpu->arch.dbsr &= ~spr_val; 143 break; 144 case SPRN_TSR: 145 kvmppc_clr_tsr_bits(vcpu, spr_val); 146 break; 147 case SPRN_TCR: 148 kvmppc_set_tcr(vcpu, spr_val); 149 break; 150 151 case SPRN_DECAR: 152 vcpu->arch.decar = spr_val; 153 break; 154 /* 155 * Note: SPRG4-7 are user-readable. 156 * These values are loaded into the real SPRGs when resuming the 157 * guest (PR-mode only). 158 */ 159 case SPRN_SPRG4: 160 vcpu->arch.shared->sprg4 = spr_val; 161 break; 162 case SPRN_SPRG5: 163 vcpu->arch.shared->sprg5 = spr_val; 164 break; 165 case SPRN_SPRG6: 166 vcpu->arch.shared->sprg6 = spr_val; 167 break; 168 case SPRN_SPRG7: 169 vcpu->arch.shared->sprg7 = spr_val; 170 break; 171 172 case SPRN_IVPR: 173 vcpu->arch.ivpr = spr_val; 174 #ifdef CONFIG_KVM_BOOKE_HV 175 mtspr(SPRN_GIVPR, spr_val); 176 #endif 177 break; 178 case SPRN_IVOR0: 179 vcpu->arch.ivor[BOOKE_IRQPRIO_CRITICAL] = spr_val; 180 break; 181 case SPRN_IVOR1: 182 vcpu->arch.ivor[BOOKE_IRQPRIO_MACHINE_CHECK] = spr_val; 183 break; 184 case SPRN_IVOR2: 185 vcpu->arch.ivor[BOOKE_IRQPRIO_DATA_STORAGE] = spr_val; 186 #ifdef CONFIG_KVM_BOOKE_HV 187 mtspr(SPRN_GIVOR2, spr_val); 188 #endif 189 break; 190 case SPRN_IVOR3: 191 vcpu->arch.ivor[BOOKE_IRQPRIO_INST_STORAGE] = spr_val; 192 break; 193 case SPRN_IVOR4: 194 vcpu->arch.ivor[BOOKE_IRQPRIO_EXTERNAL] = spr_val; 195 break; 196 case SPRN_IVOR5: 197 vcpu->arch.ivor[BOOKE_IRQPRIO_ALIGNMENT] = spr_val; 198 break; 199 case SPRN_IVOR6: 200 vcpu->arch.ivor[BOOKE_IRQPRIO_PROGRAM] = spr_val; 201 break; 202 case SPRN_IVOR7: 203 vcpu->arch.ivor[BOOKE_IRQPRIO_FP_UNAVAIL] = spr_val; 204 break; 205 case SPRN_IVOR8: 206 vcpu->arch.ivor[BOOKE_IRQPRIO_SYSCALL] = spr_val; 207 #ifdef CONFIG_KVM_BOOKE_HV 208 mtspr(SPRN_GIVOR8, spr_val); 209 #endif 210 break; 211 case SPRN_IVOR9: 212 vcpu->arch.ivor[BOOKE_IRQPRIO_AP_UNAVAIL] = spr_val; 213 break; 214 case SPRN_IVOR10: 215 vcpu->arch.ivor[BOOKE_IRQPRIO_DECREMENTER] = spr_val; 216 break; 217 case SPRN_IVOR11: 218 vcpu->arch.ivor[BOOKE_IRQPRIO_FIT] = spr_val; 219 break; 220 case SPRN_IVOR12: 221 vcpu->arch.ivor[BOOKE_IRQPRIO_WATCHDOG] = spr_val; 222 break; 223 case SPRN_IVOR13: 224 vcpu->arch.ivor[BOOKE_IRQPRIO_DTLB_MISS] = spr_val; 225 break; 226 case SPRN_IVOR14: 227 vcpu->arch.ivor[BOOKE_IRQPRIO_ITLB_MISS] = spr_val; 228 break; 229 case SPRN_IVOR15: 230 vcpu->arch.ivor[BOOKE_IRQPRIO_DEBUG] = spr_val; 231 break; 232 233 default: 234 emulated = EMULATE_FAIL; 235 } 236 237 return emulated; 238 } 239 240 int kvmppc_booke_emulate_mfspr(struct kvm_vcpu *vcpu, int sprn, ulong *spr_val) 241 { 242 int emulated = EMULATE_DONE; 243 244 switch (sprn) { 245 case SPRN_IVPR: 246 *spr_val = vcpu->arch.ivpr; 247 break; 248 case SPRN_DEAR: 249 *spr_val = vcpu->arch.shared->dar; 250 break; 251 case SPRN_ESR: 252 *spr_val = vcpu->arch.shared->esr; 253 break; 254 case SPRN_CSRR0: 255 *spr_val = vcpu->arch.csrr0; 256 break; 257 case SPRN_CSRR1: 258 *spr_val = vcpu->arch.csrr1; 259 break; 260 case SPRN_DBCR0: 261 *spr_val = vcpu->arch.dbcr0; 262 break; 263 case SPRN_DBCR1: 264 *spr_val = vcpu->arch.dbcr1; 265 break; 266 case SPRN_DBSR: 267 *spr_val = vcpu->arch.dbsr; 268 break; 269 case SPRN_TSR: 270 *spr_val = vcpu->arch.tsr; 271 break; 272 case SPRN_TCR: 273 *spr_val = vcpu->arch.tcr; 274 break; 275 276 case SPRN_IVOR0: 277 *spr_val = vcpu->arch.ivor[BOOKE_IRQPRIO_CRITICAL]; 278 break; 279 case SPRN_IVOR1: 280 *spr_val = vcpu->arch.ivor[BOOKE_IRQPRIO_MACHINE_CHECK]; 281 break; 282 case SPRN_IVOR2: 283 *spr_val = vcpu->arch.ivor[BOOKE_IRQPRIO_DATA_STORAGE]; 284 break; 285 case SPRN_IVOR3: 286 *spr_val = vcpu->arch.ivor[BOOKE_IRQPRIO_INST_STORAGE]; 287 break; 288 case SPRN_IVOR4: 289 *spr_val = vcpu->arch.ivor[BOOKE_IRQPRIO_EXTERNAL]; 290 break; 291 case SPRN_IVOR5: 292 *spr_val = vcpu->arch.ivor[BOOKE_IRQPRIO_ALIGNMENT]; 293 break; 294 case SPRN_IVOR6: 295 *spr_val = vcpu->arch.ivor[BOOKE_IRQPRIO_PROGRAM]; 296 break; 297 case SPRN_IVOR7: 298 *spr_val = vcpu->arch.ivor[BOOKE_IRQPRIO_FP_UNAVAIL]; 299 break; 300 case SPRN_IVOR8: 301 *spr_val = vcpu->arch.ivor[BOOKE_IRQPRIO_SYSCALL]; 302 break; 303 case SPRN_IVOR9: 304 *spr_val = vcpu->arch.ivor[BOOKE_IRQPRIO_AP_UNAVAIL]; 305 break; 306 case SPRN_IVOR10: 307 *spr_val = vcpu->arch.ivor[BOOKE_IRQPRIO_DECREMENTER]; 308 break; 309 case SPRN_IVOR11: 310 *spr_val = vcpu->arch.ivor[BOOKE_IRQPRIO_FIT]; 311 break; 312 case SPRN_IVOR12: 313 *spr_val = vcpu->arch.ivor[BOOKE_IRQPRIO_WATCHDOG]; 314 break; 315 case SPRN_IVOR13: 316 *spr_val = vcpu->arch.ivor[BOOKE_IRQPRIO_DTLB_MISS]; 317 break; 318 case SPRN_IVOR14: 319 *spr_val = vcpu->arch.ivor[BOOKE_IRQPRIO_ITLB_MISS]; 320 break; 321 case SPRN_IVOR15: 322 *spr_val = vcpu->arch.ivor[BOOKE_IRQPRIO_DEBUG]; 323 break; 324 325 default: 326 emulated = EMULATE_FAIL; 327 } 328 329 return emulated; 330 } 331