generate single html manual page by default
[deliverable/binutils-gdb.git] / sim / iq2000 / iq2000.c
CommitLineData
edece237 1/* IQ2000 simulator support code
3666a048 2 Copyright (C) 2000-2021 Free Software Foundation, Inc.
edece237
CV
3 Contributed by Cygnus Support.
4
5 This file is part of the GNU simulators.
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
4744ac1b
JB
9 the Free Software Foundation; either version 3 of the License, or
10 (at your option) any later version.
edece237
CV
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
4744ac1b
JB
17 You should have received a copy of the GNU General Public License
18 along with this program. If not, see <http://www.gnu.org/licenses/>. */
edece237
CV
19
20#define WANT_CPU
21#define WANT_CPU_IQ2000BF
22
23#include "sim-main.h"
24#include "cgen-mem.h"
25#include "cgen-ops.h"
2390d779 26#include "targ-vals.h"
32a046ab 27#include <stdlib.h>
edece237
CV
28
29enum
30{
31 GPR0_REGNUM = 0,
32 NR_GPR = 32,
33 PC_REGNUM = 32
34};
35
edece237
CV
36/* Read a null terminated string from memory, return in a buffer */
37static char *
81e6e8ae 38fetch_str (SIM_CPU *current_cpu, PCADDR pc, DI addr)
edece237
CV
39{
40 char *buf;
41 int nr = 0;
42 while (sim_core_read_1 (current_cpu,
43 pc, read_map, CPU2DATA(addr + nr)) != 0)
44 nr++;
45 buf = NZALLOC (char, nr + 1);
46 sim_read (CPU_STATE (current_cpu), CPU2DATA(addr), buf, nr);
47 return buf;
48}
49
50void
51do_syscall (SIM_CPU *current_cpu, PCADDR pc)
52{
53#if 0
54 int syscall = H2T_4 (iq2000bf_h_gr_get (current_cpu, 11));
55#endif
56 int syscall_function = iq2000bf_h_gr_get (current_cpu, 4);
57 int i;
58 char *buf;
59 int PARM1 = iq2000bf_h_gr_get (current_cpu, 5);
60 int PARM2 = iq2000bf_h_gr_get (current_cpu, 6);
61 int PARM3 = iq2000bf_h_gr_get (current_cpu, 7);
62 const int ret_reg = 2;
63
64 switch (syscall_function)
65 {
66 case 0:
67 switch (H2T_4 (iq2000bf_h_gr_get (current_cpu, 11)))
68 {
69 case 0:
70 /* Pass. */
71 puts ("pass");
72 exit (0);
73 case 1:
74 /* Fail. */
75 puts ("fail");
76 exit (1);
77 }
78
2390d779 79 case TARGET_SYS_write:
edece237
CV
80 buf = zalloc (PARM3);
81 sim_read (CPU_STATE (current_cpu), CPU2DATA(PARM2), buf, PARM3);
82 SET_H_GR (ret_reg,
83 sim_io_write (CPU_STATE (current_cpu),
84 PARM1, buf, PARM3));
d79fe0d6 85 free (buf);
edece237
CV
86 break;
87
2390d779 88 case TARGET_SYS_lseek:
edece237
CV
89 SET_H_GR (ret_reg,
90 sim_io_lseek (CPU_STATE (current_cpu),
91 PARM1, PARM2, PARM3));
92 break;
93
2390d779 94 case TARGET_SYS_exit:
edece237
CV
95 sim_engine_halt (CPU_STATE (current_cpu), current_cpu,
96 NULL, pc, sim_exited, PARM1);
97 break;
98
2390d779 99 case TARGET_SYS_read:
edece237
CV
100 buf = zalloc (PARM3);
101 SET_H_GR (ret_reg,
102 sim_io_read (CPU_STATE (current_cpu),
103 PARM1, buf, PARM3));
104 sim_write (CPU_STATE (current_cpu), CPU2DATA(PARM2), buf, PARM3);
d79fe0d6 105 free (buf);
edece237
CV
106 break;
107
2390d779 108 case TARGET_SYS_open:
edece237
CV
109 buf = fetch_str (current_cpu, pc, PARM1);
110 SET_H_GR (ret_reg,
111 sim_io_open (CPU_STATE (current_cpu),
112 buf, PARM2));
d79fe0d6 113 free (buf);
edece237
CV
114 break;
115
2390d779 116 case TARGET_SYS_close:
edece237
CV
117 SET_H_GR (ret_reg,
118 sim_io_close (CPU_STATE (current_cpu), PARM1));
119 break;
120
2390d779 121 case TARGET_SYS_time:
edece237
CV
122 SET_H_GR (ret_reg, time (0));
123 break;
124
125 default:
126 SET_H_GR (ret_reg, -1);
127 }
128}
129
130void
131do_break (SIM_CPU *current_cpu, PCADDR pc)
132{
133 SIM_DESC sd = CPU_STATE (current_cpu);
134 sim_engine_halt (sd, current_cpu, NULL, pc, sim_stopped, SIM_SIGTRAP);
135}
136
137/* The semantic code invokes this for invalid (unrecognized) instructions. */
138
139SEM_PC
140sim_engine_invalid_insn (SIM_CPU *current_cpu, IADDR cia, SEM_PC vpc)
141{
142 SIM_DESC sd = CPU_STATE (current_cpu);
143 sim_engine_halt (sd, current_cpu, NULL, cia, sim_stopped, SIM_SIGILL);
144
145 return vpc;
146}
147
148
149/* Process an address exception. */
150
151void
152iq2000_core_signal (SIM_DESC sd, SIM_CPU *current_cpu, sim_cia cia,
153 unsigned int map, int nr_bytes, address_word addr,
154 transfer_type transfer, sim_core_signals sig)
155{
156 sim_core_signal (sd, current_cpu, cia, map, nr_bytes, addr,
157 transfer, sig);
158}
159
160
161/* Initialize cycle counting for an insn.
162 FIRST_P is non-zero if this is the first insn in a set of parallel
163 insns. */
164
165void
166iq2000bf_model_insn_before (SIM_CPU *cpu, int first_p)
167{
168 /* Do nothing. */
169}
170
171
172/* Record the cycles computed for an insn.
173 LAST_P is non-zero if this is the last insn in a set of parallel insns,
174 and we update the total cycle count.
175 CYCLES is the cycle count of the insn. */
176
177void
178iq2000bf_model_insn_after(SIM_CPU *cpu, int last_p, int cycles)
179{
180 /* Do nothing. */
181}
182
183
184int
185iq2000bf_model_iq2000_u_exec (SIM_CPU *cpu, const IDESC *idesc,
186 int unit_num, int referenced)
187{
188 return idesc->timing->units[unit_num].done;
189}
190
191PCADDR
192get_h_pc (SIM_CPU *cpu)
193{
194 return CPU_CGEN_HW(cpu)->h_pc;
195}
196
197void
198set_h_pc (SIM_CPU *cpu, PCADDR addr)
199{
200 CPU_CGEN_HW(cpu)->h_pc = addr | IQ2000_INSN_MASK;
201}
202
203int
204iq2000bf_fetch_register (SIM_CPU *cpu, int nr, unsigned char *buf, int len)
205{
206 if (nr >= GPR0_REGNUM
207 && nr < (GPR0_REGNUM + NR_GPR)
208 && len == 4)
209 {
210 *((unsigned32*)buf) =
211 H2T_4 (iq2000bf_h_gr_get (cpu, nr - GPR0_REGNUM));
212 return 4;
213 }
214 else if (nr == PC_REGNUM
215 && len == 4)
216 {
217 *((unsigned32*)buf) = H2T_4 (get_h_pc (cpu));
218 return 4;
219 }
220 else
221 return 0;
222}
223
224int
225iq2000bf_store_register (SIM_CPU *cpu, int nr, unsigned char *buf, int len)
226{
227 if (nr >= GPR0_REGNUM
228 && nr < (GPR0_REGNUM + NR_GPR)
229 && len == 4)
230 {
231 iq2000bf_h_gr_set (cpu, nr - GPR0_REGNUM, T2H_4 (*((unsigned32*)buf)));
232 return 4;
233 }
234 else if (nr == PC_REGNUM
235 && len == 4)
236 {
237 set_h_pc (cpu, T2H_4 (*((unsigned32*)buf)));
238 return 4;
239 }
240 else
241 return 0;
242}
This page took 0.719835 seconds and 4 git commands to generate.