comparison 68kinst.c @ 8:23b83d94c633

Finish bit/movep/immediate group except for 68020 instructions
author Mike Pavone <pavone@retrodev.com>
date Fri, 09 Nov 2012 22:01:26 -0800
parents 85699517043f
children 0a0cd3705c19
comparison
equal deleted inserted replaced
7:a74c2969e8f3 8:23b83d94c633
122 break; 122 break;
123 } 123 }
124 decoded->src.addr_mode = MODE_REG; 124 decoded->src.addr_mode = MODE_REG;
125 decoded->src.params.regs.pri = m68K_reg_quick_field(*istream); 125 decoded->src.params.regs.pri = m68K_reg_quick_field(*istream);
126 istream = m68k_decode_op(istream, OPSIZE_LONG, &(decoded->dst)); 126 istream = m68k_decode_op(istream, OPSIZE_LONG, &(decoded->dst));
127 } else if ((*istream & 0xF00) == 0x800) {
128 } else if ((*istream & 0xC0) == 0xC0) {
129 #ifdef M68020
130 //CMP2, CHK2, CAS, CAS2, RTM, CALLM
131 #endif
127 } else { 132 } else {
128 switch ((*istream >> 9) & 0x7) 133 switch ((*istream >> 9) & 0x7)
129 { 134 {
130 case 0: 135 case 0:
131 if ((*istream & 0xFF) == 0x3C) { 136 if ((*istream & 0xFF) == 0x3C) {
137 decoded->op = M68K_ORI_SR; 142 decoded->op = M68K_ORI_SR;
138 decoded->extra.size = OPSIZE_WORD; 143 decoded->extra.size = OPSIZE_WORD;
139 decoded->src.addr_mode = MODE_IMMEDIATE; 144 decoded->src.addr_mode = MODE_IMMEDIATE;
140 decoded->src.params.u16 = *(++istream); 145 decoded->src.params.u16 = *(++istream);
141 } else { 146 } else {
142 //ORI, CMP2.b, CHK2.b 147 decoded->op = M68K_OR;
143 if ((*istream & 0xC0) != 0xC0) { 148 decoded->variant = VAR_IMMEDIATE;
144 decoded->op = M68K_OR; 149 decoded->src.addr_mode = MODE_IMMEDIATE;
145 decoded->src.addr_mode = MODE_IMMEDIATE; 150 decoded->extra.size = size = (*istream >> 6) & 3;
146 decoded->extra.size = size = (*istream >> 6) & 3; 151 reg = *istream & 0x7;
147 reg = *istream & 0x7; 152 opmode = (*istream >> 3) & 0x7;
148 opmode = (*istream >> 3) & 0x7; 153 switch (size)
149 switch (size) 154 {
150 { 155 case OPSIZE_BYTE:
151 case OPSIZE_BYTE: 156 decoded->src.params.u8 = *(++istream);
152 decoded->src.params.u8 = *(++istream); 157 break;
153 break; 158 case OPSIZE_WORD:
154 case OPSIZE_WORD: 159 decoded->src.params.u16 = *(++istream);
155 decoded->src.params.16 = *(++istream); 160 break;
156 break; 161 case OPSIZE_LONG:
157 case OPSIZE_LONG: 162 immed = *(++istream);
158 immed = *(++istream); 163 decoded->src.params.u32 = immed << 16 | *(++istream);
159 decoded->src.params.u32 = immed << 16 | *(++istream); 164 break;
160 break;
161 }
162 istream = m68k_decode_op_ex(istream, opmode, reg, size, &(decoded->dst));
163 } else {
164 #ifdef M68020
165 //TODO: Implement me for 68020 support
166 #endif
167 } 165 }
166 istream = m68k_decode_op_ex(istream, opmode, reg, size, &(decoded->dst));
168 } 167 }
169 break; 168 break;
170 case 1: 169 case 1:
171 //ANDI, ANDI to CCR, ANDI to SR, CMP2.w CHK2.w 170 //ANDI, ANDI to CCR, ANDI to SR
172 if ((*istream & 0xFF) == 0x3C) { 171 if ((*istream & 0xFF) == 0x3C) {
173 decoded->op = M68K_ANDI_CCR; 172 decoded->op = M68K_ANDI_CCR;
174 decoded->extra.size = OPSIZE_BYTE; 173 decoded->extra.size = OPSIZE_BYTE;
175 decoded->src.addr_mode = MODE_IMMEDIATE; 174 decoded->src.addr_mode = MODE_IMMEDIATE;
176 decoded->src.params.u8 = *(++istream); 175 decoded->src.params.u8 = *(++istream);
178 decoded->op = M68K_ANDI_SR; 177 decoded->op = M68K_ANDI_SR;
179 decoded->extra.size = OPSIZE_WORD; 178 decoded->extra.size = OPSIZE_WORD;
180 decoded->src.addr_mode = MODE_IMMEDIATE; 179 decoded->src.addr_mode = MODE_IMMEDIATE;
181 decoded->src.params.u16 = *(++istream); 180 decoded->src.params.u16 = *(++istream);
182 } else { 181 } else {
183 //ANDI, CMP2.w, CHK2.w 182 decoded->op = M68K_AND;
184 if ((*istream & 0xC0) != 0xC0) { 183 decoded->variant = VAR_IMMEDIATE;
185 decoded->op = M68K_AND;
186 decoded->src.addr_mode = MODE_IMMEDIATE;
187 decoded->extra.size = size = (*istream >> 6) & 3;
188 reg = *istream & 0x7;
189 opmode = (*istream >> 3) & 0x7;
190 switch (size)
191 {
192 case OPSIZE_BYTE:
193 decoded->src.params.u8 = *(++istream);
194 break;
195 case OPSIZE_WORD:
196 decoded->src.params.16 = *(++istream);
197 break;
198 case OPSIZE_LONG:
199 immed = *(++istream);
200 decoded->src.params.u32 = immed << 16 | *(++istream);
201 break;
202 }
203 istream = m68k_decode_op_ex(istream, opmode, reg, size, &(decoded->dst));
204 } else {
205 #ifdef M68020
206 //TODO: Implement me for 68020 support
207 #endif
208 }
209 }
210 break;
211 case 2:
212 //SUBI, CMP2.l, CHK2.l
213 if ((*istream & 0xC0) != 0xC0) {
214 decoded->op = M68K_SUB;
215 decoded->src.addr_mode = MODE_IMMEDIATE; 184 decoded->src.addr_mode = MODE_IMMEDIATE;
216 decoded->extra.size = size = (*istream >> 6) & 3; 185 decoded->extra.size = size = (*istream >> 6) & 3;
217 reg = *istream & 0x7; 186 reg = *istream & 0x7;
218 opmode = (*istream >> 3) & 0x7; 187 opmode = (*istream >> 3) & 0x7;
219 switch (size) 188 switch (size)
220 { 189 {
221 case OPSIZE_BYTE: 190 case OPSIZE_BYTE:
222 decoded->src.params.u8 = *(++istream); 191 decoded->src.params.u8 = *(++istream);
223 break; 192 break;
224 case OPSIZE_WORD: 193 case OPSIZE_WORD:
225 decoded->src.params.16 = *(++istream); 194 decoded->src.params.u16 = *(++istream);
226 break; 195 break;
227 case OPSIZE_LONG: 196 case OPSIZE_LONG:
228 immed = *(++istream); 197 immed = *(++istream);
229 decoded->src.params.u32 = immed << 16 | *(++istream); 198 decoded->src.params.u32 = immed << 16 | *(++istream);
230 break; 199 break;
231 } 200 }
232 istream = m68k_decode_op_ex(istream, opmode, reg, size, &(decoded->dst)); 201 istream = m68k_decode_op_ex(istream, opmode, reg, size, &(decoded->dst));
233 } else { 202 }
234 #ifdef M68020 203 break;
235 //TODO: Implement me for 68020 support 204 case 2:
236 #endif 205 decoded->op = M68K_SUB;
237 } 206 decoded->variant = VAR_IMMEDIATE;
207 decoded->src.addr_mode = MODE_IMMEDIATE;
208 decoded->extra.size = size = (*istream >> 6) & 3;
209 reg = *istream & 0x7;
210 opmode = (*istream >> 3) & 0x7;
211 switch (size)
212 {
213 case OPSIZE_BYTE:
214 decoded->src.params.u8 = *(++istream);
215 break;
216 case OPSIZE_WORD:
217 decoded->src.params.u16 = *(++istream);
218 break;
219 case OPSIZE_LONG:
220 immed = *(++istream);
221 decoded->src.params.u32 = immed << 16 | *(++istream);
222 break;
223 }
224 istream = m68k_decode_op_ex(istream, opmode, reg, size, &(decoded->dst));
238 break; 225 break;
239 case 3: 226 case 3:
240 //RTM, CALLM, ADDI 227 decoded->op = M68K_ADD;
241 if ((*istream & 0xC0) != 0xC0) { 228 decoded->variant = VAR_IMMEDIATE;
242 decoded->op = M68K_ADD; 229 decoded->src.addr_mode = MODE_IMMEDIATE;
243 decoded->src.addr_mode = MODE_IMMEDIATE; 230 decoded->extra.size = size = (*istream >> 6) & 3;
244 decoded->extra.size = size = (*istream >> 6) & 3; 231 reg = *istream & 0x7;
245 reg = *istream & 0x7; 232 opmode = (*istream >> 3) & 0x7;
246 opmode = (*istream >> 3) & 0x7; 233 switch (size)
247 switch (size) 234 {
248 { 235 case OPSIZE_BYTE:
249 case OPSIZE_BYTE: 236 decoded->src.params.u8 = *(++istream);
250 decoded->src.params.u8 = *(++istream); 237 break;
251 break; 238 case OPSIZE_WORD:
252 case OPSIZE_WORD: 239 decoded->src.params.u16 = *(++istream);
253 decoded->src.params.16 = *(++istream); 240 break;
254 break; 241 case OPSIZE_LONG:
255 case OPSIZE_LONG: 242 immed = *(++istream);
256 immed = *(++istream); 243 decoded->src.params.u32 = immed << 16 | *(++istream);
257 decoded->src.params.u32 = immed << 16 | *(++istream); 244 break;
258 break; 245 }
259 } 246 istream = m68k_decode_op_ex(istream, opmode, reg, size, &(decoded->dst));
260 istream = m68k_decode_op_ex(istream, opmode, reg, size, &(decoded->dst));
261 } else {
262 #ifdef M68020
263 //TODO: Implement me for 68020 support
264 #endif
265 }
266 break; 247 break;
267 case 4: 248 case 4:
268 //BTST, BCHG, BCLR, BSET 249 //BTST, BCHG, BCLR, BSET
269 switch ((*istream >> 6) & 0x3) 250 switch ((*istream >> 6) & 0x3)
270 { 251 {
296 decoded->op = M68K_EORI_SR; 277 decoded->op = M68K_EORI_SR;
297 decoded->extra.size = OPSIZE_WORD; 278 decoded->extra.size = OPSIZE_WORD;
298 decoded->src.addr_mode = MODE_IMMEDIATE; 279 decoded->src.addr_mode = MODE_IMMEDIATE;
299 decoded->src.params.u16 = *(++istream); 280 decoded->src.params.u16 = *(++istream);
300 } else { 281 } else {
301 //EORI, CMP2.w, CHK2.w 282 decoded->op = M68K_EOR;
302 if ((*istream & 0xC0) != 0xC0) { 283 decoded->variant = VAR_IMMEDIATE;
303 decoded->op = M68K_EOR; 284 decoded->src.addr_mode = MODE_IMMEDIATE;
304 decoded->src.addr_mode = MODE_IMMEDIATE; 285 decoded->extra.size = size = (*istream >> 6) & 3;
305 decoded->extra.size = size = (*istream >> 6) & 3; 286 reg = *istream & 0x7;
306 reg = *istream & 0x7; 287 opmode = (*istream >> 3) & 0x7;
307 opmode = (*istream >> 3) & 0x7; 288 switch (size)
308 switch (size) 289 {
309 { 290 case OPSIZE_BYTE:
310 case OPSIZE_BYTE: 291 decoded->src.params.u8 = *(++istream);
311 decoded->src.params.u8 = *(++istream); 292 break;
312 break; 293 case OPSIZE_WORD:
313 case OPSIZE_WORD: 294 decoded->src.params.u16 = *(++istream);
314 decoded->src.params.16 = *(++istream); 295 break;
315 break; 296 case OPSIZE_LONG:
316 case OPSIZE_LONG: 297 immed = *(++istream);
317 immed = *(++istream); 298 decoded->src.params.u32 = immed << 16 | *(++istream);
318 decoded->src.params.u32 = immed << 16 | *(++istream); 299 break;
319 break;
320 }
321 istream = m68k_decode_op_ex(istream, opmode, reg, size, &(decoded->dst));
322 } 300 }
301 istream = m68k_decode_op_ex(istream, opmode, reg, size, &(decoded->dst));
323 } 302 }
324 break; 303 break;
325 case 6: 304 case 6:
305 decoded->op = M68K_CMP;
306 decoded->variant = VAR_IMMEDIATE;
307 decoded->extra.size = (*istream >> 6) & 0x3;
308 decoded->src.addr_mode = MODE_IMMEDIATE;
309 reg = *istream & 0x7;
310 opmode = (*istream >> 3) & 0x7;
311 switch (decoded->extra.size)
312 {
313 case OPSIZE_BYTE:
314 decoded->src.params.u8 = *(++istream);
315 break;
316 case OPSIZE_WORD:
317 decoded->src.params.u16 = *(++istream);
318 break;
319 case OPSIZE_LONG:
320 immed = *(++istream);
321 decoded->src.params.u32 = (immed << 16) | *(++istream);
322 break;
323 }
324 istream = m68k_decode_op_ex(istream, opmode, reg, size, &(decoded->dst));
325 break;
326 case 7:
327 //MOVEP
328 deocded->op = M68K_MOVEP;
329 decoded->extra.size = *istream & 0x40 ? OPSIZE_LONG : OPSIZE_WORD;
330 if (*istream & 0x80) {
331 //memory dest
332 decoded->src.addr_mode = MODE_REG;
333 decoded->src.params.regs.pri = m68K_reg_quick_field(*istream);
334 decoded->dst.addr_mode = MODE_AREG_DISPLACE;
335 decoded->dst.params.regs.pri = *istream & 0x7;
336 } else {
337 //memory source
338 decoded->dst.addr_mode = MODE_REG;
339 decoded->dst.params.regs.pri = m68K_reg_quick_field(*istream);
340 decoded->sr.addr_mode = MODE_AREG_DISPLACE;
341 decoded->sr.params.regs.pri = *istream & 0x7;
342 }
343 immed = *(++istream);
326 344
327 break;
328 case 7:
329 break; 345 break;
330 } 346 }
331 } 347 }
332 break; 348 break;
333 case MOVE_BYTE: 349 case MOVE_BYTE:
858 ret = sprintf(dst, "bsr%s", decoded->variant == VAR_BYTE ? ".s" : ""); 874 ret = sprintf(dst, "bsr%s", decoded->variant == VAR_BYTE ? ".s" : "");
859 } else { 875 } else {
860 size = decoded->extra.size; 876 size = decoded->extra.size;
861 ret = sprintf(dst, "%s%s.%c", 877 ret = sprintf(dst, "%s%s.%c",
862 mnemonics[decoded->op], 878 mnemonics[decoded->op],
863 decoded->variant == VAR_QUICK ? "q" : "", 879 decoded->variant == VAR_QUICK ? "q" : (decoded->variant == VAR_IMMEDIATE ? "i" : ""),
864 decoded->extra.size == OPSIZE_BYTE ? 'b' : (size == OPSIZE_WORD ? 'w' : 'l')); 880 decoded->extra.size == OPSIZE_BYTE ? 'b' : (size == OPSIZE_WORD ? 'w' : 'l'));
865 } 881 }
866 op1len = m68K_disasm_op(&(decoded->src), size, dst + ret, 0); 882 op1len = m68K_disasm_op(&(decoded->src), size, dst + ret, 0);
867 ret += op1len; 883 ret += op1len;
868 ret += m68K_disasm_op(&(decoded->dst), size, dst + ret, op1len); 884 ret += m68K_disasm_op(&(decoded->dst), size, dst + ret, op1len);