Commit 6d35524c40a7c884462b852ae697f16f7c90ee9e

Authored by ths
1 parent cbd669da

Improved PABITS handling, and config register fixes.


git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@3855 c046a42c-6fe2-441c-8c8c-71466251a162
target-mips/cpu.h
@@ -162,6 +162,8 @@ struct CPUMIPSState { @@ -162,6 +162,8 @@ struct CPUMIPSState {
162 162
163 uint32_t SEGBITS; 163 uint32_t SEGBITS;
164 target_ulong SEGMask; 164 target_ulong SEGMask;
  165 + uint32_t PABITS;
  166 + target_ulong PAMask;
165 167
166 int32_t CP0_Index; 168 int32_t CP0_Index;
167 /* CP0_MVP* are per MVP registers. */ 169 /* CP0_MVP* are per MVP registers. */
target-mips/helper.c
@@ -148,10 +148,9 @@ static int get_physical_address (CPUState *env, target_ulong *physical, @@ -148,10 +148,9 @@ static int get_physical_address (CPUState *env, target_ulong *physical,
148 } 148 }
149 } else if (address < 0xC000000000000000ULL) { 149 } else if (address < 0xC000000000000000ULL) {
150 /* xkphys */ 150 /* xkphys */
151 - /* XXX: Assumes PABITS = 36 (correct for MIPS64R1) */  
152 if (kernel_mode && KX && 151 if (kernel_mode && KX &&
153 - (address & 0x07FFFFFFFFFFFFFFULL) <= 0x0000000FFFFFFFFFULL) {  
154 - *physical = address & 0x0000000FFFFFFFFFULL; 152 + (address & 0x07FFFFFFFFFFFFFFULL) <= env->PAMask) {
  153 + *physical = address & env->PAMask;
155 *prot = PAGE_READ | PAGE_WRITE; 154 *prot = PAGE_READ | PAGE_WRITE;
156 } else { 155 } else {
157 ret = TLBRET_BADADDR; 156 ret = TLBRET_BADADDR;
target-mips/op.c
@@ -1563,7 +1563,7 @@ void op_mtc0_vpeopt (void) @@ -1563,7 +1563,7 @@ void op_mtc0_vpeopt (void)
1563 1563
1564 void op_mtc0_entrylo0 (void) 1564 void op_mtc0_entrylo0 (void)
1565 { 1565 {
1566 - /* Large physaddr not implemented */ 1566 + /* Large physaddr (PABITS) not implemented */
1567 /* 1k pages not implemented */ 1567 /* 1k pages not implemented */
1568 env->CP0_EntryLo0 = T0 & 0x3FFFFFFF; 1568 env->CP0_EntryLo0 = T0 & 0x3FFFFFFF;
1569 FORCE_RET(); 1569 FORCE_RET();
@@ -1700,7 +1700,7 @@ void op_mttc0_tcschefback (void) @@ -1700,7 +1700,7 @@ void op_mttc0_tcschefback (void)
1700 1700
1701 void op_mtc0_entrylo1 (void) 1701 void op_mtc0_entrylo1 (void)
1702 { 1702 {
1703 - /* Large physaddr not implemented */ 1703 + /* Large physaddr (PABITS) not implemented */
1704 /* 1k pages not implemented */ 1704 /* 1k pages not implemented */
1705 env->CP0_EntryLo1 = T0 & 0x3FFFFFFF; 1705 env->CP0_EntryLo1 = T0 & 0x3FFFFFFF;
1706 FORCE_RET(); 1706 FORCE_RET();
@@ -1722,7 +1722,7 @@ void op_mtc0_pagemask (void) @@ -1722,7 +1722,7 @@ void op_mtc0_pagemask (void)
1722 void op_mtc0_pagegrain (void) 1722 void op_mtc0_pagegrain (void)
1723 { 1723 {
1724 /* SmartMIPS not implemented */ 1724 /* SmartMIPS not implemented */
1725 - /* Large physaddr not implemented */ 1725 + /* Large physaddr (PABITS) not implemented */
1726 /* 1k pages not implemented */ 1726 /* 1k pages not implemented */
1727 env->CP0_PageGrain = 0; 1727 env->CP0_PageGrain = 0;
1728 FORCE_RET(); 1728 FORCE_RET();
target-mips/translate_init.c
@@ -21,12 +21,9 @@ @@ -21,12 +21,9 @@
21 21
22 /* CPU / CPU family specific config register values. */ 22 /* CPU / CPU family specific config register values. */
23 23
24 -/* Have config1, is MIPS32R1, uses TLB, no virtual icache,  
25 - uncached coherency */ 24 +/* Have config1, uncached coherency */
26 #define MIPS_CONFIG0 \ 25 #define MIPS_CONFIG0 \
27 - ((1 << CP0C0_M) | (0x0 << CP0C0_K23) | (0x0 << CP0C0_KU) | \  
28 - (0x0 << CP0C0_AT) | (0x0 << CP0C0_AR) | (0x1 << CP0C0_MT) | \  
29 - (0x2 << CP0C0_K0)) 26 + ((1 << CP0C0_M) | (0x2 << CP0C0_K0))
30 27
31 /* Have config2, no coprocessor2 attached, no MDMX support attached, 28 /* Have config2, no coprocessor2 attached, no MDMX support attached,
32 no performance counters, watch registers present, 29 no performance counters, watch registers present,
@@ -41,7 +38,7 @@ @@ -41,7 +38,7 @@
41 #define MIPS_CONFIG2 \ 38 #define MIPS_CONFIG2 \
42 ((1 << CP0C2_M)) 39 ((1 << CP0C2_M))
43 40
44 -/* No config4, no DSP ASE, no large physaddr, 41 +/* No config4, no DSP ASE, no large physaddr (PABITS),
45 no external interrupt controller, no vectored interupts, 42 no external interrupt controller, no vectored interupts,
46 no 1kb pages, no SmartMIPS ASE, no trace logic */ 43 no 1kb pages, no SmartMIPS ASE, no trace logic */
47 #define MIPS_CONFIG3 \ 44 #define MIPS_CONFIG3 \
@@ -53,6 +50,18 @@ @@ -53,6 +50,18 @@
53 Define a major version 1, minor version 0. */ 50 Define a major version 1, minor version 0. */
54 #define MIPS_FCR0 ((0 << FCR0_S) | (0x1 << FCR0_PRID) | (0x10 << FCR0_REV)) 51 #define MIPS_FCR0 ((0 << FCR0_S) | (0x1 << FCR0_PRID) | (0x10 << FCR0_REV))
55 52
  53 +/* MMU types, the first four entries have the same layout as the
  54 + CP0C0_MT field. */
  55 +enum mips_mmu_types {
  56 + MMU_TYPE_NONE,
  57 + MMU_TYPE_R4000,
  58 + MMU_TYPE_RESERVED,
  59 + MMU_TYPE_FMT,
  60 + MMU_TYPE_R3000,
  61 + MMU_TYPE_R6000,
  62 + MMU_TYPE_R8000
  63 +};
  64 +
56 struct mips_def_t { 65 struct mips_def_t {
57 const unsigned char *name; 66 const unsigned char *name;
58 int32_t CP0_PRid; 67 int32_t CP0_PRid;
@@ -69,6 +78,7 @@ struct mips_def_t { @@ -69,6 +78,7 @@ struct mips_def_t {
69 int32_t CP0_SRSCtl; 78 int32_t CP0_SRSCtl;
70 int32_t CP1_fcr0; 79 int32_t CP1_fcr0;
71 int32_t SEGBITS; 80 int32_t SEGBITS;
  81 + int32_t PABITS;
72 int32_t CP0_SRSConf0_rw_bitmask; 82 int32_t CP0_SRSConf0_rw_bitmask;
73 int32_t CP0_SRSConf0; 83 int32_t CP0_SRSConf0;
74 int32_t CP0_SRSConf1_rw_bitmask; 84 int32_t CP0_SRSConf1_rw_bitmask;
@@ -80,6 +90,7 @@ struct mips_def_t { @@ -80,6 +90,7 @@ struct mips_def_t {
80 int32_t CP0_SRSConf4_rw_bitmask; 90 int32_t CP0_SRSConf4_rw_bitmask;
81 int32_t CP0_SRSConf4; 91 int32_t CP0_SRSConf4;
82 int insn_flags; 92 int insn_flags;
  93 + enum mips_mmu_types mmu_type;
83 }; 94 };
84 95
85 /*****************************************************************************/ 96 /*****************************************************************************/
@@ -89,7 +100,7 @@ static mips_def_t mips_defs[] = @@ -89,7 +100,7 @@ static mips_def_t mips_defs[] =
89 { 100 {
90 .name = "4Kc", 101 .name = "4Kc",
91 .CP0_PRid = 0x00018000, 102 .CP0_PRid = 0x00018000,
92 - .CP0_Config0 = MIPS_CONFIG0, 103 + .CP0_Config0 = MIPS_CONFIG0 | (MMU_TYPE_R4000 << CP0C0_MT),
93 .CP0_Config1 = MIPS_CONFIG1 | (15 << CP0C1_MMU) | 104 .CP0_Config1 = MIPS_CONFIG1 | (15 << CP0C1_MMU) |
94 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) | 105 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) |
95 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA), 106 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA),
@@ -98,15 +109,17 @@ static mips_def_t mips_defs[] = @@ -98,15 +109,17 @@ static mips_def_t mips_defs[] =
98 .SYNCI_Step = 32, 109 .SYNCI_Step = 32,
99 .CCRes = 2, 110 .CCRes = 2,
100 .CP0_Status_rw_bitmask = 0x1278FF17, 111 .CP0_Status_rw_bitmask = 0x1278FF17,
  112 + .SEGBITS = 32,
  113 + .PABITS = 32,
101 .insn_flags = CPU_MIPS32 | ASE_MIPS16, 114 .insn_flags = CPU_MIPS32 | ASE_MIPS16,
  115 + .mmu_type = MMU_TYPE_R4000,
102 }, 116 },
103 { 117 {
104 .name = "4Km", 118 .name = "4Km",
105 .CP0_PRid = 0x00018300, 119 .CP0_PRid = 0x00018300,
106 /* Config1 implemented, fixed mapping MMU, 120 /* Config1 implemented, fixed mapping MMU,
107 no virtual icache, uncached coherency. */ 121 no virtual icache, uncached coherency. */
108 - .CP0_Config0 = (1 << CP0C0_M) |  
109 - (0x3 << CP0C0_MT) | (0x2 << CP0C0_K0), 122 + .CP0_Config0 = MIPS_CONFIG0 | (MMU_TYPE_FMT << CP0C0_MT),
110 .CP0_Config1 = MIPS_CONFIG1 | 123 .CP0_Config1 = MIPS_CONFIG1 |
111 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) | 124 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) |
112 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA), 125 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA),
@@ -115,12 +128,15 @@ static mips_def_t mips_defs[] = @@ -115,12 +128,15 @@ static mips_def_t mips_defs[] =
115 .SYNCI_Step = 32, 128 .SYNCI_Step = 32,
116 .CCRes = 2, 129 .CCRes = 2,
117 .CP0_Status_rw_bitmask = 0x1258FF17, 130 .CP0_Status_rw_bitmask = 0x1258FF17,
  131 + .SEGBITS = 32,
  132 + .PABITS = 32,
118 .insn_flags = CPU_MIPS32 | ASE_MIPS16, 133 .insn_flags = CPU_MIPS32 | ASE_MIPS16,
  134 + .mmu_type = MMU_TYPE_FMT,
119 }, 135 },
120 { 136 {
121 .name = "4KEcR1", 137 .name = "4KEcR1",
122 .CP0_PRid = 0x00018400, 138 .CP0_PRid = 0x00018400,
123 - .CP0_Config0 = MIPS_CONFIG0, 139 + .CP0_Config0 = MIPS_CONFIG0 | (MMU_TYPE_R4000 << CP0C0_MT),
124 .CP0_Config1 = MIPS_CONFIG1 | (15 << CP0C1_MMU) | 140 .CP0_Config1 = MIPS_CONFIG1 | (15 << CP0C1_MMU) |
125 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) | 141 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) |
126 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA), 142 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA),
@@ -129,15 +145,15 @@ static mips_def_t mips_defs[] = @@ -129,15 +145,15 @@ static mips_def_t mips_defs[] =
129 .SYNCI_Step = 32, 145 .SYNCI_Step = 32,
130 .CCRes = 2, 146 .CCRes = 2,
131 .CP0_Status_rw_bitmask = 0x1278FF17, 147 .CP0_Status_rw_bitmask = 0x1278FF17,
  148 + .SEGBITS = 32,
  149 + .PABITS = 32,
132 .insn_flags = CPU_MIPS32 | ASE_MIPS16, 150 .insn_flags = CPU_MIPS32 | ASE_MIPS16,
  151 + .mmu_type = MMU_TYPE_R4000,
133 }, 152 },
134 { 153 {
135 .name = "4KEmR1", 154 .name = "4KEmR1",
136 .CP0_PRid = 0x00018500, 155 .CP0_PRid = 0x00018500,
137 - /* Config1 implemented, fixed mapping MMU,  
138 - no virtual icache, uncached coherency. */  
139 - .CP0_Config0 = (1 << CP0C0_M) |  
140 - (0x3 << CP0C0_MT) | (0x2 << CP0C0_K0), 156 + .CP0_Config0 = MIPS_CONFIG0 | (MMU_TYPE_FMT << CP0C0_MT),
141 .CP0_Config1 = MIPS_CONFIG1 | 157 .CP0_Config1 = MIPS_CONFIG1 |
142 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) | 158 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) |
143 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA), 159 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA),
@@ -146,12 +162,16 @@ static mips_def_t mips_defs[] = @@ -146,12 +162,16 @@ static mips_def_t mips_defs[] =
146 .SYNCI_Step = 32, 162 .SYNCI_Step = 32,
147 .CCRes = 2, 163 .CCRes = 2,
148 .CP0_Status_rw_bitmask = 0x1258FF17, 164 .CP0_Status_rw_bitmask = 0x1258FF17,
  165 + .SEGBITS = 32,
  166 + .PABITS = 32,
