[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: [Qemu-ppc] [Qemu-PPC] [PATCH 3/3] target/ppc: Add debug function to
From: |
David Gibson |
Subject: |
Re: [Qemu-ppc] [Qemu-PPC] [PATCH 3/3] target/ppc: Add debug function to dump radix mmu translations |
Date: |
Mon, 3 Jul 2017 17:51:21 +1000 |
User-agent: |
Mutt/1.8.0 (2017-02-23) |
On Mon, Jul 03, 2017 at 04:19:48PM +1000, Suraj Jitindar Singh wrote:
> In target/ppc/mmu-hash64.c there already exists the function
> dump_slb() to dump the hash translation entries (for effective to
> virtual translation at least).
>
> Implement the function ppc_radix64_dump() to allow all the kernel
> effective to real address mappings and corresponding ptes to be dumped.
> This is called when "info tlb" is invoked in the qemu console. Previously
> this command had no output when invoked with a radix guest.
>
> Signed-off-by: Suraj Jitindar Singh <address@hidden>
This doesn't really seem equivalent to the other dump_mmu() paths.
For HPT, it just dumps the SLB, which is 32 entries. The RPT is
likely to have thousands of PTEs.
Similarly the other embedded paths generally just dump a (software
loaded) TLB, which will have a fixed number of entries. 6xx dumps a
TLB and various metadata, but not its whole hash table.
In the other direction the info dumped for other platforms *is*
affected by the process context (or equivalent), whereas here you just
dump the RPT for the kernel (PID 0).
So instead of dumping the RPT itself, what I think you want is to
pretty print:
PID
LPID
partition table entry 0
partition table entry LPID
process table entry 0
process table entry PID
and maybe any other context relevant registers I've forgotten.
Obviously some of that will need to be omitted for the 'pseries' (vhyp
!= 0) case.
In fact most of the info above would make sense to always dump for a
v3.00 MMU, regardless of HPT vs RPT mode. Obviously dumping the SLB
only makes sense for HPT mode, though.
> ---
> target/ppc/mmu-radix64.c | 49
> ++++++++++++++++++++++++++++++++++++++++++++++++
> target/ppc/mmu-radix64.h | 1 +
> target/ppc/mmu_helper.c | 2 +-
> 3 files changed, 51 insertions(+), 1 deletion(-)
>
> diff --git a/target/ppc/mmu-radix64.c b/target/ppc/mmu-radix64.c
> index bbd37e3..f7eeead 100644
> --- a/target/ppc/mmu-radix64.c
> +++ b/target/ppc/mmu-radix64.c
> @@ -296,3 +296,52 @@ hwaddr ppc_radix64_get_phys_page_debug(PowerPCCPU *cpu,
> target_ulong eaddr)
>
> return raddr & TARGET_PAGE_MASK;
> }
> +
> +static void ppc_radix64_dump_level(FILE *f, fprintf_function cpu_fprintf,
> + PowerPCCPU *cpu, uint64_t eaddr,
> + uint64_t base_addr, uint64_t nls,
> + uint64_t psize, int *num)
> +{
> + CPUState *cs = CPU(cpu);
> + uint64_t i, pte;
> +
> + for (i = 0; i < (1 << nls); i++) {
> + eaddr &= ~((1ULL << psize) - 1); /* Clear the low bits */
> + eaddr |= (i << (psize - nls));
> +
> + pte = ldq_phys(cs->as, base_addr + (i * sizeof(pte)));
> + if (!(pte & R_PTE_VALID)) { /* Invalid Entry */
> + continue;
> + }
> +
> + if (pte & R_PTE_LEAF) {
> + uint64_t mask = (1ULL << (psize - nls)) - 1;
> + cpu_fprintf(f, "%d\t0x%.16" PRIx64 " -> 0x%.16" PRIx64
> + " pte: 0x%.16" PRIx64 "\n", (*num)++,
> + eaddr, pte & R_PTE_RPN & ~mask, pte);
> + } else {
> + ppc_radix64_dump_level(f, cpu_fprintf, cpu, eaddr, pte &
> R_PDE_NLB,
> + pte & R_PDE_NLS, psize - nls, num);
> + }
> + }
> +}
> +
> +void ppc_radix64_dump(FILE *f, fprintf_function cpu_fprintf, PowerPCCPU *cpu)
> +{
> + CPUState *cs = CPU(cpu);
> + PPCVirtualHypervisorClass *vhc =
> + PPC_VIRTUAL_HYPERVISOR_GET_CLASS(cpu->vhyp);
> + uint64_t patbe, prtbe0;
> + int num = 0;
> +
> + /* Get Process Table */
> + patbe = vhc->get_patbe(cpu->vhyp);
> +
> + /* Load the first entry -> Guest kernel mappings (all we dump for now) */
> + prtbe0 = ldq_phys(cs->as, patbe & PATBE1_R_PRTB);
> +
> + cpu_fprintf(f, "\tEADDR\t\t RADDR\n");
> + ppc_radix64_dump_level(f, cpu_fprintf, cpu, 0ULL, prtbe0 & PRTBE_R_RPDB,
> + prtbe0 & PRTBE_R_RPDS, PRTBE_R_GET_RTS(prtbe0),
> + &num);
> +}
> diff --git a/target/ppc/mmu-radix64.h b/target/ppc/mmu-radix64.h
> index 0ecf063..c6c22bd 100644
> --- a/target/ppc/mmu-radix64.h
> +++ b/target/ppc/mmu-radix64.h
> @@ -47,6 +47,7 @@
> int ppc_radix64_handle_mmu_fault(PowerPCCPU *cpu, vaddr eaddr, int rwx,
> int mmu_idx);
> hwaddr ppc_radix64_get_phys_page_debug(PowerPCCPU *cpu, target_ulong addr);
> +void ppc_radix64_dump(FILE *f, fprintf_function cpu_fprintf, PowerPCCPU
> *cpu);
>
> static inline int ppc_radix64_get_prot_eaa(uint64_t pte)
> {
> diff --git a/target/ppc/mmu_helper.c b/target/ppc/mmu_helper.c
> index b7b9088..9587b07 100644
> --- a/target/ppc/mmu_helper.c
> +++ b/target/ppc/mmu_helper.c
> @@ -1287,7 +1287,7 @@ void dump_mmu(FILE *f, fprintf_function cpu_fprintf,
> CPUPPCState *env)
> break;
> case POWERPC_MMU_VER_3_00:
> if (ppc64_radix_guest(ppc_env_get_cpu(env))) {
> - /* TODO - Unsupported */
> + ppc_radix64_dump(f, cpu_fprintf, ppc_env_get_cpu(env));
> } else {
> dump_slb(f, cpu_fprintf, ppc_env_get_cpu(env));
> break;
--
David Gibson | I'll have my music baroque, and my code
david AT gibson.dropbear.id.au | minimalist, thank you. NOT _the_ _other_
| _way_ _around_!
http://www.ozlabs.org/~dgibson
signature.asc
Description: PGP signature