1 /* Simulator parallel routines for CGEN simulators (and maybe others).
2 Copyright (C) 1999 Free Software Foundation, Inc.
3 Contributed by Cygnus Solutions.
5 This file is part of the GNU instruction set simulator.
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
9 the Free Software Foundation; either version 2, or (at your option)
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.
17 You should have received a copy of the GNU General Public License along
18 with this program; if not, write to the Free Software Foundation, Inc.,
19 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
25 /* Functions required by the cgen interface. These functions add various
26 kinds of writes to the write queue. */
27 void sim_queue_bi_write (SIM_CPU
*cpu
, BI
*target
, BI value
)
29 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
30 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
31 element
->kind
= CGEN_BI_WRITE
;
32 element
->insn_address
= CPU_PC_GET (cpu
);
33 element
->kinds
.bi_write
.target
= target
;
34 element
->kinds
.bi_write
.value
= value
;
37 void sim_queue_qi_write (SIM_CPU
*cpu
, UQI
*target
, UQI value
)
39 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
40 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
41 element
->kind
= CGEN_QI_WRITE
;
42 element
->insn_address
= CPU_PC_GET (cpu
);
43 element
->kinds
.qi_write
.target
= target
;
44 element
->kinds
.qi_write
.value
= value
;
47 void sim_queue_si_write (SIM_CPU
*cpu
, SI
*target
, SI value
)
49 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
50 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
51 element
->kind
= CGEN_SI_WRITE
;
52 element
->insn_address
= CPU_PC_GET (cpu
);
53 element
->kinds
.si_write
.target
= target
;
54 element
->kinds
.si_write
.value
= value
;
57 void sim_queue_sf_write (SIM_CPU
*cpu
, SI
*target
, SF value
)
59 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
60 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
61 element
->kind
= CGEN_SF_WRITE
;
62 element
->insn_address
= CPU_PC_GET (cpu
);
63 element
->kinds
.sf_write
.target
= target
;
64 element
->kinds
.sf_write
.value
= value
;
67 void sim_queue_pc_write (SIM_CPU
*cpu
, USI value
)
69 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
70 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
71 element
->kind
= CGEN_PC_WRITE
;
72 element
->insn_address
= CPU_PC_GET (cpu
);
73 element
->kinds
.pc_write
.value
= value
;
76 void sim_queue_fn_hi_write (
78 void (*write_function
)(SIM_CPU
*cpu
, UINT
, UHI
),
83 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
84 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
85 element
->kind
= CGEN_FN_HI_WRITE
;
86 element
->insn_address
= CPU_PC_GET (cpu
);
87 element
->kinds
.fn_hi_write
.function
= write_function
;
88 element
->kinds
.fn_hi_write
.regno
= regno
;
89 element
->kinds
.fn_hi_write
.value
= value
;
92 void sim_queue_fn_si_write (
94 void (*write_function
)(SIM_CPU
*cpu
, UINT
, USI
),
99 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
100 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
101 element
->kind
= CGEN_FN_SI_WRITE
;
102 element
->insn_address
= CPU_PC_GET (cpu
);
103 element
->kinds
.fn_si_write
.function
= write_function
;
104 element
->kinds
.fn_si_write
.regno
= regno
;
105 element
->kinds
.fn_si_write
.value
= value
;
108 void sim_queue_fn_di_write (
110 void (*write_function
)(SIM_CPU
*cpu
, UINT
, DI
),
115 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
116 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
117 element
->kind
= CGEN_FN_DI_WRITE
;
118 element
->insn_address
= CPU_PC_GET (cpu
);
119 element
->kinds
.fn_di_write
.function
= write_function
;
120 element
->kinds
.fn_di_write
.regno
= regno
;
121 element
->kinds
.fn_di_write
.value
= value
;
124 void sim_queue_fn_xi_write (
126 void (*write_function
)(SIM_CPU
*cpu
, UINT
, SI
*),
131 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
132 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
133 element
->kind
= CGEN_FN_XI_WRITE
;
134 element
->insn_address
= CPU_PC_GET (cpu
);
135 element
->kinds
.fn_xi_write
.function
= write_function
;
136 element
->kinds
.fn_xi_write
.regno
= regno
;
137 element
->kinds
.fn_xi_write
.value
[0] = value
[0];
138 element
->kinds
.fn_xi_write
.value
[1] = value
[1];
139 element
->kinds
.fn_xi_write
.value
[2] = value
[2];
140 element
->kinds
.fn_xi_write
.value
[3] = value
[3];
143 void sim_queue_fn_df_write (
145 void (*write_function
)(SIM_CPU
*cpu
, UINT
, DF
),
150 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
151 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
152 element
->kind
= CGEN_FN_DF_WRITE
;
153 element
->insn_address
= CPU_PC_GET (cpu
);
154 element
->kinds
.fn_df_write
.function
= write_function
;
155 element
->kinds
.fn_df_write
.regno
= regno
;
156 element
->kinds
.fn_df_write
.value
= value
;
159 void sim_queue_fn_pc_write (
161 void (*write_function
)(SIM_CPU
*cpu
, USI
),
165 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
166 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
167 element
->kind
= CGEN_FN_PC_WRITE
;
168 element
->insn_address
= CPU_PC_GET (cpu
);
169 element
->kinds
.fn_pc_write
.function
= write_function
;
170 element
->kinds
.fn_pc_write
.value
= value
;
173 void sim_queue_mem_qi_write (SIM_CPU
*cpu
, SI address
, QI value
)
175 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
176 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
177 element
->kind
= CGEN_MEM_QI_WRITE
;
178 element
->insn_address
= CPU_PC_GET (cpu
);
179 element
->kinds
.mem_qi_write
.address
= address
;
180 element
->kinds
.mem_qi_write
.value
= value
;
183 void sim_queue_mem_hi_write (SIM_CPU
*cpu
, SI address
, HI value
)
185 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
186 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
187 element
->kind
= CGEN_MEM_HI_WRITE
;
188 element
->insn_address
= CPU_PC_GET (cpu
);
189 element
->kinds
.mem_hi_write
.address
= address
;
190 element
->kinds
.mem_hi_write
.value
= value
;
193 void sim_queue_mem_si_write (SIM_CPU
*cpu
, SI address
, SI value
)
195 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
196 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
197 element
->kind
= CGEN_MEM_SI_WRITE
;
198 element
->insn_address
= CPU_PC_GET (cpu
);
199 element
->kinds
.mem_si_write
.address
= address
;
200 element
->kinds
.mem_si_write
.value
= value
;
203 void sim_queue_mem_di_write (SIM_CPU
*cpu
, SI address
, DI value
)
205 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
206 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
207 element
->kind
= CGEN_MEM_DI_WRITE
;
208 element
->insn_address
= CPU_PC_GET (cpu
);
209 element
->kinds
.mem_di_write
.address
= address
;
210 element
->kinds
.mem_di_write
.value
= value
;
213 void sim_queue_mem_df_write (SIM_CPU
*cpu
, SI address
, DF value
)
215 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
216 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
217 element
->kind
= CGEN_MEM_DF_WRITE
;
218 element
->insn_address
= CPU_PC_GET (cpu
);
219 element
->kinds
.mem_df_write
.address
= address
;
220 element
->kinds
.mem_df_write
.value
= value
;
223 void sim_queue_mem_xi_write (SIM_CPU
*cpu
, SI address
, SI
*value
)
225 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
226 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
227 element
->kind
= CGEN_MEM_XI_WRITE
;
228 element
->insn_address
= CPU_PC_GET (cpu
);
229 element
->kinds
.mem_xi_write
.address
= address
;
230 element
->kinds
.mem_xi_write
.value
[0] = value
[0];
231 element
->kinds
.mem_xi_write
.value
[1] = value
[1];
232 element
->kinds
.mem_xi_write
.value
[2] = value
[2];
233 element
->kinds
.mem_xi_write
.value
[3] = value
[3];
236 void sim_queue_fn_mem_qi_write (
238 void (*write_function
)(SIM_CPU
*cpu
, IADDR
, SI
, QI
),
243 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
244 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
245 element
->kind
= CGEN_FN_MEM_QI_WRITE
;
246 element
->insn_address
= CPU_PC_GET (cpu
);
247 element
->kinds
.fn_mem_qi_write
.function
= write_function
;
248 element
->kinds
.fn_mem_qi_write
.address
= address
;
249 element
->kinds
.fn_mem_qi_write
.value
= value
;
252 void sim_queue_fn_mem_hi_write (
254 void (*write_function
)(SIM_CPU
*cpu
, IADDR
, SI
, HI
),
259 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
260 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
261 element
->kind
= CGEN_FN_MEM_HI_WRITE
;
262 element
->insn_address
= CPU_PC_GET (cpu
);
263 element
->kinds
.fn_mem_hi_write
.function
= write_function
;
264 element
->kinds
.fn_mem_hi_write
.address
= address
;
265 element
->kinds
.fn_mem_hi_write
.value
= value
;
268 void sim_queue_fn_mem_si_write (
270 void (*write_function
)(SIM_CPU
*cpu
, IADDR
, SI
, SI
),
275 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
276 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
277 element
->kind
= CGEN_FN_MEM_SI_WRITE
;
278 element
->insn_address
= CPU_PC_GET (cpu
);
279 element
->kinds
.fn_mem_si_write
.function
= write_function
;
280 element
->kinds
.fn_mem_si_write
.address
= address
;
281 element
->kinds
.fn_mem_si_write
.value
= value
;
284 void sim_queue_fn_mem_di_write (
286 void (*write_function
)(SIM_CPU
*cpu
, IADDR
, SI
, DI
),
291 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
292 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
293 element
->kind
= CGEN_FN_MEM_DI_WRITE
;
294 element
->insn_address
= CPU_PC_GET (cpu
);
295 element
->kinds
.fn_mem_di_write
.function
= write_function
;
296 element
->kinds
.fn_mem_di_write
.address
= address
;
297 element
->kinds
.fn_mem_di_write
.value
= value
;
300 void sim_queue_fn_mem_df_write (
302 void (*write_function
)(SIM_CPU
*cpu
, IADDR
, SI
, DF
),
307 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
308 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
309 element
->kind
= CGEN_FN_MEM_DF_WRITE
;
310 element
->insn_address
= CPU_PC_GET (cpu
);
311 element
->kinds
.fn_mem_df_write
.function
= write_function
;
312 element
->kinds
.fn_mem_df_write
.address
= address
;
313 element
->kinds
.fn_mem_df_write
.value
= value
;
316 void sim_queue_fn_mem_xi_write (
318 void (*write_function
)(SIM_CPU
*cpu
, IADDR
, SI
, SI
*),
323 CGEN_WRITE_QUEUE
*q
= CPU_WRITE_QUEUE (cpu
);
324 CGEN_WRITE_QUEUE_ELEMENT
*element
= CGEN_WRITE_QUEUE_NEXT (q
);
325 element
->kind
= CGEN_FN_MEM_XI_WRITE
;
326 element
->insn_address
= CPU_PC_GET (cpu
);
327 element
->kinds
.fn_mem_xi_write
.function
= write_function
;
328 element
->kinds
.fn_mem_xi_write
.address
= address
;
329 element
->kinds
.fn_mem_xi_write
.value
[0] = value
[0];
330 element
->kinds
.fn_mem_xi_write
.value
[1] = value
[1];
331 element
->kinds
.fn_mem_xi_write
.value
[2] = value
[2];
332 element
->kinds
.fn_mem_xi_write
.value
[3] = value
[3];
335 /* Execute a write stored on the write queue. */
337 cgen_write_queue_element_execute (SIM_CPU
*cpu
, CGEN_WRITE_QUEUE_ELEMENT
*item
)
340 switch (CGEN_WRITE_QUEUE_ELEMENT_KIND (item
))
343 *item
->kinds
.bi_write
.target
= item
->kinds
.bi_write
.value
;
346 *item
->kinds
.qi_write
.target
= item
->kinds
.qi_write
.value
;
349 *item
->kinds
.si_write
.target
= item
->kinds
.si_write
.value
;
352 *item
->kinds
.sf_write
.target
= item
->kinds
.sf_write
.value
;
355 CPU_PC_SET (cpu
, item
->kinds
.pc_write
.value
);
357 case CGEN_FN_HI_WRITE
:
358 item
->kinds
.fn_hi_write
.function (cpu
,
359 item
->kinds
.fn_hi_write
.regno
,
360 item
->kinds
.fn_hi_write
.value
);
362 case CGEN_FN_SI_WRITE
:
363 item
->kinds
.fn_si_write
.function (cpu
,
364 item
->kinds
.fn_si_write
.regno
,
365 item
->kinds
.fn_si_write
.value
);
367 case CGEN_FN_DI_WRITE
:
368 item
->kinds
.fn_di_write
.function (cpu
,
369 item
->kinds
.fn_di_write
.regno
,
370 item
->kinds
.fn_di_write
.value
);
372 case CGEN_FN_DF_WRITE
:
373 item
->kinds
.fn_df_write
.function (cpu
,
374 item
->kinds
.fn_df_write
.regno
,
375 item
->kinds
.fn_df_write
.value
);
377 case CGEN_FN_XI_WRITE
:
378 item
->kinds
.fn_xi_write
.function (cpu
,
379 item
->kinds
.fn_xi_write
.regno
,
380 item
->kinds
.fn_xi_write
.value
);
382 case CGEN_FN_PC_WRITE
:
383 item
->kinds
.fn_pc_write
.function (cpu
, item
->kinds
.fn_pc_write
.value
);
385 case CGEN_MEM_QI_WRITE
:
386 pc
= item
->insn_address
;
387 SETMEMQI (cpu
, pc
, item
->kinds
.mem_qi_write
.address
,
388 item
->kinds
.mem_qi_write
.value
);
390 case CGEN_MEM_HI_WRITE
:
391 pc
= item
->insn_address
;
392 SETMEMHI (cpu
, pc
, item
->kinds
.mem_hi_write
.address
,
393 item
->kinds
.mem_hi_write
.value
);
395 case CGEN_MEM_SI_WRITE
:
396 pc
= item
->insn_address
;
397 SETMEMSI (cpu
, pc
, item
->kinds
.mem_si_write
.address
,
398 item
->kinds
.mem_si_write
.value
);
400 case CGEN_MEM_DI_WRITE
:
401 pc
= item
->insn_address
;
402 SETMEMDI (cpu
, pc
, item
->kinds
.mem_di_write
.address
,
403 item
->kinds
.mem_di_write
.value
);
405 case CGEN_MEM_DF_WRITE
:
406 pc
= item
->insn_address
;
407 SETMEMDF (cpu
, pc
, item
->kinds
.mem_df_write
.address
,
408 item
->kinds
.mem_df_write
.value
);
410 case CGEN_MEM_XI_WRITE
:
411 pc
= item
->insn_address
;
412 SETMEMSI (cpu
, pc
, item
->kinds
.mem_xi_write
.address
,
413 item
->kinds
.mem_xi_write
.value
[0]);
414 SETMEMSI (cpu
, pc
, item
->kinds
.mem_xi_write
.address
+ 4,
415 item
->kinds
.mem_xi_write
.value
[1]);
416 SETMEMSI (cpu
, pc
, item
->kinds
.mem_xi_write
.address
+ 8,
417 item
->kinds
.mem_xi_write
.value
[2]);
418 SETMEMSI (cpu
, pc
, item
->kinds
.mem_xi_write
.address
+ 12,
419 item
->kinds
.mem_xi_write
.value
[3]);
421 case CGEN_FN_MEM_QI_WRITE
:
422 pc
= item
->insn_address
;
423 item
->kinds
.fn_mem_qi_write
.function (cpu
, pc
,
424 item
->kinds
.fn_mem_qi_write
.address
,
425 item
->kinds
.fn_mem_qi_write
.value
);
427 case CGEN_FN_MEM_HI_WRITE
:
428 pc
= item
->insn_address
;
429 item
->kinds
.fn_mem_hi_write
.function (cpu
, pc
,
430 item
->kinds
.fn_mem_hi_write
.address
,
431 item
->kinds
.fn_mem_hi_write
.value
);
433 case CGEN_FN_MEM_SI_WRITE
:
434 pc
= item
->insn_address
;
435 item
->kinds
.fn_mem_si_write
.function (cpu
, pc
,
436 item
->kinds
.fn_mem_si_write
.address
,
437 item
->kinds
.fn_mem_si_write
.value
);
439 case CGEN_FN_MEM_DI_WRITE
:
440 pc
= item
->insn_address
;
441 item
->kinds
.fn_mem_di_write
.function (cpu
, pc
,
442 item
->kinds
.fn_mem_di_write
.address
,
443 item
->kinds
.fn_mem_di_write
.value
);
445 case CGEN_FN_MEM_DF_WRITE
:
446 pc
= item
->insn_address
;
447 item
->kinds
.fn_mem_df_write
.function (cpu
, pc
,
448 item
->kinds
.fn_mem_df_write
.address
,
449 item
->kinds
.fn_mem_df_write
.value
);
451 case CGEN_FN_MEM_XI_WRITE
:
452 pc
= item
->insn_address
;
453 item
->kinds
.fn_mem_xi_write
.function (cpu
, pc
,
454 item
->kinds
.fn_mem_xi_write
.address
,
455 item
->kinds
.fn_mem_xi_write
.value
);
459 break; /* FIXME: for now....print message later. */
463 /* Utilities for the write queue. */
464 CGEN_WRITE_QUEUE_ELEMENT
*
465 cgen_write_queue_overflow (CGEN_WRITE_QUEUE
*q
)
467 abort (); /* FIXME: for now....print message later. */
This page took 0.113514 seconds and 4 git commands to generate.