98670d47cd
The MC68040 MMU provides the size of the access that triggers the page fault. This size is set in the Special Status Word which is written in the stack frame of the access fault exception. So we need the size in m68k_cpu_unassigned_access() and m68k_cpu_handle_mmu_fault(). To be able to do that, this patch modifies the prototype of handle_mmu_fault handler, tlb_fill() and probe_write(). do_unassigned_access() already includes a size parameter. This patch also updates handle_mmu_fault handlers and tlb_fill() of all targets (only parameter, no code change). Signed-off-by: Laurent Vivier <laurent@vivier.eu> Reviewed-by: David Hildenbrand <david@redhat.com> Reviewed-by: Richard Henderson <richard.henderson@linaro.org> Message-Id: <20180118193846.24953-2-laurent@vivier.eu>
190 lines
6.1 KiB
C
190 lines
6.1 KiB
C
/*
|
|
* UniCore32 virtual CPU header
|
|
*
|
|
* Copyright (C) 2010-2012 Guan Xuetao
|
|
*
|
|
* This program is free software; you can redistribute it and/or modify
|
|
* it under the terms of the GNU General Public License version 2 as
|
|
* published by the Free Software Foundation, or (at your option) any
|
|
* later version. See the COPYING file in the top-level directory.
|
|
*/
|
|
|
|
#ifndef UNICORE32_CPU_H
|
|
#define UNICORE32_CPU_H
|
|
|
|
#define TARGET_LONG_BITS 32
|
|
#define TARGET_PAGE_BITS 12
|
|
|
|
#define TARGET_PHYS_ADDR_SPACE_BITS 32
|
|
#define TARGET_VIRT_ADDR_SPACE_BITS 32
|
|
|
|
#define CPUArchState struct CPUUniCore32State
|
|
|
|
#include "qemu-common.h"
|
|
#include "cpu-qom.h"
|
|
#include "exec/cpu-defs.h"
|
|
#include "fpu/softfloat.h"
|
|
|
|
#define NB_MMU_MODES 2
|
|
|
|
typedef struct CPUUniCore32State {
|
|
/* Regs for current mode. */
|
|
uint32_t regs[32];
|
|
/* Frequently accessed ASR bits are stored separately for efficiently.
|
|
This contains all the other bits. Use asr_{read,write} to access
|
|
the whole ASR. */
|
|
uint32_t uncached_asr;
|
|
uint32_t bsr;
|
|
|
|
/* Banked registers. */
|
|
uint32_t banked_bsr[6];
|
|
uint32_t banked_r29[6];
|
|
uint32_t banked_r30[6];
|
|
|
|
/* asr flag cache for faster execution */
|
|
uint32_t CF; /* 0 or 1 */
|
|
uint32_t VF; /* V is the bit 31. All other bits are undefined */
|
|
uint32_t NF; /* N is bit 31. All other bits are undefined. */
|
|
uint32_t ZF; /* Z set if zero. */
|
|
|
|
/* System control coprocessor (cp0) */
|
|
struct {
|
|
uint32_t c0_cpuid;
|
|
uint32_t c0_cachetype;
|
|
uint32_t c1_sys; /* System control register. */
|
|
uint32_t c2_base; /* MMU translation table base. */
|
|
uint32_t c3_faultstatus; /* Fault status registers. */
|
|
uint32_t c4_faultaddr; /* Fault address registers. */
|
|
uint32_t c5_cacheop; /* Cache operation registers. */
|
|
uint32_t c6_tlbop; /* TLB operation registers. */
|
|
} cp0;
|
|
|
|
/* UniCore-F64 coprocessor state. */
|
|
struct {
|
|
float64 regs[16];
|
|
uint32_t xregs[32];
|
|
float_status fp_status;
|
|
} ucf64;
|
|
|
|
CPU_COMMON
|
|
|
|
/* Internal CPU feature flags. */
|
|
uint32_t features;
|
|
|
|
} CPUUniCore32State;
|
|
|
|
/**
|
|
* UniCore32CPU:
|
|
* @env: #CPUUniCore32State
|
|
*
|
|
* A UniCore32 CPU.
|
|
*/
|
|
struct UniCore32CPU {
|
|
/*< private >*/
|
|
CPUState parent_obj;
|
|
/*< public >*/
|
|
|
|
CPUUniCore32State env;
|
|
};
|
|
|
|
static inline UniCore32CPU *uc32_env_get_cpu(CPUUniCore32State *env)
|
|
{
|
|
return container_of(env, UniCore32CPU, env);
|
|
}
|
|
|
|
#define ENV_GET_CPU(e) CPU(uc32_env_get_cpu(e))
|
|
|
|
#define ENV_OFFSET offsetof(UniCore32CPU, env)
|
|
|
|
void uc32_cpu_do_interrupt(CPUState *cpu);
|
|
bool uc32_cpu_exec_interrupt(CPUState *cpu, int int_req);
|
|
void uc32_cpu_dump_state(CPUState *cpu, FILE *f,
|
|
fprintf_function cpu_fprintf, int flags);
|
|
hwaddr uc32_cpu_get_phys_page_debug(CPUState *cpu, vaddr addr);
|
|
|
|
#define ASR_M (0x1f)
|
|
#define ASR_MODE_USER (0x10)
|
|
#define ASR_MODE_INTR (0x12)
|
|
#define ASR_MODE_PRIV (0x13)
|
|
#define ASR_MODE_TRAP (0x17)
|
|
#define ASR_MODE_EXTN (0x1b)
|
|
#define ASR_MODE_SUSR (0x1f)
|
|
#define ASR_I (1 << 7)
|
|
#define ASR_V (1 << 28)
|
|
#define ASR_C (1 << 29)
|
|
#define ASR_Z (1 << 30)
|
|
#define ASR_N (1 << 31)
|
|
#define ASR_NZCV (ASR_N | ASR_Z | ASR_C | ASR_V)
|
|
#define ASR_RESERVED (~(ASR_M | ASR_I | ASR_NZCV))
|
|
|
|
#define UC32_EXCP_PRIV (1)
|
|
#define UC32_EXCP_ITRAP (2)
|
|
#define UC32_EXCP_DTRAP (3)
|
|
#define UC32_EXCP_INTR (4)
|
|
|
|
/* Return the current ASR value. */
|
|
target_ulong cpu_asr_read(CPUUniCore32State *env1);
|
|
/* Set the ASR. Note that some bits of mask must be all-set or all-clear. */
|
|
void cpu_asr_write(CPUUniCore32State *env1, target_ulong val, target_ulong mask);
|
|
|
|
/* UniCore-F64 system registers. */
|
|
#define UC32_UCF64_FPSCR (31)
|
|
#define UCF64_FPSCR_MASK (0x27ffffff)
|
|
#define UCF64_FPSCR_RND_MASK (0x7)
|
|
#define UCF64_FPSCR_RND(r) (((r) >> 0) & UCF64_FPSCR_RND_MASK)
|
|
#define UCF64_FPSCR_TRAPEN_MASK (0x7f)
|
|
#define UCF64_FPSCR_TRAPEN(r) (((r) >> 10) & UCF64_FPSCR_TRAPEN_MASK)
|
|
#define UCF64_FPSCR_FLAG_MASK (0x3ff)
|
|
#define UCF64_FPSCR_FLAG(r) (((r) >> 17) & UCF64_FPSCR_FLAG_MASK)
|
|
#define UCF64_FPSCR_FLAG_ZERO (1 << 17)
|
|
#define UCF64_FPSCR_FLAG_INFINITY (1 << 18)
|
|
#define UCF64_FPSCR_FLAG_INVALID (1 << 19)
|
|
#define UCF64_FPSCR_FLAG_UNDERFLOW (1 << 20)
|
|
#define UCF64_FPSCR_FLAG_OVERFLOW (1 << 21)
|
|
#define UCF64_FPSCR_FLAG_INEXACT (1 << 22)
|
|
#define UCF64_FPSCR_FLAG_HUGEINT (1 << 23)
|
|
#define UCF64_FPSCR_FLAG_DENORMAL (1 << 24)
|
|
#define UCF64_FPSCR_FLAG_UNIMP (1 << 25)
|
|
#define UCF64_FPSCR_FLAG_DIVZERO (1 << 26)
|
|
|
|
#define UC32_HWCAP_CMOV 4 /* 1 << 2 */
|
|
#define UC32_HWCAP_UCF64 8 /* 1 << 3 */
|
|
|
|
#define cpu_signal_handler uc32_cpu_signal_handler
|
|
|
|
int uc32_cpu_signal_handler(int host_signum, void *pinfo, void *puc);
|
|
|
|
/* MMU modes definitions */
|
|
#define MMU_MODE0_SUFFIX _kernel
|
|
#define MMU_MODE1_SUFFIX _user
|
|
#define MMU_USER_IDX 1
|
|
static inline int cpu_mmu_index(CPUUniCore32State *env, bool ifetch)
|
|
{
|
|
return (env->uncached_asr & ASR_M) == ASR_MODE_USER ? 1 : 0;
|
|
}
|
|
|
|
#include "exec/cpu-all.h"
|
|
|
|
#define cpu_init(cpu_model) cpu_generic_init(TYPE_UNICORE32_CPU, cpu_model)
|
|
|
|
#define UNICORE32_CPU_TYPE_SUFFIX "-" TYPE_UNICORE32_CPU
|
|
#define UNICORE32_CPU_TYPE_NAME(model) model UNICORE32_CPU_TYPE_SUFFIX
|
|
|
|
static inline void cpu_get_tb_cpu_state(CPUUniCore32State *env, target_ulong *pc,
|
|
target_ulong *cs_base, uint32_t *flags)
|
|
{
|
|
*pc = env->regs[31];
|
|
*cs_base = 0;
|
|
*flags = 0;
|
|
if ((env->uncached_asr & ASR_M) != ASR_MODE_USER) {
|
|
*flags |= (1 << 6);
|
|
}
|
|
}
|
|
|
|
int uc32_cpu_handle_mmu_fault(CPUState *cpu, vaddr address, int size, int rw,
|
|
int mmu_idx);
|
|
void uc32_translate_init(void);
|
|
void switch_mode(CPUUniCore32State *, int);
|
|
|
|
#endif /* UNICORE32_CPU_H */
|