1*4882a593Smuzhiyun /* 2*4882a593Smuzhiyun * PowerPC memory management structures 3*4882a593Smuzhiyun */ 4*4882a593Smuzhiyun 5*4882a593Smuzhiyun #ifndef _PPC_MMU_H_ 6*4882a593Smuzhiyun #define _PPC_MMU_H_ 7*4882a593Smuzhiyun 8*4882a593Smuzhiyun #ifndef __ASSEMBLY__ 9*4882a593Smuzhiyun /* Hardware Page Table Entry */ 10*4882a593Smuzhiyun typedef struct _PTE { 11*4882a593Smuzhiyun #ifdef CONFIG_PPC64BRIDGE 12*4882a593Smuzhiyun unsigned long long vsid:52; 13*4882a593Smuzhiyun unsigned long api:5; 14*4882a593Smuzhiyun unsigned long :5; 15*4882a593Smuzhiyun unsigned long h:1; 16*4882a593Smuzhiyun unsigned long v:1; 17*4882a593Smuzhiyun unsigned long long rpn:52; 18*4882a593Smuzhiyun #else /* CONFIG_PPC64BRIDGE */ 19*4882a593Smuzhiyun unsigned long v:1; /* Entry is valid */ 20*4882a593Smuzhiyun unsigned long vsid:24; /* Virtual segment identifier */ 21*4882a593Smuzhiyun unsigned long h:1; /* Hash algorithm indicator */ 22*4882a593Smuzhiyun unsigned long api:6; /* Abbreviated page index */ 23*4882a593Smuzhiyun unsigned long rpn:20; /* Real (physical) page number */ 24*4882a593Smuzhiyun #endif /* CONFIG_PPC64BRIDGE */ 25*4882a593Smuzhiyun unsigned long :3; /* Unused */ 26*4882a593Smuzhiyun unsigned long r:1; /* Referenced */ 27*4882a593Smuzhiyun unsigned long c:1; /* Changed */ 28*4882a593Smuzhiyun unsigned long w:1; /* Write-thru cache mode */ 29*4882a593Smuzhiyun unsigned long i:1; /* Cache inhibited */ 30*4882a593Smuzhiyun unsigned long m:1; /* Memory coherence */ 31*4882a593Smuzhiyun unsigned long g:1; /* Guarded */ 32*4882a593Smuzhiyun unsigned long :1; /* Unused */ 33*4882a593Smuzhiyun unsigned long pp:2; /* Page protection */ 34*4882a593Smuzhiyun } PTE; 35*4882a593Smuzhiyun 36*4882a593Smuzhiyun /* Values for PP (assumes Ks=0, Kp=1) */ 37*4882a593Smuzhiyun #define PP_RWXX 0 /* Supervisor read/write, User none */ 38*4882a593Smuzhiyun #define PP_RWRX 1 /* Supervisor read/write, User read */ 39*4882a593Smuzhiyun #define PP_RWRW 2 /* Supervisor read/write, User read/write */ 40*4882a593Smuzhiyun #define PP_RXRX 3 /* Supervisor read, User read */ 41*4882a593Smuzhiyun 42*4882a593Smuzhiyun /* Segment Register */ 43*4882a593Smuzhiyun typedef struct _SEGREG { 44*4882a593Smuzhiyun unsigned long t:1; /* Normal or I/O type */ 45*4882a593Smuzhiyun unsigned long ks:1; /* Supervisor 'key' (normally 0) */ 46*4882a593Smuzhiyun unsigned long kp:1; /* User 'key' (normally 1) */ 47*4882a593Smuzhiyun unsigned long n:1; /* No-execute */ 48*4882a593Smuzhiyun unsigned long :4; /* Unused */ 49*4882a593Smuzhiyun unsigned long vsid:24; /* Virtual Segment Identifier */ 50*4882a593Smuzhiyun } SEGREG; 51*4882a593Smuzhiyun 52*4882a593Smuzhiyun /* Block Address Translation (BAT) Registers */ 53*4882a593Smuzhiyun typedef struct _P601_BATU { /* Upper part of BAT for 601 processor */ 54*4882a593Smuzhiyun unsigned long bepi:15; /* Effective page index (virtual address) */ 55*4882a593Smuzhiyun unsigned long :8; /* unused */ 56*4882a593Smuzhiyun unsigned long w:1; 57*4882a593Smuzhiyun unsigned long i:1; /* Cache inhibit */ 58*4882a593Smuzhiyun unsigned long m:1; /* Memory coherence */ 59*4882a593Smuzhiyun unsigned long ks:1; /* Supervisor key (normally 0) */ 60*4882a593Smuzhiyun unsigned long kp:1; /* User key (normally 1) */ 61*4882a593Smuzhiyun unsigned long pp:2; /* Page access protections */ 62*4882a593Smuzhiyun } P601_BATU; 63*4882a593Smuzhiyun 64*4882a593Smuzhiyun typedef struct _BATU { /* Upper part of BAT (all except 601) */ 65*4882a593Smuzhiyun #ifdef CONFIG_PPC64BRIDGE 66*4882a593Smuzhiyun unsigned long long bepi:47; 67*4882a593Smuzhiyun #else /* CONFIG_PPC64BRIDGE */ 68*4882a593Smuzhiyun unsigned long bepi:15; /* Effective page index (virtual address) */ 69*4882a593Smuzhiyun #endif /* CONFIG_PPC64BRIDGE */ 70*4882a593Smuzhiyun unsigned long :4; /* Unused */ 71*4882a593Smuzhiyun unsigned long bl:11; /* Block size mask */ 72*4882a593Smuzhiyun unsigned long vs:1; /* Supervisor valid */ 73*4882a593Smuzhiyun unsigned long vp:1; /* User valid */ 74*4882a593Smuzhiyun } BATU; 75*4882a593Smuzhiyun 76*4882a593Smuzhiyun typedef struct _P601_BATL { /* Lower part of BAT for 601 processor */ 77*4882a593Smuzhiyun unsigned long brpn:15; /* Real page index (physical address) */ 78*4882a593Smuzhiyun unsigned long :10; /* Unused */ 79*4882a593Smuzhiyun unsigned long v:1; /* Valid bit */ 80*4882a593Smuzhiyun unsigned long bl:6; /* Block size mask */ 81*4882a593Smuzhiyun } P601_BATL; 82*4882a593Smuzhiyun 83*4882a593Smuzhiyun typedef struct _BATL { /* Lower part of BAT (all except 601) */ 84*4882a593Smuzhiyun #ifdef CONFIG_PPC64BRIDGE 85*4882a593Smuzhiyun unsigned long long brpn:47; 86*4882a593Smuzhiyun #else /* CONFIG_PPC64BRIDGE */ 87*4882a593Smuzhiyun unsigned long brpn:15; /* Real page index (physical address) */ 88*4882a593Smuzhiyun #endif /* CONFIG_PPC64BRIDGE */ 89*4882a593Smuzhiyun unsigned long :10; /* Unused */ 90*4882a593Smuzhiyun unsigned long w:1; /* Write-thru cache */ 91*4882a593Smuzhiyun unsigned long i:1; /* Cache inhibit */ 92*4882a593Smuzhiyun unsigned long m:1; /* Memory coherence */ 93*4882a593Smuzhiyun unsigned long g:1; /* Guarded (MBZ in IBAT) */ 94*4882a593Smuzhiyun unsigned long :1; /* Unused */ 95*4882a593Smuzhiyun unsigned long pp:2; /* Page access protections */ 96*4882a593Smuzhiyun } BATL; 97*4882a593Smuzhiyun 98*4882a593Smuzhiyun typedef struct _BAT { 99*4882a593Smuzhiyun BATU batu; /* Upper register */ 100*4882a593Smuzhiyun BATL batl; /* Lower register */ 101*4882a593Smuzhiyun } BAT; 102*4882a593Smuzhiyun 103*4882a593Smuzhiyun typedef struct _P601_BAT { 104*4882a593Smuzhiyun P601_BATU batu; /* Upper register */ 105*4882a593Smuzhiyun P601_BATL batl; /* Lower register */ 106*4882a593Smuzhiyun } P601_BAT; 107*4882a593Smuzhiyun 108*4882a593Smuzhiyun /* 109*4882a593Smuzhiyun * Simulated two-level MMU. This structure is used by the kernel 110*4882a593Smuzhiyun * to keep track of MMU mappings and is used to update/maintain 111*4882a593Smuzhiyun * the hardware HASH table which is really a cache of mappings. 112*4882a593Smuzhiyun * 113*4882a593Smuzhiyun * The simulated structures mimic the hardware available on other 114*4882a593Smuzhiyun * platforms, notably the 80x86 and 680x0. 115*4882a593Smuzhiyun */ 116*4882a593Smuzhiyun 117*4882a593Smuzhiyun typedef struct _pte { 118*4882a593Smuzhiyun unsigned long page_num:20; 119*4882a593Smuzhiyun unsigned long flags:12; /* Page flags (some unused bits) */ 120*4882a593Smuzhiyun } pte; 121*4882a593Smuzhiyun 122*4882a593Smuzhiyun #define PD_SHIFT (10+12) /* Page directory */ 123*4882a593Smuzhiyun #define PD_MASK 0x02FF 124*4882a593Smuzhiyun #define PT_SHIFT (12) /* Page Table */ 125*4882a593Smuzhiyun #define PT_MASK 0x02FF 126*4882a593Smuzhiyun #define PG_SHIFT (12) /* Page Entry */ 127*4882a593Smuzhiyun 128*4882a593Smuzhiyun 129*4882a593Smuzhiyun /* MMU context */ 130*4882a593Smuzhiyun 131*4882a593Smuzhiyun typedef struct _MMU_context { 132*4882a593Smuzhiyun SEGREG segs[16]; /* Segment registers */ 133*4882a593Smuzhiyun pte **pmap; /* Two-level page-map structure */ 134*4882a593Smuzhiyun } MMU_context; 135*4882a593Smuzhiyun 136*4882a593Smuzhiyun extern void _tlbie(unsigned long va); /* invalidate a TLB entry */ 137*4882a593Smuzhiyun extern void _tlbia(void); /* invalidate all TLB entries */ 138*4882a593Smuzhiyun 139*4882a593Smuzhiyun #ifdef CONFIG_ADDR_MAP 140*4882a593Smuzhiyun extern void init_addr_map(void); 141*4882a593Smuzhiyun #endif 142*4882a593Smuzhiyun 143*4882a593Smuzhiyun typedef enum { 144*4882a593Smuzhiyun IBAT0 = 0, IBAT1, IBAT2, IBAT3, 145*4882a593Smuzhiyun DBAT0, DBAT1, DBAT2, DBAT3, 146*4882a593Smuzhiyun #ifdef CONFIG_HIGH_BATS 147*4882a593Smuzhiyun IBAT4, IBAT5, IBAT6, IBAT7, 148*4882a593Smuzhiyun DBAT4, DBAT5, DBAT6, DBAT7 149*4882a593Smuzhiyun #endif 150*4882a593Smuzhiyun } ppc_bat_t; 151*4882a593Smuzhiyun 152*4882a593Smuzhiyun extern int read_bat(ppc_bat_t bat, unsigned long *upper, unsigned long *lower); 153*4882a593Smuzhiyun extern int write_bat(ppc_bat_t bat, unsigned long upper, unsigned long lower); 154*4882a593Smuzhiyun extern void print_bats(void); 155*4882a593Smuzhiyun 156*4882a593Smuzhiyun #endif /* __ASSEMBLY__ */ 157*4882a593Smuzhiyun 158*4882a593Smuzhiyun #define BATU_VS 0x00000002 159*4882a593Smuzhiyun #define BATU_VP 0x00000001 160*4882a593Smuzhiyun #define BATU_INVALID 0x00000000 161*4882a593Smuzhiyun 162*4882a593Smuzhiyun #define BATL_WRITETHROUGH 0x00000040 163*4882a593Smuzhiyun #define BATL_CACHEINHIBIT 0x00000020 164*4882a593Smuzhiyun #define BATL_MEMCOHERENCE 0x00000010 165*4882a593Smuzhiyun #define BATL_GUARDEDSTORAGE 0x00000008 166*4882a593Smuzhiyun #define BATL_NO_ACCESS 0x00000000 167*4882a593Smuzhiyun 168*4882a593Smuzhiyun #define BATL_PP_MSK 0x00000003 169*4882a593Smuzhiyun #define BATL_PP_00 0x00000000 /* No access */ 170*4882a593Smuzhiyun #define BATL_PP_01 0x00000001 /* Read-only */ 171*4882a593Smuzhiyun #define BATL_PP_10 0x00000002 /* Read-write */ 172*4882a593Smuzhiyun #define BATL_PP_11 0x00000003 173*4882a593Smuzhiyun 174*4882a593Smuzhiyun #define BATL_PP_NO_ACCESS BATL_PP_00 175*4882a593Smuzhiyun #define BATL_PP_RO BATL_PP_01 176*4882a593Smuzhiyun #define BATL_PP_RW BATL_PP_10 177*4882a593Smuzhiyun 178*4882a593Smuzhiyun /* BAT Block size values */ 179*4882a593Smuzhiyun #define BATU_BL_128K 0x00000000 180*4882a593Smuzhiyun #define BATU_BL_256K 0x00000004 181*4882a593Smuzhiyun #define BATU_BL_512K 0x0000000c 182*4882a593Smuzhiyun #define BATU_BL_1M 0x0000001c 183*4882a593Smuzhiyun #define BATU_BL_2M 0x0000003c 184*4882a593Smuzhiyun #define BATU_BL_4M 0x0000007c 185*4882a593Smuzhiyun #define BATU_BL_8M 0x000000fc 186*4882a593Smuzhiyun #define BATU_BL_16M 0x000001fc 187*4882a593Smuzhiyun #define BATU_BL_32M 0x000003fc 188*4882a593Smuzhiyun #define BATU_BL_64M 0x000007fc 189*4882a593Smuzhiyun #define BATU_BL_128M 0x00000ffc 190*4882a593Smuzhiyun #define BATU_BL_256M 0x00001ffc 191*4882a593Smuzhiyun 192*4882a593Smuzhiyun /* Block lengths for processors that support extended block length */ 193*4882a593Smuzhiyun #ifdef HID0_XBSEN 194*4882a593Smuzhiyun #define BATU_BL_512M 0x00003ffc 195*4882a593Smuzhiyun #define BATU_BL_1G 0x00007ffc 196*4882a593Smuzhiyun #define BATU_BL_2G 0x0000fffc 197*4882a593Smuzhiyun #define BATU_BL_4G 0x0001fffc 198*4882a593Smuzhiyun #define BATU_BL_MAX BATU_BL_4G 199*4882a593Smuzhiyun #else 200*4882a593Smuzhiyun #define BATU_BL_MAX BATU_BL_256M 201*4882a593Smuzhiyun #endif 202*4882a593Smuzhiyun 203*4882a593Smuzhiyun /* BAT Access Protection */ 204*4882a593Smuzhiyun #define BPP_XX 0x00 /* No access */ 205*4882a593Smuzhiyun #define BPP_RX 0x01 /* Read only */ 206*4882a593Smuzhiyun #define BPP_RW 0x02 /* Read/write */ 207*4882a593Smuzhiyun 208*4882a593Smuzhiyun /* Macros to get values from BATs, once data is in the BAT register format */ 209*4882a593Smuzhiyun #define BATU_VALID(x) (x & 0x3) 210*4882a593Smuzhiyun #define BATU_VADDR(x) (x & 0xfffe0000) 211*4882a593Smuzhiyun #define BATL_PADDR(x) ((phys_addr_t)((x & 0xfffe0000) \ 212*4882a593Smuzhiyun | ((x & 0x0e00ULL) << 24) \ 213*4882a593Smuzhiyun | ((x & 0x04ULL) << 30))) 214*4882a593Smuzhiyun #define BATU_SIZE(x) (1ULL << (fls((x & BATU_BL_MAX) >> 2) + 17)) 215*4882a593Smuzhiyun 216*4882a593Smuzhiyun /* bytes into BATU_BL */ 217*4882a593Smuzhiyun #define TO_BATU_BL(x) \ 218*4882a593Smuzhiyun (u32)((((1ull << __ilog2_u64((u64)x)) / (128 * 1024)) - 1) * 4) 219*4882a593Smuzhiyun 220*4882a593Smuzhiyun /* Used to set up SDR1 register */ 221*4882a593Smuzhiyun #define HASH_TABLE_SIZE_64K 0x00010000 222*4882a593Smuzhiyun #define HASH_TABLE_SIZE_128K 0x00020000 223*4882a593Smuzhiyun #define HASH_TABLE_SIZE_256K 0x00040000 224*4882a593Smuzhiyun #define HASH_TABLE_SIZE_512K 0x00080000 225*4882a593Smuzhiyun #define HASH_TABLE_SIZE_1M 0x00100000 226*4882a593Smuzhiyun #define HASH_TABLE_SIZE_2M 0x00200000 227*4882a593Smuzhiyun #define HASH_TABLE_SIZE_4M 0x00400000 228*4882a593Smuzhiyun #define HASH_TABLE_MASK_64K 0x000 229*4882a593Smuzhiyun #define HASH_TABLE_MASK_128K 0x001 230*4882a593Smuzhiyun #define HASH_TABLE_MASK_256K 0x003 231*4882a593Smuzhiyun #define HASH_TABLE_MASK_512K 0x007 232*4882a593Smuzhiyun #define HASH_TABLE_MASK_1M 0x00F 233*4882a593Smuzhiyun #define HASH_TABLE_MASK_2M 0x01F 234*4882a593Smuzhiyun #define HASH_TABLE_MASK_4M 0x03F 235*4882a593Smuzhiyun 236*4882a593Smuzhiyun /* Control/status registers for the MPC8xx. 237*4882a593Smuzhiyun * A write operation to these registers causes serialized access. 238*4882a593Smuzhiyun * During software tablewalk, the registers used perform mask/shift-add 239*4882a593Smuzhiyun * operations when written/read. A TLB entry is created when the Mx_RPN 240*4882a593Smuzhiyun * is written, and the contents of several registers are used to 241*4882a593Smuzhiyun * create the entry. 242*4882a593Smuzhiyun */ 243*4882a593Smuzhiyun #define MI_CTR 784 /* Instruction TLB control register */ 244*4882a593Smuzhiyun #define MI_GPM 0x80000000 /* Set domain manager mode */ 245*4882a593Smuzhiyun #define MI_PPM 0x40000000 /* Set subpage protection */ 246*4882a593Smuzhiyun #define MI_CIDEF 0x20000000 /* Set cache inhibit when MMU dis */ 247*4882a593Smuzhiyun #define MI_RSV4I 0x08000000 /* Reserve 4 TLB entries */ 248*4882a593Smuzhiyun #define MI_PPCS 0x02000000 /* Use MI_RPN prob/priv state */ 249*4882a593Smuzhiyun #define MI_IDXMASK 0x00001f00 /* TLB index to be loaded */ 250*4882a593Smuzhiyun #define MI_RESETVAL 0x00000000 /* Value of register at reset */ 251*4882a593Smuzhiyun 252*4882a593Smuzhiyun /* These are the Ks and Kp from the PowerPC books. For proper operation, 253*4882a593Smuzhiyun * Ks = 0, Kp = 1. 254*4882a593Smuzhiyun */ 255*4882a593Smuzhiyun #define MI_AP 786 256*4882a593Smuzhiyun #define MI_Ks 0x80000000 /* Should not be set */ 257*4882a593Smuzhiyun #define MI_Kp 0x40000000 /* Should always be set */ 258*4882a593Smuzhiyun 259*4882a593Smuzhiyun /* The effective page number register. When read, contains the information 260*4882a593Smuzhiyun * about the last instruction TLB miss. When MI_RPN is written, bits in 261*4882a593Smuzhiyun * this register are used to create the TLB entry. 262*4882a593Smuzhiyun */ 263*4882a593Smuzhiyun #define MI_EPN 787 264*4882a593Smuzhiyun #define MI_EPNMASK 0xfffff000 /* Effective page number for entry */ 265*4882a593Smuzhiyun #define MI_EVALID 0x00000200 /* Entry is valid */ 266*4882a593Smuzhiyun #define MI_ASIDMASK 0x0000000f /* ASID match value */ 267*4882a593Smuzhiyun /* Reset value is undefined */ 268*4882a593Smuzhiyun 269*4882a593Smuzhiyun /* A "level 1" or "segment" or whatever you want to call it register. 270*4882a593Smuzhiyun * For the instruction TLB, it contains bits that get loaded into the 271*4882a593Smuzhiyun * TLB entry when the MI_RPN is written. 272*4882a593Smuzhiyun */ 273*4882a593Smuzhiyun #define MI_TWC 789 274*4882a593Smuzhiyun #define MI_APG 0x000001e0 /* Access protection group (0) */ 275*4882a593Smuzhiyun #define MI_GUARDED 0x00000010 /* Guarded storage */ 276*4882a593Smuzhiyun #define MI_PSMASK 0x0000000c /* Mask of page size bits */ 277*4882a593Smuzhiyun #define MI_PS8MEG 0x0000000c /* 8M page size */ 278*4882a593Smuzhiyun #define MI_PS512K 0x00000004 /* 512K page size */ 279*4882a593Smuzhiyun #define MI_PS4K_16K 0x00000000 /* 4K or 16K page size */ 280*4882a593Smuzhiyun #define MI_SVALID 0x00000001 /* Segment entry is valid */ 281*4882a593Smuzhiyun /* Reset value is undefined */ 282*4882a593Smuzhiyun 283*4882a593Smuzhiyun /* Real page number. Defined by the pte. Writing this register 284*4882a593Smuzhiyun * causes a TLB entry to be created for the instruction TLB, using 285*4882a593Smuzhiyun * additional information from the MI_EPN, and MI_TWC registers. 286*4882a593Smuzhiyun */ 287*4882a593Smuzhiyun #define MI_RPN 790 288*4882a593Smuzhiyun 289*4882a593Smuzhiyun /* Define an RPN value for mapping kernel memory to large virtual 290*4882a593Smuzhiyun * pages for boot initialization. This has real page number of 0, 291*4882a593Smuzhiyun * large page size, shared page, cache enabled, and valid. 292*4882a593Smuzhiyun * Also mark all subpages valid and write access. 293*4882a593Smuzhiyun */ 294*4882a593Smuzhiyun #define MI_BOOTINIT 0x000001fd 295*4882a593Smuzhiyun 296*4882a593Smuzhiyun #define MD_CTR 792 /* Data TLB control register */ 297*4882a593Smuzhiyun #define MD_GPM 0x80000000 /* Set domain manager mode */ 298*4882a593Smuzhiyun #define MD_PPM 0x40000000 /* Set subpage protection */ 299*4882a593Smuzhiyun #define MD_CIDEF 0x20000000 /* Set cache inhibit when MMU dis */ 300*4882a593Smuzhiyun #define MD_WTDEF 0x10000000 /* Set writethrough when MMU dis */ 301*4882a593Smuzhiyun #define MD_RSV4I 0x08000000 /* Reserve 4 TLB entries */ 302*4882a593Smuzhiyun #define MD_TWAM 0x04000000 /* Use 4K page hardware assist */ 303*4882a593Smuzhiyun #define MD_PPCS 0x02000000 /* Use MI_RPN prob/priv state */ 304*4882a593Smuzhiyun #define MD_IDXMASK 0x00001f00 /* TLB index to be loaded */ 305*4882a593Smuzhiyun #define MD_RESETVAL 0x04000000 /* Value of register at reset */ 306*4882a593Smuzhiyun 307*4882a593Smuzhiyun #define M_CASID 793 /* Address space ID (context) to match */ 308*4882a593Smuzhiyun #define MC_ASIDMASK 0x0000000f /* Bits used for ASID value */ 309*4882a593Smuzhiyun 310*4882a593Smuzhiyun 311*4882a593Smuzhiyun /* These are the Ks and Kp from the PowerPC books. For proper operation, 312*4882a593Smuzhiyun * Ks = 0, Kp = 1. 313*4882a593Smuzhiyun */ 314*4882a593Smuzhiyun #define MD_AP 794 315*4882a593Smuzhiyun #define MD_Ks 0x80000000 /* Should not be set */ 316*4882a593Smuzhiyun #define MD_Kp 0x40000000 /* Should always be set */ 317*4882a593Smuzhiyun 318*4882a593Smuzhiyun /* The effective page number register. When read, contains the information 319*4882a593Smuzhiyun * about the last instruction TLB miss. When MD_RPN is written, bits in 320*4882a593Smuzhiyun * this register are used to create the TLB entry. 321*4882a593Smuzhiyun */ 322*4882a593Smuzhiyun #define MD_EPN 795 323*4882a593Smuzhiyun #define MD_EPNMASK 0xfffff000 /* Effective page number for entry */ 324*4882a593Smuzhiyun #define MD_EVALID 0x00000200 /* Entry is valid */ 325*4882a593Smuzhiyun #define MD_ASIDMASK 0x0000000f /* ASID match value */ 326*4882a593Smuzhiyun /* Reset value is undefined */ 327*4882a593Smuzhiyun 328*4882a593Smuzhiyun /* The pointer to the base address of the first level page table. 329*4882a593Smuzhiyun * During a software tablewalk, reading this register provides the address 330*4882a593Smuzhiyun * of the entry associated with MD_EPN. 331*4882a593Smuzhiyun */ 332*4882a593Smuzhiyun #define M_TWB 796 333*4882a593Smuzhiyun #define M_L1TB 0xfffff000 /* Level 1 table base address */ 334*4882a593Smuzhiyun #define M_L1INDX 0x00000ffc /* Level 1 index, when read */ 335*4882a593Smuzhiyun /* Reset value is undefined */ 336*4882a593Smuzhiyun 337*4882a593Smuzhiyun /* A "level 1" or "segment" or whatever you want to call it register. 338*4882a593Smuzhiyun * For the data TLB, it contains bits that get loaded into the TLB entry 339*4882a593Smuzhiyun * when the MD_RPN is written. It is also provides the hardware assist 340*4882a593Smuzhiyun * for finding the PTE address during software tablewalk. 341*4882a593Smuzhiyun */ 342*4882a593Smuzhiyun #define MD_TWC 797 343*4882a593Smuzhiyun #define MD_L2TB 0xfffff000 /* Level 2 table base address */ 344*4882a593Smuzhiyun #define MD_L2INDX 0xfffffe00 /* Level 2 index (*pte), when read */ 345*4882a593Smuzhiyun #define MD_APG 0x000001e0 /* Access protection group (0) */ 346*4882a593Smuzhiyun #define MD_GUARDED 0x00000010 /* Guarded storage */ 347*4882a593Smuzhiyun #define MD_PSMASK 0x0000000c /* Mask of page size bits */ 348*4882a593Smuzhiyun #define MD_PS8MEG 0x0000000c /* 8M page size */ 349*4882a593Smuzhiyun #define MD_PS512K 0x00000004 /* 512K page size */ 350*4882a593Smuzhiyun #define MD_PS4K_16K 0x00000000 /* 4K or 16K page size */ 351*4882a593Smuzhiyun #define MD_WT 0x00000002 /* Use writethrough page attribute */ 352*4882a593Smuzhiyun #define MD_SVALID 0x00000001 /* Segment entry is valid */ 353*4882a593Smuzhiyun /* Reset value is undefined */ 354*4882a593Smuzhiyun 355*4882a593Smuzhiyun 356*4882a593Smuzhiyun /* Real page number. Defined by the pte. Writing this register 357*4882a593Smuzhiyun * causes a TLB entry to be created for the data TLB, using 358*4882a593Smuzhiyun * additional information from the MD_EPN, and MD_TWC registers. 359*4882a593Smuzhiyun */ 360*4882a593Smuzhiyun #define MD_RPN 798 361*4882a593Smuzhiyun 362*4882a593Smuzhiyun /* This is a temporary storage register that could be used to save 363*4882a593Smuzhiyun * a processor working register during a tablewalk. 364*4882a593Smuzhiyun */ 365*4882a593Smuzhiyun #define M_TW 799 366*4882a593Smuzhiyun 367*4882a593Smuzhiyun /* 368*4882a593Smuzhiyun * At present, all PowerPC 400-class processors share a similar TLB 369*4882a593Smuzhiyun * architecture. The instruction and data sides share a unified, 370*4882a593Smuzhiyun * 64-entry, fully-associative TLB which is maintained totally under 371*4882a593Smuzhiyun * software control. In addition, the instruction side has a 372*4882a593Smuzhiyun * hardware-managed, 4-entry, fully- associative TLB which serves as a 373*4882a593Smuzhiyun * first level to the shared TLB. These two TLBs are known as the UTLB 374*4882a593Smuzhiyun * and ITLB, respectively. 375*4882a593Smuzhiyun */ 376*4882a593Smuzhiyun 377*4882a593Smuzhiyun #define PPC4XX_TLB_SIZE 64 378*4882a593Smuzhiyun 379*4882a593Smuzhiyun /* 380*4882a593Smuzhiyun * TLB entries are defined by a "high" tag portion and a "low" data 381*4882a593Smuzhiyun * portion. On all architectures, the data portion is 32-bits. 382*4882a593Smuzhiyun * 383*4882a593Smuzhiyun * TLB entries are managed entirely under software control by reading, 384*4882a593Smuzhiyun * writing, and searchoing using the 4xx-specific tlbre, tlbwr, and tlbsx 385*4882a593Smuzhiyun * instructions. 386*4882a593Smuzhiyun */ 387*4882a593Smuzhiyun 388*4882a593Smuzhiyun /* 389*4882a593Smuzhiyun * FSL Book-E support 390*4882a593Smuzhiyun */ 391*4882a593Smuzhiyun 392*4882a593Smuzhiyun #define MAS0_TLBSEL_MSK 0x30000000 393*4882a593Smuzhiyun #define MAS0_TLBSEL(x) (((x) << 28) & MAS0_TLBSEL_MSK) 394*4882a593Smuzhiyun #define MAS0_ESEL_MSK 0x0FFF0000 395*4882a593Smuzhiyun #define MAS0_ESEL(x) (((x) << 16) & MAS0_ESEL_MSK) 396*4882a593Smuzhiyun #define MAS0_NV(x) ((x) & 0x00000FFF) 397*4882a593Smuzhiyun 398*4882a593Smuzhiyun #define MAS1_VALID 0x80000000 399*4882a593Smuzhiyun #define MAS1_IPROT 0x40000000 400*4882a593Smuzhiyun #define MAS1_TID(x) (((x) << 16) & 0x3FFF0000) 401*4882a593Smuzhiyun #define MAS1_TS 0x00001000 402*4882a593Smuzhiyun #define MAS1_TSIZE(x) (((x) << 7) & 0x00000F80) 403*4882a593Smuzhiyun #define TSIZE_TO_BYTES(x) (1ULL << ((x) + 10)) 404*4882a593Smuzhiyun 405*4882a593Smuzhiyun #define MAS2_EPN 0xFFFFF000 406*4882a593Smuzhiyun #define MAS2_X0 0x00000040 407*4882a593Smuzhiyun #define MAS2_X1 0x00000020 408*4882a593Smuzhiyun #define MAS2_W 0x00000010 409*4882a593Smuzhiyun #define MAS2_I 0x00000008 410*4882a593Smuzhiyun #define MAS2_M 0x00000004 411*4882a593Smuzhiyun #define MAS2_G 0x00000002 412*4882a593Smuzhiyun #define MAS2_E 0x00000001 413*4882a593Smuzhiyun 414*4882a593Smuzhiyun #define MAS3_RPN 0xFFFFF000 415*4882a593Smuzhiyun #define MAS3_U0 0x00000200 416*4882a593Smuzhiyun #define MAS3_U1 0x00000100 417*4882a593Smuzhiyun #define MAS3_U2 0x00000080 418*4882a593Smuzhiyun #define MAS3_U3 0x00000040 419*4882a593Smuzhiyun #define MAS3_UX 0x00000020 420*4882a593Smuzhiyun #define MAS3_SX 0x00000010 421*4882a593Smuzhiyun #define MAS3_UW 0x00000008 422*4882a593Smuzhiyun #define MAS3_SW 0x00000004 423*4882a593Smuzhiyun #define MAS3_UR 0x00000002 424*4882a593Smuzhiyun #define MAS3_SR 0x00000001 425*4882a593Smuzhiyun 426*4882a593Smuzhiyun #define MAS4_TLBSELD(x) MAS0_TLBSEL(x) 427*4882a593Smuzhiyun #define MAS4_TIDDSEL 0x000F0000 428*4882a593Smuzhiyun #define MAS4_TSIZED(x) MAS1_TSIZE(x) 429*4882a593Smuzhiyun #define MAS4_X0D 0x00000040 430*4882a593Smuzhiyun #define MAS4_X1D 0x00000020 431*4882a593Smuzhiyun #define MAS4_WD 0x00000010 432*4882a593Smuzhiyun #define MAS4_ID 0x00000008 433*4882a593Smuzhiyun #define MAS4_MD 0x00000004 434*4882a593Smuzhiyun #define MAS4_GD 0x00000002 435*4882a593Smuzhiyun #define MAS4_ED 0x00000001 436*4882a593Smuzhiyun 437*4882a593Smuzhiyun #define MAS6_SPID0 0x3FFF0000 438*4882a593Smuzhiyun #define MAS6_SPID1 0x00007FFE 439*4882a593Smuzhiyun #define MAS6_SAS 0x00000001 440*4882a593Smuzhiyun #define MAS6_SPID MAS6_SPID0 441*4882a593Smuzhiyun 442*4882a593Smuzhiyun #define MAS7_RPN 0xFFFFFFFF 443*4882a593Smuzhiyun 444*4882a593Smuzhiyun #define FSL_BOOKE_MAS0(tlbsel,esel,nv) \ 445*4882a593Smuzhiyun (MAS0_TLBSEL(tlbsel) | MAS0_ESEL(esel) | MAS0_NV(nv)) 446*4882a593Smuzhiyun #define FSL_BOOKE_MAS1(v,iprot,tid,ts,tsize) \ 447*4882a593Smuzhiyun ((((v) << 31) & MAS1_VALID) |\ 448*4882a593Smuzhiyun (((iprot) << 30) & MAS1_IPROT) |\ 449*4882a593Smuzhiyun (MAS1_TID(tid)) |\ 450*4882a593Smuzhiyun (((ts) << 12) & MAS1_TS) |\ 451*4882a593Smuzhiyun (MAS1_TSIZE(tsize))) 452*4882a593Smuzhiyun #define FSL_BOOKE_MAS2(epn, wimge) \ 453*4882a593Smuzhiyun (((epn) & MAS3_RPN) | (wimge)) 454*4882a593Smuzhiyun #define FSL_BOOKE_MAS3(rpn, user, perms) \ 455*4882a593Smuzhiyun (((rpn) & MAS3_RPN) | (user) | (perms)) 456*4882a593Smuzhiyun #define FSL_BOOKE_MAS7(rpn) \ 457*4882a593Smuzhiyun (((u64)(rpn)) >> 32) 458*4882a593Smuzhiyun 459*4882a593Smuzhiyun #define BOOKE_PAGESZ_1K 0 460*4882a593Smuzhiyun #define BOOKE_PAGESZ_2K 1 461*4882a593Smuzhiyun #define BOOKE_PAGESZ_4K 2 462*4882a593Smuzhiyun #define BOOKE_PAGESZ_8K 3 463*4882a593Smuzhiyun #define BOOKE_PAGESZ_16K 4 464*4882a593Smuzhiyun #define BOOKE_PAGESZ_32K 5 465*4882a593Smuzhiyun #define BOOKE_PAGESZ_64K 6 466*4882a593Smuzhiyun #define BOOKE_PAGESZ_128K 7 467*4882a593Smuzhiyun #define BOOKE_PAGESZ_256K 8 468*4882a593Smuzhiyun #define BOOKE_PAGESZ_512K 9 469*4882a593Smuzhiyun #define BOOKE_PAGESZ_1M 10 470*4882a593Smuzhiyun #define BOOKE_PAGESZ_2M 11 471*4882a593Smuzhiyun #define BOOKE_PAGESZ_4M 12 472*4882a593Smuzhiyun #define BOOKE_PAGESZ_8M 13 473*4882a593Smuzhiyun #define BOOKE_PAGESZ_16M 14 474*4882a593Smuzhiyun #define BOOKE_PAGESZ_32M 15 475*4882a593Smuzhiyun #define BOOKE_PAGESZ_64M 16 476*4882a593Smuzhiyun #define BOOKE_PAGESZ_128M 17 477*4882a593Smuzhiyun #define BOOKE_PAGESZ_256M 18 478*4882a593Smuzhiyun #define BOOKE_PAGESZ_512M 19 479*4882a593Smuzhiyun #define BOOKE_PAGESZ_1G 20 480*4882a593Smuzhiyun #define BOOKE_PAGESZ_2G 21 481*4882a593Smuzhiyun #define BOOKE_PAGESZ_4G 22 482*4882a593Smuzhiyun #define BOOKE_PAGESZ_8G 23 483*4882a593Smuzhiyun #define BOOKE_PAGESZ_16GB 24 484*4882a593Smuzhiyun #define BOOKE_PAGESZ_32GB 25 485*4882a593Smuzhiyun #define BOOKE_PAGESZ_64GB 26 486*4882a593Smuzhiyun #define BOOKE_PAGESZ_128GB 27 487*4882a593Smuzhiyun #define BOOKE_PAGESZ_256GB 28 488*4882a593Smuzhiyun #define BOOKE_PAGESZ_512GB 29 489*4882a593Smuzhiyun #define BOOKE_PAGESZ_1TB 30 490*4882a593Smuzhiyun #define BOOKE_PAGESZ_2TB 31 491*4882a593Smuzhiyun 492*4882a593Smuzhiyun #define TLBIVAX_ALL 4 493*4882a593Smuzhiyun #define TLBIVAX_TLB0 0 494*4882a593Smuzhiyun #define TLBIVAX_TLB1 8 495*4882a593Smuzhiyun 496*4882a593Smuzhiyun #ifdef CONFIG_E500 497*4882a593Smuzhiyun #ifndef __ASSEMBLY__ 498*4882a593Smuzhiyun extern void set_tlb(u8 tlb, u32 epn, u64 rpn, 499*4882a593Smuzhiyun u8 perms, u8 wimge, 500*4882a593Smuzhiyun u8 ts, u8 esel, u8 tsize, u8 iprot); 501*4882a593Smuzhiyun extern void disable_tlb(u8 esel); 502*4882a593Smuzhiyun extern void invalidate_tlb(u8 tlb); 503*4882a593Smuzhiyun extern void init_tlbs(void); 504*4882a593Smuzhiyun extern int find_tlb_idx(void *addr, u8 tlbsel); 505*4882a593Smuzhiyun extern void init_used_tlb_cams(void); 506*4882a593Smuzhiyun extern int find_free_tlbcam(void); 507*4882a593Smuzhiyun extern void print_tlbcam(void); 508*4882a593Smuzhiyun 509*4882a593Smuzhiyun extern unsigned int setup_ddr_tlbs(unsigned int memsize_in_meg); 510*4882a593Smuzhiyun extern void clear_ddr_tlbs(unsigned int memsize_in_meg); 511*4882a593Smuzhiyun 512*4882a593Smuzhiyun enum tlb_map_type { 513*4882a593Smuzhiyun TLB_MAP_RAM, 514*4882a593Smuzhiyun TLB_MAP_IO, 515*4882a593Smuzhiyun }; 516*4882a593Smuzhiyun 517*4882a593Smuzhiyun extern uint64_t tlb_map_range(ulong v_addr, phys_addr_t p_addr, uint64_t size, 518*4882a593Smuzhiyun enum tlb_map_type map_type); 519*4882a593Smuzhiyun 520*4882a593Smuzhiyun extern void write_tlb(u32 _mas0, u32 _mas1, u32 _mas2, u32 _mas3, u32 _mas7); 521*4882a593Smuzhiyun 522*4882a593Smuzhiyun #define SET_TLB_ENTRY(_tlb, _epn, _rpn, _perms, _wimge, _ts, _esel, _sz, _iprot) \ 523*4882a593Smuzhiyun { .mas0 = FSL_BOOKE_MAS0(_tlb, _esel, 0), \ 524*4882a593Smuzhiyun .mas1 = FSL_BOOKE_MAS1(1, _iprot, 0, _ts, _sz), \ 525*4882a593Smuzhiyun .mas2 = FSL_BOOKE_MAS2(_epn, _wimge), \ 526*4882a593Smuzhiyun .mas3 = FSL_BOOKE_MAS3(_rpn, 0, _perms), \ 527*4882a593Smuzhiyun .mas7 = FSL_BOOKE_MAS7(_rpn), } 528*4882a593Smuzhiyun 529*4882a593Smuzhiyun struct fsl_e_tlb_entry { 530*4882a593Smuzhiyun u32 mas0; 531*4882a593Smuzhiyun u32 mas1; 532*4882a593Smuzhiyun u32 mas2; 533*4882a593Smuzhiyun u32 mas3; 534*4882a593Smuzhiyun u32 mas7; 535*4882a593Smuzhiyun }; 536*4882a593Smuzhiyun 537*4882a593Smuzhiyun extern struct fsl_e_tlb_entry tlb_table[]; 538*4882a593Smuzhiyun extern int num_tlb_entries; 539*4882a593Smuzhiyun #endif 540*4882a593Smuzhiyun #endif 541*4882a593Smuzhiyun 542*4882a593Smuzhiyun #ifdef CONFIG_E300 543*4882a593Smuzhiyun #define LAWAR_EN 0x80000000 544*4882a593Smuzhiyun #define LAWAR_SIZE 0x0000003F 545*4882a593Smuzhiyun 546*4882a593Smuzhiyun #define LAWAR_TRGT_IF_PCI 0x00000000 547*4882a593Smuzhiyun #define LAWAR_TRGT_IF_PCI1 0x00000000 548*4882a593Smuzhiyun #define LAWAR_TRGT_IF_PCIX 0x00000000 549*4882a593Smuzhiyun #define LAWAR_TRGT_IF_PCI2 0x00100000 550*4882a593Smuzhiyun #define LAWAR_TRGT_IF_PCIE1 0x00200000 551*4882a593Smuzhiyun #define LAWAR_TRGT_IF_PCIE2 0x00100000 552*4882a593Smuzhiyun #define LAWAR_TRGT_IF_PCIE3 0x00300000 553*4882a593Smuzhiyun #define LAWAR_TRGT_IF_LBC 0x00400000 554*4882a593Smuzhiyun #define LAWAR_TRGT_IF_CCSR 0x00800000 555*4882a593Smuzhiyun #define LAWAR_TRGT_IF_DDR_INTERLEAVED 0x00B00000 556*4882a593Smuzhiyun #define LAWAR_TRGT_IF_RIO 0x00c00000 557*4882a593Smuzhiyun #define LAWAR_TRGT_IF_DDR 0x00f00000 558*4882a593Smuzhiyun #define LAWAR_TRGT_IF_DDR1 0x00f00000 559*4882a593Smuzhiyun #define LAWAR_TRGT_IF_DDR2 0x01600000 560*4882a593Smuzhiyun 561*4882a593Smuzhiyun #define LAWAR_SIZE_BASE 0xa 562*4882a593Smuzhiyun #define LAWAR_SIZE_4K (LAWAR_SIZE_BASE+1) 563*4882a593Smuzhiyun #define LAWAR_SIZE_8K (LAWAR_SIZE_BASE+2) 564*4882a593Smuzhiyun #define LAWAR_SIZE_16K (LAWAR_SIZE_BASE+3) 565*4882a593Smuzhiyun #define LAWAR_SIZE_32K (LAWAR_SIZE_BASE+4) 566*4882a593Smuzhiyun #define LAWAR_SIZE_64K (LAWAR_SIZE_BASE+5) 567*4882a593Smuzhiyun #define LAWAR_SIZE_128K (LAWAR_SIZE_BASE+6) 568*4882a593Smuzhiyun #define LAWAR_SIZE_256K (LAWAR_SIZE_BASE+7) 569*4882a593Smuzhiyun #define LAWAR_SIZE_512K (LAWAR_SIZE_BASE+8) 570*4882a593Smuzhiyun #define LAWAR_SIZE_1M (LAWAR_SIZE_BASE+9) 571*4882a593Smuzhiyun #define LAWAR_SIZE_2M (LAWAR_SIZE_BASE+10) 572*4882a593Smuzhiyun #define LAWAR_SIZE_4M (LAWAR_SIZE_BASE+11) 573*4882a593Smuzhiyun #define LAWAR_SIZE_8M (LAWAR_SIZE_BASE+12) 574*4882a593Smuzhiyun #define LAWAR_SIZE_16M (LAWAR_SIZE_BASE+13) 575*4882a593Smuzhiyun #define LAWAR_SIZE_32M (LAWAR_SIZE_BASE+14) 576*4882a593Smuzhiyun #define LAWAR_SIZE_64M (LAWAR_SIZE_BASE+15) 577*4882a593Smuzhiyun #define LAWAR_SIZE_128M (LAWAR_SIZE_BASE+16) 578*4882a593Smuzhiyun #define LAWAR_SIZE_256M (LAWAR_SIZE_BASE+17) 579*4882a593Smuzhiyun #define LAWAR_SIZE_512M (LAWAR_SIZE_BASE+18) 580*4882a593Smuzhiyun #define LAWAR_SIZE_1G (LAWAR_SIZE_BASE+19) 581*4882a593Smuzhiyun #define LAWAR_SIZE_2G (LAWAR_SIZE_BASE+20) 582*4882a593Smuzhiyun #define LAWAR_SIZE_4G (LAWAR_SIZE_BASE+21) 583*4882a593Smuzhiyun #define LAWAR_SIZE_8G (LAWAR_SIZE_BASE+22) 584*4882a593Smuzhiyun #define LAWAR_SIZE_16G (LAWAR_SIZE_BASE+23) 585*4882a593Smuzhiyun #define LAWAR_SIZE_32G (LAWAR_SIZE_BASE+24) 586*4882a593Smuzhiyun #endif 587*4882a593Smuzhiyun 588*4882a593Smuzhiyun #endif /* _PPC_MMU_H_ */ 589