149 .insn_flags = CPU_MIPS32 | ASE_MIPS16, 167 .insn_flags = CPU_MIPS32 | ASE_MIPS16,
  168 + .mmu_type = MMU_TYPE_FMT,
150 }, 169 },
151 { 170 {
152 .name = "4KEc", 171 .name = "4KEc",
153 .CP0_PRid = 0x00019000, 172 .CP0_PRid = 0x00019000,
154 - .CP0_Config0 = MIPS_CONFIG0 | (0x1 << CP0C0_AR), 173 + .CP0_Config0 = MIPS_CONFIG0 | (0x1 << CP0C0_AR) |
  174 + (MMU_TYPE_R4000 << CP0C0_MT),
155 .CP0_Config1 = MIPS_CONFIG1 | (15 << CP0C1_MMU) | 175 .CP0_Config1 = MIPS_CONFIG1 | (15 << CP0C1_MMU) |
156 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) | 176 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) |
157 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA), 177 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA),
@@ -160,15 +180,16 @@ static mips_def_t mips_defs[] = @@ -160,15 +180,16 @@ static mips_def_t mips_defs[] =
160 .SYNCI_Step = 32, 180 .SYNCI_Step = 32,
161 .CCRes = 2, 181 .CCRes = 2,
162 .CP0_Status_rw_bitmask = 0x1278FF17, 182 .CP0_Status_rw_bitmask = 0x1278FF17,
  183 + .SEGBITS = 32,
  184 + .PABITS = 32,
