1 /* 2 * Copyright 2003-2004, Axel Dörfler, axeld@pinc-software.de. 3 * Distributed under the terms of the MIT License. 4 */ 5 #ifndef _KERNEL_ARCH_PPC_CPU_H 6 #define _KERNEL_ARCH_PPC_CPU_H 7 8 9 #include <arch/ppc/arch_thread_types.h> 10 #include <arch/ppc/cpu.h> 11 #include <kernel.h> 12 13 14 #define CPU_MAX_CACHE_LEVEL 8 15 #define CACHE_LINE_SIZE 128 16 // 128 Byte lines on PPC970 17 18 19 #define set_ac() 20 #define clear_ac() 21 22 23 struct iframe { 24 uint32 vector; 25 uint32 srr0; 26 uint32 srr1; 27 uint32 dar; 28 uint32 dsisr; 29 uint32 lr; 30 uint32 cr; 31 uint32 xer; 32 uint32 ctr; 33 uint32 fpscr; 34 uint32 r31; 35 uint32 r30; 36 uint32 r29; 37 uint32 r28; 38 uint32 r27; 39 uint32 r26; 40 uint32 r25; 41 uint32 r24; 42 uint32 r23; 43 uint32 r22; 44 uint32 r21; 45 uint32 r20; 46 uint32 r19; 47 uint32 r18; 48 uint32 r17; 49 uint32 r16; 50 uint32 r15; 51 uint32 r14; 52 uint32 r13; 53 uint32 r12; 54 uint32 r11; 55 uint32 r10; 56 uint32 r9; 57 uint32 r8; 58 uint32 r7; 59 uint32 r6; 60 uint32 r5; 61 uint32 r4; 62 uint32 r3; 63 uint32 r2; 64 uint32 r1; 65 uint32 r0; 66 double f31; 67 double f30; 68 double f29; 69 double f28; 70 double f27; 71 double f26; 72 double f25; 73 double f24; 74 double f23; 75 double f22; 76 double f21; 77 double f20; 78 double f19; 79 double f18; 80 double f17; 81 double f16; 82 double f15; 83 double f14; 84 double f13; 85 double f12; 86 double f11; 87 double f10; 88 double f9; 89 double f8; 90 double f7; 91 double f6; 92 double f5; 93 double f4; 94 double f3; 95 double f2; 96 double f1; 97 double f0; 98 }; 99 100 enum machine_state { 101 MSR_EXCEPTIONS_ENABLED = 1L << 15, // EE 102 MSR_PRIVILEGE_LEVEL = 1L << 14, // PR 103 MSR_FP_AVAILABLE = 1L << 13, // FP 104 MSR_MACHINE_CHECK_ENABLED = 1L << 12, // ME 105 MSR_EXCEPTION_PREFIX = 1L << 6, // IP 106 MSR_INST_ADDRESS_TRANSLATION = 1L << 5, // IR 107 MSR_DATA_ADDRESS_TRANSLATION = 1L << 4, // DR 108 }; 109 110 struct block_address_translation; 111 112 typedef struct arch_cpu_info { 113 int null; 114 } arch_cpu_info; 115 116 117 #define eieio() asm volatile("eieio") 118 #define isync() asm volatile("isync") 119 #define tlbsync() asm volatile("tlbsync") 120 #define ppc_sync() asm volatile("sync") 121 #define tlbia() asm volatile("tlbia") 122 #define tlbie(addr) asm volatile("tlbie %0" :: "r" (addr)) 123 124 // adjust thread priority on PowerPC (Shared resource hints) 125 #define SRH_very_low() asm volatile("or 31,31,31") 126 #define SRH_low() asm volatile("or 1,1,1") 127 #define SRH_medium_low() asm volatile("or 6,6,6") 128 #define SRH_medium() asm volatile("or 2,2,2") 129 #define SRH_medium_high() asm volatile("or 5,5,5") 130 #define SRH_high() asm volatile("or 3,3,3") 131 132 133 #ifdef __cplusplus 134 extern "C" { 135 #endif 136 137 extern uint32 get_sdr1(void); 138 extern void set_sdr1(uint32 value); 139 extern uint32 get_sr(void *virtualAddress); 140 extern void set_sr(void *virtualAddress, uint32 value); 141 extern uint32 get_msr(void); 142 extern uint32 set_msr(uint32 value); 143 extern uint32 get_pvr(void); 144 145 extern void set_ibat0(struct block_address_translation *bat); 146 extern void set_ibat1(struct block_address_translation *bat); 147 extern void set_ibat2(struct block_address_translation *bat); 148 extern void set_ibat3(struct block_address_translation *bat); 149 extern void set_dbat0(struct block_address_translation *bat); 150 extern void set_dbat1(struct block_address_translation *bat); 151 extern void set_dbat2(struct block_address_translation *bat); 152 extern void set_dbat3(struct block_address_translation *bat); 153 154 extern void get_ibat0(struct block_address_translation *bat); 155 extern void get_ibat1(struct block_address_translation *bat); 156 extern void get_ibat2(struct block_address_translation *bat); 157 extern void get_ibat3(struct block_address_translation *bat); 158 extern void get_dbat0(struct block_address_translation *bat); 159 extern void get_dbat1(struct block_address_translation *bat); 160 extern void get_dbat2(struct block_address_translation *bat); 161 extern void get_dbat3(struct block_address_translation *bat); 162 163 extern void reset_ibats(void); 164 extern void reset_dbats(void); 165 166 //extern void sethid0(unsigned int val); 167 //extern unsigned int getl2cr(void); 168 //extern void setl2cr(unsigned int val); 169 extern long long get_time_base(void); 170 171 void __ppc_setup_system_time(vint32 *cvFactor); 172 // defined in libroot: os/arch/system_time.c 173 int64 __ppc_get_time_base(void); 174 // defined in libroot: os/arch/system_time_asm.S 175 176 extern void ppc_context_switch(void **_oldStackPointer, void *newStackPointer); 177 178 extern bool ppc_set_fault_handler(addr_t *handlerLocation, addr_t handler) 179 __attribute__((noinline)); 180 181 182 static inline void 183 arch_cpu_pause(void) 184 { 185 // TODO: PowerPC review logic of setting very low for pause 186 SRH_very_low(); 187 } 188 189 190 static inline void 191 arch_cpu_idle(void) 192 { 193 // TODO: PowerPC CPU idle call 194 } 195 196 197 #ifdef __cplusplus 198 } 199 #endif 200 201 // PowerPC processor version (the upper 16 bits of the PVR). 202 enum ppc_processor_version { 203 MPC601 = 0x0001, 204 MPC603 = 0x0003, 205 MPC604 = 0x0004, 206 MPC602 = 0x0005, 207 MPC603e = 0x0006, 208 MPC603ev = 0x0007, 209 MPC750 = 0x0008, 210 MPC604ev = 0x0009, 211 MPC7400 = 0x000c, 212 MPC620 = 0x0014, 213 IBM403 = 0x0020, 214 IBM401A1 = 0x0021, 215 IBM401B2 = 0x0022, 216 IBM401C2 = 0x0023, 217 IBM401D2 = 0x0024, 218 IBM401E2 = 0x0025, 219 IBM401F2 = 0x0026, 220 IBM401G2 = 0x0027, 221 IBMPOWER3 = 0x0041, 222 MPC860 = 0x0050, 223 MPC8240 = 0x0081, 224 AMCC460EX = 0x1302, 225 IBM405GP = 0x4011, 226 IBM405L = 0x4161, 227 AMCC440EP = 0x4222, 228 IBM750FX = 0x7000, 229 MPC7450 = 0x8000, 230 MPC7455 = 0x8001, 231 MPC7457 = 0x8002, 232 MPC7447A = 0x8003, 233 MPC7448 = 0x8004, 234 MPC7410 = 0x800c, 235 MPC8245 = 0x8081, 236 }; 237 238 239 /* 240 Use of (some) special purpose registers. 241 242 SPRG0: per CPU physical address pointer to an ppc_cpu_exception_context 243 structure 244 SPRG1: scratch 245 SPRG2: current Thread* 246 SPRG3: TLS base pointer (only for userland threads) 247 */ 248 249 #endif /* _KERNEL_ARCH_PPC_CPU_H */ 250