MIPS: KVM: Recognise r6 CACHE encoding
authorJames Hogan <james.hogan@imgtec.com>
Mon, 4 Jul 2016 18:35:13 +0000 (19:35 +0100)
committerPaolo Bonzini <pbonzini@redhat.com>
Tue, 5 Jul 2016 14:09:17 +0000 (16:09 +0200)
Recognise the new MIPSr6 CACHE instruction encoding rather than the
pre-r6 one when an r6 kernel is being built. A SPECIAL3 opcode is used
and the immediate field is reduced to 9 bits wide since MIPSr6.

Signed-off-by: James Hogan <james.hogan@imgtec.com>
Cc: Paolo Bonzini <pbonzini@redhat.com>
Cc: Radim KrÄmář <rkrcmar@redhat.com>
Cc: Ralf Baechle <ralf@linux-mips.org>
Cc: linux-mips@linux-mips.org
Cc: kvm@vger.kernel.org
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
arch/mips/kvm/dyntrans.c
arch/mips/kvm/emulate.c

index 8a1833b9eb384dde8544a32ecd12265bb131468c..91ebd2b6034f678c00649ab0621b2bc31b8ed262 100644 (file)
@@ -72,7 +72,10 @@ int kvm_mips_trans_cache_va(union mips_instruction inst, u32 *opc,
        synci_inst.i_format.opcode = bcond_op;
        synci_inst.i_format.rs = inst.i_format.rs;
        synci_inst.i_format.rt = synci_op;
-       synci_inst.i_format.simmediate = inst.i_format.simmediate;
+       if (cpu_has_mips_r6)
+               synci_inst.i_format.simmediate = inst.spec3_format.simmediate;
+       else
+               synci_inst.i_format.simmediate = inst.i_format.simmediate;
 
        return kvm_mips_trans_replace(vcpu, opc, synci_inst);
 }
index f0fa9e95605696624179ad263bb53db18e1183cb..62e6a7b313aea58c84827b1a6905aaf3125c2480 100644 (file)
@@ -1601,7 +1601,10 @@ enum emulation_result kvm_mips_emulate_cache(union mips_instruction inst,
 
        base = inst.i_format.rs;
        op_inst = inst.i_format.rt;
-       offset = inst.i_format.simmediate;
+       if (cpu_has_mips_r6)
+               offset = inst.spec3_format.simmediate;
+       else
+               offset = inst.i_format.simmediate;
        cache = op_inst & CacheOp_Cache;
        op = op_inst & CacheOp_Op;
 
@@ -1764,11 +1767,27 @@ enum emulation_result kvm_mips_emulate_inst(u32 cause, u32 *opc,
                er = kvm_mips_emulate_load(inst, cause, run, vcpu);
                break;
 
+#ifndef CONFIG_CPU_MIPSR6
        case cache_op:
                ++vcpu->stat.cache_exits;
                trace_kvm_exit(vcpu, KVM_TRACE_EXIT_CACHE);
                er = kvm_mips_emulate_cache(inst, opc, cause, run, vcpu);
                break;
+#else
+       case spec3_op:
+               switch (inst.spec3_format.func) {
+               case cache6_op:
+                       ++vcpu->stat.cache_exits;
+                       trace_kvm_exit(vcpu, KVM_TRACE_EXIT_CACHE);
+                       er = kvm_mips_emulate_cache(inst, opc, cause, run,
+                                                   vcpu);
+                       break;
+               default:
+                       goto unknown;
+               };
+               break;
+unknown:
+#endif
 
        default:
                kvm_err("Instruction emulation not supported (%p/%#x)\n", opc,
This page took 0.034385 seconds and 5 git commands to generate.