163 .insn_flags = CPU_MIPS32R2 | ASE_MIPS16, 185 .insn_flags = CPU_MIPS32R2 | ASE_MIPS16,
  186 + .mmu_type = MMU_TYPE_R4000,
164 }, 187 },
165 { 188 {
166 .name = "4KEm", 189 .name = "4KEm",
167 .CP0_PRid = 0x00019100, 190 .CP0_PRid = 0x00019100,
168 - /* Config1 implemented, MIPS32R2, fixed mapping MMU,  
169 - no virtual icache, uncached coherency. */  
170 - .CP0_Config0 = (1 << CP0C0_M) | (0x1 << CP0C0_AR) |  
171 - (0x3 << CP0C0_MT) | (0x2 << CP0C0_K0), 191 + .CP0_Config0 = MIPS_CONFIG0 | (0x1 << CP0C0_AR) |
  192 + (MMU_TYPE_FMT << CP0C0_MT),
172 .CP0_Config1 = MIPS_CONFIG1 | 193 .CP0_Config1 = MIPS_CONFIG1 |
173 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) | 194 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) |
174 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA), 195 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA),
@@ -177,12 +198,16 @@ static mips_def_t mips_defs[] = @@ -177,12 +198,16 @@ static mips_def_t mips_defs[] =
177 .SYNCI_Step = 32, 198 .SYNCI_Step = 32,
178 .CCRes = 2, 199 .CCRes = 2,
179 .CP0_Status_rw_bitmask = 0x1258FF17, 200 .CP0_Status_rw_bitmask = 0x1258FF17,
  201 + .SEGBITS = 32,
  202 + .PABITS = 32,
