]> git.ipfire.org Git - thirdparty/binutils-gdb.git/blame - sim/d10v/simops.c
Rename sim_bfd -> exec_bfd for gdb compatibility
[thirdparty/binutils-gdb.git] / sim / d10v / simops.c
CommitLineData
4f425a32 1#include <signal.h>
63a91cfb
MM
2#include <errno.h>
3#include <sys/types.h>
4#include <sys/stat.h>
5#include <unistd.h>
6
2934d1c9
MH
7#include "d10v_sim.h"
8#include "simops.h"
8719be26 9#include "sys/syscall.h"
a49a15ad 10#include "bfd.h"
2934d1c9 11
87178dbd
MM
12enum op_types {
13 OP_VOID,
14 OP_REG,
15 OP_REG_OUTPUT,
16 OP_DREG,
17 OP_DREG_OUTPUT,
18 OP_ACCUM,
19 OP_ACCUM_OUTPUT,
20 OP_ACCUM_REVERSE,
21 OP_CR,
22 OP_CR_OUTPUT,
23 OP_CR_REVERSE,
24 OP_FLAG,
60fc5b72 25 OP_FLAG_OUTPUT,
87178dbd
MM
26 OP_CONSTANT16,
27 OP_CONSTANT3,
28 OP_CONSTANT4,
29 OP_MEMREF,
30 OP_MEMREF2,
31 OP_POSTDEC,
32 OP_POSTINC,
33 OP_PREDEC
34};
35
7eebfc62 36#ifdef DEBUG
a49a15ad
MM
37static void trace_input_func PARAMS ((char *name,
38 enum op_types in1,
39 enum op_types in2,
40 enum op_types in3));
87178dbd 41
a49a15ad
MM
42#define trace_input(name, in1, in2, in3) do { if (d10v_debug) trace_input_func (name, in1, in2, in3); } while (0)
43
44static void trace_output_func PARAMS ((enum op_types result));
45
46#define trace_output(result) do { if (d10v_debug) trace_output_func (result); } while (0)
47
48static int init_text_p = 0;
49static asection *text;
50static bfd_vma text_start;
51static bfd_vma text_end;
0535fa1a 52extern bfd *exec_bfd;
87178dbd
MM
53
54#ifndef SIZE_INSTRUCTION
a49a15ad 55#define SIZE_INSTRUCTION 8
87178dbd
MM
56#endif
57
58#ifndef SIZE_OPERANDS
a49a15ad 59#define SIZE_OPERANDS 18
87178dbd
MM
60#endif
61
62#ifndef SIZE_VALUES
63#define SIZE_VALUES 13
64#endif
65
a49a15ad
MM
66#ifndef SIZE_LOCATION
67#define SIZE_LOCATION 20
68#endif
69
87178dbd 70static void
a49a15ad 71trace_input_func (name, in1, in2, in3)
87178dbd
MM
72 char *name;
73 enum op_types in1;
74 enum op_types in2;
75 enum op_types in3;
76{
77 char *comma;
78 enum op_types in[3];
79 int i;
a49a15ad 80 char buf[1024];
87178dbd
MM
81 char *p;
82 long tmp;
83 char *type;
a49a15ad
MM
84 asection *s;
85 const char *filename;
86 const char *functionname;
87 unsigned int linenumber;
88 bfd_vma byte_pc;
87178dbd 89
7eebfc62
MM
90 if ((d10v_debug & DEBUG_TRACE) == 0)
91 return;
92
87178dbd
MM
93 switch (State.ins_type)
94 {
95 default:
96 case INS_UNKNOWN: type = " ?"; break;
97 case INS_LEFT: type = " L"; break;
98 case INS_RIGHT: type = " R"; break;
99 case INS_LEFT_PARALLEL: type = "*L"; break;
100 case INS_RIGHT_PARALLEL: type = "*R"; break;
101 case INS_LONG: type = " B"; break;
102 }
103
a49a15ad
MM
104 if ((d10v_debug & DEBUG_LINE_NUMBER) == 0)
105 (*d10v_callback->printf_filtered) (d10v_callback,
106 "0x%.6x %s: %-*s",
107 (unsigned)PC, type,
108 SIZE_INSTRUCTION, name);
109
110 else
111 {
112 buf[0] = '\0';
113 if (!init_text_p)
114 {
115 init_text_p = 1;
0535fa1a
MM
116 for (s = exec_bfd->sections; s; s = s->next)
117 if (strcmp (bfd_get_section_name (exec_bfd, s), ".text") == 0)
a49a15ad
MM
118 {
119 text = s;
0535fa1a
MM
120 text_start = bfd_get_section_vma (exec_bfd, s);
121 text_end = text_start + bfd_section_size (exec_bfd, s);
a49a15ad
MM
122 break;
123 }
124 }
125
126 byte_pc = (bfd_vma)PC << 2;
127 if (text && byte_pc >= text_start && byte_pc < text_end)
128 {
129 filename = (const char *)0;
130 functionname = (const char *)0;
131 linenumber = 0;
0535fa1a 132 if (bfd_find_nearest_line (exec_bfd, text, (struct symbol_cache_entry **)0, byte_pc - text_start,
a49a15ad
MM
133 &filename, &functionname, &linenumber))
134 {
135 p = buf;
136 if (linenumber)
137 {
138 sprintf (p, "#%-4d ", linenumber);
139 p += strlen (p);
140 }
141
142 if (functionname)
143 {
144 sprintf (p, "%s ", functionname);
145 p += strlen (p);
146 }
147 else if (filename)
148 {
149 char *q = (char *) strrchr (filename, '/');
150 sprintf (p, "%s ", (q) ? q+1 : filename);
151 p += strlen (p);
152 }
153
154 if (*p == ' ')
155 *p = '\0';
156 }
157 }
158
159 (*d10v_callback->printf_filtered) (d10v_callback,
160 "0x%.6x %s: %-*.*s %-*s",
161 (unsigned)PC, type,
162 SIZE_LOCATION, SIZE_LOCATION, buf,
163 SIZE_INSTRUCTION, name);
164 }
87178dbd
MM
165
166 in[0] = in1;
167 in[1] = in2;
168 in[2] = in3;
169 comma = "";
170 p = buf;
171 for (i = 0; i < 3; i++)
172 {
173 switch (in[i])
174 {
175 case OP_VOID:
176 break;
177
178 case OP_REG:
179 case OP_REG_OUTPUT:
180 case OP_DREG:
181 case OP_DREG_OUTPUT:
182 sprintf (p, "%sr%d", comma, OP[i]);
183 p += strlen (p);
184 comma = ",";
185 break;
186
187 case OP_CR:
188 case OP_CR_OUTPUT:
189 case OP_CR_REVERSE:
190 sprintf (p, "%scr%d", comma, OP[i]);
191 p += strlen (p);
192 comma = ",";
193 break;
194
195 case OP_ACCUM:
196 case OP_ACCUM_OUTPUT:
197 case OP_ACCUM_REVERSE:
198 sprintf (p, "%sa%d", comma, OP[i]);
199 p += strlen (p);
200 comma = ",";
201 break;
202
203 case OP_CONSTANT16:
204 sprintf (p, "%s%d", comma, OP[i]);
205 p += strlen (p);
206 comma = ",";
207 break;
208
209 case OP_CONSTANT4:
210 sprintf (p, "%s%d", comma, SEXT4(OP[i]));
211 p += strlen (p);
212 comma = ",";
213 break;
214
215 case OP_CONSTANT3:
216 sprintf (p, "%s%d", comma, SEXT3(OP[i]));
217 p += strlen (p);
218 comma = ",";
219 break;
220
221 case OP_MEMREF:
222 sprintf (p, "%s@r%d", comma, OP[i]);
223 p += strlen (p);
224 comma = ",";
225 break;
226
227 case OP_MEMREF2:
228 sprintf (p, "%s@(%d,r%d)", comma, (int16)OP[i], OP[i+1]);
229 p += strlen (p);
230 comma = ",";
231 break;
232
233 case OP_POSTINC:
234 sprintf (p, "%s@r%d+", comma, OP[i]);
235 p += strlen (p);
236 comma = ",";
237 break;
238
239 case OP_POSTDEC:
240 sprintf (p, "%s@r%d-", comma, OP[i]);
241 p += strlen (p);
242 comma = ",";
243 break;
244
245 case OP_PREDEC:
246 sprintf (p, "%s@-r%d", comma, OP[i]);
247 p += strlen (p);
248 comma = ",";
249 break;
250
251 case OP_FLAG:
60fc5b72 252 case OP_FLAG_OUTPUT:
87178dbd
MM
253 if (OP[i] == 0)
254 sprintf (p, "%sf0", comma);
255
256 else if (OP[i] == 1)
257 sprintf (p, "%sf1", comma);
258
259 else
60fc5b72 260 sprintf (p, "%sc", comma);
87178dbd
MM
261
262 p += strlen (p);
263 comma = ",";
264 break;
265 }
266 }
267
7eebfc62
MM
268 if ((d10v_debug & DEBUG_VALUES) == 0)
269 {
270 *p++ = '\n';
271 *p = '\0';
272 (*d10v_callback->printf_filtered) (d10v_callback, "%s", buf);
273 }
274 else
275 {
276 *p = '\0';
277 (*d10v_callback->printf_filtered) (d10v_callback, "%-*s", SIZE_OPERANDS, buf);
87178dbd 278
7eebfc62
MM
279 p = buf;
280 for (i = 0; i < 3; i++)
281 {
282 buf[0] = '\0';
283 switch (in[i])
284 {
285 case OP_VOID:
286 (*d10v_callback->printf_filtered) (d10v_callback, "%*s", SIZE_VALUES, "");
287 break;
288
289 case OP_REG_OUTPUT:
290 case OP_DREG_OUTPUT:
291 case OP_CR_OUTPUT:
292 case OP_ACCUM_OUTPUT:
60fc5b72 293 case OP_FLAG_OUTPUT:
7eebfc62
MM
294 (*d10v_callback->printf_filtered) (d10v_callback, "%*s", SIZE_VALUES, "---");
295 break;
296
297 case OP_REG:
298 case OP_MEMREF:
299 case OP_POSTDEC:
300 case OP_POSTINC:
301 case OP_PREDEC:
302 (*d10v_callback->printf_filtered) (d10v_callback, "%*s0x%.4x", SIZE_VALUES-6, "",
303 (uint16)State.regs[OP[i]]);
304 break;
305
306 case OP_DREG:
307 tmp = (long)((((uint32) State.regs[OP[i]]) << 16) | ((uint32) State.regs[OP[i]+1]));
308 (*d10v_callback->printf_filtered) (d10v_callback, "%*s0x%.8lx", SIZE_VALUES-10, "", tmp);
309 break;
310
311 case OP_CR:
312 case OP_CR_REVERSE:
313 (*d10v_callback->printf_filtered) (d10v_callback, "%*s0x%.4x", SIZE_VALUES-6, "",
314 (uint16)State.cregs[OP[i]]);
315 break;
316
317 case OP_ACCUM:
318 case OP_ACCUM_REVERSE:
319 (*d10v_callback->printf_filtered) (d10v_callback, "%*s0x%.2x%.8lx", SIZE_VALUES-12, "",
320 ((int)(State.a[OP[i]] >> 32) & 0xff),
321 ((unsigned long)State.a[OP[i]]) & 0xffffffff);
322 break;
323
324 case OP_CONSTANT16:
325 (*d10v_callback->printf_filtered) (d10v_callback, "%*s0x%.4x", SIZE_VALUES-6, "",
326 (uint16)OP[i]);
327 break;
328
329 case OP_CONSTANT4:
330 (*d10v_callback->printf_filtered) (d10v_callback, "%*s0x%.4x", SIZE_VALUES-6, "",
331 (uint16)SEXT4(OP[i]));
332 break;
333
334 case OP_CONSTANT3:
335 (*d10v_callback->printf_filtered) (d10v_callback, "%*s0x%.4x", SIZE_VALUES-6, "",
336 (uint16)SEXT3(OP[i]));
337 break;
338
339 case OP_FLAG:
340 if (OP[i] == 0)
341 (*d10v_callback->printf_filtered) (d10v_callback, "%*sF0 = %d", SIZE_VALUES-6, "",
342 State.F0 != 0);
343
344 else if (OP[i] == 1)
345 (*d10v_callback->printf_filtered) (d10v_callback, "%*sF1 = %d", SIZE_VALUES-6, "",
346 State.F1 != 0);
347
348 else
349 (*d10v_callback->printf_filtered) (d10v_callback, "%*sC = %d", SIZE_VALUES-5, "",
350 State.C != 0);
351
352 break;
353
354 case OP_MEMREF2:
355 (*d10v_callback->printf_filtered) (d10v_callback, "%*s0x%.4x", SIZE_VALUES-6, "",
356 (uint16)OP[i]);
357 (*d10v_callback->printf_filtered) (d10v_callback, "%*s0x%.4x", SIZE_VALUES-6, "",
358 (uint16)State.regs[OP[++i]]);
359 break;
360 }
361 }
362 }
363}
87178dbd 364
7eebfc62 365static void
a49a15ad 366trace_output_func (result)
7eebfc62
MM
367 enum op_types result;
368{
369 if ((d10v_debug & (DEBUG_TRACE | DEBUG_VALUES)) == (DEBUG_TRACE | DEBUG_VALUES))
87178dbd 370 {
7eebfc62 371 long tmp;
87178dbd 372
7eebfc62
MM
373 switch (result)
374 {
375 default:
376 putchar ('\n');
87178dbd
MM
377 break;
378
379 case OP_REG:
7eebfc62
MM
380 case OP_REG_OUTPUT:
381 (*d10v_callback->printf_filtered) (d10v_callback, " :: %*s0x%.4x F0=%d F1=%d C=%d\n", SIZE_VALUES-6, "",
382 (uint16)State.regs[OP[0]],
383 State.F0 != 0, State.F1 != 0, State.C != 0);
87178dbd
MM
384 break;
385
386 case OP_DREG:
7eebfc62
MM
387 case OP_DREG_OUTPUT:
388 tmp = (long)((((uint32) State.regs[OP[0]]) << 16) | ((uint32) State.regs[OP[0]+1]));
389 (*d10v_callback->printf_filtered) (d10v_callback, " :: %*s0x%.8lx F0=%d F1=%d C=%d\n", SIZE_VALUES-10, "", tmp,
390 State.F0 != 0, State.F1 != 0, State.C != 0);
87178dbd
MM
391 break;
392
393 case OP_CR:
7eebfc62
MM
394 case OP_CR_OUTPUT:
395 (*d10v_callback->printf_filtered) (d10v_callback, " :: %*s0x%.4x F0=%d F1=%d C=%d\n", SIZE_VALUES-6, "",
396 (uint16)State.cregs[OP[0]],
397 State.F0 != 0, State.F1 != 0, State.C != 0);
87178dbd
MM
398 break;
399
7eebfc62
MM
400 case OP_CR_REVERSE:
401 (*d10v_callback->printf_filtered) (d10v_callback, " :: %*s0x%.4x F0=%d F1=%d C=%d\n", SIZE_VALUES-6, "",
402 (uint16)State.cregs[OP[1]],
403 State.F0 != 0, State.F1 != 0, State.C != 0);
87178dbd
MM
404 break;
405
7eebfc62
MM
406 case OP_ACCUM:
407 case OP_ACCUM_OUTPUT:
069398aa 408 (*d10v_callback->printf_filtered) (d10v_callback, " :: %*s0x%.2x%.8lx F0=%d F1=%d C=%d\n", SIZE_VALUES-12, "",
7eebfc62
MM
409 ((int)(State.a[OP[0]] >> 32) & 0xff),
410 ((unsigned long)State.a[OP[0]]) & 0xffffffff,
411 State.F0 != 0, State.F1 != 0, State.C != 0);
87178dbd
MM
412 break;
413
7eebfc62 414 case OP_ACCUM_REVERSE:
069398aa 415 (*d10v_callback->printf_filtered) (d10v_callback, " :: %*s0x%.2x%.8lx F0=%d F1=%d C=%d\n", SIZE_VALUES-12, "",
7eebfc62
MM
416 ((int)(State.a[OP[1]] >> 32) & 0xff),
417 ((unsigned long)State.a[OP[1]]) & 0xffffffff,
418 State.F0 != 0, State.F1 != 0, State.C != 0);
87178dbd
MM
419 break;
420
421 case OP_FLAG:
60fc5b72 422 case OP_FLAG_OUTPUT:
7eebfc62
MM
423 (*d10v_callback->printf_filtered) (d10v_callback, " :: %*s F0=%d F1=%d C=%d\n", SIZE_VALUES, "",
424 State.F0 != 0, State.F1 != 0, State.C != 0);
87178dbd
MM
425 break;
426 }
427 }
87178dbd
MM
428}
429
430#else
431#define trace_input(NAME, IN1, IN2, IN3)
432#define trace_output(RESULT)
433#endif
2934d1c9
MH
434
435/* abs */
436void
437OP_4607 ()
438{
87178dbd 439 trace_input ("abs", OP_REG, OP_VOID, OP_VOID);
2934d1c9
MH
440 State.F1 = State.F0;
441 if ((int16)(State.regs[OP[0]]) < 0)
442 {
443 State.regs[OP[0]] = -(int16)(State.regs[OP[0]]);
444 State.F0 = 1;
445 }
446 else
447 State.F0 = 0;
87178dbd 448 trace_output (OP_REG);
2934d1c9
MH
449}
450
451/* abs */
452void
453OP_5607 ()
454{
455 int64 tmp;
456
87178dbd 457 trace_input ("abs", OP_ACCUM, OP_VOID, OP_VOID);
4f425a32
MH
458 State.F1 = State.F0;
459 State.a[OP[0]] = SEXT40(State.a[OP[0]]);
460
4c38885c 461 if (State.a[OP[0]] < 0 )
2934d1c9 462 {
4c38885c 463 tmp = -State.a[OP[0]];
2934d1c9
MH
464 if (State.ST)
465 {
4c38885c 466 if (tmp > MAX32)
2934d1c9 467 State.a[OP[0]] = MAX32;
4c38885c 468 else if (tmp < MIN32)
2934d1c9
MH
469 State.a[OP[0]] = MIN32;
470 else
4f425a32 471 State.a[OP[0]] = tmp & MASK40;
2934d1c9
MH
472 }
473 else
4f425a32 474 State.a[OP[0]] = tmp & MASK40;
2934d1c9
MH
475 State.F0 = 1;
476 }
477 else
478 State.F0 = 0;
87178dbd 479 trace_output (OP_ACCUM);
2934d1c9
MH
480}
481
482/* add */
483void
484OP_200 ()
485{
486 uint16 tmp = State.regs[OP[0]];
87178dbd 487 trace_input ("add", OP_REG, OP_REG, OP_VOID);
2934d1c9
MH
488 State.regs[OP[0]] += State.regs[OP[1]];
489 if ( tmp > State.regs[OP[0]])
490 State.C = 1;
491 else
492 State.C = 0;
87178dbd 493 trace_output (OP_REG);
2934d1c9
MH
494}
495
496/* add */
497void
498OP_1201 ()
499{
4c38885c 500 int64 tmp;
4f425a32 501 tmp = SEXT40(State.a[OP[0]]) + (SEXT16 (State.regs[OP[1]]) << 16 | State.regs[OP[1]+1]);
87178dbd
MM
502
503 trace_input ("add", OP_ACCUM, OP_REG, OP_VOID);
4c38885c
MH
504 if (State.ST)
505 {
506 if ( tmp > MAX32)
507 State.a[OP[0]] = MAX32;
508 else if ( tmp < MIN32)
509 State.a[OP[0]] = MIN32;
510 else
4f425a32 511 State.a[OP[0]] = tmp & MASK40;
4c38885c
MH
512 }
513 else
4f425a32 514 State.a[OP[0]] = tmp & MASK40;
87178dbd 515 trace_output (OP_ACCUM);
2934d1c9
MH
516}
517
518/* add */
519void
520OP_1203 ()
521{
4c38885c 522 int64 tmp;
4f425a32 523 tmp = SEXT40(State.a[OP[0]]) + SEXT40(State.a[OP[1]]);
87178dbd
MM
524
525 trace_input ("add", OP_ACCUM, OP_ACCUM, OP_VOID);
4c38885c
MH
526 if (State.ST)
527 {
528 if (tmp > MAX32)
529 State.a[OP[0]] = MAX32;
530 else if ( tmp < MIN32)
531 State.a[OP[0]] = MIN32;
532 else
4f425a32 533 State.a[OP[0]] = tmp & MASK40;
4c38885c
MH
534 }
535 else
4f425a32 536 State.a[OP[0]] = tmp & MASK40;
87178dbd 537 trace_output (OP_ACCUM);
2934d1c9
MH
538}
539
540/* add2w */
541void
542OP_1200 ()
543{
544 uint32 tmp;
545 uint32 tmp1 = (State.regs[OP[0]]) << 16 | State.regs[OP[0]+1];
546 uint32 tmp2 = (State.regs[OP[1]]) << 16 | State.regs[OP[1]+1];
87178dbd
MM
547
548 trace_input ("add2w", OP_DREG, OP_DREG, OP_VOID);
2934d1c9
MH
549 tmp = tmp1 + tmp2;
550 if ( (tmp < tmp1) || (tmp < tmp2) )
551 State.C = 1;
552 else
553 State.C = 0;
554 State.regs[OP[0]] = tmp >> 16;
555 State.regs[OP[0]+1] = tmp & 0xFFFF;
87178dbd 556 trace_output (OP_DREG);
2934d1c9
MH
557}
558
559/* add3 */
560void
561OP_1000000 ()
562{
563 uint16 tmp = State.regs[OP[0]];
2934d1c9 564 State.regs[OP[0]] = State.regs[OP[1]] + OP[2];
87178dbd
MM
565
566 trace_input ("add3", OP_REG_OUTPUT, OP_REG, OP_CONSTANT16);
2934d1c9
MH
567 if ( tmp > State.regs[OP[0]])
568 State.C = 1;
569 else
570 State.C = 0;
87178dbd 571 trace_output (OP_REG);
2934d1c9
MH
572}
573
574/* addac3 */
575void
576OP_17000200 ()
577{
4c38885c 578 int64 tmp;
4f425a32 579 tmp = SEXT40(State.a[OP[2]]) + SEXT40 ((State.regs[OP[1]] << 16) | State.regs[OP[1]+1]);
87178dbd
MM
580
581 trace_input ("addac3", OP_DREG_OUTPUT, OP_DREG, OP_ACCUM);
4c38885c
MH
582 State.regs[OP[0]] = (tmp >> 16) & 0xffff;
583 State.regs[OP[0]+1] = tmp & 0xffff;
87178dbd 584 trace_output (OP_DREG);
2934d1c9
MH
585}
586
587/* addac3 */
588void
589OP_17000202 ()
590{
4c38885c 591 int64 tmp;
4f425a32 592 tmp = SEXT40(State.a[OP[1]]) + SEXT40(State.a[OP[2]]);
87178dbd
MM
593
594 trace_input ("addac3", OP_DREG_OUTPUT, OP_ACCUM, OP_ACCUM);
4c38885c
MH
595 State.regs[OP[0]] = (tmp >> 16) & 0xffff;
596 State.regs[OP[0]+1] = tmp & 0xffff;
87178dbd 597 trace_output (OP_DREG);
2934d1c9
MH
598}
599
600/* addac3s */
601void
602OP_17001200 ()
603{
4c38885c 604 int64 tmp;
4c38885c 605 State.F1 = State.F0;
87178dbd
MM
606
607 trace_input ("addac3s", OP_DREG_OUTPUT, OP_DREG, OP_ACCUM);
4f425a32 608 tmp = SEXT40(State.a[OP[2]]) + SEXT40 ((State.regs[OP[1]] << 16) | State.regs[OP[1]+1]);
4c38885c
MH
609 if ( tmp > MAX32)
610 {
611 State.regs[OP[0]] = 0x7fff;
612 State.regs[OP[0]+1] = 0xffff;
613 State.F0 = 1;
614 }
615 else if (tmp < MIN32)
616 {
617 State.regs[OP[0]] = 0x8000;
618 State.regs[OP[0]+1] = 0;
619 State.F0 = 1;
620 }
621 else
622 {
623 State.regs[OP[0]] = (tmp >> 16) & 0xffff;
624 State.regs[OP[0]+1] = tmp & 0xffff;
625 State.F0 = 0;
626 }
87178dbd 627 trace_output (OP_DREG);
2934d1c9
MH
628}
629
630/* addac3s */
631void
632OP_17001202 ()
633{
4c38885c 634 int64 tmp;
4c38885c 635 State.F1 = State.F0;
87178dbd
MM
636
637 trace_input ("addac3s", OP_DREG_OUTPUT, OP_ACCUM, OP_ACCUM);
4f425a32 638 tmp = SEXT40(State.a[OP[1]]) + SEXT40(State.a[OP[2]]);
4c38885c
MH
639 if ( tmp > MAX32)
640 {
641 State.regs[OP[0]] = 0x7fff;
642 State.regs[OP[0]+1] = 0xffff;
643 State.F0 = 1;
644 }
645 else if (tmp < MIN32)
646 {
647 State.regs[OP[0]] = 0x8000;
648 State.regs[OP[0]+1] = 0;
649 State.F0 = 1;
650 }
651 else
652 {
653 State.regs[OP[0]] = (tmp >> 16) & 0xffff;
654 State.regs[OP[0]+1] = tmp & 0xffff;
655 State.F0 = 0;
656 }
87178dbd 657 trace_output (OP_DREG);
2934d1c9
MH
658}
659
660/* addi */
661void
662OP_201 ()
663{
2254cd90 664 uint tmp = State.regs[OP[0]];
4f425a32
MH
665 if (OP[1] == 0)
666 OP[1] = 16;
87178dbd 667 trace_input ("addi", OP_REG, OP_CONSTANT16, OP_VOID);
2934d1c9 668 State.regs[OP[0]] += OP[1];
2254cd90
MM
669 if (tmp > State.regs[OP[0]])
670 State.C = 1;
671 else
672 State.C = 0;
87178dbd 673 trace_output (OP_REG);
2934d1c9
MH
674}
675
676/* and */
677void
678OP_C00 ()
679{
87178dbd 680 trace_input ("and", OP_REG, OP_REG, OP_VOID);
2934d1c9 681 State.regs[OP[0]] &= State.regs[OP[1]];
87178dbd 682 trace_output (OP_REG);
2934d1c9
MH
683}
684
685/* and3 */
686void
687OP_6000000 ()
688{
87178dbd 689 trace_input ("and3", OP_REG_OUTPUT, OP_REG, OP_CONSTANT16);
2934d1c9 690 State.regs[OP[0]] = State.regs[OP[1]] & OP[2];
87178dbd 691 trace_output (OP_REG);
2934d1c9
MH
692}
693
694/* bclri */
695void
696OP_C01 ()
697{
87178dbd 698 trace_input ("bclri", OP_REG, OP_CONSTANT16, OP_VOID);
2934d1c9 699 State.regs[OP[0]] &= ~(0x8000 >> OP[1]);
87178dbd 700 trace_output (OP_REG);
2934d1c9
MH
701}
702
703/* bl.s */
704void
705OP_4900 ()
706{
87178dbd 707 trace_input ("bl.s", OP_CONSTANT16, OP_VOID, OP_VOID);
2934d1c9
MH
708 State.regs[13] = PC+1;
709 PC += SEXT8 (OP[0]);
87178dbd 710 trace_output (OP_VOID);
2934d1c9
MH
711}
712
713/* bl.l */
714void
715OP_24800000 ()
716{
87178dbd 717 trace_input ("bl.l", OP_CONSTANT16, OP_VOID, OP_VOID);
2934d1c9
MH
718 State.regs[13] = PC+1;
719 PC += OP[0];
87178dbd 720 trace_output (OP_VOID);
2934d1c9
MH
721}
722
723/* bnoti */
724void
725OP_A01 ()
726{
87178dbd 727 trace_input ("bnoti", OP_REG, OP_CONSTANT16, OP_VOID);
2934d1c9 728 State.regs[OP[0]] ^= 0x8000 >> OP[1];
87178dbd 729 trace_output (OP_REG);
2934d1c9
MH
730}
731
732/* bra.s */
733void
734OP_4800 ()
735{
87178dbd 736 trace_input ("bra.s", OP_CONSTANT16, OP_VOID, OP_VOID);
2934d1c9 737 PC += SEXT8 (OP[0]);
87178dbd 738 trace_output (OP_VOID);
2934d1c9
MH
739}
740
741/* bra.l */
742void
743OP_24000000 ()
744{
87178dbd 745 trace_input ("bra.l", OP_CONSTANT16, OP_VOID, OP_VOID);
2934d1c9 746 PC += OP[0];
87178dbd 747 trace_output (OP_VOID);
2934d1c9
MH
748}
749
750/* brf0f.s */
751void
752OP_4A00 ()
753{
87178dbd 754 trace_input ("brf0f.s", OP_CONSTANT16, OP_VOID, OP_VOID);
2934d1c9
MH
755 if (State.F0 == 0)
756 PC += SEXT8 (OP[0]);
87178dbd 757 trace_output (OP_FLAG);
2934d1c9
MH
758}
759
760/* brf0f.l */
761void
762OP_25000000 ()
763{
87178dbd 764 trace_input ("brf0f.l", OP_CONSTANT16, OP_VOID, OP_VOID);
2934d1c9
MH
765 if (State.F0 == 0)
766 PC += OP[0];
87178dbd 767 trace_output (OP_FLAG);
2934d1c9
MH
768}
769
770/* brf0t.s */
771void
772OP_4B00 ()
773{
87178dbd 774 trace_input ("brf0t.s", OP_CONSTANT16, OP_VOID, OP_VOID);
2934d1c9
MH
775 if (State.F0)
776 PC += SEXT8 (OP[0]);
87178dbd 777 trace_output (OP_FLAG);
2934d1c9
MH
778}
779
780/* brf0t.l */
781void
782OP_25800000 ()
783{
87178dbd 784 trace_input ("brf0t.l", OP_CONSTANT16, OP_VOID, OP_VOID);
2934d1c9
MH
785 if (State.F0)
786 PC += OP[0];
87178dbd 787 trace_output (OP_FLAG);
2934d1c9
MH
788}
789
790/* bseti */
791void
792OP_801 ()
793{
87178dbd 794 trace_input ("bseti", OP_REG, OP_CONSTANT16, OP_VOID);
2934d1c9 795 State.regs[OP[0]] |= 0x8000 >> OP[1];
87178dbd 796 trace_output (OP_REG);
2934d1c9
MH
797}
798
799/* btsti */
800void
801OP_E01 ()
802{
87178dbd 803 trace_input ("btsti", OP_REG, OP_CONSTANT16, OP_VOID);
2934d1c9
MH
804 State.F1 = State.F0;
805 State.F0 = (State.regs[OP[0]] & (0x8000 >> OP[1])) ? 1 : 0;
87178dbd 806 trace_output (OP_FLAG);
2934d1c9
MH
807}
808
809/* clrac */
810void
811OP_5601 ()
812{
87178dbd 813 trace_input ("clrac", OP_ACCUM_OUTPUT, OP_VOID, OP_VOID);
2934d1c9 814 State.a[OP[0]] = 0;
87178dbd 815 trace_output (OP_ACCUM);
2934d1c9
MH
816}
817
818/* cmp */
819void
820OP_600 ()
821{
87178dbd 822 trace_input ("cmp", OP_REG, OP_REG, OP_VOID);
2934d1c9
MH
823 State.F1 = State.F0;
824 State.F0 = ((int16)(State.regs[OP[0]]) < (int16)(State.regs[OP[1]])) ? 1 : 0;
87178dbd 825 trace_output (OP_FLAG);
2934d1c9
MH
826}
827
828/* cmp */
829void
830OP_1603 ()
831{
87178dbd 832 trace_input ("cmp", OP_ACCUM, OP_ACCUM, OP_VOID);
4c38885c 833 State.F1 = State.F0;
4f425a32 834 State.F0 = (SEXT40(State.a[OP[0]]) < SEXT40(State.a[OP[1]])) ? 1 : 0;
87178dbd 835 trace_output (OP_FLAG);
2934d1c9
MH
836}
837
838/* cmpeq */
839void
840OP_400 ()
841{
87178dbd 842 trace_input ("cmpeq", OP_REG, OP_REG, OP_VOID);
2934d1c9
MH
843 State.F1 = State.F0;
844 State.F0 = (State.regs[OP[0]] == State.regs[OP[1]]) ? 1 : 0;
87178dbd 845 trace_output (OP_FLAG);
2934d1c9
MH
846}
847
848/* cmpeq */
849void
850OP_1403 ()
851{
87178dbd 852 trace_input ("cmpeq", OP_ACCUM, OP_ACCUM, OP_VOID);
4c38885c
MH
853 State.F1 = State.F0;
854 State.F0 = (State.a[OP[0]] == State.a[OP[1]]) ? 1 : 0;
87178dbd 855 trace_output (OP_FLAG);
2934d1c9
MH
856}
857
858/* cmpeqi.s */
859void
860OP_401 ()
861{
87178dbd 862 trace_input ("cmpeqi.s", OP_REG, OP_CONSTANT16, OP_VOID);
2934d1c9
MH
863 State.F1 = State.F0;
864 State.F0 = (State.regs[OP[0]] == SEXT4(OP[1])) ? 1 : 0;
87178dbd 865 trace_output (OP_FLAG);
2934d1c9
MH
866}
867
868/* cmpeqi.l */
869void
870OP_2000000 ()
871{
87178dbd 872 trace_input ("cmpeqi.l", OP_REG, OP_CONSTANT16, OP_VOID);
2934d1c9
MH
873 State.F1 = State.F0;
874 State.F0 = (State.regs[OP[0]] == OP[1]) ? 1 : 0;
87178dbd 875 trace_output (OP_FLAG);
2934d1c9
MH
876}
877
878/* cmpi.s */
879void
880OP_601 ()
881{
87178dbd 882 trace_input ("cmpi.s", OP_REG, OP_CONSTANT4, OP_VOID);
2934d1c9
MH
883 State.F1 = State.F0;
884 State.F0 = ((int16)(State.regs[OP[0]]) < SEXT4(OP[1])) ? 1 : 0;
87178dbd 885 trace_output (OP_FLAG);
2934d1c9
MH
886}
887
888/* cmpi.l */
889void
890OP_3000000 ()
891{
87178dbd 892 trace_input ("cmpi.l", OP_REG, OP_CONSTANT16, OP_VOID);
2934d1c9
MH
893 State.F1 = State.F0;
894 State.F0 = ((int16)(State.regs[OP[0]]) < (int16)(OP[1])) ? 1 : 0;
87178dbd 895 trace_output (OP_FLAG);
2934d1c9
MH
896}
897
898/* cmpu */
899void
900OP_4600 ()
901{
87178dbd 902 trace_input ("cmpu", OP_REG, OP_REG, OP_VOID);
2934d1c9
MH
903 State.F1 = State.F0;
904 State.F0 = (State.regs[OP[0]] < State.regs[OP[1]]) ? 1 : 0;
87178dbd 905 trace_output (OP_FLAG);
2934d1c9
MH
906}
907
908/* cmpui */
909void
910OP_23000000 ()
911{
87178dbd 912 trace_input ("cmpui", OP_REG, OP_CONSTANT16, OP_VOID);
2934d1c9
MH
913 State.F1 = State.F0;
914 State.F0 = (State.regs[OP[0]] < OP[1]) ? 1 : 0;
87178dbd 915 trace_output (OP_FLAG);
2934d1c9
MH
916}
917
918/* cpfg */
919void
920OP_4E09 ()
921{
922 uint8 *src, *dst;
2934d1c9 923
60fc5b72 924 trace_input ("cpfg", OP_FLAG_OUTPUT, OP_FLAG, OP_VOID);
2934d1c9
MH
925 if (OP[0] == 0)
926 dst = &State.F0;
927 else
928 dst = &State.F1;
929
930 if (OP[1] == 0)
931 src = &State.F0;
932 else if (OP[1] == 1)
933 src = &State.F1;
934 else
935 src = &State.C;
936
937 *dst = *src;
87178dbd 938 trace_output (OP_FLAG);
2934d1c9
MH
939}
940
941/* dbt */
942void
943OP_5F20 ()
944{
a49a15ad 945 /* d10v_callback->printf_filtered(d10v_callback, "***** DBT ***** PC=%x\n",PC); */
4f425a32 946 State.exception = SIGTRAP;
2934d1c9
MH
947}
948
949/* divs */
950void
951OP_14002800 ()
952{
953 uint16 foo, tmp, tmpf;
87178dbd
MM
954
955 trace_input ("divs", OP_DREG, OP_REG, OP_VOID);
2934d1c9
MH
956 foo = (State.regs[OP[0]] << 1) | (State.regs[OP[0]+1] >> 15);
957 tmp = (int16)foo - (int16)(State.regs[OP[1]]);
958 tmpf = (foo >= State.regs[OP[1]]) ? 1 : 0;
959 State.regs[OP[0]] = (tmpf == 1) ? tmp : foo;
960 State.regs[OP[0]+1] = (State.regs[OP[0]+1] << 1) | tmpf;
87178dbd 961 trace_output (OP_DREG);
2934d1c9
MH
962}
963
964/* exef0f */
965void
966OP_4E04 ()
967{
87178dbd 968 trace_input ("exef0f", OP_VOID, OP_VOID, OP_VOID);
293c76a3 969 State.exe = (State.F0 == 0);
87178dbd 970 trace_output (OP_FLAG);
2934d1c9
MH
971}
972
973/* exef0t */
974void
975OP_4E24 ()
976{
87178dbd 977 trace_input ("exef0t", OP_VOID, OP_VOID, OP_VOID);
293c76a3 978 State.exe = (State.F0 != 0);
87178dbd 979 trace_output (OP_FLAG);
2934d1c9
MH
980}
981
982/* exef1f */
983void
984OP_4E40 ()
985{
87178dbd 986 trace_input ("exef1f", OP_VOID, OP_VOID, OP_VOID);
293c76a3 987 State.exe = (State.F1 == 0);
87178dbd 988 trace_output (OP_FLAG);
2934d1c9
MH
989}
990
991/* exef1t */
992void
993OP_4E42 ()
994{
87178dbd 995 trace_input ("exef1t", OP_VOID, OP_VOID, OP_VOID);
293c76a3 996 State.exe = (State.F1 != 0);
87178dbd 997 trace_output (OP_FLAG);
2934d1c9
MH
998}
999
1000/* exefaf */
1001void
1002OP_4E00 ()
1003{
87178dbd 1004 trace_input ("exefaf", OP_VOID, OP_VOID, OP_VOID);
293c76a3 1005 State.exe = (State.F0 == 0) & (State.F1 == 0);
87178dbd 1006 trace_output (OP_FLAG);
2934d1c9
MH
1007}
1008
1009/* exefat */
1010void
1011OP_4E02 ()
1012{
87178dbd 1013 trace_input ("exefat", OP_VOID, OP_VOID, OP_VOID);
293c76a3 1014 State.exe = (State.F0 == 0) & (State.F1 != 0);
87178dbd 1015 trace_output (OP_FLAG);
2934d1c9
MH
1016}
1017
1018/* exetaf */
1019void
1020OP_4E20 ()
1021{
87178dbd 1022 trace_input ("exetaf", OP_VOID, OP_VOID, OP_VOID);
293c76a3 1023 State.exe = (State.F0 != 0) & (State.F1 == 0);
87178dbd 1024 trace_output (OP_FLAG);
2934d1c9
MH
1025}
1026
1027/* exetat */
1028void
1029OP_4E22 ()
1030{
87178dbd 1031 trace_input ("exetat", OP_VOID, OP_VOID, OP_VOID);
293c76a3 1032 State.exe = (State.F0 != 0) & (State.F1 != 0);
87178dbd 1033 trace_output (OP_FLAG);
2934d1c9
MH
1034}
1035
1036/* exp */
1037void
1038OP_15002A00 ()
1039{
1040 uint32 tmp, foo;
1041 int i;
1042
87178dbd 1043 trace_input ("exp", OP_REG_OUTPUT, OP_DREG, OP_VOID);
4c38885c
MH
1044 if (((int16)State.regs[OP[1]]) >= 0)
1045 tmp = (State.regs[OP[1]] << 16) | State.regs[OP[1]+1];
2934d1c9 1046 else
4c38885c 1047 tmp = ~((State.regs[OP[1]] << 16) | State.regs[OP[1]+1]);
2934d1c9
MH
1048
1049 foo = 0x40000000;
4c38885c 1050 for (i=1;i<17;i++)
2934d1c9
MH
1051 {
1052 if (tmp & foo)
1053 {
1054 State.regs[OP[0]] = i-1;
87178dbd 1055 trace_output (OP_REG);
2934d1c9
MH
1056 return;
1057 }
4c38885c 1058 foo >>= 1;
2934d1c9
MH
1059 }
1060 State.regs[OP[0]] = 16;
87178dbd 1061 trace_output (OP_REG);
2934d1c9
MH
1062}
1063
1064/* exp */
1065void
1066OP_15002A02 ()
1067{
4c38885c
MH
1068 int64 tmp, foo;
1069 int i;
87178dbd
MM
1070
1071 trace_input ("exp", OP_REG_OUTPUT, OP_ACCUM, OP_VOID);
4f425a32 1072 if (SEXT40(State.a[OP[1]]) >= 0)
4c38885c
MH
1073 tmp = State.a[OP[1]];
1074 else
1075 tmp = ~(State.a[OP[1]]);
1076
1077 foo = 0x4000000000LL;
1078 for (i=1;i<25;i++)
1079 {
1080 if (tmp & foo)
1081 {
1082 State.regs[OP[0]] = i-9;
87178dbd 1083 trace_output (OP_REG);
4c38885c
MH
1084 return;
1085 }
1086 foo >>= 1;
1087 }
1088 State.regs[OP[0]] = 16;
87178dbd 1089 trace_output (OP_REG);
2934d1c9
MH
1090}
1091
1092/* jl */
1093void
1094OP_4D00 ()
1095{
87178dbd 1096 trace_input ("jl", OP_REG, OP_VOID, OP_VOID);
2934d1c9
MH
1097 State.regs[13] = PC+1;
1098 PC = State.regs[OP[0]];
87178dbd 1099 trace_output (OP_VOID);
2934d1c9
MH
1100}
1101
1102/* jmp */
1103void
1104OP_4C00 ()
1105{
87178dbd 1106 trace_input ("jmp", OP_REG, OP_VOID, OP_VOID);
2934d1c9 1107 PC = State.regs[OP[0]];
87178dbd 1108 trace_output (OP_VOID);
2934d1c9
MH
1109}
1110
1111/* ld */
1112void
1113OP_30000000 ()
1114{
87178dbd 1115 trace_input ("ld", OP_REG_OUTPUT, OP_MEMREF2, OP_VOID);
2934d1c9 1116 State.regs[OP[0]] = RW (OP[1] + State.regs[OP[2]]);
87178dbd 1117 trace_output (OP_REG);
2934d1c9
MH
1118}
1119
1120/* ld */
1121void
1122OP_6401 ()
1123{
87178dbd 1124 trace_input ("ld", OP_REG_OUTPUT, OP_POSTDEC, OP_VOID);
4c38885c 1125 State.regs[OP[0]] = RW (State.regs[OP[1]]);
4f425a32 1126 INC_ADDR(State.regs[OP[1]],-2);
87178dbd 1127 trace_output (OP_REG);
2934d1c9
MH
1128}
1129
1130/* ld */
1131void
1132OP_6001 ()
1133{
87178dbd 1134 trace_input ("ld", OP_REG_OUTPUT, OP_POSTINC, OP_VOID);
4c38885c 1135 State.regs[OP[0]] = RW (State.regs[OP[1]]);
4f425a32 1136 INC_ADDR(State.regs[OP[1]],2);
87178dbd 1137 trace_output (OP_REG);
2934d1c9
MH
1138}
1139
1140/* ld */
1141void
1142OP_6000 ()
1143{
87178dbd 1144 trace_input ("ld", OP_REG_OUTPUT, OP_MEMREF, OP_VOID);
2934d1c9 1145 State.regs[OP[0]] = RW (State.regs[OP[1]]);
87178dbd 1146 trace_output (OP_REG);
2934d1c9
MH
1147}
1148
1149/* ld2w */
1150void
1151OP_31000000 ()
1152{
308f64d3 1153 trace_input ("ld2w", OP_REG_OUTPUT, OP_MEMREF2, OP_VOID);
2934d1c9
MH
1154 State.regs[OP[0]] = RW (OP[1] + State.regs[OP[2]]);
1155 State.regs[OP[0]+1] = RW (OP[1] + State.regs[OP[2]] + 2);
87178dbd 1156 trace_output (OP_DREG);
2934d1c9
MH
1157}
1158
1159/* ld2w */
1160void
1161OP_6601 ()
1162{
87178dbd 1163 trace_input ("ld2w", OP_REG_OUTPUT, OP_POSTDEC, OP_VOID);
4c38885c
MH
1164 State.regs[OP[0]] = RW (State.regs[OP[1]]);
1165 State.regs[OP[0]+1] = RW (State.regs[OP[1]]+2);
4f425a32 1166 INC_ADDR(State.regs[OP[1]],-4);
87178dbd 1167 trace_output (OP_DREG);
2934d1c9
MH
1168}
1169
1170/* ld2w */
1171void
1172OP_6201 ()
1173{
87178dbd 1174 trace_input ("ld2w", OP_REG_OUTPUT, OP_POSTINC, OP_VOID);
4c38885c
MH
1175 State.regs[OP[0]] = RW (State.regs[OP[1]]);
1176 State.regs[OP[0]+1] = RW (State.regs[OP[1]]+2);
4f425a32 1177 INC_ADDR(State.regs[OP[1]],4);
87178dbd 1178 trace_output (OP_REG);
2934d1c9
MH
1179}
1180
1181/* ld2w */
1182void
1183OP_6200 ()
1184{
87178dbd 1185 trace_input ("ld", OP_REG_OUTPUT, OP_MEMREF, OP_VOID);
4c38885c
MH
1186 State.regs[OP[0]] = RW (State.regs[OP[1]]);
1187 State.regs[OP[0]+1] = RW (State.regs[OP[1]]+2);
87178dbd 1188 trace_output (OP_REG);
2934d1c9
MH
1189}
1190
1191/* ldb */
1192void
1193OP_38000000 ()
1194{
87178dbd 1195 trace_input ("ldb", OP_REG_OUTPUT, OP_MEMREF2, OP_VOID);
2934d1c9
MH
1196 State.regs[OP[0]] = RB (OP[1] + State.regs[OP[2]]);
1197 SEXT8 (State.regs[OP[0]]);
87178dbd 1198 trace_output (OP_REG);
2934d1c9
MH
1199}
1200
1201/* ldb */
1202void
1203OP_7000 ()
1204{
87178dbd 1205 trace_input ("ldb", OP_REG_OUTPUT, OP_MEMREF, OP_VOID);
2934d1c9
MH
1206 State.regs[OP[0]] = RB (State.regs[OP[1]]);
1207 SEXT8 (State.regs[OP[0]]);
87178dbd 1208 trace_output (OP_REG);
2934d1c9
MH
1209}
1210
1211/* ldi.s */
1212void
1213OP_4001 ()
1214{
87178dbd 1215 trace_input ("ldi.s", OP_REG_OUTPUT, OP_CONSTANT4, OP_VOID);
2934d1c9 1216 State.regs[OP[0]] = SEXT4(OP[1]);
87178dbd 1217 trace_output (OP_REG);
2934d1c9
MH
1218}
1219
1220/* ldi.l */
1221void
1222OP_20000000 ()
1223{
87178dbd 1224 trace_input ("ldi.s", OP_REG_OUTPUT, OP_CONSTANT16, OP_VOID);
2934d1c9 1225 State.regs[OP[0]] = OP[1];
87178dbd 1226 trace_output (OP_REG);
2934d1c9
MH
1227}
1228
1229/* ldub */
1230void
1231OP_39000000 ()
1232{
87178dbd 1233 trace_input ("ldub", OP_REG_OUTPUT, OP_MEMREF2, OP_VOID);
2934d1c9 1234 State.regs[OP[0]] = RB (OP[1] + State.regs[OP[2]]);
87178dbd 1235 trace_output (OP_REG);
2934d1c9
MH
1236}
1237
1238/* ldub */
1239void
1240OP_7200 ()
1241{
87178dbd 1242 trace_input ("ldub", OP_REG_OUTPUT, OP_MEMREF, OP_VOID);
2934d1c9 1243 State.regs[OP[0]] = RB (State.regs[OP[1]]);
87178dbd 1244 trace_output (OP_REG);
2934d1c9
MH
1245}
1246
1247/* mac */
1248void
1249OP_2A00 ()
1250{
4c38885c 1251 int64 tmp;
87178dbd
MM
1252
1253 trace_input ("mac", OP_ACCUM, OP_REG, OP_REG);
4f425a32 1254 tmp = SEXT40 ((int16)(State.regs[OP[1]]) * (int16)(State.regs[OP[2]]));
4c38885c
MH
1255
1256 if (State.FX)
4f425a32 1257 tmp = SEXT40( (tmp << 1) & MASK40);
4c38885c
MH
1258
1259 if (State.ST && tmp > MAX32)
1260 tmp = MAX32;
1261
4f425a32 1262 tmp += SEXT40(State.a[OP[0]]);
4c38885c
MH
1263 if (State.ST)
1264 {
1265 if (tmp > MAX32)
1266 State.a[OP[0]] = MAX32;
1267 else if (tmp < MIN32)
1268 State.a[OP[0]] = MIN32;
1269 else
4f425a32 1270 State.a[OP[0]] = tmp & MASK40;
4c38885c
MH
1271 }
1272 else
4f425a32 1273 State.a[OP[0]] = tmp & MASK40;
87178dbd 1274 trace_output (OP_ACCUM);
2934d1c9
MH
1275}
1276
1277/* macsu */
1278void
1279OP_1A00 ()
1280{
4f425a32 1281 int64 tmp;
87178dbd
MM
1282
1283 trace_input ("macsu", OP_ACCUM, OP_REG, OP_REG);
4f425a32
MH
1284 tmp = SEXT40 ((int16)State.regs[OP[1]] * State.regs[OP[2]]);
1285 if (State.FX)
1286 tmp = SEXT40( (tmp << 1) & MASK40);
1287
1288 State.a[OP[0]] = (SEXT40 (State.a[OP[0]]) + tmp) & MASK40;
87178dbd 1289 trace_output (OP_ACCUM);
2934d1c9
MH
1290}
1291
1292/* macu */
1293void
1294OP_3A00 ()
1295{
4f425a32 1296 int64 tmp;
87178dbd
MM
1297
1298 trace_input ("macu", OP_ACCUM, OP_REG, OP_REG);
4f425a32
MH
1299 tmp = SEXT40 (State.regs[OP[1]] * State.regs[OP[2]]);
1300 if (State.FX)
1301 tmp = SEXT40( (tmp << 1) & MASK40);
1302 State.a[OP[0]] = (SEXT40 (State.a[OP[0]]) + tmp) & MASK40;
87178dbd 1303 trace_output (OP_ACCUM);
2934d1c9
MH
1304}
1305
1306/* max */
1307void
1308OP_2600 ()
1309{
87178dbd 1310 trace_input ("max", OP_REG, OP_REG, OP_VOID);
2934d1c9 1311 State.F1 = State.F0;
ea2155e8 1312 if ((int16)State.regs[OP[1]] > (int16)State.regs[OP[0]])
2934d1c9
MH
1313 {
1314 State.regs[OP[0]] = State.regs[OP[1]];
1315 State.F0 = 1;
1316 }
1317 else
1318 State.F0 = 0;
87178dbd 1319 trace_output (OP_REG);
2934d1c9
MH
1320}
1321
1322/* max */
1323void
1324OP_3600 ()
1325{
4f425a32 1326 int64 tmp;
87178dbd
MM
1327
1328 trace_input ("max", OP_ACCUM, OP_DREG, OP_VOID);
4f425a32
MH
1329 State.F1 = State.F0;
1330 tmp = SEXT16 (State.regs[OP[1]]) << 16 | State.regs[OP[1]+1];
1331 if (tmp > SEXT40(State.a[OP[0]]))
1332 {
1333 State.a[OP[0]] = tmp & MASK40;
1334 State.F0 = 1;
1335 }
1336 else
1337 State.F0 = 0;
87178dbd 1338 trace_output (OP_ACCUM);
2934d1c9
MH
1339}
1340
1341/* max */
1342void
1343OP_3602 ()
1344{
87178dbd 1345 trace_input ("max", OP_ACCUM, OP_ACCUM, OP_VOID);
4f425a32
MH
1346 State.F1 = State.F0;
1347 if (SEXT40(State.a[OP[1]]) > SEXT40(State.a[OP[0]]))
1348 {
1349 State.a[OP[0]] = State.a[OP[1]];
1350 State.F0 = 1;
1351 }
1352 else
1353 State.F0 = 0;
87178dbd 1354 trace_output (OP_ACCUM);
2934d1c9
MH
1355}
1356
4f425a32 1357
2934d1c9
MH
1358/* min */
1359void
1360OP_2601 ()
1361{
87178dbd 1362 trace_input ("min", OP_REG, OP_REG, OP_VOID);
2934d1c9 1363 State.F1 = State.F0;
ea2155e8 1364 if ((int16)State.regs[OP[1]] < (int16)State.regs[OP[0]])
2934d1c9
MH
1365 {
1366 State.regs[OP[0]] = State.regs[OP[1]];
1367 State.F0 = 1;
1368 }
1369 else
1370 State.F0 = 0;
87178dbd 1371 trace_output (OP_REG);
2934d1c9
MH
1372}
1373
1374/* min */
1375void
1376OP_3601 ()
1377{
4f425a32 1378 int64 tmp;
87178dbd
MM
1379
1380 trace_input ("min", OP_ACCUM, OP_DREG, OP_VOID);
4f425a32
MH
1381 State.F1 = State.F0;
1382 tmp = SEXT16 (State.regs[OP[1]]) << 16 | State.regs[OP[1]+1];
1383 if (tmp < SEXT40(State.a[OP[0]]))
1384 {
1385 State.a[OP[0]] = tmp & MASK40;
1386 State.F0 = 1;
1387 }
1388 else
1389 State.F0 = 0;
87178dbd 1390 trace_output (OP_ACCUM);
2934d1c9
MH
1391}
1392
1393/* min */
1394void
1395OP_3603 ()
1396{
87178dbd 1397 trace_input ("min", OP_ACCUM, OP_ACCUM, OP_VOID);
4f425a32
MH
1398 State.F1 = State.F0;
1399 if (SEXT40(State.a[OP[1]]) < SEXT40(State.a[OP[0]]))
1400 {
1401 State.a[OP[0]] = State.a[OP[1]];
1402 State.F0 = 1;
1403 }
1404 else
1405 State.F0 = 0;
87178dbd 1406 trace_output (OP_ACCUM);
2934d1c9
MH
1407}
1408
1409/* msb */
1410void
1411OP_2800 ()
1412{
4f425a32 1413 int64 tmp;
87178dbd
MM
1414
1415 trace_input ("msb", OP_ACCUM, OP_REG, OP_REG);
4f425a32
MH
1416 tmp = SEXT40 ((int16)(State.regs[OP[1]]) * (int16)(State.regs[OP[2]]));
1417
1418 if (State.FX)
1419 tmp = SEXT40 ((tmp << 1) & MASK40);
1420
1421 if (State.ST && tmp > MAX32)
1422 tmp = MAX32;
1423
1424 tmp = SEXT40(State.a[OP[0]]) - tmp;
1425 if (State.ST)
1426 {
1427 if (tmp > MAX32)
1428 State.a[OP[0]] = MAX32;
1429 else if (tmp < MIN32)
1430 State.a[OP[0]] = MIN32;
1431 else
1432 State.a[OP[0]] = tmp & MASK40;
1433 }
1434 else
1435 State.a[OP[0]] = tmp & MASK40;
87178dbd 1436 trace_output (OP_ACCUM);
2934d1c9
MH
1437}
1438
1439/* msbsu */
1440void
1441OP_1800 ()
1442{
4f425a32 1443 int64 tmp;
87178dbd
MM
1444
1445 trace_input ("msbsu", OP_ACCUM, OP_REG, OP_REG);
4f425a32
MH
1446 tmp = SEXT40 ((int16)State.regs[OP[1]] * State.regs[OP[2]]);
1447 if (State.FX)
1448 tmp = SEXT40( (tmp << 1) & MASK40);
1449
1450 State.a[OP[0]] = (SEXT40 (State.a[OP[0]]) - tmp) & MASK40;
87178dbd 1451 trace_output (OP_ACCUM);
2934d1c9
MH
1452}
1453
1454/* msbu */
1455void
1456OP_3800 ()
1457{
4f425a32 1458 int64 tmp;
87178dbd
MM
1459
1460 trace_input ("msbu", OP_ACCUM, OP_REG, OP_REG);
4f425a32
MH
1461 tmp = SEXT40 (State.regs[OP[1]] * State.regs[OP[2]]);
1462 if (State.FX)
1463 tmp = SEXT40( (tmp << 1) & MASK40);
1464
1465 State.a[OP[0]] = (SEXT40 (State.a[OP[0]]) - tmp) & MASK40;
87178dbd 1466 trace_output (OP_ACCUM);
2934d1c9
MH
1467}
1468
1469/* mul */
1470void
1471OP_2E00 ()
1472{
87178dbd 1473 trace_input ("mul", OP_REG, OP_REG, OP_VOID);
2934d1c9 1474 State.regs[OP[0]] *= State.regs[OP[1]];
87178dbd 1475 trace_output (OP_REG);
2934d1c9
MH
1476}
1477
1478/* mulx */
1479void
1480OP_2C00 ()
1481{
4f425a32 1482 int64 tmp;
87178dbd
MM
1483
1484 trace_input ("mulx", OP_ACCUM_OUTPUT, OP_REG, OP_REG);
4f425a32
MH
1485 tmp = SEXT40 ((int16)(State.regs[OP[1]]) * (int16)(State.regs[OP[2]]));
1486
1487 if (State.FX)
1488 tmp = SEXT40 ((tmp << 1) & MASK40);
1489
1490 if (State.ST && tmp > MAX32)
1491 State.a[OP[0]] = MAX32;
1492 else
1493 State.a[OP[0]] = tmp & MASK40;
87178dbd 1494 trace_output (OP_ACCUM);
2934d1c9
MH
1495}
1496
1497/* mulxsu */
1498void
1499OP_1C00 ()
1500{
4f425a32 1501 int64 tmp;
87178dbd
MM
1502
1503 trace_input ("mulxsu", OP_ACCUM_OUTPUT, OP_REG, OP_REG);
4f425a32
MH
1504 tmp = SEXT40 ((int16)(State.regs[OP[1]]) * State.regs[OP[2]]);
1505
1506 if (State.FX)
1507 tmp <<= 1;
1508
1509 State.a[OP[0]] = tmp & MASK40;
87178dbd 1510 trace_output (OP_ACCUM);
2934d1c9
MH
1511}
1512
1513/* mulxu */
1514void
1515OP_3C00 ()
1516{
4f425a32 1517 int64 tmp;
87178dbd
MM
1518
1519 trace_input ("mulxu", OP_ACCUM_OUTPUT, OP_REG, OP_REG);
4f425a32
MH
1520 tmp = SEXT40 (State.regs[OP[1]] * State.regs[OP[2]]);
1521
1522 if (State.FX)
1523 tmp <<= 1;
1524
1525 State.a[OP[0]] = tmp & MASK40;
87178dbd 1526 trace_output (OP_ACCUM);
2934d1c9
MH
1527}
1528
1529/* mv */
1530void
1531OP_4000 ()
1532{
87178dbd 1533 trace_input ("mv", OP_REG_OUTPUT, OP_REG, OP_VOID);
2934d1c9 1534 State.regs[OP[0]] = State.regs[OP[1]];
87178dbd 1535 trace_output (OP_REG);
2934d1c9
MH
1536}
1537
1538/* mv2w */
1539void
1540OP_5000 ()
1541{
87178dbd 1542 trace_input ("mv2w", OP_DREG_OUTPUT, OP_DREG, OP_VOID);
2934d1c9
MH
1543 State.regs[OP[0]] = State.regs[OP[1]];
1544 State.regs[OP[0]+1] = State.regs[OP[1]+1];
87178dbd 1545 trace_output (OP_DREG);
2934d1c9
MH
1546}
1547
1548/* mv2wfac */
1549void
1550OP_3E00 ()
1551{
87178dbd 1552 trace_input ("mv2wfac", OP_DREG_OUTPUT, OP_ACCUM, OP_VOID);
2934d1c9
MH
1553 State.regs[OP[0]] = (State.a[OP[1]] >> 16) & 0xffff;
1554 State.regs[OP[0]+1] = State.a[OP[1]] & 0xffff;
87178dbd 1555 trace_output (OP_DREG);
2934d1c9
MH
1556}
1557
1558/* mv2wtac */
1559void
1560OP_3E01 ()
1561{
87178dbd 1562 trace_input ("mv2wtac", OP_ACCUM_OUTPUT, OP_DREG, OP_VOID);
4f425a32 1563 State.a[OP[1]] = (SEXT16 (State.regs[OP[0]]) << 16 | State.regs[OP[0]+1]) & MASK40;
87178dbd 1564 trace_output (OP_ACCUM);
2934d1c9
MH
1565}
1566
1567/* mvac */
1568void
1569OP_3E03 ()
1570{
87178dbd 1571 trace_input ("mvac", OP_ACCUM_OUTPUT, OP_ACCUM, OP_VOID);
2934d1c9 1572 State.a[OP[0]] = State.a[OP[1]];
87178dbd 1573 trace_output (OP_ACCUM);
2934d1c9
MH
1574}
1575
1576/* mvb */
1577void
1578OP_5400 ()
1579{
87178dbd 1580 trace_input ("mvb", OP_REG_OUTPUT, OP_REG, OP_VOID);
2934d1c9 1581 State.regs[OP[0]] = SEXT8 (State.regs[OP[1]] & 0xff);
87178dbd 1582 trace_output (OP_REG);
2934d1c9
MH
1583}
1584
1585/* mvf0f */
1586void
1587OP_4400 ()
1588{
87178dbd 1589 trace_input ("mf0f", OP_REG_OUTPUT, OP_REG, OP_VOID);
2934d1c9
MH
1590 if (State.F0 == 0)
1591 State.regs[OP[0]] = State.regs[OP[1]];
87178dbd 1592 trace_output (OP_REG);
2934d1c9
MH
1593}
1594
1595/* mvf0t */
1596void
1597OP_4401 ()
1598{
87178dbd 1599 trace_input ("mf0t", OP_REG_OUTPUT, OP_REG, OP_VOID);
2934d1c9
MH
1600 if (State.F0)
1601 State.regs[OP[0]] = State.regs[OP[1]];
87178dbd 1602 trace_output (OP_REG);
2934d1c9
MH
1603}
1604
1605/* mvfacg */
1606void
1607OP_1E04 ()
1608{
87178dbd 1609 trace_input ("mvfacg", OP_REG_OUTPUT, OP_ACCUM, OP_VOID);
2934d1c9 1610 State.regs[OP[0]] = (State.a[OP[1]] >> 32) & 0xff;
87178dbd 1611 trace_output (OP_ACCUM);
2934d1c9
MH
1612}
1613
1614/* mvfachi */
1615void
1616OP_1E00 ()
1617{
87178dbd 1618 trace_input ("mvfachi", OP_REG_OUTPUT, OP_ACCUM, OP_VOID);
2934d1c9 1619 State.regs[OP[0]] = (State.a[OP[1]] >> 16) & 0xffff;
87178dbd 1620 trace_output (OP_REG);
2934d1c9
MH
1621}
1622
1623/* mvfaclo */
1624void
1625OP_1E02 ()
1626{
87178dbd 1627 trace_input ("mvfaclo", OP_REG_OUTPUT, OP_ACCUM, OP_VOID);
2934d1c9 1628 State.regs[OP[0]] = State.a[OP[1]] & 0xffff;
87178dbd 1629 trace_output (OP_REG);
2934d1c9
MH
1630}
1631
1632/* mvfc */
1633void
1634OP_5200 ()
1635{
87178dbd 1636 trace_input ("mvfc", OP_REG_OUTPUT, OP_CR, OP_VOID);
2934d1c9
MH
1637 if (OP[1] == 0)
1638 {
1639 /* PSW is treated specially */
1640 PSW = 0;
1641 if (State.SM) PSW |= 0x8000;
1642 if (State.EA) PSW |= 0x2000;
1643 if (State.DB) PSW |= 0x1000;
1644 if (State.IE) PSW |= 0x400;
1645 if (State.RP) PSW |= 0x200;
1646 if (State.MD) PSW |= 0x100;
1647 if (State.FX) PSW |= 0x80;
1648 if (State.ST) PSW |= 0x40;
1649 if (State.F0) PSW |= 8;
1650 if (State.F1) PSW |= 4;
1651 if (State.C) PSW |= 1;
1652 }
1653 State.regs[OP[0]] = State.cregs[OP[1]];
87178dbd 1654 trace_output (OP_REG);
2934d1c9
MH
1655}
1656
1657/* mvtacg */
1658void
1659OP_1E41 ()
1660{
87178dbd 1661 trace_input ("mvtacg", OP_REG, OP_ACCUM, OP_VOID);
2934d1c9
MH
1662 State.a[OP[1]] &= MASK32;
1663 State.a[OP[1]] |= (int64)(State.regs[OP[0]] & 0xff) << 32;
87178dbd 1664 trace_output (OP_ACCUM_REVERSE);
2934d1c9
MH
1665}
1666
1667/* mvtachi */
1668void
1669OP_1E01 ()
1670{
1671 uint16 tmp;
87178dbd
MM
1672
1673 trace_input ("mvtachi", OP_REG, OP_ACCUM, OP_VOID);
2934d1c9 1674 tmp = State.a[OP[1]] & 0xffff;
4f425a32 1675 State.a[OP[1]] = (SEXT16 (State.regs[OP[0]]) << 16 | tmp) & MASK40;
87178dbd 1676 trace_output (OP_ACCUM_REVERSE);
2934d1c9
MH
1677}
1678
1679/* mvtaclo */
1680void
1681OP_1E21 ()
1682{
87178dbd 1683 trace_input ("mvtaclo", OP_REG, OP_ACCUM, OP_VOID);
4f425a32 1684 State.a[OP[1]] = (SEXT16 (State.regs[OP[0]])) & MASK40;
87178dbd 1685 trace_output (OP_ACCUM_REVERSE);
2934d1c9
MH
1686}
1687
1688/* mvtc */
1689void
1690OP_5600 ()
1691{
87178dbd 1692 trace_input ("mvtc", OP_REG, OP_CR_OUTPUT, OP_VOID);
2934d1c9
MH
1693 State.cregs[OP[1]] = State.regs[OP[0]];
1694 if (OP[1] == 0)
1695 {
1696 /* PSW is treated specially */
1697 State.SM = (PSW & 0x8000) ? 1 : 0;
1698 State.EA = (PSW & 0x2000) ? 1 : 0;
1699 State.DB = (PSW & 0x1000) ? 1 : 0;
1700 State.IE = (PSW & 0x400) ? 1 : 0;
1701 State.RP = (PSW & 0x200) ? 1 : 0;
1702 State.MD = (PSW & 0x100) ? 1 : 0;
1703 State.FX = (PSW & 0x80) ? 1 : 0;
1704 State.ST = (PSW & 0x40) ? 1 : 0;
1705 State.F0 = (PSW & 8) ? 1 : 0;
1706 State.F1 = (PSW & 4) ? 1 : 0;
1707 State.C = PSW & 1;
1708 if (State.ST && !State.FX)
1709 {
7eebfc62
MM
1710 (*d10v_callback->printf_filtered) (d10v_callback,
1711 "ERROR at PC 0x%x: ST can only be set when FX is set.\n",
1712 PC<<2);
4f425a32 1713 State.exception = SIGILL;
2934d1c9
MH
1714 }
1715 }
87178dbd 1716 trace_output (OP_CR_REVERSE);
2934d1c9
MH
1717}
1718
1719/* mvub */
1720void
1721OP_5401 ()
1722{
87178dbd 1723 trace_input ("mvub", OP_REG_OUTPUT, OP_REG, OP_VOID);
2934d1c9 1724 State.regs[OP[0]] = State.regs[OP[1]] & 0xff;
87178dbd 1725 trace_output (OP_REG);
2934d1c9
MH
1726}
1727
1728/* neg */
1729void
1730OP_4605 ()
1731{
87178dbd 1732 trace_input ("neg", OP_REG, OP_VOID, OP_VOID);
2934d1c9 1733 State.regs[OP[0]] = 0 - State.regs[OP[0]];
87178dbd 1734 trace_output (OP_REG);
2934d1c9
MH
1735}
1736
1737/* neg */
1738void
1739OP_5605 ()
1740{
1741 int64 tmp;
87178dbd
MM
1742
1743 trace_input ("neg", OP_ACCUM, OP_VOID, OP_VOID);
4f425a32 1744 tmp = -SEXT40(State.a[OP[0]]);
2934d1c9
MH
1745 if (State.ST)
1746 {
4c38885c 1747 if ( tmp > MAX32)
2934d1c9 1748 State.a[OP[0]] = MAX32;
4c38885c 1749 else if (tmp < MIN32)
2934d1c9
MH
1750 State.a[OP[0]] = MIN32;
1751 else
4f425a32 1752 State.a[OP[0]] = tmp & MASK40;
2934d1c9
MH
1753 }
1754 else
4f425a32 1755 State.a[OP[0]] = tmp & MASK40;
87178dbd 1756 trace_output (OP_ACCUM);
2934d1c9
MH
1757}
1758
1759
1760/* nop */
1761void
1762OP_5E00 ()
1763{
87178dbd
MM
1764 trace_input ("nop", OP_VOID, OP_VOID, OP_VOID);
1765 trace_output (OP_VOID);
7eebfc62
MM
1766
1767 if (State.ins_type == INS_LEFT || State.ins_type == INS_LEFT_PARALLEL)
1768 left_nops++;
1769 else
1770 right_nops++;
2934d1c9
MH
1771}
1772
1773/* not */
1774void
1775OP_4603 ()
1776{
87178dbd 1777 trace_input ("not", OP_REG, OP_VOID, OP_VOID);
2934d1c9 1778 State.regs[OP[0]] = ~(State.regs[OP[0]]);
87178dbd 1779 trace_output (OP_REG);
2934d1c9
MH
1780}
1781
1782/* or */
1783void
1784OP_800 ()
1785{
87178dbd 1786 trace_input ("or", OP_REG, OP_REG, OP_VOID);
2934d1c9 1787 State.regs[OP[0]] |= State.regs[OP[1]];
87178dbd 1788 trace_output (OP_REG);
2934d1c9
MH
1789}
1790
1791/* or3 */
1792void
1793OP_4000000 ()
1794{
87178dbd 1795 trace_input ("or3", OP_REG_OUTPUT, OP_REG, OP_CONSTANT16);
2934d1c9 1796 State.regs[OP[0]] = State.regs[OP[1]] | OP[2];
87178dbd 1797 trace_output (OP_REG);
2934d1c9
MH
1798}
1799
1800/* rac */
1801void
1802OP_5201 ()
1803{
1804 int64 tmp;
1805 int shift = SEXT3 (OP[2]);
87178dbd
MM
1806
1807 trace_input ("rac", OP_DREG_OUTPUT, OP_ACCUM, OP_CONSTANT3);
166acb9f
MH
1808 if (OP[1] != 0)
1809 {
7eebfc62
MM
1810 (*d10v_callback->printf_filtered) (d10v_callback,
1811 "ERROR at PC 0x%x: instruction only valid for A0\n",
1812 PC<<2);
166acb9f
MH
1813 State.exception = SIGILL;
1814 }
1815
2934d1c9
MH
1816 State.F1 = State.F0;
1817 if (shift >=0)
1818 tmp = ((State.a[0] << 16) | (State.a[1] & 0xffff)) << shift;
1819 else
1820 tmp = ((State.a[0] << 16) | (State.a[1] & 0xffff)) >> -shift;
166acb9f 1821 tmp = ( SEXT60(tmp) + 0x8000 ) >> 16;
4c38885c 1822 if (tmp > MAX32)
2934d1c9
MH
1823 {
1824 State.regs[OP[0]] = 0x7fff;
1825 State.regs[OP[0]+1] = 0xffff;
1826 State.F0 = 1;
1827 }
4c38885c 1828 else if (tmp < MIN32)
2934d1c9
MH
1829 {
1830 State.regs[OP[0]] = 0x8000;
1831 State.regs[OP[0]+1] = 0;
1832 State.F0 = 1;
1833 }
1834 else
1835 {
1836 State.regs[OP[0]] = (tmp >> 16) & 0xffff;
1837 State.regs[OP[0]+1] = tmp & 0xffff;
1838 State.F0 = 0;
1839 }
87178dbd 1840 trace_output (OP_DREG);
2934d1c9
MH
1841}
1842
1843/* rachi */
1844void
1845OP_4201 ()
1846{
4c38885c
MH
1847 int64 tmp;
1848 int shift = SEXT3 (OP[2]);
87178dbd
MM
1849
1850 trace_input ("rachi", OP_REG_OUTPUT, OP_ACCUM, OP_CONSTANT3);
4c38885c
MH
1851 State.F1 = State.F0;
1852 if (shift >=0)
166acb9f 1853 tmp = SEXT44 (State.a[1]) << shift;
4c38885c 1854 else
166acb9f 1855 tmp = SEXT44 (State.a[1]) >> -shift;
4c38885c 1856 tmp += 0x8000;
63a91cfb 1857
4c38885c
MH
1858 if (tmp > MAX32)
1859 {
1860 State.regs[OP[0]] = 0x7fff;
1861 State.F0 = 1;
1862 }
1863 else if (tmp < 0xfff80000000LL)
1864 {
1865 State.regs[OP[0]] = 0x8000;
1866 State.F0 = 1;
1867 }
1868 else
1869 {
1870 State.regs[OP[0]] = (tmp >> 16) & 0xffff;
1871 State.F0 = 0;
1872 }
87178dbd 1873 trace_output (OP_REG);
2934d1c9
MH
1874}
1875
1876/* rep */
1877void
1878OP_27000000 ()
1879{
87178dbd 1880 trace_input ("rep", OP_REG, OP_CONSTANT16, OP_VOID);
2934d1c9
MH
1881 RPT_S = PC + 1;
1882 RPT_E = PC + OP[1];
1883 RPT_C = State.regs[OP[0]];
1884 State.RP = 1;
1885 if (RPT_C == 0)
1886 {
7eebfc62 1887 (*d10v_callback->printf_filtered) (d10v_callback, "ERROR: rep with count=0 is illegal.\n");
4f425a32 1888 State.exception = SIGILL;
2934d1c9 1889 }
4c38885c
MH
1890 if (OP[1] < 4)
1891 {
7eebfc62 1892 (*d10v_callback->printf_filtered) (d10v_callback, "ERROR: rep must include at least 4 instructions.\n");
4f425a32 1893 State.exception = SIGILL;
4c38885c 1894 }
87178dbd 1895 trace_output (OP_VOID);
2934d1c9
MH
1896}
1897
1898/* repi */
1899void
1900OP_2F000000 ()
1901{
87178dbd 1902 trace_input ("repi", OP_CONSTANT16, OP_CONSTANT16, OP_VOID);
2934d1c9
MH
1903 RPT_S = PC + 1;
1904 RPT_E = PC + OP[1];
1905 RPT_C = OP[0];
1906 State.RP = 1;
1907 if (RPT_C == 0)
1908 {
7eebfc62 1909 (*d10v_callback->printf_filtered) (d10v_callback, "ERROR: repi with count=0 is illegal.\n");
4f425a32 1910 State.exception = SIGILL;
4c38885c
MH
1911 }
1912 if (OP[1] < 4)
1913 {
7eebfc62 1914 (*d10v_callback->printf_filtered) (d10v_callback, "ERROR: repi must include at least 4 instructions.\n");
4f425a32 1915 State.exception = SIGILL;
2934d1c9 1916 }
87178dbd 1917 trace_output (OP_VOID);
2934d1c9
MH
1918}
1919
1920/* rtd */
1921void
1922OP_5F60 ()
1923{
7eebfc62 1924 d10v_callback->printf_filtered(d10v_callback, "ERROR: rtd - NOT IMPLEMENTED\n");
87178dbd 1925 State.exception = SIGILL;
2934d1c9
MH
1926}
1927
1928/* rte */
1929void
1930OP_5F40 ()
1931{
87178dbd 1932 trace_input ("rte", OP_VOID, OP_VOID, OP_VOID);
4c38885c
MH
1933 PC = BPC;
1934 PSW = BPSW;
87178dbd 1935 trace_output (OP_VOID);
2934d1c9
MH
1936}
1937
1938/* sadd */
1939void
1940OP_1223 ()
1941{
4c38885c 1942 int64 tmp;
87178dbd
MM
1943
1944 trace_input ("sadd", OP_ACCUM, OP_ACCUM, OP_VOID);
4f425a32 1945 tmp = SEXT40(State.a[OP[0]]) + (SEXT40(State.a[OP[1]]) >> 16);
4c38885c
MH
1946 if (State.ST)
1947 {
1948 if (tmp > MAX32)
1949 State.a[OP[0]] = MAX32;
1950 else if (tmp < MIN32)
1951 State.a[OP[0]] = MIN32;
1952 else
4f425a32 1953 State.a[OP[0]] = tmp & MASK40;
4c38885c
MH
1954 }
1955 else
4f425a32 1956 State.a[OP[0]] = tmp & MASK40;
87178dbd 1957 trace_output (OP_ACCUM);
2934d1c9
MH
1958}
1959
1960/* setf0f */
1961void
1962OP_4611 ()
1963{
87178dbd 1964 trace_input ("setf0f", OP_REG_OUTPUT, OP_VOID, OP_VOID);
4c38885c 1965 State.regs[OP[0]] = (State.F0 == 0) ? 1 : 0;
87178dbd 1966 trace_output (OP_REG);
2934d1c9
MH
1967}
1968
1969/* setf0t */
1970void
1971OP_4613 ()
1972{
87178dbd 1973 trace_input ("setf0t", OP_REG_OUTPUT, OP_VOID, OP_VOID);
4c38885c 1974 State.regs[OP[0]] = (State.F0 == 1) ? 1 : 0;
87178dbd 1975 trace_output (OP_REG);
2934d1c9
MH
1976}
1977
1978/* sleep */
1979void
1980OP_5FC0 ()
1981{
87178dbd 1982 trace_input ("sleep", OP_VOID, OP_VOID, OP_VOID);
4c38885c 1983 State.IE = 1;
87178dbd 1984 trace_output (OP_VOID);
2934d1c9
MH
1985}
1986
1987/* sll */
1988void
1989OP_2200 ()
1990{
87178dbd 1991 trace_input ("sll", OP_REG, OP_REG, OP_VOID);
2934d1c9 1992 State.regs[OP[0]] <<= (State.regs[OP[1]] & 0xf);
87178dbd 1993 trace_output (OP_REG);
2934d1c9
MH
1994}
1995
1996/* sll */
1997void
1998OP_3200 ()
1999{
4c38885c 2000 int64 tmp;
87178dbd 2001 trace_input ("sll", OP_ACCUM, OP_REG, OP_VOID);
069398aa 2002 if ((State.regs[OP[1]] & 31) <= 16)
4c38885c 2003 tmp = SEXT40 (State.a[OP[0]]) << (State.regs[OP[1]] & 31);
069398aa
MM
2004 else
2005 {
2006 (*d10v_callback->printf_filtered) (d10v_callback, "ERROR: shift value %d too large.\n", State.regs[OP[1]] & 31);
2007 State.exception = SIGILL;
2008 return;
2009 }
4c38885c
MH
2010
2011 if (State.ST)
2012 {
2013 if (tmp > MAX32)
2014 State.a[OP[0]] = MAX32;
2015 else if (tmp < 0xffffff80000000LL)
2016 State.a[OP[0]] = MIN32;
2017 else
2018 State.a[OP[0]] = tmp & MASK40;
2019 }
2020 else
2021 State.a[OP[0]] = tmp & MASK40;
87178dbd 2022 trace_output (OP_ACCUM);
2934d1c9
MH
2023}
2024
2025/* slli */
2026void
2027OP_2201 ()
2028{
87178dbd 2029 trace_input ("slli", OP_REG, OP_CONSTANT16, OP_VOID);
2934d1c9 2030 State.regs[OP[0]] <<= OP[1];
87178dbd 2031 trace_output (OP_REG);
2934d1c9
MH
2032}
2033
2034/* slli */
2035void
2036OP_3201 ()
2037{
4c38885c 2038 int64 tmp;
4f425a32
MH
2039
2040 if (OP[1] == 0)
2041 OP[1] = 16;
4f425a32 2042
87178dbd 2043 trace_input ("slli", OP_ACCUM, OP_CONSTANT16, OP_VOID);
4f425a32 2044 tmp = SEXT40(State.a[OP[0]]) << OP[1];
4c38885c
MH
2045
2046 if (State.ST)
2047 {
2048 if (tmp > MAX32)
2049 State.a[OP[0]] = MAX32;
2050 else if (tmp < 0xffffff80000000LL)
2051 State.a[OP[0]] = MIN32;
2052 else
2053 State.a[OP[0]] = tmp & MASK40;
2054 }
2055 else
2056 State.a[OP[0]] = tmp & MASK40;
87178dbd 2057 trace_output (OP_ACCUM);
2934d1c9
MH
2058}
2059
2060/* slx */
2061void
2062OP_460B ()
2063{
2064 uint16 tmp;
87178dbd
MM
2065
2066 trace_input ("slx", OP_REG, OP_FLAG, OP_VOID);
2934d1c9 2067 State.regs[OP[0]] = (State.regs[OP[0]] << 1) | State.F0;
87178dbd 2068 trace_output (OP_REG);
2934d1c9
MH
2069}
2070
2071/* sra */
2072void
2073OP_2400 ()
2074{
87178dbd 2075 trace_input ("sra", OP_REG, OP_REG, OP_VOID);
2934d1c9 2076 State.regs[OP[0]] = ((int16)(State.regs[OP[0]])) >> (State.regs[OP[1]] & 0xf);
87178dbd 2077 trace_output (OP_REG);
2934d1c9
MH
2078}
2079
2080/* sra */
2081void
2082OP_3400 ()
2083{
87178dbd 2084 trace_input ("sra", OP_ACCUM, OP_REG, OP_VOID);
069398aa 2085 if ((State.regs[OP[1]] & 31) <= 16)
4c38885c 2086 State.a[OP[0]] >>= (State.regs[OP[1]] & 31);
069398aa
MM
2087 else
2088 {
2089 (*d10v_callback->printf_filtered) (d10v_callback, "ERROR: shift value %d too large.\n", State.regs[OP[1]] & 31);
2090 State.exception = SIGILL;
2091 return;
2092 }
2093
87178dbd 2094 trace_output (OP_ACCUM);
2934d1c9
MH
2095}
2096
2097/* srai */
2098void
2099OP_2401 ()
2100{
87178dbd 2101 trace_input ("srai", OP_REG, OP_CONSTANT16, OP_VOID);
2934d1c9 2102 State.regs[OP[0]] = ((int16)(State.regs[OP[0]])) >> OP[1];
87178dbd 2103 trace_output (OP_REG);
2934d1c9
MH
2104}
2105
2106/* srai */
2107void
2108OP_3401 ()
2109{
4f425a32
MH
2110 if (OP[1] == 0)
2111 OP[1] = 16;
87178dbd
MM
2112
2113 trace_input ("srai", OP_ACCUM, OP_CONSTANT16, OP_VOID);
2114 State.a[OP[0]] >>= OP[1];
2115 trace_output (OP_ACCUM);
2934d1c9
MH
2116}
2117
2118/* srl */
2119void
2120OP_2000 ()
2121{
87178dbd 2122 trace_input ("srl", OP_REG, OP_REG, OP_VOID);
2934d1c9 2123 State.regs[OP[0]] >>= (State.regs[OP[1]] & 0xf);
87178dbd 2124 trace_output (OP_REG);
2934d1c9
MH
2125}
2126
2127/* srl */
2128void
2129OP_3000 ()
2130{
87178dbd 2131 trace_input ("srl", OP_ACCUM, OP_REG, OP_VOID);
069398aa 2132 if ((State.regs[OP[1]] & 31) <= 16)
4c38885c 2133 State.a[OP[0]] >>= (State.regs[OP[1]] & 31);
069398aa
MM
2134 else
2135 {
2136 (*d10v_callback->printf_filtered) (d10v_callback, "ERROR: shift value %d too large.\n", State.regs[OP[1]] & 31);
2137 State.exception = SIGILL;
2138 return;
2139 }
2140
87178dbd 2141 trace_output (OP_ACCUM);
2934d1c9
MH
2142}
2143
2144/* srli */
2145void
2146OP_2001 ()
2147{
87178dbd 2148 trace_input ("srli", OP_REG, OP_CONSTANT16, OP_VOID);
2934d1c9 2149 State.regs[OP[0]] >>= OP[1];
87178dbd 2150 trace_output (OP_REG);
2934d1c9
MH
2151}
2152
2153/* srli */
2154void
2155OP_3001 ()
2156{
4f425a32
MH
2157 if (OP[1] == 0)
2158 OP[1] = 16;
87178dbd
MM
2159
2160 trace_input ("srli", OP_ACCUM, OP_CONSTANT16, OP_VOID);
2161 State.a[OP[0]] >>= OP[1];
2162 trace_output (OP_ACCUM);
2934d1c9
MH
2163}
2164
2165/* srx */
2166void
2167OP_4609 ()
2168{
2169 uint16 tmp;
87178dbd
MM
2170
2171 trace_input ("srx", OP_REG, OP_FLAG, OP_VOID);
2934d1c9
MH
2172 tmp = State.F0 << 15;
2173 State.regs[OP[0]] = (State.regs[OP[0]] >> 1) | tmp;
87178dbd 2174 trace_output (OP_REG);
2934d1c9
MH
2175}
2176
2177/* st */
2178void
2179OP_34000000 ()
2180{
87178dbd 2181 trace_input ("st", OP_REG, OP_MEMREF2, OP_VOID);
2934d1c9 2182 SW (OP[1] + State.regs[OP[2]], State.regs[OP[0]]);
87178dbd 2183 trace_output (OP_VOID);
2934d1c9
MH
2184}
2185
2186/* st */
2187void
2188OP_6800 ()
2189{
87178dbd 2190 trace_input ("st", OP_REG, OP_MEMREF, OP_VOID);
2934d1c9 2191 SW (State.regs[OP[1]], State.regs[OP[0]]);
87178dbd 2192 trace_output (OP_VOID);
2934d1c9
MH
2193}
2194
2195/* st */
2196void
2197OP_6C1F ()
2198{
87178dbd 2199 trace_input ("st", OP_REG, OP_PREDEC, OP_VOID);
4c38885c
MH
2200 if ( OP[1] != 15 )
2201 {
7eebfc62 2202 (*d10v_callback->printf_filtered) (d10v_callback, "ERROR: cannot pre-decrement any registers but r15 (SP).\n");
4f425a32
MH
2203 State.exception = SIGILL;
2204 return;
4c38885c
MH
2205 }
2206 State.regs[OP[1]] -= 2;
2207 SW (State.regs[OP[1]], State.regs[OP[0]]);
87178dbd 2208 trace_output (OP_VOID);
2934d1c9
MH
2209}
2210
2211/* st */
2212void
2213OP_6801 ()
2214{
87178dbd 2215 trace_input ("st", OP_REG, OP_POSTINC, OP_VOID);
4c38885c 2216 SW (State.regs[OP[1]], State.regs[OP[0]]);
4f425a32 2217 INC_ADDR (State.regs[OP[1]],2);
87178dbd 2218 trace_output (OP_VOID);
2934d1c9
MH
2219}
2220
2221/* st */
2222void
2223OP_6C01 ()
2224{
87178dbd 2225 trace_input ("st", OP_REG, OP_POSTDEC, OP_VOID);
4c38885c 2226 SW (State.regs[OP[1]], State.regs[OP[0]]);
4f425a32 2227 INC_ADDR (State.regs[OP[1]],-2);
87178dbd 2228 trace_output (OP_VOID);
2934d1c9
MH
2229}
2230
2231/* st2w */
2232void
2233OP_35000000 ()
2234{
87178dbd 2235 trace_input ("st2w", OP_DREG, OP_MEMREF2, OP_VOID);
4f425a32
MH
2236 SW (State.regs[OP[2]]+OP[1], State.regs[OP[0]]);
2237 SW (State.regs[OP[2]]+OP[1]+2, State.regs[OP[0]+1]);
87178dbd 2238 trace_output (OP_VOID);
2934d1c9
MH
2239}
2240
2241/* st2w */
2242void
2243OP_6A00 ()
2244{
87178dbd 2245 trace_input ("st2w", OP_REG, OP_MEMREF, OP_VOID);
4c38885c
MH
2246 SW (State.regs[OP[1]], State.regs[OP[0]]);
2247 SW (State.regs[OP[1]]+2, State.regs[OP[0]+1]);
87178dbd 2248 trace_output (OP_VOID);
2934d1c9
MH
2249}
2250
2251/* st2w */
2252void
2253OP_6E1F ()
2254{
87178dbd 2255 trace_input ("st2w", OP_REG, OP_PREDEC, OP_VOID);
4c38885c
MH
2256 if ( OP[1] != 15 )
2257 {
7eebfc62 2258 (*d10v_callback->printf_filtered) (d10v_callback, "ERROR: cannot pre-decrement any registers but r15 (SP).\n");
4f425a32
MH
2259 State.exception = SIGILL;
2260 return;
4c38885c
MH
2261 }
2262 State.regs[OP[1]] -= 4;
2263 SW (State.regs[OP[1]], State.regs[OP[0]]);
2264 SW (State.regs[OP[1]]+2, State.regs[OP[0]+1]);
87178dbd 2265 trace_output (OP_VOID);
2934d1c9
MH
2266}
2267
2268/* st2w */
2269void
2270OP_6A01 ()
2271{
87178dbd 2272 trace_input ("st2w", OP_REG, OP_POSTDEC, OP_VOID);
4c38885c
MH
2273 SW (State.regs[OP[1]], State.regs[OP[0]]);
2274 SW (State.regs[OP[1]]+2, State.regs[OP[0]+1]);
4f425a32 2275 INC_ADDR (State.regs[OP[1]],4);
87178dbd 2276 trace_output (OP_VOID);
2934d1c9
MH
2277}
2278
2279/* st2w */
2280void
2281OP_6E01 ()
2282{
87178dbd 2283 trace_input ("st2w", OP_REG, OP_POSTINC, OP_VOID);
4c38885c
MH
2284 SW (State.regs[OP[1]], State.regs[OP[0]]);
2285 SW (State.regs[OP[1]]+2, State.regs[OP[0]+1]);
4f425a32 2286 INC_ADDR (State.regs[OP[1]],-4);
87178dbd 2287 trace_output (OP_VOID);
2934d1c9
MH
2288}
2289
2290/* stb */
2291void
2292OP_3C000000 ()
2293{
87178dbd 2294 trace_input ("stb", OP_REG, OP_MEMREF2, OP_VOID);
4f425a32 2295 SB (State.regs[OP[2]]+OP[1], State.regs[OP[0]]);
87178dbd 2296 trace_output (OP_VOID);
2934d1c9
MH
2297}
2298
2299/* stb */
2300void
2301OP_7800 ()
2302{
87178dbd 2303 trace_input ("stb", OP_REG, OP_MEMREF, OP_VOID);
4c38885c 2304 SB (State.regs[OP[1]], State.regs[OP[0]]);
87178dbd 2305 trace_output (OP_VOID);
2934d1c9
MH
2306}
2307
2308/* stop */
2309void
2310OP_5FE0 ()
2311{
87178dbd 2312 trace_input ("stop", OP_VOID, OP_VOID, OP_VOID);
a49a15ad 2313 State.exception = SIG_D10V_STOP;
87178dbd 2314 trace_output (OP_VOID);
2934d1c9
MH
2315}
2316
2317/* sub */
2318void
2319OP_0 ()
4c38885c
MH
2320{
2321 int32 tmp;
87178dbd
MM
2322
2323 trace_input ("sub", OP_REG, OP_REG, OP_VOID);
4c38885c
MH
2324 tmp = (int16)State.regs[OP[0]]- (int16)State.regs[OP[1]];
2325 State.C = (tmp & 0xffff0000) ? 1 : 0;
2326 State.regs[OP[0]] = tmp & 0xffff;
87178dbd 2327 trace_output (OP_REG);
4c38885c
MH
2328}
2329
2330/* sub */
2331void
2332OP_1001 ()
2333{
4f425a32 2334 int64 tmp;
87178dbd
MM
2335
2336 trace_input ("sub", OP_ACCUM, OP_DREG, OP_VOID);
4f425a32
MH
2337 tmp = SEXT40(State.a[OP[0]]) - (SEXT16 (State.regs[OP[1]]) << 16 | State.regs[OP[1]+1]);
2338 if (State.ST)
2339 {
2340 if ( tmp > MAX32)
2341 State.a[OP[0]] = MAX32;
2342 else if ( tmp < MIN32)
2343 State.a[OP[0]] = MIN32;
2344 else
2345 State.a[OP[0]] = tmp & MASK40;
2346 }
2347 else
2348 State.a[OP[0]] = tmp & MASK40;
87178dbd
MM
2349
2350 trace_output (OP_ACCUM);
4c38885c
MH
2351}
2352
2353/* sub */
2354
2355void
2356OP_1003 ()
2934d1c9 2357{
4f425a32 2358 int64 tmp;
87178dbd
MM
2359
2360 trace_input ("sub", OP_ACCUM, OP_ACCUM, OP_VOID);
4f425a32
MH
2361 tmp = SEXT40(State.a[OP[0]]) - SEXT40(State.a[OP[1]]);
2362 if (State.ST)
2363 {
2364 if (tmp > MAX32)
2365 State.a[OP[0]] = MAX32;
2366 else if ( tmp < MIN32)
2367 State.a[OP[0]] = MIN32;
2368 else
2369 State.a[OP[0]] = tmp & MASK40;
2370 }
2371 else
2372 State.a[OP[0]] = tmp & MASK40;
87178dbd
MM
2373
2374 trace_output (OP_ACCUM);
2934d1c9
MH
2375}
2376
2377/* sub2w */
2378void
2379OP_1000 ()
2380{
4c38885c
MH
2381 int64 tmp;
2382 int32 a,b;
4c38885c 2383
87178dbd 2384 trace_input ("sub2w", OP_DREG, OP_DREG, OP_VOID);
4c38885c
MH
2385 a = (int32)((State.regs[OP[0]] << 16) | State.regs[OP[0]+1]);
2386 b = (int32)((State.regs[OP[1]] << 16) | State.regs[OP[1]+1]);
2387 tmp = a-b;
2388 State.C = (tmp & 0xffffffff00000000LL) ? 1 : 0;
2389 State.regs[OP[0]] = (tmp >> 16) & 0xffff;
2390 State.regs[OP[0]+1] = tmp & 0xffff;
87178dbd 2391 trace_output (OP_DREG);
2934d1c9
MH
2392}
2393
2394/* subac3 */
2395void
2396OP_17000000 ()
2397{
4f425a32 2398 int64 tmp;
87178dbd
MM
2399
2400 trace_input ("subac3", OP_DREG_OUTPUT, OP_DREG, OP_ACCUM);
4f425a32
MH
2401 tmp = SEXT40 ((State.regs[OP[1]] << 16) | State.regs[OP[1]+1]) - SEXT40 (State.a[OP[2]]);
2402 State.regs[OP[0]] = (tmp >> 16) & 0xffff;
2403 State.regs[OP[0]+1] = tmp & 0xffff;
87178dbd 2404 trace_output (OP_DREG);
2934d1c9
MH
2405}
2406
2407/* subac3 */
2408void
2409OP_17000002 ()
2410{
4f425a32 2411 int64 tmp;
87178dbd
MM
2412
2413 trace_input ("subac3", OP_DREG_OUTPUT, OP_ACCUM, OP_ACCUM);
4f425a32
MH
2414 tmp = SEXT40(State.a[OP[1]]) - SEXT40(State.a[OP[2]]);
2415 State.regs[OP[0]] = (tmp >> 16) & 0xffff;
2416 State.regs[OP[0]+1] = tmp & 0xffff;
87178dbd 2417 trace_output (OP_DREG);
2934d1c9
MH
2418}
2419
2420/* subac3s */
2421void
2422OP_17001000 ()
2423{
4f425a32 2424 int64 tmp;
87178dbd
MM
2425
2426 trace_input ("subac3s", OP_DREG_OUTPUT, OP_DREG, OP_ACCUM);
4f425a32
MH
2427 State.F1 = State.F0;
2428 tmp = SEXT40 ((State.regs[OP[1]] << 16) | State.regs[OP[1]+1]) - SEXT40(State.a[OP[2]]);
2429 if ( tmp > MAX32)
2430 {
2431 State.regs[OP[0]] = 0x7fff;
2432 State.regs[OP[0]+1] = 0xffff;
2433 State.F0 = 1;
2434 }
2435 else if (tmp < MIN32)
2436 {
2437 State.regs[OP[0]] = 0x8000;
2438 State.regs[OP[0]+1] = 0;
2439 State.F0 = 1;
2440 }
2441 else
2442 {
2443 State.regs[OP[0]] = (tmp >> 16) & 0xffff;
2444 State.regs[OP[0]+1] = tmp & 0xffff;
2445 State.F0 = 0;
2446 }
87178dbd 2447 trace_output (OP_DREG);
2934d1c9
MH
2448}
2449
2450/* subac3s */
2451void
2452OP_17001002 ()
2453{
4f425a32 2454 int64 tmp;
87178dbd
MM
2455
2456 trace_input ("subac3s", OP_DREG_OUTPUT, OP_ACCUM, OP_ACCUM);
4f425a32
MH
2457 State.F1 = State.F0;
2458 tmp = SEXT40(State.a[OP[1]]) - SEXT40(State.a[OP[2]]);
2459 if ( tmp > MAX32)
2460 {
2461 State.regs[OP[0]] = 0x7fff;
2462 State.regs[OP[0]+1] = 0xffff;
2463 State.F0 = 1;
2464 }
2465 else if (tmp < MIN32)
2466 {
2467 State.regs[OP[0]] = 0x8000;
2468 State.regs[OP[0]+1] = 0;
2469 State.F0 = 1;
2470 }
2471 else
2472 {
2473 State.regs[OP[0]] = (tmp >> 16) & 0xffff;
2474 State.regs[OP[0]+1] = tmp & 0xffff;
2475 State.F0 = 0;
2476 }
87178dbd 2477 trace_output (OP_DREG);
2934d1c9
MH
2478}
2479
2480/* subi */
2481void
2482OP_1 ()
2483{
4c38885c 2484 int32 tmp;
4f425a32
MH
2485 if (OP[1] == 0)
2486 OP[1] = 16;
87178dbd
MM
2487
2488 trace_input ("subi", OP_REG, OP_CONSTANT16, OP_VOID);
4c38885c
MH
2489 tmp = (int16)State.regs[OP[0]] - OP[1];
2490 State.C = (tmp & 0xffff0000) ? 1 : 0;
2491 State.regs[OP[0]] = tmp & 0xffff;
87178dbd 2492 trace_output (OP_REG);
2934d1c9
MH
2493}
2494
2495/* trap */
2496void
2497OP_5F00 ()
2498{
a5719092 2499 trace_input ("trap", OP_CONSTANT4, OP_VOID, OP_VOID);
87178dbd 2500 trace_output (OP_VOID);
2934d1c9 2501
63a91cfb 2502 switch (OP[0])
2934d1c9 2503 {
63a91cfb 2504 default:
19d44375 2505#if 0
7eebfc62 2506 (*d10v_callback->printf_filtered) (d10v_callback, "Unknown trap code %d\n", OP[0]);
63a91cfb 2507 State.exception = SIGILL;
19d44375
MM
2508#else
2509 /* Use any other traps for batch debugging. */
2510 {
2511 int i;
2512 static int first_time = 1;
2513
2514 if (first_time)
2515 {
2516 first_time = 0;
2517 (*d10v_callback->printf_filtered) (d10v_callback, "Trap # PC ");
2518 for (i = 0; i < 16; i++)
2519 (*d10v_callback->printf_filtered) (d10v_callback, " %sr%d", (i > 9) ? "" : " ", i);
2520 (*d10v_callback->printf_filtered) (d10v_callback, " a0 a1 f0 f1 c\n");
2521 }
2522
2523 (*d10v_callback->printf_filtered) (d10v_callback, "Trap %2d 0x%.4x:", (int)OP[0], (int)PC);
2524
2525 for (i = 0; i < 16; i++)
2526 (*d10v_callback->printf_filtered) (d10v_callback, " %.4x", (int) State.regs[i]);
2527
2528 for (i = 0; i < 2; i++)
2529 (*d10v_callback->printf_filtered) (d10v_callback, " %.2x%.8lx",
2530 ((int)(State.a[OP[i]] >> 32) & 0xff),
2531 ((unsigned long)State.a[OP[i]]) & 0xffffffff);
2532
2533 (*d10v_callback->printf_filtered) (d10v_callback, " %d %d %d\n",
2534 State.F0 != 0, State.F1 != 0, State.C != 0);
2535 break;
2536#endif
63a91cfb
MM
2537
2538 case 0:
2539 /* Trap 0 is used for simulating low-level I/O */
2540 {
2541 int save_errno = errno;
2542 errno = 0;
2543
2544/* Registers passed to trap 0 */
2545
65c0d7de
MA
2546#define FUNC State.regs[6] /* function number */
2547#define PARM1 State.regs[2] /* optional parm 1 */
2548#define PARM2 State.regs[3] /* optional parm 2 */
2549#define PARM3 State.regs[4] /* optional parm 3 */
2550#define PARM4 State.regs[5] /* optional parm 3 */
63a91cfb
MM
2551
2552/* Registers set by trap 0 */
2553
65c0d7de
MA
2554#define RETVAL State.regs[2] /* return value */
2555#define RETVAL_HIGH State.regs[2] /* return value */
2556#define RETVAL_LOW State.regs[3] /* return value */
2557#define RETERR State.regs[4] /* return error code */
63a91cfb
MM
2558
2559/* Turn a pointer in a register into a pointer into real memory. */
2560
2561#define MEMPTR(x) ((char *)((x) + State.imem))
2562
2563 switch (FUNC)
2564 {
2565#if !defined(__GO32__) && !defined(_WIN32)
63a91cfb
MM
2566 case SYS_fork:
2567 RETVAL = fork ();
2568 break;
63a91cfb
MM
2569 case SYS_execve:
2570 RETVAL = execve (MEMPTR (PARM1), (char **) MEMPTR (PARM2),
2571 (char **)MEMPTR (PARM3));
2572 break;
63a91cfb
MM
2573 case SYS_execv:
2574 RETVAL = execve (MEMPTR (PARM1), (char **) MEMPTR (PARM2), NULL);
2575 break;
63a91cfb
MM
2576 case SYS_pipe:
2577 {
2578 reg_t buf;
2579 int host_fd[2];
2580
2581 buf = PARM1;
2582 RETVAL = pipe (host_fd);
2583 SW (buf, host_fd[0]);
2584 buf += sizeof(uint16);
2585 SW (buf, host_fd[1]);
2586 }
2587 break;
63a91cfb
MM
2588 case SYS_wait:
2589 {
2590 int status;
2591
2592 RETVAL = wait (&status);
2593 SW (PARM1, status);
2594 }
2595 break;
2596#endif
63a91cfb
MM
2597 case SYS_read:
2598 RETVAL = d10v_callback->read (d10v_callback, PARM1, MEMPTR (PARM2),
2599 PARM3);
2600 break;
63a91cfb
MM
2601 case SYS_write:
2602 if (PARM1 == 1)
2603 RETVAL = (int)d10v_callback->write_stdout (d10v_callback,
2604 MEMPTR (PARM2), PARM3);
2605 else
2606 RETVAL = (int)d10v_callback->write (d10v_callback, PARM1,
2607 MEMPTR (PARM2), PARM3);
2608 break;
63a91cfb 2609 case SYS_lseek:
65c0d7de
MA
2610 {
2611 unsigned long ret = d10v_callback->lseek (d10v_callback, PARM1,
2612 (((unsigned long)PARM2) << 16) || (unsigned long)PARM3,
2613 PARM4);
2614 RETVAL_HIGH = ret >> 16;
2615 RETVAL_LOW = ret & 0xffff;
2616 }
63a91cfb 2617 break;
63a91cfb
MM
2618 case SYS_close:
2619 RETVAL = d10v_callback->close (d10v_callback, PARM1);
2620 break;
63a91cfb
MM
2621 case SYS_open:
2622 RETVAL = d10v_callback->open (d10v_callback, MEMPTR (PARM1), PARM2);
2623 break;
63a91cfb 2624 case SYS_exit:
a49a15ad 2625 State.exception = SIG_D10V_EXIT;
63a91cfb 2626 break;
63a91cfb 2627
8719be26 2628 case SYS_stat:
63a91cfb
MM
2629 /* stat system call */
2630 {
2631 struct stat host_stat;
2632 reg_t buf;
2633
2634 RETVAL = stat (MEMPTR (PARM1), &host_stat);
2635
2636 buf = PARM2;
2637
2638 /* The hard-coded offsets and sizes were determined by using
2639 * the D10V compiler on a test program that used struct stat.
2640 */
2641 SW (buf, host_stat.st_dev);
2642 SW (buf+2, host_stat.st_ino);
2643 SW (buf+4, host_stat.st_mode);
2644 SW (buf+6, host_stat.st_nlink);
2645 SW (buf+8, host_stat.st_uid);
2646 SW (buf+10, host_stat.st_gid);
2647 SW (buf+12, host_stat.st_rdev);
2648 SLW (buf+16, host_stat.st_size);
2649 SLW (buf+20, host_stat.st_atime);
2650 SLW (buf+28, host_stat.st_mtime);
2651 SLW (buf+36, host_stat.st_ctime);
2652 }
2653 break;
63a91cfb 2654
63a91cfb
MM
2655 case SYS_chown:
2656 RETVAL = chown (MEMPTR (PARM1), PARM2, PARM3);
2657 break;
63a91cfb
MM
2658 case SYS_chmod:
2659 RETVAL = chmod (MEMPTR (PARM1), PARM2);
2660 break;
63a91cfb
MM
2661 case SYS_utime:
2662 /* Cast the second argument to void *, to avoid type mismatch
2663 if a prototype is present. */
2664 RETVAL = utime (MEMPTR (PARM1), (void *) MEMPTR (PARM2));
2665 break;
63a91cfb
MM
2666 default:
2667 abort ();
2668 }
65c0d7de 2669 RETERR = d10v_callback->get_errno(d10v_callback);
63a91cfb
MM
2670 break;
2671 }
2672
2673 case 1:
2674 /* Trap 1 prints a string */
2675 {
2676 char *fstr = State.regs[2] + State.imem;
2677 fputs (fstr, stdout);
2678 break;
2679 }
2680
2681 case 2:
2682 /* Trap 2 calls printf */
2683 {
2684 char *fstr = State.regs[2] + State.imem;
7eebfc62
MM
2685 (*d10v_callback->printf_filtered) (d10v_callback, fstr,
2686 (int16)State.regs[3],
2687 (int16)State.regs[4],
2688 (int16)State.regs[5]);
63a91cfb
MM
2689 break;
2690 }
2691
2692 case 3:
2693 /* Trap 3 writes a character */
2694 putchar (State.regs[2]);
2695 break;
19d44375 2696 }
2934d1c9
MH
2697 }
2698}
2699
2700/* tst0i */
2701void
2702OP_7000000 ()
2703{
87178dbd 2704 trace_input ("tst0i", OP_REG, OP_CONSTANT16, OP_VOID);
4c38885c 2705 State.F1 = State.F0;
4f425a32 2706 State.F0 = (State.regs[OP[0]] & OP[1]) ? 1 : 0;
87178dbd 2707 trace_output (OP_FLAG);
2934d1c9
MH
2708}
2709
2710/* tst1i */
2711void
2712OP_F000000 ()
2713{
87178dbd 2714 trace_input ("tst1i", OP_REG, OP_CONSTANT16, OP_VOID);
4c38885c 2715 State.F1 = State.F0;
4f425a32 2716 State.F0 = (~(State.regs[OP[0]]) & OP[1]) ? 1 : 0;
87178dbd 2717 trace_output (OP_FLAG);
2934d1c9
MH
2718}
2719
2720/* wait */
2721void
2722OP_5F80 ()
2723{
87178dbd 2724 trace_input ("wait", OP_VOID, OP_VOID, OP_VOID);
4c38885c 2725 State.IE = 1;
87178dbd 2726 trace_output (OP_VOID);
2934d1c9
MH
2727}
2728
2729/* xor */
2730void
2731OP_A00 ()
2732{
87178dbd 2733 trace_input ("xor", OP_REG, OP_REG, OP_VOID);
4c38885c 2734 State.regs[OP[0]] ^= State.regs[OP[1]];
87178dbd 2735 trace_output (OP_REG);
2934d1c9
MH
2736}
2737
2738/* xor3 */
2739void
2740OP_5000000 ()
2741{
87178dbd 2742 trace_input ("xor3", OP_REG_OUTPUT, OP_REG, OP_CONSTANT16);
4c38885c 2743 State.regs[OP[0]] = State.regs[OP[1]] ^ OP[2];
87178dbd 2744 trace_output (OP_REG);
2934d1c9
MH
2745}
2746