1 #ifndef CPU_PPC_H 2 #define CPU_PPC_H 3 4 /* 5 * Copyright (C) 2005-2012 Anders Gavare. All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions are met: 9 * 10 * 1. Redistributions of source code must retain the above copyright 11 * notice, this list of conditions and the following disclaimer. 12 * 2. Redistributions in binary form must reproduce the above copyright 13 * notice, this list of conditions and the following disclaimer in the 14 * documentation and/or other materials provided with the distribution. 15 * 3. The name of the author may not be used to endorse or promote products 16 * derived from this software without specific prior written permission. 17 * 18 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 19 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 20 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 21 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 22 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 23 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 24 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 25 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 26 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 27 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 28 * SUCH DAMAGE. 29 * 30 * 31 * POWER and PowerPC CPU definitions. 32 */ 33 34 #include "misc.h" 35 36 37 struct cpu_family; 38 39 #define MODE_PPC 0 40 #define MODE_POWER 1 41 42 /* PPC CPU types: */ 43 struct ppc_cpu_type_def { 44 const char *name; 45 int pvr; 46 int bits; 47 int flags; 48 int icache_shift; 49 int ilinesize; 50 int iway; 51 int dcache_shift; 52 int dlinesize; 53 int dway; 54 int l2cache_shift; 55 int l2linesize; 56 int l2way; 57 int altivec; 58 59 /* TODO: POWER vs PowerPC? */ 60 }; 61 62 /* Flags: */ 63 #define PPC_NOFP 1 64 #define PPC_601 2 65 #define PPC_603 4 66 #define PPC_NO_DEC 8 /* No DEC (decrementer) SPR */ 67 68 /* 69 * TODO: Most of these just bogus 70 */ 71 72 #define PPC_CPU_TYPE_DEFS { \ 73 { "PPC405GP", 0x40110000, 32, PPC_NOFP|PPC_NO_DEC, \ 74 13,5,2, 13,5,2, 0,5,1, 0 }, \ 75 { "PPC601", 0, 32, PPC_601, 14,5,4, 14,5,4, 0,0,0, 0 },\ 76 { "PPC603", 0x00030302, 32, PPC_603, 14,5,4, 14,5,4, 0,0,0, 0 },\ 77 { "PPC603e", 0x00060104, 32, PPC_603, 14,5,4, 14,5,4, 0,0,0, 0 },\ 78 { "PPC604", 0x00040304, 32, 0, 15,5,4, 15,5,4, 0,0,0, 0 }, \ 79 { "PPC620", 0x00140000, 64, 0, 15,5,4, 15,5,4, 0,0,0, 0 }, \ 80 { "MPC7400", 0x000c0000, 32, 0, 15,5,2, 15,5,2, 19,5,1, 1 }, \ 81 { "PPC750", 0x00084202, 32, 0, 15,5,2, 15,5,2, 20,5,1, 0 }, \ 82 { "G4e", 0, 32, 0, 15,5,8, 15,5,8, 18,5,8, 1 }, \ 83 { "PPC970", 0x00390000, 64, 0, 16,7,1, 15,7,2, 19,7,1, 1 }, \ 84 { NULL, 0, 0,0,0,0,0,0,0,0,0,0,0,0 } \ 85 } 86 87 #define PPC_NGPRS 32 88 #define PPC_NFPRS 32 89 #define PPC_NVRS 32 90 #define PPC_N_TGPRS 4 91 92 #define PPC_N_IC_ARGS 3 93 #define PPC_INSTR_ALIGNMENT_SHIFT 2 94 #define PPC_IC_ENTRIES_SHIFT 10 95 #define PPC_IC_ENTRIES_PER_PAGE (1 << PPC_IC_ENTRIES_SHIFT) 96 #define PPC_PC_TO_IC_ENTRY(a) (((a)>>PPC_INSTR_ALIGNMENT_SHIFT) \ 97 & (PPC_IC_ENTRIES_PER_PAGE-1)) 98 #define PPC_ADDR_TO_PAGENR(a) ((a) >> (PPC_IC_ENTRIES_SHIFT \ 99 + PPC_INSTR_ALIGNMENT_SHIFT)) 100 101 #define PPC_L2N 17 102 #define PPC_L3N 18 103 104 DYNTRANS_MISC_DECLARATIONS(ppc,PPC,uint64_t) 105 DYNTRANS_MISC64_DECLARATIONS(ppc,PPC,uint8_t) 106 107 #define PPC_MAX_VPH_TLB_ENTRIES 128 108 109 110 struct ppc_cpu { 111 struct ppc_cpu_type_def cpu_type; 112 113 uint64_t of_emul_addr; 114 115 int mode; /* MODE_PPC or MODE_POWER */ 116 int bits; /* 32 or 64 */ 117 118 int irq_asserted; /* External Interrupt flag */ 119 int dec_intr_pending;/* Decrementer interrupt pending */ 120 uint64_t zero; /* A zero register */ 121 122 uint32_t cr; /* Condition Register */ 123 uint32_t fpscr; /* FP Status and Control Register */ 124 uint64_t gpr[PPC_NGPRS]; /* General Purpose Registers */ 125 uint64_t fpr[PPC_NFPRS]; /* Floating-Point Registers */ 126 127 uint64_t vr_hi[PPC_NVRS];/* 128-bit Vector registers */ 128 uint64_t vr_lo[PPC_NVRS];/* (Hi and lo 64-bit parts) */ 129 130 uint64_t msr; /* Machine state register */ 131 uint64_t tgpr[PPC_N_TGPRS];/*Temporary gpr 0..3 */ 132 133 uint32_t sr[16]; /* Segment registers. */ 134 uint64_t spr[1024]; 135 136 uint64_t ll_addr; /* Load-linked / store-conditional */ 137 int ll_bit; 138 139 140 /* 141 * Instruction translation cache and Virtual->Physical->Host 142 * address translation: 143 */ 144 DYNTRANS_ITC(ppc) 145 VPH_TLBS(ppc,PPC) 146 VPH32(ppc,PPC) 147 VPH64(ppc,PPC) 148 }; 149 150 151 /* Machine status word bits: (according to Book 3) */ 152 #define PPC_MSR_SF (1ULL << 63) /* Sixty-Four-Bit Mode */ 153 /* bits 62..61 are reserved */ 154 #define PPC_MSR_HV (1ULL << 60) /* Hypervisor */ 155 /* bits 59..17 are reserved */ 156 #define PPC_MSR_VEC (1 << 25) /* Altivec Enable */ 157 #define PPC_MSR_TGPR (1 << 17) /* Temporary gpr0..3 */ 158 #define PPC_MSR_ILE (1 << 16) /* Interrupt Little-Endian Mode */ 159 #define PPC_MSR_EE (1 << 15) /* External Interrupt Enable */ 160 #define PPC_MSR_PR (1 << 14) /* Problem/Privilege State */ 161 #define PPC_MSR_FP (1 << 13) /* Floating-Point Available */ 162 #define PPC_MSR_ME (1 << 12) /* Machine Check Interrupt Enable */ 163 #define PPC_MSR_FE0 (1 << 11) /* Floating-Point Exception Mode 0 */ 164 #define PPC_MSR_SE (1 << 10) /* Single-Step Trace Enable */ 165 #define PPC_MSR_BE (1 << 9) /* Branch Trace Enable */ 166 #define PPC_MSR_FE1 (1 << 8) /* Floating-Point Exception Mode 1 */ 167 #define PPC_MSR_IP (1 << 6) /* Vector Table at 0xfff00000 */ 168 #define PPC_MSR_IR (1 << 5) /* Instruction Relocate */ 169 #define PPC_MSR_DR (1 << 4) /* Data Relocate */ 170 #define PPC_MSR_PMM (1 << 2) /* Performance Monitor Mark */ 171 #define PPC_MSR_RI (1 << 1) /* Recoverable Interrupt */ 172 #define PPC_MSR_LE (1) /* Little-Endian Mode */ 173 174 /* Floating-point Status: */ 175 #define PPC_FPSCR_FX (1 << 31) /* Exception summary */ 176 #define PPC_FPSCR_FEX (1 << 30) /* Enabled Exception summary */ 177 #define PPC_FPSCR_VX (1 << 29) /* Invalid Operation summary */ 178 /* .. TODO */ 179 #define PPC_FPSCR_VXNAN (1 << 24) 180 /* .. TODO */ 181 #define PPC_FPSCR_FPCC 0x0000f000 182 #define PPC_FPSCR_FPCC_SHIFT 12 183 #define PPC_FPSCR_FL (1 << 15) /* Less than */ 184 #define PPC_FPSCR_FG (1 << 14) /* Greater than */ 185 #define PPC_FPSCR_FE (1 << 13) /* Equal or Zero */ 186 #define PPC_FPSCR_FU (1 << 12) /* Unordered or NaN */ 187 188 /* Exceptions: */ 189 #define PPC_EXCEPTION_DSI 0x3 /* Data Storage Interrupt */ 190 #define PPC_EXCEPTION_ISI 0x4 /* Instruction Storage Interrupt */ 191 #define PPC_EXCEPTION_EI 0x5 /* External interrupt */ 192 #define PPC_EXCEPTION_FPU 0x8 /* Floating-Point unavailable */ 193 #define PPC_EXCEPTION_DEC 0x9 /* Decrementer */ 194 #define PPC_EXCEPTION_SC 0xc /* Syscall */ 195 196 /* XER bits: */ 197 #define PPC_XER_SO (1UL << 31) /* Summary Overflow */ 198 #define PPC_XER_OV (1 << 30) /* Overflow */ 199 #define PPC_XER_CA (1 << 29) /* Carry */ 200 201 202 /* cpu_ppc.c: */ 203 int ppc_run_instr(struct cpu *cpu); 204 int ppc32_run_instr(struct cpu *cpu); 205 void ppc_exception(struct cpu *cpu, int exception_nr); 206 void ppc_update_translation_table(struct cpu *cpu, uint64_t vaddr_page, 207 unsigned char *host_page, int writeflag, uint64_t paddr_page); 208 void ppc32_update_translation_table(struct cpu *cpu, uint64_t vaddr_page, 209 unsigned char *host_page, int writeflag, uint64_t paddr_page); 210 void ppc_invalidate_translation_caches(struct cpu *cpu, uint64_t, int); 211 void ppc32_invalidate_translation_caches(struct cpu *cpu, uint64_t, int); 212 void ppc_invalidate_code_translation(struct cpu *cpu, uint64_t, int); 213 void ppc32_invalidate_code_translation(struct cpu *cpu, uint64_t, int); 214 void ppc_init_64bit_dummy_tables(struct cpu *cpu); 215 int ppc_memory_rw(struct cpu *cpu, struct memory *mem, uint64_t vaddr, 216 unsigned char *data, size_t len, int writeflag, int cache_flags); 217 int ppc_cpu_family_init(struct cpu_family *); 218 219 /* memory_ppc.c: */ 220 int ppc_translate_v2p(struct cpu *cpu, uint64_t vaddr, 221 uint64_t *return_addr, int flags); 222 223 #endif /* CPU_PPC_H */ 224