180 .insn_flags = CPU_MIPS32R2 | ASE_MIPS16, 203 .insn_flags = CPU_MIPS32R2 | ASE_MIPS16,
  204 + .mmu_type = MMU_TYPE_FMT,
181 }, 205 },
182 { 206 {
183 .name = "24Kc", 207 .name = "24Kc",
184 .CP0_PRid = 0x00019300, 208 .CP0_PRid = 0x00019300,
185 - .CP0_Config0 = MIPS_CONFIG0 | (0x1 << CP0C0_AR), 209 + .CP0_Config0 = MIPS_CONFIG0 | (0x1 << CP0C0_AR) |
  210 + (MMU_TYPE_R4000 << CP0C0_MT),
186 .CP0_Config1 = MIPS_CONFIG1 | (15 << CP0C1_MMU) | 211 .CP0_Config1 = MIPS_CONFIG1 | (15 << CP0C1_MMU) |
187 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) | 212 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) |
188 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA), 213 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA),
@@ -192,12 +217,16 @@ static mips_def_t mips_defs[] = @@ -192,12 +217,16 @@ static mips_def_t mips_defs[] =
192 .CCRes = 2, 217 .CCRes = 2,
193 /* No DSP implemented. */ 218 /* No DSP implemented. */
194 .CP0_Status_rw_bitmask = 0x1278FF1F, 219 .CP0_Status_rw_bitmask = 0x1278FF1F,
  220 + .SEGBITS = 32,
  221 + .PABITS = 32,
195 .insn_flags = CPU_MIPS32R2 | ASE_MIPS16, 222 .insn_flags = CPU_MIPS32R2 | ASE_MIPS16,
  223 + .mmu_type = MMU_TYPE_R4000,
