locore.h revision 1.69
1/* $NetBSD: locore.h,v 1.69 2005/09/08 15:13:23 tsutsui Exp $ */ 2 3/* 4 * Copyright 1996 The Board of Trustees of The Leland Stanford 5 * Junior University. All Rights Reserved. 6 * 7 * Permission to use, copy, modify, and distribute this 8 * software and its documentation for any purpose and without 9 * fee is hereby granted, provided that the above copyright 10 * notice appear in all copies. Stanford University 11 * makes no representations about the suitability of this 12 * software for any purpose. It is provided "as is" without 13 * express or implied warranty. 14 */ 15 16/* 17 * Jump table for MIPS CPU locore functions that are implemented 18 * differently on different generations, or instruction-level 19 * archtecture (ISA) level, the Mips family. 20 * 21 * We currently provide support for MIPS I and MIPS III. 22 */ 23 24#ifndef _MIPS_LOCORE_H 25#define _MIPS_LOCORE_H 26 27#ifndef _LKM 28#include "opt_cputype.h" 29#endif 30 31#include <mips/cpuregs.h> 32 33struct tlb; 34 35uint32_t mips_cp0_cause_read(void); 36void mips_cp0_cause_write(uint32_t); 37uint32_t mips_cp0_status_read(void); 38void mips_cp0_status_write(uint32_t); 39 40#ifdef MIPS1 41void mips1_SetPID(int); 42void mips1_TBIA(int); 43void mips1_TBIAP(int); 44void mips1_TBIS(vaddr_t); 45int mips1_TLBUpdate(u_int, u_int); 46void mips1_wbflush(void); 47void mips1_proc_trampoline(void); 48void mips1_cpu_switch_resume(void); 49 50uint32_t tx3900_cp0_config_read(void); 51#endif 52 53#if defined(MIPS3) || defined(MIPS4) 54void mips3_SetPID(int); 55void mips3_TBIA(int); 56void mips3_TBIAP(int); 57void mips3_TBIS(vaddr_t); 58int mips3_TLBUpdate(u_int, u_int); 59void mips3_TLBRead(int, struct tlb *); 60void mips3_wbflush(void); 61void mips3_proc_trampoline(void); 62void mips3_cpu_switch_resume(void); 63void mips3_pagezero(caddr_t dst); 64 65#ifdef MIPS3_5900 66void mips5900_SetPID(int); 67void mips5900_TBIA(int); 68void mips5900_TBIAP(int); 69void mips5900_TBIS(vaddr_t); 70int mips5900_TLBUpdate(u_int, u_int); 71void mips5900_TLBRead(int, struct tlb *); 72void mips5900_wbflush(void); 73void mips5900_proc_trampoline(void); 74void mips5900_cpu_switch_resume(void); 75void mips5900_pagezero(caddr_t dst); 76#endif 77#endif 78 79#ifdef MIPS32 80void mips32_SetPID(int); 81void mips32_TBIA(int); 82void mips32_TBIAP(int); 83void mips32_TBIS(vaddr_t); 84int mips32_TLBUpdate(u_int, u_int); 85void mips32_TLBRead(int, struct tlb *); 86void mips32_wbflush(void); 87void mips32_proc_trampoline(void); 88void mips32_cpu_switch_resume(void); 89#endif 90 91#ifdef MIPS64 92void mips64_SetPID(int); 93void mips64_TBIA(int); 94void mips64_TBIAP(int); 95void mips64_TBIS(vaddr_t); 96int mips64_TLBUpdate(u_int, u_int); 97void mips64_TLBRead(int, struct tlb *); 98void mips64_wbflush(void); 99void mips64_proc_trampoline(void); 100void mips64_cpu_switch_resume(void); 101void mips64_pagezero(caddr_t dst); 102#endif 103 104#if defined(MIPS3) || defined(MIPS4) || defined(MIPS32) || defined(MIPS64) 105uint32_t mips3_cp0_compare_read(void); 106void mips3_cp0_compare_write(uint32_t); 107 108uint32_t mips3_cp0_config_read(void); 109void mips3_cp0_config_write(uint32_t); 110#if defined(MIPS32) || defined(MIPS64) 111uint32_t mipsNN_cp0_config1_read(void); 112void mipsNN_cp0_config1_write(uint32_t); 113uint32_t mipsNN_cp0_config2_read(void); 114uint32_t mipsNN_cp0_config3_read(void); 115#endif 116 117uint32_t mips3_cp0_count_read(void); 118void mips3_cp0_count_write(uint32_t); 119 120uint32_t mips3_cp0_wired_read(void); 121void mips3_cp0_wired_write(uint32_t); 122void mips3_cp0_pg_mask_write(uint32_t); 123 124uint64_t mips3_ld(uint64_t *); 125void mips3_sd(uint64_t *, uint64_t); 126#endif /* MIPS3 || MIPS4 || MIPS32 || MIPS64 */ 127 128#if defined(MIPS3) || defined(MIPS4) || defined(MIPS64) 129static inline uint32_t mips3_lw_a64(uint64_t addr) 130 __attribute__((__unused__)); 131static inline void mips3_sw_a64(uint64_t addr, uint32_t val) 132 __attribute__ ((__unused__)); 133 134static inline uint32_t 135mips3_lw_a64(uint64_t addr) 136{ 137 uint32_t addrlo, addrhi; 138 uint32_t rv; 139 uint32_t sr; 140 141 sr = mips_cp0_status_read(); 142 mips_cp0_status_write(sr | MIPS3_SR_KX); 143 144 addrlo = addr & 0xffffffff; 145 addrhi = addr >> 32; 146 __asm__ __volatile__ (" \n\ 147 .set push \n\ 148 .set mips3 \n\ 149 .set noreorder \n\ 150 .set noat \n\ 151 dsll32 $3, %1, 0 \n\ 152 dsll32 $1, %2, 0 \n\ 153 dsrl32 $3, $3, 0 \n\ 154 or $1, $1, $3 \n\ 155 lw %0, 0($1) \n\ 156 .set pop \n\ 157 " : "=r"(rv) : "r"(addrlo), "r"(addrhi) : "$1", "$3" ); 158 159 mips_cp0_status_write(sr); 160 161 return (rv); 162} 163 164static inline void 165mips3_sw_a64(uint64_t addr, uint32_t val) 166{ 167 uint32_t addrlo, addrhi; 168 uint32_t sr; 169 170 sr = mips_cp0_status_read(); 171 mips_cp0_status_write(sr | MIPS3_SR_KX); 172 173 addrlo = addr & 0xffffffff; 174 addrhi = addr >> 32; 175 __asm__ __volatile__ (" \n\ 176 .set push \n\ 177 .set mips3 \n\ 178 .set noreorder \n\ 179 .set noat \n\ 180 dsll32 $3, %1, 0 \n\ 181 dsll32 $1, %2, 0 \n\ 182 dsrl32 $3, $3, 0 \n\ 183 or $1, $1, $3 \n\ 184 sw %0, 0($1) \n\ 185 .set pop \n\ 186 " : : "r"(val), "r"(addrlo), "r"(addrhi) : "$1", "$3" ); 187 188 mips_cp0_status_write(sr); 189} 190#endif /* MIPS3 || MIPS4 || MIPS64 */ 191 192/* 193 * A vector with an entry for each mips-ISA-level dependent 194 * locore function, and macros which jump through it. 195 * 196 * XXX the macro names are chosen to be compatible with the old 197 * XXX Sprite coding-convention names used in 4.4bsd/pmax. 198 */ 199typedef struct { 200 void (*setTLBpid)(int pid); 201 void (*TBIAP)(int); 202 void (*TBIS)(vaddr_t); 203 int (*tlbUpdate)(u_int highreg, u_int lowreg); 204 void (*wbflush)(void); 205} mips_locore_jumpvec_t; 206 207void mips_set_wbflush(void (*)(void)); 208void mips_wait_idle(void); 209 210void stacktrace(void); 211void logstacktrace(void); 212 213/* 214 * The "active" locore-fuction vector, and 215 */ 216extern mips_locore_jumpvec_t mips_locore_jumpvec; 217extern long *mips_locoresw[]; 218 219#if defined(MIPS1) && !defined(MIPS3) && !defined(MIPS32) && !defined(MIPS64) 220#define MachSetPID mips1_SetPID 221#define MIPS_TBIAP() mips1_TBIAP(mips_num_tlb_entries) 222#define MIPS_TBIS mips1_TBIS 223#define MachTLBUpdate mips1_TLBUpdate 224#define wbflush() mips1_wbflush() 225#define proc_trampoline mips1_proc_trampoline 226#elif !defined(MIPS1) && defined(MIPS3) && !defined(MIPS32) && !defined(MIPS64) && !defined(MIPS3_5900) 227#define MachSetPID mips3_SetPID 228#define MIPS_TBIAP() mips3_TBIAP(mips_num_tlb_entries) 229#define MIPS_TBIS mips3_TBIS 230#define MachTLBUpdate mips3_TLBUpdate 231#define proc_trampoline mips3_proc_trampoline 232#define wbflush() mips3_wbflush() 233#elif !defined(MIPS1) && !defined(MIPS3) && defined(MIPS32) && !defined(MIPS64) 234#define MachSetPID mips32_SetPID 235#define MIPS_TBIAP() mips32_TBIAP(mips_num_tlb_entries) 236#define MIPS_TBIS mips32_TBIS 237#define MachTLBUpdate mips32_TLBUpdate 238#define proc_trampoline mips32_proc_trampoline 239#define wbflush() mips32_wbflush() 240#elif !defined(MIPS1) && !defined(MIPS3) && !defined(MIPS32) && defined(MIPS64) 241 /* all common with mips3 */ 242#define MachSetPID mips64_SetPID 243#define MIPS_TBIAP() mips64_TBIAP(mips_num_tlb_entries) 244#define MIPS_TBIS mips64_TBIS 245#define MachTLBUpdate mips64_TLBUpdate 246#define proc_trampoline mips64_proc_trampoline 247#define wbflush() mips64_wbflush() 248#elif !defined(MIPS1) && defined(MIPS3) && !defined(MIPS32) && !defined(MIPS64) && defined(MIPS3_5900) 249#define MachSetPID mips5900_SetPID 250#define MIPS_TBIAP() mips5900_TBIAP(mips_num_tlb_entries) 251#define MIPS_TBIS mips5900_TBIS 252#define MachTLBUpdate mips5900_TLBUpdate 253#define proc_trampoline mips5900_proc_trampoline 254#define wbflush() mips5900_wbflush() 255#else 256#define MachSetPID (*(mips_locore_jumpvec.setTLBpid)) 257#define MIPS_TBIAP() (*(mips_locore_jumpvec.TBIAP))(mips_num_tlb_entries) 258#define MIPS_TBIS (*(mips_locore_jumpvec.TBIS)) 259#define MachTLBUpdate (*(mips_locore_jumpvec.tlbUpdate)) 260#define wbflush() (*(mips_locore_jumpvec.wbflush))() 261#define proc_trampoline (mips_locoresw[1]) 262#endif 263 264#define CPU_IDLE (mips_locoresw[2]) 265 266/* cpu_switch_resume is called inside locore.S */ 267 268/* 269 * CPU identification, from PRID register. 270 */ 271typedef int mips_prid_t; 272 273#define MIPS_PRID_REV(x) (((x) >> 0) & 0x00ff) 274#define MIPS_PRID_IMPL(x) (((x) >> 8) & 0x00ff) 275 276/* pre-MIPS32/64 */ 277#define MIPS_PRID_RSVD(x) (((x) >> 16) & 0xffff) 278#define MIPS_PRID_REV_MIN(x) ((MIPS_PRID_REV(x) >> 0) & 0x0f) 279#define MIPS_PRID_REV_MAJ(x) ((MIPS_PRID_REV(x) >> 4) & 0x0f) 280 281/* MIPS32/64 */ 282#define MIPS_PRID_CID(x) (((x) >> 16) & 0x00ff) /* Company ID */ 283#define MIPS_PRID_CID_PREHISTORIC 0x00 /* Not MIPS32/64 */ 284#define MIPS_PRID_CID_MTI 0x01 /* MIPS Technologies, Inc. */ 285#define MIPS_PRID_CID_BROADCOM 0x02 /* Broadcom */ 286#define MIPS_PRID_CID_ALCHEMY 0x03 /* Alchemy Semiconductor */ 287#define MIPS_PRID_CID_SIBYTE 0x04 /* SiByte */ 288#define MIPS_PRID_CID_SANDCRAFT 0x05 /* SandCraft */ 289#define MIPS_PRID_CID_PHILIPS 0x06 /* Philips */ 290#define MIPS_PRID_CID_TOSHIBA 0x07 /* Toshiba */ 291#define MIPS_PRID_CID_LSI 0x08 /* LSI */ 292 /* 0x09 unannounced */ 293 /* 0x0a unannounced */ 294#define MIPS_PRID_CID_LEXRA 0x0b /* Lexra */ 295#define MIPS_PRID_COPTS(x) (((x) >> 24) & 0x00ff) /* Company Options */ 296 297#ifdef _KERNEL 298/* 299 * Global variables used to communicate CPU type, and parameters 300 * such as cache size, from locore to higher-level code (e.g., pmap). 301 */ 302 303extern mips_prid_t cpu_id; 304extern mips_prid_t fpu_id; 305extern int mips_num_tlb_entries; 306 307void mips_pagecopy(caddr_t dst, caddr_t src); 308void mips_pagezero(caddr_t dst); 309 310#ifdef __HAVE_MIPS_MACHDEP_CACHE_CONFIG 311void mips_machdep_cache_config(void); 312#endif 313 314/* 315 * trapframe argument passed to trap() 316 */ 317 318#define TF_AST 0 319#define TF_V0 1 320#define TF_V1 2 321#define TF_A0 3 322#define TF_A1 4 323#define TF_A2 5 324#define TF_A3 6 325#define TF_T0 7 326#define TF_T1 8 327#define TF_T2 9 328#define TF_T3 10 329 330#if defined(__mips_n32) || defined(__mips_n64) 331#define TF_A4 11 332#define TF_A5 12 333#define TF_A6 13 334#define TF_A7 14 335#else 336#define TF_T4 11 337#define TF_T5 12 338#define TF_T6 13 339#define TF_T7 14 340#endif /* __mips_n32 || __mips_n64 */ 341 342#define TF_TA0 11 343#define TF_TA1 12 344#define TF_TA2 13 345#define TF_TA3 14 346 347#define TF_T8 15 348#define TF_T9 16 349 350#define TF_RA 17 351#define TF_SR 18 352#define TF_MULLO 19 353#define TF_MULHI 20 354#define TF_EPC 21 /* may be changed by trap() call */ 355 356#define TF_NREGS 22 357 358struct trapframe { 359 mips_reg_t tf_regs[TF_NREGS]; 360 u_int32_t tf_ppl; /* previous priority level */ 361 int32_t tf_pad; /* for 8 byte aligned */ 362}; 363 364/* 365 * Stack frame for kernel traps. four args passed in registers. 366 * A trapframe is pointed to by the 5th arg, and a dummy sixth argument 367 * is used to avoid alignment problems 368 */ 369 370struct kernframe { 371 register_t cf_args[4 + 1]; 372 register_t cf_pad; /* (for 8 word alignment) */ 373 register_t cf_sp; 374 register_t cf_ra; 375 struct trapframe cf_frame; 376}; 377#endif /* _KERNEL */ 378#endif /* _MIPS_LOCORE_H */ 379