Anforderungen  |   Konzepte  |   Entwurf  |   Entwicklung  |   Qualitätssicherung  |   Lebenszyklus  |   Steuerung
 
 
 
 


Quelle  book3s_hv_tm_builtin.c   Sprache: C

 
// SPDX-License-Identifier: GPL-2.0-only
/*
 * Copyright 2017 Paul Mackerras, IBM Corp. <paulus@au1.ibm.com>
 */


#include <linux/kvm_host.h>

#include <asm/kvm_ppc.h>
#include <asm/kvm_book3s.h>
#include <asm/kvm_book3s_64.h>
#include <asm/reg.h>
#include <asm/ppc-opcode.h>

/*
 * This handles the cases where the guest is in real suspend mode
 * and we want to get back to the guest without dooming the transaction.
 * The caller has checked that the guest is in real-suspend mode
 * (MSR[TS] = S and the fake-suspend flag is not set).
 */

int kvmhv_p9_tm_emulation_early(struct kvm_vcpu *vcpu)
{
 u32 instr = vcpu->arch.emul_inst;
 u64 newmsr, msr, bescr;
 int rs;

 /*
 * rfid, rfebb, and mtmsrd encode bit 31 = 0 since it's a reserved bit
 * in these instructions, so masking bit 31 out doesn't change these
 * instructions. For the tsr. instruction if bit 31 = 0 then it is per
 * ISA an invalid form, however P9 UM, in section 4.6.10 Book II Invalid
 * Forms, informs specifically that ignoring bit 31 is an acceptable way
 * to handle TM-related invalid forms that have bit 31 = 0. Moreover,
 * for emulation purposes both forms (w/ and wo/ bit 31 set) can
 * generate a softpatch interrupt. Hence both forms are handled below
 * for tsr. to make them behave the same way.
 */

 switch (instr & PO_XOP_OPCODE_MASK) {
 case PPC_INST_RFID:
  /* XXX do we need to check for PR=0 here? */
  newmsr = vcpu->arch.shregs.srr1;
  /* should only get here for Sx -> T1 transition */
  if (!(MSR_TM_TRANSACTIONAL(newmsr) && (newmsr & MSR_TM)))
   return 0;
  newmsr = sanitize_msr(newmsr);
  vcpu->arch.shregs.msr = newmsr;
  vcpu->arch.cfar = vcpu->arch.regs.nip - 4;
  vcpu->arch.regs.nip = vcpu->arch.shregs.srr0;
  return 1;

 case PPC_INST_RFEBB:
  /* check for PR=1 and arch 2.06 bit set in PCR */
  msr = vcpu->arch.shregs.msr;
  if ((msr & MSR_PR) && (vcpu->arch.vcore->pcr & PCR_ARCH_206))
   return 0;
  /* check EBB facility is available */
  if (!(vcpu->arch.hfscr & HFSCR_EBB) ||
      ((msr & MSR_PR) && !(mfspr(SPRN_FSCR) & FSCR_EBB)))
   return 0;
  bescr = mfspr(SPRN_BESCR);
  /* expect to see a S->T transition requested */
  if (((bescr >> 30) & 3) != 2)
   return 0;
  bescr &= ~BESCR_GE;
  if (instr & (1 << 11))
   bescr |= BESCR_GE;
  mtspr(SPRN_BESCR, bescr);
  msr = (msr & ~MSR_TS_MASK) | MSR_TS_T;
  vcpu->arch.shregs.msr = msr;
  vcpu->arch.cfar = vcpu->arch.regs.nip - 4;
  vcpu->arch.regs.nip = mfspr(SPRN_EBBRR);
  return 1;

 case PPC_INST_MTMSRD:
  /* XXX do we need to check for PR=0 here? */
  rs = (instr >> 21) & 0x1f;
  newmsr = kvmppc_get_gpr(vcpu, rs);
  msr = vcpu->arch.shregs.msr;
  /* check this is a Sx -> T1 transition */
  if (!(MSR_TM_TRANSACTIONAL(newmsr) && (newmsr & MSR_TM)))
   return 0;
  /* mtmsrd doesn't change LE */
  newmsr = (newmsr & ~MSR_LE) | (msr & MSR_LE);
  newmsr = sanitize_msr(newmsr);
  vcpu->arch.shregs.msr = newmsr;
  return 1;

 /* ignore bit 31, see comment above */
 case (PPC_INST_TSR & PO_XOP_OPCODE_MASK):
  /* we know the MSR has the TS field = S (0b01) here */
  msr = vcpu->arch.shregs.msr;
  /* check for PR=1 and arch 2.06 bit set in PCR */
  if ((msr & MSR_PR) && (vcpu->arch.vcore->pcr & PCR_ARCH_206))
   return 0;
  /* check for TM disabled in the HFSCR or MSR */
  if (!(vcpu->arch.hfscr & HFSCR_TM) || !(msr & MSR_TM))
   return 0;
  /* L=1 => tresume => set TS to T (0b10) */
  if (instr & (1 << 21))
   vcpu->arch.shregs.msr = (msr & ~MSR_TS_MASK) | MSR_TS_T;
  /* Set CR0 to 0b0010 */
  vcpu->arch.regs.ccr = (vcpu->arch.regs.ccr & 0x0fffffff) |
   0x20000000;
  return 1;
 }

 return 0;
}

/*
 * This is called when we are returning to a guest in TM transactional
 * state.  We roll the guest state back to the checkpointed state.
 */

void kvmhv_emulate_tm_rollback(struct kvm_vcpu *vcpu)
{
 vcpu->arch.shregs.msr &= ~MSR_TS_MASK; /* go to N state */
 vcpu->arch.regs.nip = vcpu->arch.tfhar;
 copy_from_checkpoint(vcpu);
 vcpu->arch.regs.ccr = (vcpu->arch.regs.ccr & 0x0fffffff) | 0xa0000000;
}

Messung V0.5
C=93 H=91 G=91

¤ Dauer der Verarbeitung: 0.4 Sekunden  ¤

*© Formatika GbR, Deutschland






Wurzel

Suchen

Beweissystem der NASA

Beweissystem Isabelle

NIST Cobol Testsuite

Cephes Mathematical Library

Wiener Entwicklungsmethode

Haftungshinweis

Die Informationen auf dieser Webseite wurden nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit, noch Qualität der bereit gestellten Informationen zugesichert.

Bemerkung:

Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.






                                                                                                                                                                                                                                                                                                                                                                                                     


Neuigkeiten

     Aktuelles
     Motto des Tages

Software

     Produkte
     Quellcodebibliothek

Aktivitäten

     Artikel über Sicherheit
     Anleitung zur Aktivierung von SSL

Muße

     Gedichte
     Musik
     Bilder

Jenseits des Üblichen ....
    

Besucherstatistik

Besucherstatistik

Monitoring

Montastic status badge