196 }, 224 },
197 { 225 {
198 .name = "24Kf", 226 .name = "24Kf",
199 .CP0_PRid = 0x00019300, 227 .CP0_PRid = 0x00019300,
200 - .CP0_Config0 = MIPS_CONFIG0 | (0x1 << CP0C0_AR), 228 + .CP0_Config0 = MIPS_CONFIG0 | (0x1 << CP0C0_AR) |
  229 + (MMU_TYPE_R4000 << CP0C0_MT),
201 .CP0_Config1 = MIPS_CONFIG1 | (1 << CP0C1_FP) | (15 << CP0C1_MMU) | 230 .CP0_Config1 = MIPS_CONFIG1 | (1 << CP0C1_FP) | (15 << CP0C1_MMU) |
202 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) | 231 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) |
203 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA), 232 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA),
@@ -209,12 +238,16 @@ static mips_def_t mips_defs[] = @@ -209,12 +238,16 @@ static mips_def_t mips_defs[] =
209 .CP0_Status_rw_bitmask = 0x3678FF1F, 238 .CP0_Status_rw_bitmask = 0x3678FF1F,
210 .CP1_fcr0 = (1 << FCR0_F64) | (1 << FCR0_L) | (1 << FCR0_W) | 239 .CP1_fcr0 = (1 << FCR0_F64) | (1 << FCR0_L) | (1 << FCR0_W) |
211 (1 << FCR0_D) | (1 << FCR0_S) | (0x93 << FCR0_PRID), 240 (1 << FCR0_D) | (1 << FCR0_S) | (0x93 << FCR0_PRID),
  241 + .SEGBITS = 32,
  242 + .PABITS = 32,
212 .insn_flags = CPU_MIPS32R2 | ASE_MIPS16, 243 .insn_flags = CPU_MIPS32R2 | ASE_MIPS16,
  244 + .mmu_type = MMU_TYPE_R4000,
213 }, 245 },
214 { 246 {
215 .name = "34Kf", 247 .name = "34Kf",
216 .CP0_PRid = 0x00019500, 248 .CP0_PRid = 0x00019500,
217 - .CP0_Config0 = MIPS_CONFIG0 | (0x1 << CP0C0_AR), 249 + .CP0_Config0 = MIPS_CONFIG0 | (0x1 << CP0C0_AR) |
  250 + (MMU_TYPE_R4000 << CP0C0_MT),
218 .CP0_Config1 = MIPS_CONFIG1 | (1 << CP0C1_FP) | (15 << CP0C1_MMU) | 251 .CP0_Config1 = MIPS_CONFIG1 | (1 << CP0C1_FP) | (15 << CP0C1_MMU) |
219 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) | 252 (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) |
220 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA), 253 (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA),
@@ -249,30 +282,34 @@ static mips_def_t mips_defs[] = @@ -249,30 +282,34 @@ static mips_def_t mips_defs[] =
249 .CP0_SRSConf4_rw_bitmask = 0x3fffffff, 282 .CP0_SRSConf4_rw_bitmask = 0x3fffffff,
250 .CP0_SRSConf4 = (0x3fe << CP0SRSC4_SRS15) | 283 .CP0_SRSConf4 = (0x3fe << CP0SRSC4_SRS15) |
251 (0x3fe << CP0SRSC4_SRS14) | (0x3fe << CP0SRSC4_SRS13), 284 (0x3fe << CP0SRSC4_SRS14) | (0x3fe << CP0SRSC4_SRS13),
  285 + .SEGBITS = 32,
  286 + .PABITS = 32,
252 .insn_flags = CPU_MIPS32R2 | ASE_MIPS16 | ASE_DSP | ASE_MT, 287 .insn_flags = CPU_MIPS32R2 | ASE_MIPS16 | ASE_DSP | ASE_MT,
  288 + .mmu_type = MMU_TYPE_R4000,
