msp430-sim.c revision 1.1.1.5
1/* Simulator for TI MSP430 and MSP430X
2
3   Copyright (C) 2013-2017 Free Software Foundation, Inc.
4   Contributed by Red Hat.
5   Based on sim/bfin/bfin-sim.c which was contributed by Analog Devices, Inc.
6
7   This file is part of simulators.
8
9   This program is free software; you can redistribute it and/or modify
10   it under the terms of the GNU General Public License as published by
11   the Free Software Foundation; either version 3 of the License, or
12   (at your option) any later version.
13
14   This program is distributed in the hope that it will be useful,
15   but WITHOUT ANY WARRANTY; without even the implied warranty of
16   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17   GNU General Public License for more details.
18
19   You should have received a copy of the GNU General Public License
20   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
21
22#include "config.h"
23#include <stdio.h>
24#include <stdlib.h>
25#include <string.h>
26#include <inttypes.h>
27#include <unistd.h>
28#include <assert.h>
29#include "opcode/msp430-decode.h"
30#include "sim-main.h"
31#include "sim-syscall.h"
32#include "targ-vals.h"
33
34static sim_cia
35msp430_pc_fetch (SIM_CPU *cpu)
36{
37  return cpu->state.regs[0];
38}
39
40static void
41msp430_pc_store (SIM_CPU *cpu, sim_cia newpc)
42{
43  cpu->state.regs[0] = newpc;
44}
45
46static int
47msp430_reg_fetch (SIM_CPU *cpu, int regno, unsigned char *buf, int len)
48{
49  if (0 <= regno && regno < 16)
50    {
51      if (len == 2)
52	{
53	  int val = cpu->state.regs[regno];
54	  buf[0] = val & 0xff;
55	  buf[1] = (val >> 8) & 0xff;
56	  return 0;
57	}
58      else if (len == 4)
59	{
60	  int val = cpu->state.regs[regno];
61	  buf[0] = val & 0xff;
62	  buf[1] = (val >> 8) & 0xff;
63	  buf[2] = (val >> 16) & 0x0f; /* Registers are only 20 bits wide.  */
64	  buf[3] = 0;
65	  return 0;
66	}
67      else
68	return -1;
69    }
70  else
71    return -1;
72}
73
74static int
75msp430_reg_store (SIM_CPU *cpu, int regno, unsigned char *buf, int len)
76{
77  if (0 <= regno && regno < 16)
78    {
79      if (len == 2)
80	{
81	  cpu->state.regs[regno] = (buf[1] << 8) | buf[0];
82	  return len;
83	}
84
85      if (len == 4)
86	{
87	  cpu->state.regs[regno] = ((buf[2] << 16) & 0xf0000)
88				   | (buf[1] << 8) | buf[0];
89	  return len;
90	}
91    }
92
93  return -1;
94}
95
96static inline void
97msp430_initialize_cpu (SIM_DESC sd, SIM_CPU *cpu)
98{
99  memset (&cpu->state, 0, sizeof (cpu->state));
100}
101
102SIM_DESC
103sim_open (SIM_OPEN_KIND kind,
104	  struct host_callback_struct *callback,
105	  struct bfd *abfd,
106	  char * const *argv)
107{
108  SIM_DESC sd = sim_state_alloc (kind, callback);
109  char c;
110
111  /* Initialise the simulator.  */
112
113  if (sim_cpu_alloc_all (sd, 1, /*cgen_cpu_max_extra_bytes ()*/0) != SIM_RC_OK)
114    {
115      sim_state_free (sd);
116      return 0;
117    }
118
119  if (sim_pre_argv_init (sd, argv[0]) != SIM_RC_OK)
120    {
121      sim_state_free (sd);
122      return 0;
123    }
124
125  if (sim_parse_args (sd, argv) != SIM_RC_OK)
126    {
127      sim_state_free (sd);
128      return 0;
129    }
130
131  CPU_PC_FETCH (MSP430_CPU (sd)) = msp430_pc_fetch;
132  CPU_PC_STORE (MSP430_CPU (sd)) = msp430_pc_store;
133  CPU_REG_FETCH (MSP430_CPU (sd)) = msp430_reg_fetch;
134  CPU_REG_STORE (MSP430_CPU (sd)) = msp430_reg_store;
135
136  /* Allocate memory if none specified by user.
137     Note - these values match the memory regions in the libgloss/msp430/msp430[xl]-sim.ld scripts.  */
138  if (sim_core_read_buffer (sd, MSP430_CPU (sd), read_map, &c, 0x2, 1) == 0)
139    sim_do_commandf (sd, "memory-region 0,0x20"); /* Needed by the GDB testsuite.  */
140  if (sim_core_read_buffer (sd, MSP430_CPU (sd), read_map, &c, 0x500, 1) == 0)
141    sim_do_commandf (sd, "memory-region 0x500,0xfa00");  /* RAM and/or ROM */
142  if (sim_core_read_buffer (sd, MSP430_CPU (sd), read_map, &c, 0xfffe, 1) == 0)
143    sim_do_commandf (sd, "memory-region 0xffc0,0x40"); /* VECTORS.  */
144  if (sim_core_read_buffer (sd, MSP430_CPU (sd), read_map, &c, 0x10000, 1) == 0)
145    sim_do_commandf (sd, "memory-region 0x10000,0x80000"); /* HIGH FLASH RAM.  */
146  if (sim_core_read_buffer (sd, MSP430_CPU (sd), read_map, &c, 0x90000, 1) == 0)
147    sim_do_commandf (sd, "memory-region 0x90000,0x70000"); /* HIGH ROM.  */
148
149  /* Check for/establish the a reference program image.  */
150  if (sim_analyze_program (sd,
151			   (STATE_PROG_ARGV (sd) != NULL
152			    ? *STATE_PROG_ARGV (sd)
153			    : NULL), abfd) != SIM_RC_OK)
154    {
155      sim_state_free (sd);
156      return 0;
157    }
158
159  /* Establish any remaining configuration options.  */
160  if (sim_config (sd) != SIM_RC_OK)
161    {
162      sim_state_free (sd);
163      return 0;
164    }
165
166  if (sim_post_argv_init (sd) != SIM_RC_OK)
167    {
168      sim_state_free (sd);
169      return 0;
170    }
171
172  /* CPU specific initialization.  */
173  assert (MAX_NR_PROCESSORS == 1);
174  msp430_initialize_cpu (sd, MSP430_CPU (sd));
175
176  MSP430_CPU (sd)->state.cio_breakpoint = trace_sym_value (sd, "C$$IO$$");
177  MSP430_CPU (sd)->state.cio_buffer = trace_sym_value (sd, "__CIOBUF__");
178  if (MSP430_CPU (sd)->state.cio_buffer == -1)
179    MSP430_CPU (sd)->state.cio_buffer = trace_sym_value (sd, "_CIOBUF_");
180
181  return sd;
182}
183
184SIM_RC
185sim_create_inferior (SIM_DESC sd,
186		     struct bfd *abfd,
187		     char * const *argv,
188		     char * const *env)
189{
190  unsigned char resetv[2];
191  int c;
192  int new_pc;
193
194  /* Set the PC to the default reset vector if available.  */
195  c = sim_core_read_buffer (sd, MSP430_CPU (sd), read_map, resetv, 0xfffe, 2);
196  new_pc = resetv[0] + 256 * resetv[1];
197
198  /* If the reset vector isn't initialized, then use the ELF entry.  */
199  if (abfd != NULL && !new_pc)
200    new_pc = bfd_get_start_address (abfd);
201
202  sim_pc_set (MSP430_CPU (sd), new_pc);
203  msp430_pc_store (MSP430_CPU (sd), new_pc);
204
205  return SIM_RC_OK;
206}
207
208typedef struct
209{
210  SIM_DESC sd;
211  int gb_addr;
212} Get_Byte_Local_Data;
213
214static int
215msp430_getbyte (void *vld)
216{
217  Get_Byte_Local_Data *ld = (Get_Byte_Local_Data *)vld;
218  char buf[1];
219  SIM_DESC sd = ld->sd;
220
221  sim_core_read_buffer (sd, MSP430_CPU (sd), read_map, buf, ld->gb_addr, 1);
222  ld->gb_addr ++;
223  return buf[0];
224}
225
226#define REG(N) MSP430_CPU (sd)->state.regs[(N)]
227#define PC REG(MSR_PC)
228#define SP REG(MSR_SP)
229#define SR REG(MSR_SR)
230
231static const char *
232register_names[] =
233{
234  "PC", "SP", "SR", "CG", "R4", "R5", "R6", "R7", "R8",
235  "R9", "R10", "R11", "R12", "R13", "R14", "R15"
236};
237
238static void
239trace_reg_put (SIM_DESC sd, int n, unsigned int v)
240{
241  TRACE_REGISTER (MSP430_CPU (sd), "PUT: %#x -> %s", v, register_names[n]);
242  REG (n) = v;
243}
244
245static unsigned int
246trace_reg_get (SIM_DESC sd, int n)
247{
248  TRACE_REGISTER (MSP430_CPU (sd), "GET: %s -> %#x", register_names[n], REG (n));
249  return REG (n);
250}
251
252#define REG_PUT(N,V) trace_reg_put (sd, N, V)
253#define REG_GET(N)   trace_reg_get (sd, N)
254
255/* Hardware multiply (and accumulate) support.  */
256
257static unsigned int
258zero_ext (unsigned int v, unsigned int bits)
259{
260  v &= ((1 << bits) - 1);
261  return v;
262}
263
264static signed long long
265sign_ext (signed long long v, unsigned int bits)
266{
267  signed long long sb = 1LL << (bits-1);	/* Sign bit.  */
268  signed long long mb = (1LL << (bits-1)) - 1LL; /* Mantissa bits.  */
269
270  if (v & sb)
271    v = v | ~mb;
272  else
273    v = v & mb;
274  return v;
275}
276
277static int
278get_op (SIM_DESC sd, MSP430_Opcode_Decoded *opc, int n)
279{
280  MSP430_Opcode_Operand *op = opc->op + n;
281  int rv;
282  int addr;
283  unsigned char buf[4];
284  int incval = 0;
285
286  switch (op->type)
287    {
288    case MSP430_Operand_Immediate:
289      rv =  op->addend;
290      break;
291    case MSP430_Operand_Register:
292      rv = REG_GET (op->reg);
293      break;
294    case MSP430_Operand_Indirect:
295    case MSP430_Operand_Indirect_Postinc:
296      addr = op->addend;
297      if (op->reg != MSR_None)
298	{
299	  int reg = REG_GET (op->reg);
300	  int sign = opc->ofs_430x ? 20 : 16;
301
302	  /* Index values are signed.  */
303	  if (addr & (1 << (sign - 1)))
304	    addr |= -(1 << sign);
305
306	  addr += reg;
307
308	  /* For MSP430 instructions the sum is limited to 16 bits if the
309	     address in the index register is less than 64k even if we are
310	     running on an MSP430X CPU.  This is for MSP430 compatibility.  */
311	  if (reg < 0x10000 && ! opc->ofs_430x)
312	    {
313	      if (addr >= 0x10000)
314		fprintf (stderr, " XXX WRAPPING ADDRESS %x on read\n", addr);
315
316	      addr &= 0xffff;
317	    }
318	}
319      addr &= 0xfffff;
320      switch (opc->size)
321	{
322	case 8:
323	  sim_core_read_buffer (sd, MSP430_CPU (sd), read_map, buf, addr, 1);
324	  rv = buf[0];
325	  break;
326	case 16:
327	  sim_core_read_buffer (sd, MSP430_CPU (sd), read_map, buf, addr, 2);
328	  rv = buf[0] | (buf[1] << 8);
329	  break;
330	case 20:
331	case 32:
332	  sim_core_read_buffer (sd, MSP430_CPU (sd), read_map, buf, addr, 4);
333	  rv = buf[0] | (buf[1] << 8) | (buf[2] << 16) | (buf[3] << 24);
334	  break;
335	default:
336	  assert (! opc->size);
337	  break;
338	}
339#if 0
340      /* Hack - MSP430X5438 serial port status register.  */
341      if (addr == 0x5dd)
342	rv = 2;
343#endif
344      if ((addr >= 0x130 && addr <= 0x15B)
345	  || (addr >= 0x4C0 && addr <= 0x4EB))
346	{
347	  switch (addr)
348	    {
349	    case 0x4CA:
350	    case 0x13A:
351	      switch (HWMULT (sd, hwmult_type))
352		{
353		case UNSIGN_MAC_32:
354		case UNSIGN_32:
355		  rv = zero_ext (HWMULT (sd, hwmult_result), 16);
356		  break;
357		case SIGN_MAC_32:
358		case SIGN_32:
359		  rv = sign_ext (HWMULT (sd, hwmult_signed_result), 16);
360		  break;
361		}
362	      break;
363
364	    case 0x4CC:
365	    case 0x13C:
366	      switch (HWMULT (sd, hwmult_type))
367		{
368		case UNSIGN_MAC_32:
369		case UNSIGN_32:
370		  rv = zero_ext (HWMULT (sd, hwmult_result) >> 16, 16);
371		  break;
372
373		case SIGN_MAC_32:
374		case SIGN_32:
375		  rv = sign_ext (HWMULT (sd, hwmult_signed_result) >> 16, 16);
376		  break;
377		}
378	      break;
379
380	    case 0x4CE:
381	    case 0x13E:
382	      switch (HWMULT (sd, hwmult_type))
383		{
384		case UNSIGN_32:
385		  rv = 0;
386		  break;
387		case SIGN_32:
388		  rv = HWMULT (sd, hwmult_signed_result) < 0 ? -1 : 0;
389		  break;
390		case UNSIGN_MAC_32:
391		  rv = 0; /* FIXME: Should be carry of last accumulate.  */
392		  break;
393		case SIGN_MAC_32:
394		  rv = HWMULT (sd, hwmult_signed_accumulator) < 0 ? -1 : 0;
395		  break;
396		}
397	      break;
398
399	    case 0x4E4:
400	    case 0x154:
401	      rv = zero_ext (HWMULT (sd, hw32mult_result), 16);
402	      break;
403
404	    case 0x4E6:
405	    case 0x156:
406	      rv = zero_ext (HWMULT (sd, hw32mult_result) >> 16, 16);
407	      break;
408
409	    case 0x4E8:
410	    case 0x158:
411	      rv = zero_ext (HWMULT (sd, hw32mult_result) >> 32, 16);
412	      break;
413
414	    case 0x4EA:
415	    case 0x15A:
416	      switch (HWMULT (sd, hw32mult_type))
417		{
418		case UNSIGN_64: rv = zero_ext (HWMULT (sd, hw32mult_result) >> 48, 16); break;
419		case   SIGN_64: rv = sign_ext (HWMULT (sd, hw32mult_result) >> 48, 16); break;
420		}
421	      break;
422
423	    default:
424	      fprintf (stderr, "unimplemented HW MULT read from %x!\n", addr);
425	      break;
426	    }
427	}
428
429      TRACE_MEMORY (MSP430_CPU (sd), "GET: [%#x].%d -> %#x", addr, opc->size,
430		    rv);
431      break;
432
433    default:
434      fprintf (stderr, "invalid operand %d type %d\n", n, op->type);
435      abort ();
436    }
437
438  switch (opc->size)
439    {
440    case 8:
441      rv &= 0xff;
442      incval = 1;
443      break;
444    case 16:
445      rv &= 0xffff;
446      incval = 2;
447      break;
448    case 20:
449      rv &= 0xfffff;
450      incval = 4;
451      break;
452    case 32:
453      rv &= 0xffffffff;
454      incval = 4;
455      break;
456    }
457
458  if (op->type == MSP430_Operand_Indirect_Postinc)
459    REG_PUT (op->reg, REG_GET (op->reg) + incval);
460
461  return rv;
462}
463
464static int
465put_op (SIM_DESC sd, MSP430_Opcode_Decoded *opc, int n, int val)
466{
467  MSP430_Opcode_Operand *op = opc->op + n;
468  int rv;
469  int addr;
470  unsigned char buf[4];
471  int incval = 0;
472
473  switch (opc->size)
474    {
475    case 8:
476      val &= 0xff;
477      break;
478    case 16:
479      val &= 0xffff;
480      break;
481    case 20:
482      val &= 0xfffff;
483      break;
484    case 32:
485      val &= 0xffffffff;
486      break;
487    }
488
489  switch (op->type)
490    {
491    case MSP430_Operand_Register:
492      REG (op->reg) = val;
493      REG_PUT (op->reg, val);
494      break;
495    case MSP430_Operand_Indirect:
496    case MSP430_Operand_Indirect_Postinc:
497      addr = op->addend;
498      if (op->reg != MSR_None)
499	{
500	  int reg = REG_GET (op->reg);
501	  int sign = opc->ofs_430x ? 20 : 16;
502
503	  /* Index values are signed.  */
504	  if (addr & (1 << (sign - 1)))
505	    addr |= -(1 << sign);
506
507	  addr += reg;
508
509	  /* For MSP430 instructions the sum is limited to 16 bits if the
510	     address in the index register is less than 64k even if we are
511	     running on an MSP430X CPU.  This is for MSP430 compatibility.  */
512	  if (reg < 0x10000 && ! opc->ofs_430x)
513	    {
514	      if (addr >= 0x10000)
515		fprintf (stderr, " XXX WRAPPING ADDRESS %x on write\n", addr);
516
517	      addr &= 0xffff;
518	    }
519	}
520      addr &= 0xfffff;
521
522      TRACE_MEMORY (MSP430_CPU (sd), "PUT: [%#x].%d <- %#x", addr, opc->size,
523		    val);
524#if 0
525      /* Hack - MSP430X5438 serial port transmit register.  */
526      if (addr == 0x5ce)
527	putchar (val);
528#endif
529      if ((addr >= 0x130 && addr <= 0x15B)
530	  || (addr >= 0x4C0 && addr <= 0x4EB))
531	{
532	  signed int a,b;
533
534	  /* Hardware Multiply emulation.  */
535	  assert (opc->size == 16);
536
537	  switch (addr)
538	    {
539	    case 0x4C0:
540	    case 0x130:
541	      HWMULT (sd, hwmult_op1) = val;
542	      HWMULT (sd, hwmult_type) = UNSIGN_32;
543	      break;
544
545	    case 0x4C2:
546	    case 0x132:
547	      HWMULT (sd, hwmult_op1) = val;
548	      HWMULT (sd, hwmult_type) = SIGN_32;
549	      break;
550
551	    case 0x4C4:
552	    case 0x134:
553	      HWMULT (sd, hwmult_op1) = val;
554	      HWMULT (sd, hwmult_type) = UNSIGN_MAC_32;
555	      break;
556
557	    case 0x4C6:
558	    case 0x136:
559	      HWMULT (sd, hwmult_op1) = val;
560	      HWMULT (sd, hwmult_type) = SIGN_MAC_32;
561	      break;
562
563	    case 0x4C8:
564	    case 0x138:
565	      HWMULT (sd, hwmult_op2) = val;
566	      switch (HWMULT (sd, hwmult_type))
567		{
568		case UNSIGN_32:
569		  HWMULT (sd, hwmult_result) = HWMULT (sd, hwmult_op1) * HWMULT (sd, hwmult_op2);
570		  HWMULT (sd, hwmult_signed_result) = (signed) HWMULT (sd, hwmult_result);
571		  HWMULT (sd, hwmult_accumulator) = HWMULT (sd, hwmult_signed_accumulator) = 0;
572		  break;
573
574		case SIGN_32:
575		  a = sign_ext (HWMULT (sd, hwmult_op1), 16);
576		  b = sign_ext (HWMULT (sd, hwmult_op2), 16);
577		  HWMULT (sd, hwmult_signed_result) = a * b;
578		  HWMULT (sd, hwmult_result) = (unsigned) HWMULT (sd, hwmult_signed_result);
579		  HWMULT (sd, hwmult_accumulator) = HWMULT (sd, hwmult_signed_accumulator) = 0;
580		  break;
581
582		case UNSIGN_MAC_32:
583		  HWMULT (sd, hwmult_accumulator) += HWMULT (sd, hwmult_op1) * HWMULT (sd, hwmult_op2);
584		  HWMULT (sd, hwmult_signed_accumulator) += HWMULT (sd, hwmult_op1) * HWMULT (sd, hwmult_op2);
585		  HWMULT (sd, hwmult_result) = HWMULT (sd, hwmult_accumulator);
586		  HWMULT (sd, hwmult_signed_result) = HWMULT (sd, hwmult_signed_accumulator);
587		  break;
588
589		case SIGN_MAC_32:
590		  a = sign_ext (HWMULT (sd, hwmult_op1), 16);
591		  b = sign_ext (HWMULT (sd, hwmult_op2), 16);
592		  HWMULT (sd, hwmult_accumulator) += a * b;
593		  HWMULT (sd, hwmult_signed_accumulator) += a * b;
594		  HWMULT (sd, hwmult_result) = HWMULT (sd, hwmult_accumulator);
595		  HWMULT (sd, hwmult_signed_result) = HWMULT (sd, hwmult_signed_accumulator);
596		  break;
597		}
598	      break;
599
600	    case 0x4CA:
601	    case 0x13A:
602	      /* Copy into LOW result...  */
603	      switch (HWMULT (sd, hwmult_type))
604		{
605		case UNSIGN_MAC_32:
606		case UNSIGN_32:
607		  HWMULT (sd, hwmult_accumulator) = HWMULT (sd, hwmult_result) = zero_ext (val, 16);
608		  HWMULT (sd, hwmult_signed_accumulator) = sign_ext (val, 16);
609		  break;
610		case SIGN_MAC_32:
611		case SIGN_32:
612		  HWMULT (sd, hwmult_signed_accumulator) = HWMULT (sd, hwmult_result) = sign_ext (val, 16);
613		  HWMULT (sd, hwmult_accumulator) = zero_ext (val, 16);
614		  break;
615		}
616	      break;
617
618	    case 0x4D0:
619	    case 0x140:
620	      HWMULT (sd, hw32mult_op1) = val;
621	      HWMULT (sd, hw32mult_type) = UNSIGN_64;
622	      break;
623
624	    case 0x4D2:
625	    case 0x142:
626	      HWMULT (sd, hw32mult_op1) = (HWMULT (sd, hw32mult_op1) & 0xFFFF) | (val << 16);
627	      break;
628
629	    case 0x4D4:
630	    case 0x144:
631	      HWMULT (sd, hw32mult_op1) = val;
632	      HWMULT (sd, hw32mult_type) = SIGN_64;
633	      break;
634
635	    case 0x4D6:
636	    case 0x146:
637	      HWMULT (sd, hw32mult_op1) = (HWMULT (sd, hw32mult_op1) & 0xFFFF) | (val << 16);
638	      break;
639
640	    case 0x4E0:
641	    case 0x150:
642	      HWMULT (sd, hw32mult_op2) = val;
643	      break;
644
645	    case 0x4E2:
646	    case 0x152:
647	      HWMULT (sd, hw32mult_op2) = (HWMULT (sd, hw32mult_op2) & 0xFFFF) | (val << 16);
648	      switch (HWMULT (sd, hw32mult_type))
649		{
650		case UNSIGN_64:
651		  HWMULT (sd, hw32mult_result) = HWMULT (sd, hw32mult_op1) * HWMULT (sd, hw32mult_op2);
652		  break;
653		case SIGN_64:
654		  HWMULT (sd, hw32mult_result) = sign_ext (HWMULT (sd, hw32mult_op1), 32)
655		    * sign_ext (HWMULT (sd, hw32mult_op2), 32);
656		  break;
657		}
658	      break;
659
660	    default:
661	      fprintf (stderr, "unimplemented HW MULT write to %x!\n", addr);
662	      break;
663	    }
664	}
665
666      switch (opc->size)
667	{
668	case 8:
669	  buf[0] = val;
670	  sim_core_write_buffer (sd, MSP430_CPU (sd), write_map, buf, addr, 1);
671	  break;
672	case 16:
673	  buf[0] = val;
674	  buf[1] = val >> 8;
675	  sim_core_write_buffer (sd, MSP430_CPU (sd), write_map, buf, addr, 2);
676	  break;
677	case 20:
678	case 32:
679	  buf[0] = val;
680	  buf[1] = val >> 8;
681	  buf[2] = val >> 16;
682	  buf[3] = val >> 24;
683	  sim_core_write_buffer (sd, MSP430_CPU (sd), write_map, buf, addr, 4);
684	  break;
685	default:
686	  assert (! opc->size);
687	  break;
688	}
689      break;
690    default:
691      fprintf (stderr, "invalid operand %d type %d\n", n, op->type);
692      abort ();
693    }
694
695  switch (opc->size)
696    {
697    case 8:
698      rv &= 0xff;
699      incval = 1;
700      break;
701    case 16:
702      rv &= 0xffff;
703      incval = 2;
704      break;
705    case 20:
706      rv &= 0xfffff;
707      incval = 4;
708      break;
709    case 32:
710      rv &= 0xffffffff;
711      incval = 4;
712      break;
713    }
714
715  if (op->type == MSP430_Operand_Indirect_Postinc)
716    {
717      int new_val = REG_GET (op->reg) + incval;
718      /* SP is always word-aligned.  */
719      if (op->reg == MSR_SP && (new_val & 1))
720	new_val ++;
721      REG_PUT (op->reg, new_val);
722    }
723
724  return rv;
725}
726
727static void
728mem_put_val (SIM_DESC sd, int addr, int val, int bits)
729{
730  MSP430_Opcode_Decoded opc;
731
732  opc.size = bits;
733  opc.op[0].type = MSP430_Operand_Indirect;
734  opc.op[0].addend = addr;
735  opc.op[0].reg = MSR_None;
736  put_op (sd, &opc, 0, val);
737}
738
739static int
740mem_get_val (SIM_DESC sd, int addr, int bits)
741{
742  MSP430_Opcode_Decoded opc;
743
744  opc.size = bits;
745  opc.op[0].type = MSP430_Operand_Indirect;
746  opc.op[0].addend = addr;
747  opc.op[0].reg = MSR_None;
748  return get_op (sd, &opc, 0);
749}
750
751#define CIO_OPEN    (0xF0)
752#define CIO_CLOSE   (0xF1)
753#define CIO_READ    (0xF2)
754#define CIO_WRITE   (0xF3)
755#define CIO_LSEEK   (0xF4)
756#define CIO_UNLINK  (0xF5)
757#define CIO_GETENV  (0xF6)
758#define CIO_RENAME  (0xF7)
759#define CIO_GETTIME (0xF8)
760#define CIO_GETCLK  (0xF9)
761#define CIO_SYNC    (0xFF)
762
763#define CIO_I(n) (parms[(n)] + parms[(n)+1] * 256)
764#define CIO_L(n) (parms[(n)] + parms[(n)+1] * 256 \
765		  + parms[(n)+2] * 65536 + parms[(n)+3] * 16777216)
766
767static void
768msp430_cio (SIM_DESC sd)
769{
770  /* A block of data at __CIOBUF__ describes the I/O operation to
771     perform.  */
772
773  unsigned char raw_parms[13];
774  unsigned char parms[8];
775  long length;
776  int command;
777  unsigned char buffer[512];
778  long ret_buflen = 0;
779  long fd, addr, len, rv;
780
781  sim_core_read_buffer (sd, MSP430_CPU (sd), 0, parms,
782			MSP430_CPU (sd)->state.cio_buffer, 5);
783  length = CIO_I (0);
784  command = parms[2];
785
786  sim_core_read_buffer (sd, MSP430_CPU (sd), 0, parms,
787			MSP430_CPU (sd)->state.cio_buffer + 3, 8);
788
789  sim_core_read_buffer (sd, MSP430_CPU (sd), 0, buffer,
790			MSP430_CPU (sd)->state.cio_buffer + 11, length);
791
792  switch (command)
793    {
794    case CIO_WRITE:
795      fd = CIO_I (0);
796      len = CIO_I (2);
797
798      rv = write (fd, buffer, len);
799      parms[0] = rv & 0xff;
800      parms[1] = rv >> 8;
801
802      break;
803    }
804
805  sim_core_write_buffer (sd, MSP430_CPU (sd), 0, parms,
806			 MSP430_CPU (sd)->state.cio_buffer + 4, 8);
807  if (ret_buflen)
808    sim_core_write_buffer (sd, MSP430_CPU (sd), 0, buffer,
809			   MSP430_CPU (sd)->state.cio_buffer + 12, ret_buflen);
810}
811
812#define SRC     get_op (sd, opcode, 1)
813#define DSRC    get_op (sd, opcode, 0)
814#define DEST(V) put_op (sd, opcode, 0, (V))
815
816#define DO_ALU(OP,SOP,MORE)						\
817  {									\
818    int s1 = DSRC;							\
819    int s2 = SRC;							\
820    int result = s1 OP s2 MORE;						\
821    TRACE_ALU (MSP430_CPU (sd), "ALU: %#x %s %#x %s = %#x", s1, SOP,	\
822	       s2, #MORE, result); \
823    DEST (result);							\
824  }
825
826#define SIGN   (1 << (opcode->size - 1))
827#define POS(x) (((x) & SIGN) ? 0 : 1)
828#define NEG(x) (((x) & SIGN) ? 1 : 0)
829
830#define SX(v) sign_ext (v, opcode->size)
831#define ZX(v) zero_ext (v, opcode->size)
832
833static char *
834flags2string (int f)
835{
836  static char buf[2][6];
837  static int bi = 0;
838  char *bp = buf[bi];
839
840  bi = (bi + 1) % 2;
841
842  bp[0] = f & MSP430_FLAG_V ? 'V' : '-';
843  bp[1] = f & MSP430_FLAG_N ? 'N' : '-';
844  bp[2] = f & MSP430_FLAG_Z ? 'Z' : '-';
845  bp[3] = f & MSP430_FLAG_C ? 'C' : '-';
846  bp[4] = 0;
847  return bp;
848}
849
850/* Random number that won't show up in our usual logic.  */
851#define MAGIC_OVERFLOW 0x55000F
852
853static void
854do_flags (SIM_DESC sd,
855	  MSP430_Opcode_Decoded *opcode,
856	  int vnz_val, /* Signed result.  */
857	  int carry,
858	  int overflow)
859{
860  int f = SR;
861  int new_f = 0;
862  int signbit = 1 << (opcode->size - 1);
863
864  f &= ~opcode->flags_0;
865  f &= ~opcode->flags_set;
866  f |= opcode->flags_1;
867
868  if (vnz_val & signbit)
869    new_f |= MSP430_FLAG_N;
870  if (! (vnz_val & ((signbit << 1) - 1)))
871    new_f |= MSP430_FLAG_Z;
872  if (overflow == MAGIC_OVERFLOW)
873    {
874      if (vnz_val != SX (vnz_val))
875	new_f |= MSP430_FLAG_V;
876    }
877  else
878    if (overflow)
879      new_f |= MSP430_FLAG_V;
880  if (carry)
881    new_f |= MSP430_FLAG_C;
882
883  new_f = f | (new_f & opcode->flags_set);
884  if (SR != new_f)
885    TRACE_ALU (MSP430_CPU (sd), "FLAGS: %s -> %s", flags2string (SR),
886	       flags2string (new_f));
887  else
888    TRACE_ALU (MSP430_CPU (sd), "FLAGS: %s", flags2string (new_f));
889  SR = new_f;
890}
891
892#define FLAGS(vnz,c)    do_flags (sd, opcode, vnz, c, MAGIC_OVERFLOW)
893#define FLAGSV(vnz,c,v) do_flags (sd, opcode, vnz, c, v)
894
895/* These two assume unsigned 16-bit (four digit) words.
896   Mask off unwanted bits for byte operations.  */
897
898static int
899bcd_to_binary (int v)
900{
901  int r = (  ((v >>  0) & 0xf) * 1
902	   + ((v >>  4) & 0xf) * 10
903	   + ((v >>  8) & 0xf) * 100
904	   + ((v >> 12) & 0xf) * 1000);
905  return r;
906}
907
908static int
909binary_to_bcd (int v)
910{
911  int r = ( ((v /    1) % 10) <<  0
912	  | ((v /   10) % 10) <<  4
913	  | ((v /  100) % 10) <<  8
914	  | ((v / 1000) % 10) << 12);
915  return r;
916}
917
918static const char *
919cond_string (int cond)
920{
921  switch (cond)
922    {
923    case MSC_nz:
924      return "NZ";
925    case MSC_z:
926      return "Z";
927    case MSC_nc:
928      return "NC";
929    case MSC_c:
930      return "C";
931    case MSC_n:
932      return "N";
933    case MSC_ge:
934      return "GE";
935    case MSC_l:
936      return "L";
937    case MSC_true:
938      return "MP";
939    default:
940      return "??";
941    }
942}
943
944/* Checks a CALL to address CALL_ADDR.  If this is a special
945   syscall address then the call is simulated and non-zero is
946   returned.  Otherwise 0 is returned.  */
947
948static int
949maybe_perform_syscall (SIM_DESC sd, int call_addr)
950{
951  if (call_addr == 0x00160)
952    {
953      int i;
954
955      for (i = 0; i < 16; i++)
956	{
957	  if (i % 4 == 0)
958	    fprintf (stderr, "\t");
959	  fprintf (stderr, "R%-2d %05x   ", i, MSP430_CPU (sd)->state.regs[i]);
960	  if (i % 4 == 3)
961	    {
962	      int sp = SP + (3 - (i / 4)) * 2;
963	      unsigned char buf[2];
964
965	      sim_core_read_buffer (sd, MSP430_CPU (sd), read_map, buf, sp, 2);
966
967	      fprintf (stderr, "\tSP%+d: %04x", sp - SP,
968		       buf[0] + buf[1] * 256);
969
970	      if (i / 4 == 0)
971		{
972		  int flags = SR;
973
974		  fprintf (stderr, flags & 0x100 ? "   V" : "   -");
975		  fprintf (stderr, flags & 0x004 ? "N" : "-");
976		  fprintf (stderr, flags & 0x002 ? "Z" : "-");
977		  fprintf (stderr, flags & 0x001 ? "C" : "-");
978		}
979
980	      fprintf (stderr, "\n");
981	    }
982	}
983      return 1;
984    }
985
986  if ((call_addr & ~0x3f) == 0x00180)
987    {
988      /* Syscall!  */
989      int syscall_num = call_addr & 0x3f;
990      int arg1 = MSP430_CPU (sd)->state.regs[12];
991      int arg2 = MSP430_CPU (sd)->state.regs[13];
992      int arg3 = MSP430_CPU (sd)->state.regs[14];
993      int arg4 = MSP430_CPU (sd)->state.regs[15];
994
995      MSP430_CPU (sd)->state.regs[12] = sim_syscall (MSP430_CPU (sd),
996						     syscall_num, arg1, arg2,
997						     arg3, arg4);
998      return 1;
999    }
1000
1001  return 0;
1002}
1003
1004static void
1005msp430_step_once (SIM_DESC sd)
1006{
1007  Get_Byte_Local_Data ld;
1008  unsigned char buf[100];
1009  int i;
1010  int opsize;
1011  unsigned int opcode_pc;
1012  MSP430_Opcode_Decoded opcode_buf;
1013  MSP430_Opcode_Decoded *opcode = &opcode_buf;
1014  int s1, s2, result;
1015  int u1, u2, uresult;
1016  int c, reg;
1017  int sp;
1018  int carry_to_use;
1019  int n_repeats;
1020  int rept;
1021  int op_bytes, op_bits;
1022
1023  PC &= 0xfffff;
1024  opcode_pc = PC;
1025
1026  if (opcode_pc < 0x10)
1027    {
1028      fprintf (stderr, "Fault: PC(%#x) is less than 0x10\n", opcode_pc);
1029      sim_engine_halt (sd, MSP430_CPU (sd), NULL,
1030		       MSP430_CPU (sd)->state.regs[0],
1031		       sim_exited, -1);
1032      return;
1033    }
1034
1035  if (PC == MSP430_CPU (sd)->state.cio_breakpoint
1036      && STATE_OPEN_KIND (sd) != SIM_OPEN_DEBUG)
1037    msp430_cio (sd);
1038
1039  ld.sd = sd;
1040  ld.gb_addr = PC;
1041  opsize = msp430_decode_opcode (MSP430_CPU (sd)->state.regs[0],
1042				 opcode, msp430_getbyte, &ld);
1043  PC += opsize;
1044  if (opsize <= 0)
1045    {
1046      fprintf (stderr, "Fault: undecodable opcode at %#x\n", opcode_pc);
1047      sim_engine_halt (sd, MSP430_CPU (sd), NULL,
1048		       MSP430_CPU (sd)->state.regs[0],
1049		       sim_exited, -1);
1050      return;
1051    }
1052
1053  if (opcode->repeat_reg)
1054    n_repeats = (MSP430_CPU (sd)->state.regs[opcode->repeats] & 0x000f) + 1;
1055  else
1056    n_repeats = opcode->repeats + 1;
1057
1058  op_bits = opcode->size;
1059  switch (op_bits)
1060    {
1061    case 8:
1062      op_bytes = 1;
1063      break;
1064    case 16:
1065      op_bytes = 2;
1066      break;
1067    case 20:
1068    case 32:
1069      op_bytes = 4;
1070      break;
1071    }
1072
1073  if (TRACE_ANY_P (MSP430_CPU (sd)))
1074    trace_prefix (sd, MSP430_CPU (sd), NULL_CIA, opcode_pc,
1075		  TRACE_LINENUM_P (MSP430_CPU (sd)), NULL, 0, "");
1076
1077  TRACE_DISASM (MSP430_CPU (sd), opcode_pc);
1078
1079  carry_to_use = 0;
1080  switch (opcode->id)
1081    {
1082    case MSO_unknown:
1083      break;
1084
1085      /* Double-operand instructions.  */
1086    case MSO_mov:
1087      if (opcode->n_bytes == 2
1088	  && opcode->op[0].type == MSP430_Operand_Register
1089	  && opcode->op[0].reg == MSR_CG
1090	  && opcode->op[1].type == MSP430_Operand_Immediate
1091	  && opcode->op[1].addend == 0
1092	  /* A 16-bit write of #0 is a NOP; an 8-bit write is a BRK.  */
1093	  && opcode->size == 8)
1094	{
1095	  /* This is the designated software breakpoint instruction.  */
1096	  PC -= opsize;
1097	  sim_engine_halt (sd, MSP430_CPU (sd), NULL,
1098			   MSP430_CPU (sd)->state.regs[0],
1099			   sim_stopped, SIM_SIGTRAP);
1100
1101	}
1102      else
1103	{
1104	  /* Otherwise, do the move.  */
1105	  for (rept = 0; rept < n_repeats; rept ++)
1106	    {
1107	      DEST (SRC);
1108	    }
1109	}
1110      break;
1111
1112    case MSO_addc:
1113      for (rept = 0; rept < n_repeats; rept ++)
1114	{
1115	  carry_to_use = (SR & MSP430_FLAG_C) ? 1 : 0;
1116	  u1 = DSRC;
1117	  u2 = SRC;
1118	  s1 = SX (u1);
1119	  s2 = SX (u2);
1120	  uresult = u1 + u2 + carry_to_use;
1121	  result = s1 + s2 + carry_to_use;
1122	  TRACE_ALU (MSP430_CPU (sd), "ADDC: %#x + %#x + %d = %#x",
1123		     u1, u2, carry_to_use, uresult);
1124	  DEST (result);
1125	  FLAGS (result, uresult != ZX (uresult));
1126	}
1127      break;
1128
1129    case MSO_add:
1130      for (rept = 0; rept < n_repeats; rept ++)
1131	{
1132	  u1 = DSRC;
1133	  u2 = SRC;
1134	  s1 = SX (u1);
1135	  s2 = SX (u2);
1136	  uresult = u1 + u2;
1137	  result = s1 + s2;
1138	  TRACE_ALU (MSP430_CPU (sd), "ADD: %#x + %#x = %#x",
1139		     u1, u2, uresult);
1140	  DEST (result);
1141	  FLAGS (result, uresult != ZX (uresult));
1142	}
1143      break;
1144
1145    case MSO_subc:
1146      for (rept = 0; rept < n_repeats; rept ++)
1147	{
1148	  carry_to_use = (SR & MSP430_FLAG_C) ? 1 : 0;
1149	  u1 = DSRC;
1150	  u2 = SRC;
1151	  s1 = SX (u1);
1152	  s2 = SX (u2);
1153	  uresult = ZX (~u2) + u1 + carry_to_use;
1154	  result = s1 - s2 + (carry_to_use - 1);
1155	  TRACE_ALU (MSP430_CPU (sd), "SUBC: %#x - %#x + %d = %#x",
1156		     u1, u2, carry_to_use, uresult);
1157	  DEST (result);
1158	  FLAGS (result, uresult != ZX (uresult));
1159	}
1160      break;
1161
1162    case MSO_sub:
1163      for (rept = 0; rept < n_repeats; rept ++)
1164	{
1165	  u1 = DSRC;
1166	  u2 = SRC;
1167	  s1 = SX (u1);
1168	  s2 = SX (u2);
1169	  uresult = ZX (~u2) + u1 + 1;
1170	  result = SX (uresult);
1171	  TRACE_ALU (MSP430_CPU (sd), "SUB: %#x - %#x = %#x",
1172		     u1, u2, uresult);
1173	  DEST (result);
1174	  FLAGS (result, uresult != ZX (uresult));
1175	}
1176      break;
1177
1178    case MSO_cmp:
1179      for (rept = 0; rept < n_repeats; rept ++)
1180	{
1181	  u1 = DSRC;
1182	  u2 = SRC;
1183	  s1 = SX (u1);
1184	  s2 = SX (u2);
1185	  uresult = ZX (~u2) + u1 + 1;
1186	  result = s1 - s2;
1187	  TRACE_ALU (MSP430_CPU (sd), "CMP: %#x - %#x = %x",
1188		     u1, u2, uresult);
1189	  FLAGS (result, uresult != ZX (uresult));
1190	}
1191      break;
1192
1193    case MSO_dadd:
1194      for (rept = 0; rept < n_repeats; rept ++)
1195	{
1196	  carry_to_use = (SR & MSP430_FLAG_C) ? 1 : 0;
1197	  u1 = DSRC;
1198	  u2 = SRC;
1199	  uresult = bcd_to_binary (u1) + bcd_to_binary (u2) + carry_to_use;
1200	  result = binary_to_bcd (uresult);
1201	  TRACE_ALU (MSP430_CPU (sd), "DADD: %#x + %#x + %d = %#x",
1202		     u1, u2, carry_to_use, result);
1203	  DEST (result);
1204	  FLAGS (result, uresult > ((opcode->size == 8) ? 99 : 9999));
1205	}
1206      break;
1207
1208    case MSO_and:
1209      for (rept = 0; rept < n_repeats; rept ++)
1210	{
1211	  u1 = DSRC;
1212	  u2 = SRC;
1213	  uresult = u1 & u2;
1214	  TRACE_ALU (MSP430_CPU (sd), "AND: %#x & %#x = %#x",
1215		     u1, u2, uresult);
1216	  DEST (uresult);
1217	  FLAGS (uresult, uresult != 0);
1218	}
1219      break;
1220
1221    case MSO_bit:
1222      for (rept = 0; rept < n_repeats; rept ++)
1223	{
1224	  u1 = DSRC;
1225	  u2 = SRC;
1226	  uresult = u1 & u2;
1227	  TRACE_ALU (MSP430_CPU (sd), "BIT: %#x & %#x -> %#x",
1228		     u1, u2, uresult);
1229	  FLAGS (uresult, uresult != 0);
1230	}
1231      break;
1232
1233    case MSO_bic:
1234      for (rept = 0; rept < n_repeats; rept ++)
1235	{
1236	  u1 = DSRC;
1237	  u2 = SRC;
1238	  uresult = u1 & ~ u2;
1239	  TRACE_ALU (MSP430_CPU (sd), "BIC: %#x & ~ %#x = %#x",
1240		     u1, u2, uresult);
1241	  DEST (uresult);
1242	}
1243      break;
1244
1245    case MSO_bis:
1246      for (rept = 0; rept < n_repeats; rept ++)
1247	{
1248	  u1 = DSRC;
1249	  u2 = SRC;
1250	  uresult = u1 | u2;
1251	  TRACE_ALU (MSP430_CPU (sd), "BIS: %#x | %#x = %#x",
1252		     u1, u2, uresult);
1253	  DEST (uresult);
1254	}
1255      break;
1256
1257    case MSO_xor:
1258      for (rept = 0; rept < n_repeats; rept ++)
1259	{
1260	  s1 = 1 << (opcode->size - 1);
1261	  u1 = DSRC;
1262	  u2 = SRC;
1263	  uresult = u1 ^ u2;
1264	  TRACE_ALU (MSP430_CPU (sd), "XOR: %#x & %#x = %#x",
1265		     u1, u2, uresult);
1266	  DEST (uresult);
1267	  FLAGSV (uresult, uresult != 0, (u1 & s1) && (u2 & s1));
1268	}
1269      break;
1270
1271    /* Single-operand instructions.  Note: the decoder puts the same
1272       operand in SRC as in DEST, for our convenience.  */
1273
1274    case MSO_rrc:
1275      for (rept = 0; rept < n_repeats; rept ++)
1276	{
1277	  u1 = SRC;
1278	  carry_to_use = u1 & 1;
1279	  uresult = u1 >> 1;
1280	  if (SR & MSP430_FLAG_C)
1281	  uresult |= (1 << (opcode->size - 1));
1282	  TRACE_ALU (MSP430_CPU (sd), "RRC: %#x >>= %#x",
1283		     u1, uresult);
1284	  DEST (uresult);
1285	  FLAGS (uresult, carry_to_use);
1286	}
1287      break;
1288
1289    case MSO_swpb:
1290      for (rept = 0; rept < n_repeats; rept ++)
1291	{
1292	  u1 = SRC;
1293	  uresult = ((u1 >> 8) & 0x00ff) | ((u1 << 8) & 0xff00);
1294	  TRACE_ALU (MSP430_CPU (sd), "SWPB: %#x -> %#x",
1295		     u1, uresult);
1296	  DEST (uresult);
1297	}
1298      break;
1299
1300    case MSO_rra:
1301      for (rept = 0; rept < n_repeats; rept ++)
1302	{
1303	  u1 = SRC;
1304	  c = u1 & 1;
1305	  s1 = 1 << (opcode->size - 1);
1306	  uresult = (u1 >> 1) | (u1 & s1);
1307	  TRACE_ALU (MSP430_CPU (sd), "RRA: %#x >>= %#x",
1308		     u1, uresult);
1309	  DEST (uresult);
1310	  FLAGS (uresult, c);
1311	}
1312      break;
1313
1314    case MSO_rru:
1315      for (rept = 0; rept < n_repeats; rept ++)
1316	{
1317	  u1 = SRC;
1318	  c = u1 & 1;
1319	  uresult = (u1 >> 1);
1320	  TRACE_ALU (MSP430_CPU (sd), "RRU: %#x >>= %#x",
1321		     u1, uresult);
1322	  DEST (uresult);
1323	  FLAGS (uresult, c);
1324	}
1325      break;
1326
1327    case MSO_sxt:
1328      for (rept = 0; rept < n_repeats; rept ++)
1329	{
1330	  u1 = SRC;
1331	  if (u1 & 0x80)
1332	    uresult = u1 | 0xfff00;
1333	  else
1334	    uresult = u1 & 0x000ff;
1335	  TRACE_ALU (MSP430_CPU (sd), "SXT: %#x -> %#x",
1336		     u1, uresult);
1337	  DEST (uresult);
1338	  FLAGS (uresult, c);
1339	}
1340      break;
1341
1342    case MSO_push:
1343      for (rept = 0; rept < n_repeats; rept ++)
1344	{
1345	  int new_sp;
1346
1347	  new_sp = REG_GET (MSR_SP) - op_bytes;
1348	  /* SP is always word-aligned.  */
1349	  if (new_sp & 1)
1350	    new_sp --;
1351	  REG_PUT (MSR_SP, new_sp);
1352	  u1 = SRC;
1353	  mem_put_val (sd, SP, u1, op_bits);
1354	  if (opcode->op[1].type == MSP430_Operand_Register)
1355	    opcode->op[1].reg --;
1356	}
1357      break;
1358
1359    case MSO_pop:
1360      for (rept = 0; rept < n_repeats; rept ++)
1361	{
1362	  int new_sp;
1363
1364	  u1 = mem_get_val (sd, SP, op_bits);
1365	  DEST (u1);
1366	  if (opcode->op[0].type == MSP430_Operand_Register)
1367	    opcode->op[0].reg ++;
1368	  new_sp = REG_GET (MSR_SP) + op_bytes;
1369	  /* SP is always word-aligned.  */
1370	  if (new_sp & 1)
1371	    new_sp ++;
1372	  REG_PUT (MSR_SP, new_sp);
1373	}
1374      break;
1375
1376    case MSO_call:
1377      u1 = SRC;
1378
1379      if (maybe_perform_syscall (sd, u1))
1380	break;
1381
1382      REG_PUT (MSR_SP, REG_GET (MSR_SP) - op_bytes);
1383      mem_put_val (sd, SP, PC, op_bits);
1384      TRACE_ALU (MSP430_CPU (sd), "CALL: func %#x ret %#x, sp %#x",
1385	         u1, PC, SP);
1386      REG_PUT (MSR_PC, u1);
1387      break;
1388
1389    case MSO_reti:
1390      u1 = mem_get_val (sd, SP, 16);
1391      SR = u1 & 0xFF;
1392      SP += 2;
1393      PC = mem_get_val (sd, SP, 16);
1394      SP += 2;
1395      /* Emulate the RETI action of the 20-bit CPUX architecure.
1396	 This is safe for 16-bit CPU architectures as well, since the top
1397	 8-bits of SR will have been written to the stack here, and will
1398	 have been read as 0.  */
1399      PC |= (u1 & 0xF000) << 4;
1400      TRACE_ALU (MSP430_CPU (sd), "RETI: pc %#x sr %#x",
1401	         PC, SR);
1402      break;
1403
1404      /* Jumps.  */
1405
1406    case MSO_jmp:
1407      i = SRC;
1408      switch (opcode->cond)
1409	{
1410	case MSC_nz:
1411	  u1 = (SR & MSP430_FLAG_Z) ? 0 : 1;
1412	  break;
1413	case MSC_z:
1414	  u1 = (SR & MSP430_FLAG_Z) ? 1 : 0;
1415	  break;
1416	case MSC_nc:
1417	  u1 = (SR & MSP430_FLAG_C) ? 0 : 1;
1418	  break;
1419	case MSC_c:
1420	  u1 = (SR & MSP430_FLAG_C) ? 1 : 0;
1421	  break;
1422	case MSC_n:
1423	  u1 = (SR & MSP430_FLAG_N) ? 1 : 0;
1424	  break;
1425	case MSC_ge:
1426	  u1 = (!!(SR & MSP430_FLAG_N) == !!(SR & MSP430_FLAG_V)) ? 1 : 0;
1427	  break;
1428	case MSC_l:
1429	  u1 = (!!(SR & MSP430_FLAG_N) == !!(SR & MSP430_FLAG_V)) ? 0 : 1;
1430	  break;
1431	case MSC_true:
1432	  u1 = 1;
1433	  break;
1434	}
1435
1436      if (u1)
1437	{
1438	  TRACE_BRANCH (MSP430_CPU (sd), "J%s: pc %#x -> %#x sr %#x, taken",
1439			cond_string (opcode->cond), PC, i, SR);
1440	  PC = i;
1441	  if (PC == opcode_pc)
1442	    exit (0);
1443	}
1444      else
1445	TRACE_BRANCH (MSP430_CPU (sd), "J%s: pc %#x to %#x sr %#x, not taken",
1446		      cond_string (opcode->cond), PC, i, SR);
1447      break;
1448
1449    default:
1450      fprintf (stderr, "error: unexpected opcode id %d\n", opcode->id);
1451      exit (1);
1452    }
1453}
1454
1455void
1456sim_engine_run (SIM_DESC sd,
1457		int next_cpu_nr,
1458		int nr_cpus,
1459		int siggnal)
1460{
1461  while (1)
1462    {
1463      msp430_step_once (sd);
1464      if (sim_events_tick (sd))
1465	sim_events_process (sd);
1466    }
1467}
1468