253 }, 289 },
254 #if defined(TARGET_MIPS64) 290 #if defined(TARGET_MIPS64)
255 { 291 {
256 .name = "R4000", 292 .name = "R4000",
257 .CP0_PRid = 0x00000400, 293 .CP0_PRid = 0x00000400,
258 - .CP0_Config0 = MIPS_CONFIG0 | (0x2 << CP0C0_AT),  
259 - .CP0_Config1 = MIPS_CONFIG1 | (1 << CP0C1_FP) | (47 << CP0C1_MMU) |  
260 - (0 << CP0C1_IS) | (3 << CP0C1_IL) | (1 << CP0C1_IA) |  
261 - (0 << CP0C1_DS) | (3 << CP0C1_DL) | (1 << CP0C1_DA),  
262 - .CP0_Config2 = MIPS_CONFIG2,  
263 - .CP0_Config3 = MIPS_CONFIG3, 294 + /* No L2 cache, icache size 8k, dcache size 8k, uncached coherency. */
  295 + .CP0_Config0 = (1 << 17) | (0x1 << 9) | (0x1 << 6) | (0x2 << CP0C0_K0),
  296 + /* Note: Config1 is only used internally, the R4000 has only Config0. */
  297 + .CP0_Config1 = (1 << CP0C1_FP) | (47 << CP0C1_MMU),
264 .SYNCI_Step = 16, 298 .SYNCI_Step = 16,
265 .CCRes = 2, 299 .CCRes = 2,
266 .CP0_Status_rw_bitmask = 0x3678FFFF, 300 .CP0_Status_rw_bitmask = 0x3678FFFF,
267 - /* The R4000 has a full 64bit FPU doesn't use the fcr0 bits. */ 301 + /* The R4000 has a full 64bit FPU but doesn't use the fcr0 bits. */
268 .CP1_fcr0 = (0x5 << FCR0_PRID) | (0x0 << FCR0_REV), 302 .CP1_fcr0 = (0x5 << FCR0_PRID) | (0x0 << FCR0_REV),
269 .SEGBITS = 40, 303 .SEGBITS = 40,
  304 + .PABITS = 36,
270 .insn_flags = CPU_MIPS3, 305 .insn_flags = CPU_MIPS3,
  306 + .mmu_type = MMU_TYPE_R4000,
271 }, 307 },
272 { 308 {
273 .name = "5Kc", 309 .name = "5Kc",
274 .CP0_PRid = 0x00018100, 310 .CP0_PRid = 0x00018100,
275 - .CP0_Config0 = MIPS_CONFIG0 | (0x2 << CP0C0_AT), 311 + .CP0_Config0 = MIPS_CONFIG0 | (0x1 << CP0C0_AR) | (0x2 << CP0C0_AT) |
  312 + (MMU_TYPE_R4000 << CP0C0_MT),
276 .CP0_Config1 = MIPS_CONFIG1 | (31 << CP0C1_MMU) | 313 .CP0_Config1 = MIPS_CONFIG1 | (31 << CP0C1_MMU) |
277 (1 << CP0C1_IS) | (4 << CP0C1_IL) | (1 << CP0C1_IA) | 314 (1 << CP0C1_IS) | (4 << CP0C1_IL) | (1 << CP0C1_IA) |
278 (1 << CP0C1_DS) | (4 << CP0C1_DL) | (1 << CP0C1_DA) | 315 (1 << CP0C1_DS) | (4 << CP0C1_DL) | (1 << CP0C1_DA) |
@@ -283,12 +320,15 @@ static mips_def_t mips_defs[] = @@ -283,12 +320,15 @@ static mips_def_t mips_defs[] =
283 .CCRes = 2, 320 .CCRes = 2,
284 .CP0_Status_rw_bitmask = 0x32F8FFFF, 321 .CP0_Status_rw_bitmask = 0x32F8FFFF,
285 .SEGBITS = 42, 322 .SEGBITS = 42,
  323 + .PABITS = 36,
286 .insn_flags = CPU_MIPS64, 324 .insn_flags = CPU_MIPS64,
  325 + .mmu_type = MMU_TYPE_R4000,
287 }, 326 },
288 { 327 {
289 .name = "5Kf", 328 .name = "5Kf",
290 .CP0_PRid = 0x00018100, 329 .CP0_PRid = 0x00018100,
291 - .CP0_Config0 = MIPS_CONFIG0 | (0x2 << CP0C0_AT), 330 + .CP0_Config0 = MIPS_CONFIG0 | (0x1 << CP0C0_AR) | (0x2 << CP0C0_AT) |
  331 + (MMU_TYPE_R4000 << CP0C0_MT),
292 .CP0_Config1 = MIPS_CONFIG1 | (1 << CP0C1_FP) | (31 << CP0C1_MMU) | 332 .CP0_Config1 = MIPS_CONFIG1 | (1 << CP0C1_FP) | (31 << CP0C1_MMU) |
293 (1 << CP0C1_IS) | (4 << CP0C1_IL) | (1 << CP0C1_IA) | 333 (1 << CP0C1_IS) | (4 << CP0C1_IL) | (1 << CP0C1_IA) |
294 (1 << CP0C1_DS) | (4 << CP0C1_DL) | (1 << CP0C1_DA) | 334 (1 << CP0C1_DS) | (4 << CP0C1_DL) | (1 << CP0C1_DA) |
@@ -302,14 +342,17 @@ static mips_def_t mips_defs[] = @@ -302,14 +342,17 @@ static mips_def_t mips_defs[] =
302 .CP1_fcr0 = (1 << FCR0_D) | (1 << FCR0_S) | 342 .CP1_fcr0 = (1 << FCR0_D) | (1 << FCR0_S) |
303 (0x81 << FCR0_PRID) | (0x0 << FCR0_REV), 343 (0x81 << FCR0_PRID) | (0x0 << FCR0_REV),
304 .SEGBITS = 42, 344 .SEGBITS = 42,
  345 + .PABITS = 36,
305 .insn_flags = CPU_MIPS64, 346 .insn_flags = CPU_MIPS64,
  347 + .mmu_type = MMU_TYPE_R4000,
306 }, 348 },
307 { 349 {
308 .name = "20Kc", 350 .name = "20Kc",
309 /* We emulate a later version of the 20Kc, earlier ones had a broken 351 /* We emulate a later version of the 20Kc, earlier ones had a broken
310 WAIT instruction. */ 352 WAIT instruction. */
311 .CP0_PRid = 0x000182a0, 353 .CP0_PRid = 0x000182a0,
312 - .CP0_Config0 = MIPS_CONFIG0 | (0x2 << CP0C0_AT) | (1 << CP0C0_VI), 354 + .CP0_Config0 = MIPS_CONFIG0 | (0x1 << CP0C0_AR) | (0x2 << CP0C0_AT) |
  355 + (MMU_TYPE_R4000 << CP0C0_MT) | (1 << CP0C0_VI),
313 .CP0_Config1 = MIPS_CONFIG1 | (1 << CP0C1_FP) | (47 << CP0C1_MMU) | 356 .CP0_Config1 = MIPS_CONFIG1 | (1 << CP0C1_FP) | (47 << CP0C1_MMU) |
314 (2 << CP0C1_IS) | (4 << CP0C1_IL) | (3 << CP0C1_IA) | 357 (2 << CP0C1_IS) | (4 << CP0C1_IL) | (3 << CP0C1_IA) |
315 (2 << CP0C1_DS) | (4 << CP0C1_DL) | (3 << CP0C1_DA) | 358 (2 << CP0C1_DS) | (4 << CP0C1_DL) | (3 << CP0C1_DA) |
@@ -324,28 +367,36 @@ static mips_def_t mips_defs[] = @@ -324,28 +367,36 @@ static mips_def_t mips_defs[] =
324 (1 << FCR0_D) | (1 << FCR0_S) | 367 (1 << FCR0_D) | (1 << FCR0_S) |
325 (0x82 << FCR0_PRID) | (0x0 << FCR0_REV), 368 (0x82 << FCR0_PRID) | (0x0 << FCR0_REV),
326 .SEGBITS = 40, 369 .SEGBITS = 40,
  370 + .PABITS = 36,
327 .insn_flags = CPU_MIPS64 | ASE_MIPS3D, 371 .insn_flags = CPU_MIPS64 | ASE_MIPS3D,
  372 + .mmu_type = MMU_TYPE_R4000,
328 }, 373 },
329 { 374 {
330 /* A generic CPU providing MIPS64 Release 2 features. 375 /* A generic CPU providing MIPS64 Release 2 features.
331 FIXME: Eventually this should be replaced by a real CPU model. */ 376 FIXME: Eventually this should be replaced by a real CPU model. */
332 .name = "MIPS64R2-generic", 377 .name = "MIPS64R2-generic",
333 .CP0_PRid = 0x00010000, 378 .CP0_PRid = 0x00010000,
334 - .CP0_Config0 = MIPS_CONFIG0 | (0x2 << CP0C0_AT) | (0x1 << CP0C0_AR), 379 + .CP0_Config0 = MIPS_CONFIG0 | (0x1 << CP0C0_AR) | (0x2 << CP0C0_AT) |
  380 + (MMU_TYPE_R4000 << CP0C0_MT),
335 .CP0_Config1 = MIPS_CONFIG1 | (1 << CP0C1_FP) | (63 << CP0C1_MMU) | 381 .CP0_Config1 = MIPS_CONFIG1 | (1 << CP0C1_FP) | (63 << CP0C1_MMU) |
336 (2 << CP0C1_IS) | (4 << CP0C1_IL) | (3 << CP0C1_IA) | 382 (2 << CP0C1_IS) | (4 << CP0C1_IL) | (3 << CP0C1_IA) |
337 (2 << CP0C1_DS) | (4 << CP0C1_DL) | (3 << CP0C1_DA) | 383 (2 << CP0C1_DS) | (4 << CP0C1_DL) | (3 << CP0C1_DA) |
338 (1 << CP0C1_PC) | (1 << CP0C1_WR) | (1 << CP0C1_EP), 384 (1 << CP0C1_PC) | (1 << CP0C1_WR) | (1 << CP0C1_EP),
339 .CP0_Config2 = MIPS_CONFIG2, 385 .CP0_Config2 = MIPS_CONFIG2,
340 - .CP0_Config3 = MIPS_CONFIG3, 386 + .CP0_Config3 = MIPS_CONFIG3 | (1 << CP0C3_LPA),
341 .SYNCI_Step = 32, 387 .SYNCI_Step = 32,
342 .CCRes = 2, 388 .CCRes = 2,
343 .CP0_Status_rw_bitmask = 0x36FBFFFF, 389 .CP0_Status_rw_bitmask = 0x36FBFFFF,
344 .CP1_fcr0 = (1 << FCR0_3D) | (1 << FCR0_PS) | (1 << FCR0_L) | 390 .CP1_fcr0 = (1 << FCR0_3D) | (1 << FCR0_PS) | (1 << FCR0_L) |
345 (1 << FCR0_W) | (1 << FCR0_D) | (1 << FCR0_S) | 391 (1 << FCR0_W) | (1 << FCR0_D) | (1 << FCR0_S) |
346 (0x00 << FCR0_PRID) | (0x0 << FCR0_REV), 392 (0x00 << FCR0_PRID) | (0x0 << FCR0_REV),
347 - .SEGBITS = 40, 393 + .SEGBITS = 42,
  394 + /* The architectural limit is 59, but we have hardcoded 36 bit
  395 + in some places...
  396 + .PABITS = 59, */ /* the architectural limit */
  397 + .PABITS = 36,
348 .insn_flags = CPU_MIPS64R2 | ASE_MIPS3D, 398 .insn_flags = CPU_MIPS64R2 | ASE_MIPS3D,
  399 + .mmu_type = MMU_TYPE_R4000,
349 }, 400 },
350 #endif 401 #endif
351 }; 402 };
@@ -399,20 +450,19 @@ static void mmu_init (CPUMIPSState *env, const mips_def_t *def) @@ -399,20 +450,19 @@ static void mmu_init (CPUMIPSState *env, const mips_def_t *def)
399 { 450 {
400 env->tlb = qemu_mallocz(sizeof(CPUMIPSTLBContext)); 451 env->tlb = qemu_mallocz(sizeof(CPUMIPSTLBContext));
401 452
402 - /* There are more full-featured MMU variants in older MIPS CPUs,  
403 - R3000, R6000 and R8000 come to mind. If we ever support them,  
404 - this check will need to look up a different place than those  
405 - newfangled config registers. */  
406 - switch ((env->CP0_Config0 >> CP0C0_MT) & 3) {  
407 - case 0: 453 + switch (def->mmu_type) {
  454 + case MMU_TYPE_NONE:
408 no_mmu_init(env, def); 455 no_mmu_init(env, def);
409 break; 456 break;
410 - case 1: 457 + case MMU_TYPE_R4000:
411 r4k_mmu_init(env, def); 458 r4k_mmu_init(env, def);
412 break; 459 break;
413 - case 3: 460 + case MMU_TYPE_FMT:
414 fixed_mmu_init(env, def); 461 fixed_mmu_init(env, def);
415 break; 462 break;
  463 + case MMU_TYPE_R3000:
  464 + case MMU_TYPE_R6000:
  465 + case MMU_TYPE_R8000:
416 default: 466 default:
417 cpu_abort(env, "MMU type not supported\n"); 467 cpu_abort(env, "MMU type not supported\n");
418 } 468 }
@@ -477,17 +527,16 @@ static int cpu_mips_register (CPUMIPSState *env, const mips_def_t *def) @@ -477,17 +527,16 @@ static int cpu_mips_register (CPUMIPSState *env, const mips_def_t *def)
477 env->CP0_Status_rw_bitmask = def->CP0_Status_rw_bitmask; 527 env->CP0_Status_rw_bitmask = def->CP0_Status_rw_bitmask;
478 env->CP0_TCStatus_rw_bitmask = def->CP0_TCStatus_rw_bitmask; 528 env->CP0_TCStatus_rw_bitmask = def->CP0_TCStatus_rw_bitmask;
479 env->CP0_SRSCtl = def->CP0_SRSCtl; 529 env->CP0_SRSCtl = def->CP0_SRSCtl;
  530 + env->SEGBITS = def->SEGBITS;
  531 + env->SEGMask = (target_ulong)((1ULL << def->SEGBITS) - 1);
480 #if defined(TARGET_MIPS64) 532 #if defined(TARGET_MIPS64)
481 - if (def->insn_flags & ISA_MIPS3)  
482 - { 533 + if (def->insn_flags & ISA_MIPS3) {
483 env->hflags |= MIPS_HFLAG_64; 534 env->hflags |= MIPS_HFLAG_64;
484 - env->SEGBITS = def->SEGBITS;  
485 - env->SEGMask = (3ULL << 62) | ((1ULL << def->SEGBITS) - 1);  
486 - } else {  
487 - env->SEGBITS = 32;  
488 - env->SEGMask = 0xFFFFFFFF; 535 + env->SEGMask |= 3ULL << 62;
489 } 536 }
490 #endif 537 #endif
  538 + env->PABITS = def->PABITS;
  539 + env->PAMask = (target_ulong)((1ULL << def->PABITS) - 1);
491 env->CP0_SRSConf0_rw_bitmask = def->CP0_SRSConf0_rw_bitmask; 540 env->CP0_SRSConf0_rw_bitmask = def->CP0_SRSConf0_rw_bitmask;
492 env->CP0_SRSConf0 = def->CP0_SRSConf0; 541 env->CP0_SRSConf0 = def->CP0_SRSConf0;
493 env->CP0_SRSConf1_rw_bitmask = def->CP0_SRSConf1_rw_bitmask; 542 env->CP0_SRSConf1_rw_bitmask = def->CP0_SRSConf1_rw_bitmask;