]> git.ipfire.org Git - thirdparty/binutils-gdb.git/blob - sim/frv/profile-fr550.c
Copyright updates for 2007.
[thirdparty/binutils-gdb.git] / sim / frv / profile-fr550.c
1 /* frv simulator fr550 dependent profiling code.
2
3 Copyright (C) 2003, 2007 Free Software Foundation, Inc.
4 Contributed by Red Hat
5
6 This file is part of the GNU simulators.
7
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2, or (at your option)
11 any later version.
12
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License along
19 with this program; if not, write to the Free Software Foundation, Inc.,
20 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
21
22 */
23 #define WANT_CPU
24 #define WANT_CPU_FRVBF
25
26 #include "sim-main.h"
27 #include "bfd.h"
28
29 #if WITH_PROFILE_MODEL_P
30
31 #include "profile.h"
32 #include "profile-fr550.h"
33
34 /* Initialize cycle counting for an insn.
35 FIRST_P is non-zero if this is the first insn in a set of parallel
36 insns. */
37 void
38 fr550_model_insn_before (SIM_CPU *cpu, int first_p)
39 {
40 if (first_p)
41 {
42 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
43 d->cur_fr_load = d->prev_fr_load;
44 d->cur_fr_complex_1 = d->prev_fr_complex_1;
45 d->cur_fr_complex_2 = d->prev_fr_complex_2;
46 d->cur_ccr_complex = d->prev_ccr_complex;
47 d->cur_acc_mmac = d->prev_acc_mmac;
48 }
49 }
50
51 /* Record the cycles computed for an insn.
52 LAST_P is non-zero if this is the last insn in a set of parallel insns,
53 and we update the total cycle count.
54 CYCLES is the cycle count of the insn. */
55 void
56 fr550_model_insn_after (SIM_CPU *cpu, int last_p, int cycles)
57 {
58 if (last_p)
59 {
60 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
61 d->prev_fr_load = d->cur_fr_load;
62 d->prev_fr_complex_1 = d->cur_fr_complex_1;
63 d->prev_fr_complex_2 = d->cur_fr_complex_2;
64 d->prev_ccr_complex = d->cur_ccr_complex;
65 d->prev_acc_mmac = d->cur_acc_mmac;
66 }
67 }
68
69 static void fr550_reset_fr_flags (SIM_CPU *cpu, INT fr);
70 static void fr550_reset_ccr_flags (SIM_CPU *cpu, INT ccr);
71 static void fr550_reset_acc_flags (SIM_CPU *cpu, INT acc);
72
73 static void
74 set_use_is_fr_load (SIM_CPU *cpu, INT fr)
75 {
76 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
77 fr550_reset_fr_flags (cpu, (fr));
78 d->cur_fr_load |= (((DI)1) << (fr));
79 }
80
81 static void
82 set_use_not_fr_load (SIM_CPU *cpu, INT fr)
83 {
84 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
85 d->cur_fr_load &= ~(((DI)1) << (fr));
86 }
87
88 static int
89 use_is_fr_load (SIM_CPU *cpu, INT fr)
90 {
91 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
92 return d->prev_fr_load & (((DI)1) << (fr));
93 }
94
95 static void
96 set_use_is_fr_complex_1 (SIM_CPU *cpu, INT fr)
97 {
98 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
99 fr550_reset_fr_flags (cpu, (fr));
100 d->cur_fr_complex_1 |= (((DI)1) << (fr));
101 }
102
103 static void
104 set_use_not_fr_complex_1 (SIM_CPU *cpu, INT fr)
105 {
106 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
107 d->cur_fr_complex_1 &= ~(((DI)1) << (fr));
108 }
109
110 static int
111 use_is_fr_complex_1 (SIM_CPU *cpu, INT fr)
112 {
113 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
114 return d->prev_fr_complex_1 & (((DI)1) << (fr));
115 }
116
117 static void
118 set_use_is_fr_complex_2 (SIM_CPU *cpu, INT fr)
119 {
120 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
121 fr550_reset_fr_flags (cpu, (fr));
122 d->cur_fr_complex_2 |= (((DI)1) << (fr));
123 }
124
125 static void
126 set_use_not_fr_complex_2 (SIM_CPU *cpu, INT fr)
127 {
128 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
129 d->cur_fr_complex_2 &= ~(((DI)1) << (fr));
130 }
131
132 static int
133 use_is_fr_complex_2 (SIM_CPU *cpu, INT fr)
134 {
135 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
136 return d->prev_fr_complex_2 & (((DI)1) << (fr));
137 }
138
139 static void
140 set_use_is_ccr_complex (SIM_CPU *cpu, INT ccr)
141 {
142 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
143 fr550_reset_ccr_flags (cpu, (ccr));
144 d->cur_ccr_complex |= (((SI)1) << (ccr));
145 }
146
147 static void
148 set_use_not_ccr_complex (SIM_CPU *cpu, INT ccr)
149 {
150 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
151 d->cur_ccr_complex &= ~(((SI)1) << (ccr));
152 }
153
154 static int
155 use_is_ccr_complex (SIM_CPU *cpu, INT ccr)
156 {
157 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
158 return d->prev_ccr_complex & (((SI)1) << (ccr));
159 }
160
161 static void
162 set_use_is_acc_mmac (SIM_CPU *cpu, INT acc)
163 {
164 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
165 fr550_reset_acc_flags (cpu, (acc));
166 d->cur_acc_mmac |= (((DI)1) << (acc));
167 }
168
169 static void
170 set_use_not_acc_mmac (SIM_CPU *cpu, INT acc)
171 {
172 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
173 d->cur_acc_mmac &= ~(((DI)1) << (acc));
174 }
175
176 static int
177 use_is_acc_mmac (SIM_CPU *cpu, INT acc)
178 {
179 MODEL_FR550_DATA *d = CPU_MODEL_DATA (cpu);
180 return d->prev_acc_mmac & (((DI)1) << (acc));
181 }
182
183 static void
184 fr550_reset_fr_flags (SIM_CPU *cpu, INT fr)
185 {
186 set_use_not_fr_load (cpu, fr);
187 set_use_not_fr_complex_1 (cpu, fr);
188 set_use_not_fr_complex_2 (cpu, fr);
189 }
190
191 static void
192 fr550_reset_ccr_flags (SIM_CPU *cpu, INT ccr)
193 {
194 set_use_not_ccr_complex (cpu, ccr);
195 }
196
197 static void
198 fr550_reset_acc_flags (SIM_CPU *cpu, INT acc)
199 {
200 set_use_not_acc_mmac (cpu, acc);
201 }
202
203 /* Detect overlap between two register ranges. Works if one of the registers
204 is -1 with width 1 (i.e. undefined), but not both. */
205 #define REG_OVERLAP(r1, w1, r2, w2) ( \
206 (r1) + (w1) - 1 >= (r2) && (r2) + (w2) - 1 >= (r1) \
207 )
208
209 /* Latency of floating point registers may be less than recorded when followed
210 by another floating point insn. */
211 static void
212 adjust_float_register_busy (SIM_CPU *cpu,
213 INT in_FRi, int iwidth,
214 INT in_FRj, int jwidth,
215 INT out_FRk, int kwidth)
216 {
217 int i;
218 /* The latency of FRk may be less than previously recorded.
219 See Table 14-15 in the LSI. */
220 if (in_FRi >= 0)
221 {
222 for (i = 0; i < iwidth; ++i)
223 {
224 if (! REG_OVERLAP (in_FRi + i, 1, out_FRk, kwidth))
225 if (use_is_fr_load (cpu, in_FRi + i))
226 decrease_FR_busy (cpu, in_FRi + i, 1);
227 else
228 enforce_full_fr_latency (cpu, in_FRi + i);
229 }
230 }
231
232 if (in_FRj >= 0)
233 {
234 for (i = 0; i < jwidth; ++i)
235 {
236 if (! REG_OVERLAP (in_FRj + i, 1, in_FRi, iwidth)
237 && ! REG_OVERLAP (in_FRj + i, 1, out_FRk, kwidth))
238 if (use_is_fr_load (cpu, in_FRj + i))
239 decrease_FR_busy (cpu, in_FRj + i, 1);
240 else
241 enforce_full_fr_latency (cpu, in_FRj + i);
242 }
243 }
244
245 if (out_FRk >= 0)
246 {
247 for (i = 0; i < kwidth; ++i)
248 {
249 if (! REG_OVERLAP (out_FRk + i, 1, in_FRi, iwidth)
250 && ! REG_OVERLAP (out_FRk + i, 1, in_FRj, jwidth))
251 {
252 if (use_is_fr_complex_1 (cpu, out_FRk + i))
253 decrease_FR_busy (cpu, out_FRk + i, 1);
254 else if (use_is_fr_complex_2 (cpu, out_FRk + i))
255 decrease_FR_busy (cpu, out_FRk + i, 2);
256 else
257 enforce_full_fr_latency (cpu, out_FRk + i);
258 }
259 }
260 }
261 }
262
263 static void
264 restore_float_register_busy (SIM_CPU *cpu,
265 INT in_FRi, int iwidth,
266 INT in_FRj, int jwidth,
267 INT out_FRk, int kwidth)
268 {
269 int i;
270 /* The latency of FRk may be less than previously recorded.
271 See Table 14-15 in the LSI. */
272 if (in_FRi >= 0)
273 {
274 for (i = 0; i < iwidth; ++i)
275 {
276 if (! REG_OVERLAP (in_FRi + i, 1, out_FRk, kwidth))
277 if (use_is_fr_load (cpu, in_FRi + i))
278 increase_FR_busy (cpu, in_FRi + i, 1);
279 }
280 }
281
282 if (in_FRj >= 0)
283 {
284 for (i = 0; i < jwidth; ++i)
285 {
286 if (! REG_OVERLAP (in_FRj + i, 1, in_FRi, iwidth)
287 && ! REG_OVERLAP (in_FRj + i, 1, out_FRk, kwidth))
288 if (use_is_fr_load (cpu, in_FRj + i))
289 increase_FR_busy (cpu, in_FRj + i, 1);
290 }
291 }
292
293 if (out_FRk >= 0)
294 {
295 for (i = 0; i < kwidth; ++i)
296 {
297 if (! REG_OVERLAP (out_FRk + i, 1, in_FRi, iwidth)
298 && ! REG_OVERLAP (out_FRk + i, 1, in_FRj, jwidth))
299 {
300 if (use_is_fr_complex_1 (cpu, out_FRk + i))
301 increase_FR_busy (cpu, out_FRk + i, 1);
302 else if (use_is_fr_complex_2 (cpu, out_FRk + i))
303 increase_FR_busy (cpu, out_FRk + i, 2);
304 }
305 }
306 }
307 }
308
309 /* Latency of floating point registers may be less than recorded when used in a
310 media insns and followed by another media insn. */
311 static void
312 adjust_float_register_busy_for_media (SIM_CPU *cpu,
313 INT in_FRi, int iwidth,
314 INT in_FRj, int jwidth,
315 INT out_FRk, int kwidth)
316 {
317 int i;
318 /* The latency of FRk may be less than previously recorded.
319 See Table 14-15 in the LSI. */
320 if (out_FRk >= 0)
321 {
322 for (i = 0; i < kwidth; ++i)
323 {
324 if (! REG_OVERLAP (out_FRk + i, 1, in_FRi, iwidth)
325 && ! REG_OVERLAP (out_FRk + i, 1, in_FRj, jwidth))
326 {
327 if (use_is_fr_complex_1 (cpu, out_FRk + i))
328 decrease_FR_busy (cpu, out_FRk + i, 1);
329 else
330 enforce_full_fr_latency (cpu, out_FRk + i);
331 }
332 }
333 }
334 }
335
336 static void
337 restore_float_register_busy_for_media (SIM_CPU *cpu,
338 INT in_FRi, int iwidth,
339 INT in_FRj, int jwidth,
340 INT out_FRk, int kwidth)
341 {
342 int i;
343 if (out_FRk >= 0)
344 {
345 for (i = 0; i < kwidth; ++i)
346 {
347 if (! REG_OVERLAP (out_FRk + i, 1, in_FRi, iwidth)
348 && ! REG_OVERLAP (out_FRk + i, 1, in_FRj, jwidth))
349 {
350 if (use_is_fr_complex_1 (cpu, out_FRk + i))
351 increase_FR_busy (cpu, out_FRk + i, 1);
352 }
353 }
354 }
355 }
356
357 /* Latency of accumulator registers may be less than recorded when used in a
358 media insns and followed by another media insn. */
359 static void
360 adjust_acc_busy_for_mmac (SIM_CPU *cpu,
361 INT in_ACC, int inwidth,
362 INT out_ACC, int outwidth)
363 {
364 int i;
365 /* The latency of an accumulator may be less than previously recorded.
366 See Table 14-15 in the LSI. */
367 if (in_ACC >= 0)
368 {
369 for (i = 0; i < inwidth; ++i)
370 {
371 if (use_is_acc_mmac (cpu, in_ACC + i))
372 decrease_ACC_busy (cpu, in_ACC + i, 1);
373 else
374 enforce_full_acc_latency (cpu, in_ACC + i);
375 }
376 }
377 if (out_ACC >= 0)
378 {
379 for (i = 0; i < outwidth; ++i)
380 {
381 if (! REG_OVERLAP (out_ACC + i, 1, in_ACC, inwidth))
382 {
383 if (use_is_acc_mmac (cpu, out_ACC + i))
384 decrease_ACC_busy (cpu, out_ACC + i, 1);
385 else
386 enforce_full_acc_latency (cpu, out_ACC + i);
387 }
388 }
389 }
390 }
391
392 static void
393 restore_acc_busy_for_mmac (SIM_CPU *cpu,
394 INT in_ACC, int inwidth,
395 INT out_ACC, int outwidth)
396 {
397 int i;
398 if (in_ACC >= 0)
399 {
400 for (i = 0; i < inwidth; ++i)
401 {
402 if (use_is_acc_mmac (cpu, in_ACC + i))
403 increase_ACC_busy (cpu, in_ACC + i, 1);
404 }
405 }
406 if (out_ACC >= 0)
407 {
408 for (i = 0; i < outwidth; ++i)
409 {
410 if (! REG_OVERLAP (out_ACC + i, 1, in_ACC, inwidth))
411 {
412 if (use_is_acc_mmac (cpu, out_ACC + i))
413 increase_ACC_busy (cpu, out_ACC + i, 1);
414 }
415 }
416 }
417 }
418
419 int
420 frvbf_model_fr550_u_exec (SIM_CPU *cpu, const IDESC *idesc,
421 int unit_num, int referenced)
422 {
423 return idesc->timing->units[unit_num].done;
424 }
425
426 int
427 frvbf_model_fr550_u_integer (SIM_CPU *cpu, const IDESC *idesc,
428 int unit_num, int referenced,
429 INT in_GRi, INT in_GRj, INT out_GRk,
430 INT out_ICCi_1)
431 {
432 int cycles;
433
434 /* icc0-icc4 are the upper 4 fields of the CCR. */
435 if (out_ICCi_1 >= 0)
436 out_ICCi_1 += 4;
437
438 if (model_insn == FRV_INSN_MODEL_PASS_1)
439 {
440 /* The entire VLIW insn must wait if there is a dependency on a register
441 which is not ready yet. */
442 vliw_wait_for_GR (cpu, in_GRi);
443 vliw_wait_for_GR (cpu, in_GRj);
444 vliw_wait_for_GR (cpu, out_GRk);
445 vliw_wait_for_CCR (cpu, out_ICCi_1);
446 handle_resource_wait (cpu);
447 load_wait_for_GR (cpu, in_GRi);
448 load_wait_for_GR (cpu, in_GRj);
449 load_wait_for_GR (cpu, out_GRk);
450 trace_vliw_wait_cycles (cpu);
451 return 0;
452 }
453
454 fr550_reset_ccr_flags (cpu, out_ICCi_1);
455
456 /* GRk is available immediately to the next VLIW insn as is ICCi_1. */
457 cycles = idesc->timing->units[unit_num].done;
458 return cycles;
459 }
460
461 int
462 frvbf_model_fr550_u_imul (SIM_CPU *cpu, const IDESC *idesc,
463 int unit_num, int referenced,
464 INT in_GRi, INT in_GRj, INT out_GRk, INT out_ICCi_1)
465 {
466 int cycles;
467 /* icc0-icc4 are the upper 4 fields of the CCR. */
468 if (out_ICCi_1 >= 0)
469 out_ICCi_1 += 4;
470
471 if (model_insn == FRV_INSN_MODEL_PASS_1)
472 {
473 /* The entire VLIW insn must wait if there is a dependency on a register
474 which is not ready yet. */
475 vliw_wait_for_GR (cpu, in_GRi);
476 vliw_wait_for_GR (cpu, in_GRj);
477 vliw_wait_for_GRdouble (cpu, out_GRk);
478 vliw_wait_for_CCR (cpu, out_ICCi_1);
479 handle_resource_wait (cpu);
480 load_wait_for_GR (cpu, in_GRi);
481 load_wait_for_GR (cpu, in_GRj);
482 load_wait_for_GRdouble (cpu, out_GRk);
483 trace_vliw_wait_cycles (cpu);
484 return 0;
485 }
486
487 /* GRk has a latency of 1 cycles. */
488 cycles = idesc->timing->units[unit_num].done;
489 update_GRdouble_latency (cpu, out_GRk, cycles + 1);
490
491 /* ICCi_1 has a latency of 1 cycle. */
492 update_CCR_latency (cpu, out_ICCi_1, cycles + 1);
493
494 fr550_reset_ccr_flags (cpu, out_ICCi_1);
495
496 return cycles;
497 }
498
499 int
500 frvbf_model_fr550_u_idiv (SIM_CPU *cpu, const IDESC *idesc,
501 int unit_num, int referenced,
502 INT in_GRi, INT in_GRj, INT out_GRk, INT out_ICCi_1)
503 {
504 int cycles;
505 FRV_VLIW *vliw;
506 int slot;
507
508 /* icc0-icc4 are the upper 4 fields of the CCR. */
509 if (out_ICCi_1 >= 0)
510 out_ICCi_1 += 4;
511
512 vliw = CPU_VLIW (cpu);
513 slot = vliw->next_slot - 1;
514 slot = (*vliw->current_vliw)[slot] - UNIT_I0;
515
516 if (model_insn == FRV_INSN_MODEL_PASS_1)
517 {
518 /* The entire VLIW insn must wait if there is a dependency on a register
519 which is not ready yet. */
520 vliw_wait_for_GR (cpu, in_GRi);
521 vliw_wait_for_GR (cpu, in_GRj);
522 vliw_wait_for_GR (cpu, out_GRk);
523 vliw_wait_for_CCR (cpu, out_ICCi_1);
524 vliw_wait_for_idiv_resource (cpu, slot);
525 handle_resource_wait (cpu);
526 load_wait_for_GR (cpu, in_GRi);
527 load_wait_for_GR (cpu, in_GRj);
528 load_wait_for_GR (cpu, out_GRk);
529 trace_vliw_wait_cycles (cpu);
530 return 0;
531 }
532
533 /* GRk has a latency of 18 cycles! */
534 cycles = idesc->timing->units[unit_num].done;
535 update_GR_latency (cpu, out_GRk, cycles + 18);
536
537 /* ICCi_1 has a latency of 18 cycles. */
538 update_CCR_latency (cpu, out_ICCi_1, cycles + 18);
539
540 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
541 {
542 /* GNER has a latency of 18 cycles. */
543 update_SPR_latency (cpu, GNER_FOR_GR (out_GRk), cycles + 18);
544 }
545
546 /* the idiv resource has a latency of 18 cycles! */
547 update_idiv_resource_latency (cpu, slot, cycles + 18);
548
549 fr550_reset_ccr_flags (cpu, out_ICCi_1);
550
551 return cycles;
552 }
553
554 int
555 frvbf_model_fr550_u_branch (SIM_CPU *cpu, const IDESC *idesc,
556 int unit_num, int referenced,
557 INT in_GRi, INT in_GRj,
558 INT in_ICCi_2, INT in_FCCi_2)
559 {
560 int cycles;
561 FRV_PROFILE_STATE *ps;
562
563 if (model_insn == FRV_INSN_MODEL_PASS_1)
564 {
565 /* icc0-icc4 are the upper 4 fields of the CCR. */
566 if (in_ICCi_2 >= 0)
567 in_ICCi_2 += 4;
568
569 /* The entire VLIW insn must wait if there is a dependency on a register
570 which is not ready yet. */
571 vliw_wait_for_GR (cpu, in_GRi);
572 vliw_wait_for_GR (cpu, in_GRj);
573 vliw_wait_for_CCR (cpu, in_ICCi_2);
574 vliw_wait_for_CCR (cpu, in_FCCi_2);
575 handle_resource_wait (cpu);
576 load_wait_for_GR (cpu, in_GRi);
577 load_wait_for_GR (cpu, in_GRj);
578 trace_vliw_wait_cycles (cpu);
579 return 0;
580 }
581
582 /* When counting branches taken or not taken, don't consider branches after
583 the first taken branch in a vliw insn. */
584 ps = CPU_PROFILE_STATE (cpu);
585 if (! ps->vliw_branch_taken)
586 {
587 /* (1 << 4): The pc is the 5th element in inputs, outputs.
588 ??? can be cleaned up */
589 PROFILE_DATA *p = CPU_PROFILE_DATA (cpu);
590 int taken = (referenced & (1 << 4)) != 0;
591 if (taken)
592 {
593 ++PROFILE_MODEL_TAKEN_COUNT (p);
594 ps->vliw_branch_taken = 1;
595 }
596 else
597 ++PROFILE_MODEL_UNTAKEN_COUNT (p);
598 }
599
600 cycles = idesc->timing->units[unit_num].done;
601 return cycles;
602 }
603
604 int
605 frvbf_model_fr550_u_trap (SIM_CPU *cpu, const IDESC *idesc,
606 int unit_num, int referenced,
607 INT in_GRi, INT in_GRj,
608 INT in_ICCi_2, INT in_FCCi_2)
609 {
610 int cycles;
611
612 if (model_insn == FRV_INSN_MODEL_PASS_1)
613 {
614 /* icc0-icc4 are the upper 4 fields of the CCR. */
615 if (in_ICCi_2 >= 0)
616 in_ICCi_2 += 4;
617
618 /* The entire VLIW insn must wait if there is a dependency on a register
619 which is not ready yet. */
620 vliw_wait_for_GR (cpu, in_GRi);
621 vliw_wait_for_GR (cpu, in_GRj);
622 vliw_wait_for_CCR (cpu, in_ICCi_2);
623 vliw_wait_for_CCR (cpu, in_FCCi_2);
624 handle_resource_wait (cpu);
625 load_wait_for_GR (cpu, in_GRi);
626 load_wait_for_GR (cpu, in_GRj);
627 trace_vliw_wait_cycles (cpu);
628 return 0;
629 }
630
631 cycles = idesc->timing->units[unit_num].done;
632 return cycles;
633 }
634
635 int
636 frvbf_model_fr550_u_check (SIM_CPU *cpu, const IDESC *idesc,
637 int unit_num, int referenced,
638 INT in_ICCi_3, INT in_FCCi_3)
639 {
640 /* Modelling for this unit is the same as for fr500. */
641 return frvbf_model_fr500_u_check (cpu, idesc, unit_num, referenced,
642 in_ICCi_3, in_FCCi_3);
643 }
644
645 int
646 frvbf_model_fr550_u_set_hilo (SIM_CPU *cpu, const IDESC *idesc,
647 int unit_num, int referenced,
648 INT out_GRkhi, INT out_GRklo)
649 {
650 int cycles;
651
652 if (model_insn == FRV_INSN_MODEL_PASS_1)
653 {
654 /* The entire VLIW insn must wait if there is a dependency on a GR
655 which is not ready yet. */
656 vliw_wait_for_GR (cpu, out_GRkhi);
657 vliw_wait_for_GR (cpu, out_GRklo);
658 handle_resource_wait (cpu);
659 load_wait_for_GR (cpu, out_GRkhi);
660 load_wait_for_GR (cpu, out_GRklo);
661 trace_vliw_wait_cycles (cpu);
662 return 0;
663 }
664
665 /* GRk is available immediately to the next VLIW insn. */
666 cycles = idesc->timing->units[unit_num].done;
667
668 return cycles;
669 }
670
671 int
672 frvbf_model_fr550_u_gr_load (SIM_CPU *cpu, const IDESC *idesc,
673 int unit_num, int referenced,
674 INT in_GRi, INT in_GRj,
675 INT out_GRk, INT out_GRdoublek)
676 {
677 int cycles;
678
679 if (model_insn == FRV_INSN_MODEL_PASS_1)
680 {
681 /* The entire VLIW insn must wait if there is a dependency on a register
682 which is not ready yet. */
683 vliw_wait_for_GR (cpu, in_GRi);
684 vliw_wait_for_GR (cpu, in_GRj);
685 vliw_wait_for_GR (cpu, out_GRk);
686 vliw_wait_for_GRdouble (cpu, out_GRdoublek);
687 handle_resource_wait (cpu);
688 load_wait_for_GR (cpu, in_GRi);
689 load_wait_for_GR (cpu, in_GRj);
690 load_wait_for_GR (cpu, out_GRk);
691 load_wait_for_GRdouble (cpu, out_GRdoublek);
692 trace_vliw_wait_cycles (cpu);
693 return 0;
694 }
695
696 cycles = idesc->timing->units[unit_num].done;
697
698 /* The latency of GRk for a load will depend on how long it takes to retrieve
699 the the data from the cache or memory. */
700 update_GR_latency_for_load (cpu, out_GRk, cycles);
701 update_GRdouble_latency_for_load (cpu, out_GRdoublek, cycles);
702
703 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
704 {
705 /* GNER has a latency of 2 cycles. */
706 update_SPR_latency (cpu, GNER_FOR_GR (out_GRk), cycles + 2);
707 update_SPR_latency (cpu, GNER_FOR_GR (out_GRdoublek), cycles + 2);
708 }
709
710 return cycles;
711 }
712
713 int
714 frvbf_model_fr550_u_gr_store (SIM_CPU *cpu, const IDESC *idesc,
715 int unit_num, int referenced,
716 INT in_GRi, INT in_GRj,
717 INT in_GRk, INT in_GRdoublek)
718 {
719 int cycles;
720
721 if (model_insn == FRV_INSN_MODEL_PASS_1)
722 {
723 /* The entire VLIW insn must wait if there is a dependency on a register
724 which is not ready yet. */
725 vliw_wait_for_GR (cpu, in_GRi);
726 vliw_wait_for_GR (cpu, in_GRj);
727 vliw_wait_for_GR (cpu, in_GRk);
728 vliw_wait_for_GRdouble (cpu, in_GRdoublek);
729 handle_resource_wait (cpu);
730 load_wait_for_GR (cpu, in_GRi);
731 load_wait_for_GR (cpu, in_GRj);
732 load_wait_for_GR (cpu, in_GRk);
733 load_wait_for_GRdouble (cpu, in_GRdoublek);
734 trace_vliw_wait_cycles (cpu);
735 return 0;
736 }
737
738 /* The target register is available immediately. */
739 cycles = idesc->timing->units[unit_num].done;
740
741 return cycles;
742 }
743
744 int
745 frvbf_model_fr550_u_fr_load (SIM_CPU *cpu, const IDESC *idesc,
746 int unit_num, int referenced,
747 INT in_GRi, INT in_GRj,
748 INT out_FRk, INT out_FRdoublek)
749 {
750 int cycles;
751 if (model_insn == FRV_INSN_MODEL_PASS_1)
752 {
753 /* The entire VLIW insn must wait if there is a dependency on a register
754 which is not ready yet.
755 The latency of the registers may be less than previously recorded,
756 depending on how they were used previously.
757 See Table 13-8 in the LSI. */
758 adjust_float_register_busy (cpu, -1, 1, -1, 1, out_FRk, 1);
759 adjust_float_register_busy (cpu, -1, 1, -1, 1, out_FRdoublek, 2);
760 vliw_wait_for_GR (cpu, in_GRi);
761 vliw_wait_for_GR (cpu, in_GRj);
762 vliw_wait_for_FR (cpu, out_FRk);
763 vliw_wait_for_FRdouble (cpu, out_FRdoublek);
764 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
765 {
766 vliw_wait_for_SPR (cpu, FNER_FOR_FR (out_FRk));
767 vliw_wait_for_SPR (cpu, FNER_FOR_FR (out_FRdoublek));
768 }
769 handle_resource_wait (cpu);
770 load_wait_for_GR (cpu, in_GRi);
771 load_wait_for_GR (cpu, in_GRj);
772 load_wait_for_FR (cpu, out_FRk);
773 load_wait_for_FRdouble (cpu, out_FRdoublek);
774 trace_vliw_wait_cycles (cpu);
775 return 0;
776 }
777
778 cycles = idesc->timing->units[unit_num].done;
779
780 /* The latency of FRk for a load will depend on how long it takes to retrieve
781 the the data from the cache or memory. */
782 update_FR_latency_for_load (cpu, out_FRk, cycles);
783 update_FRdouble_latency_for_load (cpu, out_FRdoublek, cycles);
784
785 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
786 {
787 /* FNER has a latency of 3 cycles. */
788 update_SPR_latency (cpu, FNER_FOR_FR (out_FRk), cycles + 3);
789 update_SPR_latency (cpu, FNER_FOR_FR (out_FRdoublek), cycles + 3);
790 }
791
792 if (out_FRk >= 0)
793 set_use_is_fr_load (cpu, out_FRk);
794 if (out_FRdoublek >= 0)
795 {
796 set_use_is_fr_load (cpu, out_FRdoublek);
797 set_use_is_fr_load (cpu, out_FRdoublek + 1);
798 }
799
800 return cycles;
801 }
802
803 int
804 frvbf_model_fr550_u_fr_store (SIM_CPU *cpu, const IDESC *idesc,
805 int unit_num, int referenced,
806 INT in_GRi, INT in_GRj,
807 INT in_FRk, INT in_FRdoublek)
808 {
809 int cycles;
810
811 if (model_insn == FRV_INSN_MODEL_PASS_1)
812 {
813 /* The entire VLIW insn must wait if there is a dependency on a register
814 which is not ready yet. */
815 adjust_float_register_busy (cpu, in_FRk, 1, -1, 1, -1, 1);
816 adjust_float_register_busy (cpu, in_FRdoublek, 2, -1, 1, -1, 1);
817 vliw_wait_for_GR (cpu, in_GRi);
818 vliw_wait_for_GR (cpu, in_GRj);
819 vliw_wait_for_FR (cpu, in_FRk);
820 vliw_wait_for_FRdouble (cpu, in_FRdoublek);
821 handle_resource_wait (cpu);
822 load_wait_for_GR (cpu, in_GRi);
823 load_wait_for_GR (cpu, in_GRj);
824 load_wait_for_FR (cpu, in_FRk);
825 load_wait_for_FRdouble (cpu, in_FRdoublek);
826 trace_vliw_wait_cycles (cpu);
827 return 0;
828 }
829
830 /* The target register is available immediately. */
831 cycles = idesc->timing->units[unit_num].done;
832
833 return cycles;
834 }
835
836 int
837 frvbf_model_fr550_u_ici (SIM_CPU *cpu, const IDESC *idesc,
838 int unit_num, int referenced,
839 INT in_GRi, INT in_GRj)
840 {
841 int cycles;
842
843 if (model_insn == FRV_INSN_MODEL_PASS_1)
844 {
845 /* The entire VLIW insn must wait if there is a dependency on a register
846 which is not ready yet. */
847 vliw_wait_for_GR (cpu, in_GRi);
848 vliw_wait_for_GR (cpu, in_GRj);
849 handle_resource_wait (cpu);
850 load_wait_for_GR (cpu, in_GRi);
851 load_wait_for_GR (cpu, in_GRj);
852 trace_vliw_wait_cycles (cpu);
853 return 0;
854 }
855
856 cycles = idesc->timing->units[unit_num].done;
857 request_cache_invalidate (cpu, CPU_INSN_CACHE (cpu), cycles);
858 return cycles;
859 }
860
861 int
862 frvbf_model_fr550_u_dci (SIM_CPU *cpu, const IDESC *idesc,
863 int unit_num, int referenced,
864 INT in_GRi, INT in_GRj)
865 {
866 int cycles;
867
868 if (model_insn == FRV_INSN_MODEL_PASS_1)
869 {
870 /* The entire VLIW insn must wait if there is a dependency on a register
871 which is not ready yet. */
872 vliw_wait_for_GR (cpu, in_GRi);
873 vliw_wait_for_GR (cpu, in_GRj);
874 handle_resource_wait (cpu);
875 load_wait_for_GR (cpu, in_GRi);
876 load_wait_for_GR (cpu, in_GRj);
877 trace_vliw_wait_cycles (cpu);
878 return 0;
879 }
880
881 cycles = idesc->timing->units[unit_num].done;
882 request_cache_invalidate (cpu, CPU_DATA_CACHE (cpu), cycles);
883 return cycles;
884 }
885
886 int
887 frvbf_model_fr550_u_dcf (SIM_CPU *cpu, const IDESC *idesc,
888 int unit_num, int referenced,
889 INT in_GRi, INT in_GRj)
890 {
891 int cycles;
892
893 if (model_insn == FRV_INSN_MODEL_PASS_1)
894 {
895 /* The entire VLIW insn must wait if there is a dependency on a register
896 which is not ready yet. */
897 vliw_wait_for_GR (cpu, in_GRi);
898 vliw_wait_for_GR (cpu, in_GRj);
899 handle_resource_wait (cpu);
900 load_wait_for_GR (cpu, in_GRi);
901 load_wait_for_GR (cpu, in_GRj);
902 trace_vliw_wait_cycles (cpu);
903 return 0;
904 }
905
906 cycles = idesc->timing->units[unit_num].done;
907 request_cache_flush (cpu, CPU_DATA_CACHE (cpu), cycles);
908 return cycles;
909 }
910
911 int
912 frvbf_model_fr550_u_icpl (SIM_CPU *cpu, const IDESC *idesc,
913 int unit_num, int referenced,
914 INT in_GRi, INT in_GRj)
915 {
916 int cycles;
917
918 if (model_insn == FRV_INSN_MODEL_PASS_1)
919 {
920 /* The entire VLIW insn must wait if there is a dependency on a register
921 which is not ready yet. */
922 vliw_wait_for_GR (cpu, in_GRi);
923 vliw_wait_for_GR (cpu, in_GRj);
924 handle_resource_wait (cpu);
925 load_wait_for_GR (cpu, in_GRi);
926 load_wait_for_GR (cpu, in_GRj);
927 trace_vliw_wait_cycles (cpu);
928 return 0;
929 }
930
931 cycles = idesc->timing->units[unit_num].done;
932 request_cache_preload (cpu, CPU_INSN_CACHE (cpu), cycles);
933 return cycles;
934 }
935
936 int
937 frvbf_model_fr550_u_dcpl (SIM_CPU *cpu, const IDESC *idesc,
938 int unit_num, int referenced,
939 INT in_GRi, INT in_GRj)
940 {
941 int cycles;
942
943 if (model_insn == FRV_INSN_MODEL_PASS_1)
944 {
945 /* The entire VLIW insn must wait if there is a dependency on a register
946 which is not ready yet. */
947 vliw_wait_for_GR (cpu, in_GRi);
948 vliw_wait_for_GR (cpu, in_GRj);
949 handle_resource_wait (cpu);
950 load_wait_for_GR (cpu, in_GRi);
951 load_wait_for_GR (cpu, in_GRj);
952 trace_vliw_wait_cycles (cpu);
953 return 0;
954 }
955
956 cycles = idesc->timing->units[unit_num].done;
957 request_cache_preload (cpu, CPU_DATA_CACHE (cpu), cycles);
958 return cycles;
959 }
960
961 int
962 frvbf_model_fr550_u_icul (SIM_CPU *cpu, const IDESC *idesc,
963 int unit_num, int referenced,
964 INT in_GRi, INT in_GRj)
965 {
966 int cycles;
967
968 if (model_insn == FRV_INSN_MODEL_PASS_1)
969 {
970 /* The entire VLIW insn must wait if there is a dependency on a register
971 which is not ready yet. */
972 vliw_wait_for_GR (cpu, in_GRi);
973 vliw_wait_for_GR (cpu, in_GRj);
974 handle_resource_wait (cpu);
975 load_wait_for_GR (cpu, in_GRi);
976 load_wait_for_GR (cpu, in_GRj);
977 trace_vliw_wait_cycles (cpu);
978 return 0;
979 }
980
981 cycles = idesc->timing->units[unit_num].done;
982 request_cache_unlock (cpu, CPU_INSN_CACHE (cpu), cycles);
983 return cycles;
984 }
985
986 int
987 frvbf_model_fr550_u_dcul (SIM_CPU *cpu, const IDESC *idesc,
988 int unit_num, int referenced,
989 INT in_GRi, INT in_GRj)
990 {
991 int cycles;
992
993 if (model_insn == FRV_INSN_MODEL_PASS_1)
994 {
995 /* The entire VLIW insn must wait if there is a dependency on a register
996 which is not ready yet. */
997 vliw_wait_for_GR (cpu, in_GRi);
998 vliw_wait_for_GR (cpu, in_GRj);
999 handle_resource_wait (cpu);
1000 load_wait_for_GR (cpu, in_GRi);
1001 load_wait_for_GR (cpu, in_GRj);
1002 trace_vliw_wait_cycles (cpu);
1003 return 0;
1004 }
1005
1006 cycles = idesc->timing->units[unit_num].done;
1007 request_cache_unlock (cpu, CPU_DATA_CACHE (cpu), cycles);
1008 return cycles;
1009 }
1010
1011 int
1012 frvbf_model_fr550_u_float_arith (SIM_CPU *cpu, const IDESC *idesc,
1013 int unit_num, int referenced,
1014 INT in_FRi, INT in_FRj,
1015 INT in_FRdoublei, INT in_FRdoublej,
1016 INT out_FRk, INT out_FRdoublek)
1017 {
1018 int cycles;
1019 FRV_PROFILE_STATE *ps;
1020 FRV_VLIW *vliw;
1021 int slot;
1022
1023 if (model_insn == FRV_INSN_MODEL_PASS_1)
1024 return 0;
1025
1026 /* The preprocessing can execute right away. */
1027 cycles = idesc->timing->units[unit_num].done;
1028
1029 /* The post processing must wait if there is a dependency on a FR
1030 which is not ready yet. */
1031 adjust_float_register_busy (cpu, in_FRi, 1, in_FRj, 1, out_FRk, 1);
1032 adjust_float_register_busy (cpu, in_FRdoublei, 2, in_FRdoublej, 2, out_FRdoublek, 2);
1033 ps = CPU_PROFILE_STATE (cpu);
1034 ps->post_wait = cycles;
1035 vliw = CPU_VLIW (cpu);
1036 slot = vliw->next_slot - 1;
1037 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
1038 post_wait_for_float (cpu, slot);
1039 post_wait_for_FR (cpu, in_FRi);
1040 post_wait_for_FR (cpu, in_FRj);
1041 post_wait_for_FR (cpu, out_FRk);
1042 post_wait_for_FRdouble (cpu, in_FRdoublei);
1043 post_wait_for_FRdouble (cpu, in_FRdoublej);
1044 post_wait_for_FRdouble (cpu, out_FRdoublek);
1045 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
1046 {
1047 post_wait_for_SPR (cpu, FNER_FOR_FR (out_FRk));
1048 post_wait_for_SPR (cpu, FNER_FOR_FR (out_FRdoublek));
1049 }
1050 restore_float_register_busy (cpu, in_FRi, 1, in_FRj, 1, out_FRk, 1);
1051 restore_float_register_busy (cpu, in_FRdoublei, 2, in_FRdoublej, 2, out_FRdoublek, 2);
1052
1053 /* The latency of FRk will be at least the latency of the other inputs. */
1054 update_FR_latency (cpu, out_FRk, ps->post_wait);
1055 update_FRdouble_latency (cpu, out_FRdoublek, ps->post_wait);
1056
1057 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
1058 {
1059 update_SPR_latency (cpu, FNER_FOR_FR (out_FRk), ps->post_wait);
1060 update_SPR_latency (cpu, FNER_FOR_FR (out_FRdoublek), ps->post_wait);
1061 }
1062
1063 /* Once initiated, post-processing will take 2 cycles. */
1064 update_FR_ptime (cpu, out_FRk, 2);
1065 update_FRdouble_ptime (cpu, out_FRdoublek, 2);
1066 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
1067 {
1068 update_SPR_ptime (cpu, FNER_FOR_FR (out_FRk), 2);
1069 update_SPR_ptime (cpu, FNER_FOR_FR (out_FRdoublek), 2);
1070 }
1071
1072 /* Mark this use of the register as a floating point op. */
1073 if (out_FRk >= 0)
1074 set_use_is_fr_complex_2 (cpu, out_FRk);
1075 if (out_FRdoublek >= 0)
1076 {
1077 set_use_is_fr_complex_2 (cpu, out_FRdoublek);
1078 if (out_FRdoublek < 63)
1079 set_use_is_fr_complex_2 (cpu, out_FRdoublek + 1);
1080 }
1081
1082 /* the media point unit resource has a latency of 4 cycles */
1083 update_media_resource_latency (cpu, slot, cycles + 4);
1084
1085 return cycles;
1086 }
1087
1088 int
1089 frvbf_model_fr550_u_float_dual_arith (SIM_CPU *cpu, const IDESC *idesc,
1090 int unit_num, int referenced,
1091 INT in_FRi, INT in_FRj,
1092 INT in_FRdoublei, INT in_FRdoublej,
1093 INT out_FRk, INT out_FRdoublek)
1094 {
1095 int cycles;
1096 INT dual_FRi;
1097 INT dual_FRj;
1098 INT dual_FRk;
1099 INT dual_FRdoublei;
1100 INT dual_FRdoublej;
1101 INT dual_FRdoublek;
1102 FRV_PROFILE_STATE *ps;
1103 FRV_VLIW *vliw;
1104 int slot;
1105
1106 if (model_insn == FRV_INSN_MODEL_PASS_1)
1107 return 0;
1108
1109 /* The preprocessing can execute right away. */
1110 cycles = idesc->timing->units[unit_num].done;
1111
1112 /* The post processing must wait if there is a dependency on a FR
1113 which is not ready yet. */
1114 dual_FRi = DUAL_REG (in_FRi);
1115 dual_FRj = DUAL_REG (in_FRj);
1116 dual_FRk = DUAL_REG (out_FRk);
1117 dual_FRdoublei = DUAL_DOUBLE (in_FRdoublei);
1118 dual_FRdoublej = DUAL_DOUBLE (in_FRdoublej);
1119 dual_FRdoublek = DUAL_DOUBLE (out_FRdoublek);
1120
1121 adjust_float_register_busy (cpu, in_FRi, 2, in_FRj, 2, out_FRk, 2);
1122 adjust_float_register_busy (cpu, in_FRdoublei, 4, in_FRdoublej, 4, out_FRdoublek, 4);
1123 ps = CPU_PROFILE_STATE (cpu);
1124 ps->post_wait = cycles;
1125 vliw = CPU_VLIW (cpu);
1126 slot = vliw->next_slot - 1;
1127 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
1128 post_wait_for_float (cpu, slot);
1129 post_wait_for_FR (cpu, in_FRi);
1130 post_wait_for_FR (cpu, in_FRj);
1131 post_wait_for_FR (cpu, out_FRk);
1132 post_wait_for_FR (cpu, dual_FRi);
1133 post_wait_for_FR (cpu, dual_FRj);
1134 post_wait_for_FR (cpu, dual_FRk);
1135 post_wait_for_FRdouble (cpu, in_FRdoublei);
1136 post_wait_for_FRdouble (cpu, in_FRdoublej);
1137 post_wait_for_FRdouble (cpu, out_FRdoublek);
1138 post_wait_for_FRdouble (cpu, dual_FRdoublei);
1139 post_wait_for_FRdouble (cpu, dual_FRdoublej);
1140 post_wait_for_FRdouble (cpu, dual_FRdoublek);
1141 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
1142 {
1143 post_wait_for_SPR (cpu, FNER_FOR_FR (out_FRk));
1144 post_wait_for_SPR (cpu, FNER_FOR_FR (dual_FRk));
1145 post_wait_for_SPR (cpu, FNER_FOR_FR (out_FRdoublek));
1146 post_wait_for_SPR (cpu, FNER_FOR_FR (dual_FRdoublek));
1147 }
1148 restore_float_register_busy (cpu, in_FRi, 2, in_FRj, 2, out_FRk, 2);
1149 restore_float_register_busy (cpu, in_FRdoublei, 4, in_FRdoublej, 4, out_FRdoublek, 4);
1150
1151 /* The latency of FRk will be at least the latency of the other inputs. */
1152 update_FR_latency (cpu, out_FRk, ps->post_wait);
1153 update_FR_latency (cpu, dual_FRk, ps->post_wait);
1154 update_FRdouble_latency (cpu, out_FRdoublek, ps->post_wait);
1155 update_FRdouble_latency (cpu, dual_FRdoublek, ps->post_wait);
1156
1157 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
1158 {
1159 update_SPR_latency (cpu, FNER_FOR_FR (out_FRk), ps->post_wait);
1160 update_SPR_latency (cpu, FNER_FOR_FR (dual_FRk), ps->post_wait);
1161 update_SPR_latency (cpu, FNER_FOR_FR (out_FRdoublek), ps->post_wait);
1162 update_SPR_latency (cpu, FNER_FOR_FR (dual_FRdoublek), ps->post_wait);
1163 }
1164
1165 /* Once initiated, post-processing will take 3 cycles. */
1166 update_FR_ptime (cpu, out_FRk, 3);
1167 update_FR_ptime (cpu, dual_FRk, 3);
1168 update_FRdouble_ptime (cpu, out_FRdoublek, 3);
1169 update_FRdouble_ptime (cpu, dual_FRdoublek, 3);
1170
1171 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
1172 {
1173 update_SPR_ptime (cpu, FNER_FOR_FR (out_FRk), 3);
1174 update_SPR_ptime (cpu, FNER_FOR_FR (dual_FRk), 3);
1175 update_SPR_ptime (cpu, FNER_FOR_FR (out_FRdoublek), 3);
1176 update_SPR_ptime (cpu, FNER_FOR_FR (dual_FRdoublek), 3);
1177 }
1178
1179 /* Mark this use of the register as a floating point op. */
1180 if (out_FRk >= 0)
1181 fr550_reset_fr_flags (cpu, out_FRk);
1182 if (dual_FRk >= 0)
1183 fr550_reset_fr_flags (cpu, dual_FRk);
1184 if (out_FRdoublek >= 0)
1185 {
1186 fr550_reset_fr_flags (cpu, out_FRdoublek);
1187 if (out_FRdoublek < 63)
1188 fr550_reset_fr_flags (cpu, out_FRdoublek + 1);
1189 }
1190 if (dual_FRdoublek >= 0)
1191 {
1192 fr550_reset_fr_flags (cpu, dual_FRdoublek);
1193 if (dual_FRdoublek < 63)
1194 fr550_reset_fr_flags (cpu, dual_FRdoublek + 1);
1195 }
1196
1197 /* the media point unit resource has a latency of 5 cycles */
1198 update_media_resource_latency (cpu, slot, cycles + 5);
1199
1200 return cycles;
1201 }
1202
1203 int
1204 frvbf_model_fr550_u_float_div (SIM_CPU *cpu, const IDESC *idesc,
1205 int unit_num, int referenced,
1206 INT in_FRi, INT in_FRj, INT out_FRk)
1207 {
1208 int cycles;
1209 FRV_VLIW *vliw;
1210 int slot;
1211 FRV_PROFILE_STATE *ps;
1212
1213 if (model_insn == FRV_INSN_MODEL_PASS_1)
1214 return 0;
1215
1216 cycles = idesc->timing->units[unit_num].done;
1217
1218 /* The post processing must wait if there is a dependency on a FR
1219 which is not ready yet. */
1220 adjust_float_register_busy (cpu, in_FRi, 1, in_FRj, 1, out_FRk, 1);
1221 ps = CPU_PROFILE_STATE (cpu);
1222 ps->post_wait = cycles;
1223 vliw = CPU_VLIW (cpu);
1224 slot = vliw->next_slot - 1;
1225 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
1226 post_wait_for_float (cpu, slot);
1227 post_wait_for_fdiv (cpu, slot);
1228 post_wait_for_FR (cpu, in_FRi);
1229 post_wait_for_FR (cpu, in_FRj);
1230 post_wait_for_FR (cpu, out_FRk);
1231 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
1232 post_wait_for_SPR (cpu, FNER_FOR_FR (out_FRk));
1233 restore_float_register_busy (cpu, in_FRi, 1, in_FRj, 1, out_FRk, 1);
1234
1235 /* The latency of FRk will be at least the latency of the other inputs. */
1236 /* Once initiated, post-processing will take 9 cycles. */
1237 update_FR_latency (cpu, out_FRk, ps->post_wait);
1238 update_FR_ptime (cpu, out_FRk, 9);
1239
1240 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
1241 {
1242 /* FNER has a latency of 9 cycles. */
1243 update_SPR_latency (cpu, FNER_FOR_FR (out_FRk), ps->post_wait);
1244 update_SPR_ptime (cpu, FNER_FOR_FR (out_FRk), 9);
1245 }
1246
1247 /* The latency of the fdiv unit will be at least the latency of the other
1248 inputs. Once initiated, post-processing will take 9 cycles. */
1249 update_fdiv_resource_latency (cpu, slot, ps->post_wait + 9);
1250
1251 /* the media point unit resource has a latency of 11 cycles */
1252 update_media_resource_latency (cpu, slot, cycles + 11);
1253
1254 fr550_reset_fr_flags (cpu, out_FRk);
1255
1256 return cycles;
1257 }
1258
1259 int
1260 frvbf_model_fr550_u_float_sqrt (SIM_CPU *cpu, const IDESC *idesc,
1261 int unit_num, int referenced,
1262 INT in_FRj, INT in_FRdoublej,
1263 INT out_FRk, INT out_FRdoublek)
1264 {
1265 int cycles;
1266 FRV_VLIW *vliw;
1267 int slot;
1268 FRV_PROFILE_STATE *ps;
1269
1270 if (model_insn == FRV_INSN_MODEL_PASS_1)
1271 return 0;
1272
1273 cycles = idesc->timing->units[unit_num].done;
1274
1275 /* The post processing must wait if there is a dependency on a FR
1276 which is not ready yet. */
1277 adjust_float_register_busy (cpu, -1, 1, in_FRj, 1, out_FRk, 1);
1278 adjust_float_register_busy (cpu, -1, 1, in_FRdoublej, 2, out_FRdoublek, 2);
1279 ps = CPU_PROFILE_STATE (cpu);
1280 ps->post_wait = cycles;
1281 vliw = CPU_VLIW (cpu);
1282 slot = vliw->next_slot - 1;
1283 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
1284 post_wait_for_float (cpu, slot);
1285 post_wait_for_fsqrt (cpu, slot);
1286 post_wait_for_FR (cpu, in_FRj);
1287 post_wait_for_FR (cpu, out_FRk);
1288 post_wait_for_FRdouble (cpu, in_FRdoublej);
1289 post_wait_for_FRdouble (cpu, out_FRdoublek);
1290 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
1291 {
1292 post_wait_for_SPR (cpu, FNER_FOR_FR (out_FRk));
1293 post_wait_for_SPR (cpu, FNER_FOR_FR (out_FRdoublek));
1294 }
1295 restore_float_register_busy (cpu, -1, 1, in_FRj, 1, out_FRk, 1);
1296 restore_float_register_busy (cpu, -1, 1, in_FRdoublej, 2, out_FRdoublek, 2);
1297
1298 /* The latency of FRk will be at least the latency of the other inputs. */
1299 update_FR_latency (cpu, out_FRk, ps->post_wait);
1300 update_FRdouble_latency (cpu, out_FRdoublek, ps->post_wait);
1301
1302 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
1303 {
1304 /* FNER has a latency of 14 cycles. */
1305 update_SPR_latency (cpu, FNER_FOR_FR (out_FRk), ps->post_wait);
1306 update_SPR_latency (cpu, FNER_FOR_FR (out_FRdoublek), ps->post_wait);
1307 }
1308
1309 /* Once initiated, post-processing will take 14 cycles. */
1310 update_FR_ptime (cpu, out_FRk, 14);
1311 update_FRdouble_ptime (cpu, out_FRdoublek, 14);
1312
1313 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
1314 {
1315 /* FNER has a latency of 14 cycles. */
1316 update_SPR_ptime (cpu, FNER_FOR_FR (out_FRk), 14);
1317 update_SPR_ptime (cpu, FNER_FOR_FR (out_FRdoublek), 14);
1318 }
1319
1320 /* The latency of the sqrt unit will be the latency of the other
1321 inputs plus 14 cycles. */
1322 update_fsqrt_resource_latency (cpu, slot, ps->post_wait + 14);
1323
1324 fr550_reset_fr_flags (cpu, out_FRk);
1325 if (out_FRdoublek != -1)
1326 {
1327 fr550_reset_fr_flags (cpu, out_FRdoublek);
1328 fr550_reset_fr_flags (cpu, out_FRdoublek + 1);
1329 }
1330
1331 /* the media point unit resource has a latency of 16 cycles */
1332 update_media_resource_latency (cpu, slot, cycles + 16);
1333
1334 return cycles;
1335 }
1336
1337 int
1338 frvbf_model_fr550_u_float_compare (SIM_CPU *cpu, const IDESC *idesc,
1339 int unit_num, int referenced,
1340 INT in_FRi, INT in_FRj,
1341 INT in_FRdoublei, INT in_FRdoublej,
1342 INT out_FCCi_2)
1343 {
1344 int cycles;
1345 FRV_PROFILE_STATE *ps;
1346 FRV_VLIW *vliw;
1347 int slot;
1348
1349 if (model_insn == FRV_INSN_MODEL_PASS_1)
1350 return 0;
1351
1352 /* The preprocessing can execute right away. */
1353 cycles = idesc->timing->units[unit_num].done;
1354
1355 /* The post processing must wait if there is a dependency on a FR
1356 which is not ready yet. */
1357 adjust_float_register_busy (cpu, in_FRi, 1, in_FRj, 1, -1, 1);
1358 adjust_float_register_busy (cpu, in_FRdoublei, 2, in_FRdoublej, 2, -1, 1);
1359 ps = CPU_PROFILE_STATE (cpu);
1360 ps->post_wait = cycles;
1361 vliw = CPU_VLIW (cpu);
1362 slot = vliw->next_slot - 1;
1363 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
1364 post_wait_for_float (cpu, slot);
1365 post_wait_for_FR (cpu, in_FRi);
1366 post_wait_for_FR (cpu, in_FRj);
1367 post_wait_for_FRdouble (cpu, in_FRdoublei);
1368 post_wait_for_FRdouble (cpu, in_FRdoublej);
1369 post_wait_for_CCR (cpu, out_FCCi_2);
1370 restore_float_register_busy (cpu, in_FRi, 1, in_FRj, 1, -1, 1);
1371 restore_float_register_busy (cpu, in_FRdoublei, 2, in_FRdoublej, 2, -1, 1);
1372
1373 /* The latency of FCCi_2 will be the latency of the other inputs plus 2
1374 cycles. */
1375 update_CCR_latency (cpu, out_FCCi_2, ps->post_wait + 2);
1376
1377 /* the media point unit resource has a latency of 4 cycles */
1378 update_media_resource_latency (cpu, slot, cycles + 4);
1379
1380 set_use_is_ccr_complex (cpu, out_FCCi_2);
1381
1382 return cycles;
1383 }
1384
1385 int
1386 frvbf_model_fr550_u_float_dual_compare (SIM_CPU *cpu, const IDESC *idesc,
1387 int unit_num, int referenced,
1388 INT in_FRi, INT in_FRj,
1389 INT out_FCCi_2)
1390 {
1391 int cycles;
1392 INT dual_FRi;
1393 INT dual_FRj;
1394 INT dual_FCCi_2;
1395 FRV_PROFILE_STATE *ps;
1396 FRV_VLIW *vliw;
1397 int slot;
1398
1399 if (model_insn == FRV_INSN_MODEL_PASS_1)
1400 return 0;
1401
1402 /* The preprocessing can execute right away. */
1403 cycles = idesc->timing->units[unit_num].done;
1404
1405 /* The post processing must wait if there is a dependency on a FR
1406 which is not ready yet. */
1407 ps = CPU_PROFILE_STATE (cpu);
1408 ps->post_wait = cycles;
1409 dual_FRi = DUAL_REG (in_FRi);
1410 dual_FRj = DUAL_REG (in_FRj);
1411 dual_FCCi_2 = out_FCCi_2 + 1;
1412 adjust_float_register_busy (cpu, in_FRi, 2, in_FRj, 2, -1, 1);
1413 vliw = CPU_VLIW (cpu);
1414 slot = vliw->next_slot - 1;
1415 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
1416 post_wait_for_float (cpu, slot);
1417 post_wait_for_FR (cpu, in_FRi);
1418 post_wait_for_FR (cpu, in_FRj);
1419 post_wait_for_FR (cpu, dual_FRi);
1420 post_wait_for_FR (cpu, dual_FRj);
1421 post_wait_for_CCR (cpu, out_FCCi_2);
1422 post_wait_for_CCR (cpu, dual_FCCi_2);
1423 restore_float_register_busy (cpu, in_FRi, 2, in_FRj, 2, -1, 1);
1424
1425 /* The latency of FCCi_2 will be the latency of the other inputs plus 3
1426 cycles. */
1427 update_CCR_latency (cpu, out_FCCi_2, ps->post_wait + 3);
1428 update_CCR_latency (cpu, dual_FCCi_2, ps->post_wait + 3);
1429
1430 set_use_is_ccr_complex (cpu, out_FCCi_2);
1431 if (dual_FCCi_2 >= 0)
1432 set_use_is_ccr_complex (cpu, dual_FCCi_2);
1433
1434 /* the media point unit resource has a latency of 5 cycles */
1435 update_media_resource_latency (cpu, slot, cycles + 5);
1436
1437 return cycles;
1438 }
1439
1440 int
1441 frvbf_model_fr550_u_float_convert (SIM_CPU *cpu, const IDESC *idesc,
1442 int unit_num, int referenced,
1443 INT in_FRj, INT in_FRintj, INT in_FRdoublej,
1444 INT out_FRk, INT out_FRintk,
1445 INT out_FRdoublek)
1446 {
1447 int cycles;
1448 FRV_PROFILE_STATE *ps;
1449 FRV_VLIW *vliw;
1450 int slot;
1451
1452 if (model_insn == FRV_INSN_MODEL_PASS_1)
1453 return 0;
1454
1455 /* The preprocessing can execute right away. */
1456 cycles = idesc->timing->units[unit_num].done;
1457
1458 /* The post processing must wait if there is a dependency on a FR
1459 which is not ready yet. */
1460 ps = CPU_PROFILE_STATE (cpu);
1461 ps->post_wait = cycles;
1462 adjust_float_register_busy (cpu, -1, 1, in_FRj, 1, out_FRk, 1);
1463 adjust_float_register_busy (cpu, -1, 1, in_FRintj, 1, out_FRintk, 1);
1464 adjust_float_register_busy (cpu, -1, 1, in_FRdoublej, 2, out_FRdoublek, 2);
1465 vliw = CPU_VLIW (cpu);
1466 slot = vliw->next_slot - 1;
1467 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
1468 post_wait_for_float (cpu, slot);
1469 post_wait_for_FR (cpu, in_FRj);
1470 post_wait_for_FR (cpu, in_FRintj);
1471 post_wait_for_FRdouble (cpu, in_FRdoublej);
1472 post_wait_for_FR (cpu, out_FRk);
1473 post_wait_for_FR (cpu, out_FRintk);
1474 post_wait_for_FRdouble (cpu, out_FRdoublek);
1475 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
1476 {
1477 post_wait_for_SPR (cpu, FNER_FOR_FR (out_FRk));
1478 post_wait_for_SPR (cpu, FNER_FOR_FR (out_FRintk));
1479 post_wait_for_SPR (cpu, FNER_FOR_FR (out_FRdoublek));
1480 }
1481 restore_float_register_busy (cpu, -1, 1, in_FRj, 1, out_FRk, 1);
1482 restore_float_register_busy (cpu, -1, 1, in_FRintj, 1, out_FRintk, 1);
1483 restore_float_register_busy (cpu, -1, 1, in_FRdoublej, 2, out_FRdoublek, 2);
1484
1485 /* The latency of FRk will be at least the latency of the other inputs. */
1486 update_FR_latency (cpu, out_FRk, ps->post_wait);
1487 update_FR_latency (cpu, out_FRintk, ps->post_wait);
1488 update_FRdouble_latency (cpu, out_FRdoublek, ps->post_wait);
1489
1490 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
1491 {
1492 update_SPR_latency (cpu, FNER_FOR_FR (out_FRk), ps->post_wait);
1493 update_SPR_latency (cpu, FNER_FOR_FR (out_FRintk), ps->post_wait);
1494 update_SPR_latency (cpu, FNER_FOR_FR (out_FRdoublek), ps->post_wait);
1495 }
1496
1497 /* Once initiated, post-processing will take 2 cycles. */
1498 update_FR_ptime (cpu, out_FRk, 2);
1499 update_FR_ptime (cpu, out_FRintk, 2);
1500 update_FRdouble_ptime (cpu, out_FRdoublek, 2);
1501
1502 if (CGEN_ATTR_VALUE(idesc, idesc->attrs, CGEN_INSN_NON_EXCEPTING))
1503 {
1504 update_SPR_ptime (cpu, FNER_FOR_FR (out_FRk), 2);
1505 update_SPR_ptime (cpu, FNER_FOR_FR (out_FRintk), 2);
1506 update_SPR_ptime (cpu, FNER_FOR_FR (out_FRdoublek), 2);
1507 }
1508
1509 /* Mark this use of the register as a floating point op. */
1510 if (out_FRk >= 0)
1511 set_use_is_fr_complex_2 (cpu, out_FRk);
1512 if (out_FRintk >= 0)
1513 set_use_is_fr_complex_2 (cpu, out_FRintk);
1514 if (out_FRdoublek >= 0)
1515 {
1516 set_use_is_fr_complex_2 (cpu, out_FRdoublek);
1517 set_use_is_fr_complex_2 (cpu, out_FRdoublek + 1);
1518 }
1519
1520 /* the media point unit resource has a latency of 4 cycles */
1521 update_media_resource_latency (cpu, slot, cycles + 4);
1522
1523 return cycles;
1524 }
1525
1526 int
1527 frvbf_model_fr550_u_spr2gr (SIM_CPU *cpu, const IDESC *idesc,
1528 int unit_num, int referenced,
1529 INT in_spr, INT out_GRj)
1530 {
1531 /* Modelling for this unit is the same as for fr500. */
1532 return frvbf_model_fr500_u_spr2gr (cpu, idesc, unit_num, referenced,
1533 in_spr, out_GRj);
1534 }
1535
1536 int
1537 frvbf_model_fr550_u_gr2spr (SIM_CPU *cpu, const IDESC *idesc,
1538 int unit_num, int referenced,
1539 INT in_GRj, INT out_spr)
1540 {
1541 int cycles;
1542
1543 if (model_insn == FRV_INSN_MODEL_PASS_1)
1544 {
1545 /* The entire VLIW insn must wait if there is a dependency on a register
1546 which is not ready yet. */
1547 vliw_wait_for_GR (cpu, in_GRj);
1548 vliw_wait_for_SPR (cpu, out_spr);
1549 handle_resource_wait (cpu);
1550 load_wait_for_GR (cpu, in_GRj);
1551 trace_vliw_wait_cycles (cpu);
1552 return 0;
1553 }
1554
1555 cycles = idesc->timing->units[unit_num].done;
1556
1557 #if 0
1558 /* The latency of spr is ? cycles. */
1559 update_SPR_latency (cpu, out_spr, cycles + ?);
1560 #endif
1561
1562 return cycles;
1563 }
1564
1565 int
1566 frvbf_model_fr550_u_gr2fr (SIM_CPU *cpu, const IDESC *idesc,
1567 int unit_num, int referenced,
1568 INT in_GRj, INT out_FRk)
1569 {
1570 int cycles;
1571
1572 if (model_insn == FRV_INSN_MODEL_PASS_1)
1573 {
1574 /* The entire VLIW insn must wait if there is a dependency on a register
1575 which is not ready yet.
1576 The latency of the registers may be less than previously recorded,
1577 depending on how they were used previously.
1578 See Table 14-15 in the LSI. */
1579 adjust_float_register_busy (cpu, -1, 1, -1, 1, out_FRk, 1);
1580 vliw_wait_for_GR (cpu, in_GRj);
1581 vliw_wait_for_FR (cpu, out_FRk);
1582 handle_resource_wait (cpu);
1583 load_wait_for_GR (cpu, in_GRj);
1584 load_wait_for_FR (cpu, out_FRk);
1585 trace_vliw_wait_cycles (cpu);
1586 return 0;
1587 }
1588
1589 /* The latency of FRk is 1 cycles. */
1590 cycles = idesc->timing->units[unit_num].done;
1591 update_FR_latency (cpu, out_FRk, cycles + 1);
1592
1593 set_use_is_fr_complex_1 (cpu, out_FRk);
1594
1595 return cycles;
1596 }
1597
1598 int
1599 frvbf_model_fr550_u_swap (SIM_CPU *cpu, const IDESC *idesc,
1600 int unit_num, int referenced,
1601 INT in_GRi, INT in_GRj, INT out_GRk)
1602 {
1603 int cycles;
1604
1605 if (model_insn == FRV_INSN_MODEL_PASS_1)
1606 {
1607 /* The entire VLIW insn must wait if there is a dependency on a register
1608 which is not ready yet. */
1609 vliw_wait_for_GR (cpu, in_GRi);
1610 vliw_wait_for_GR (cpu, in_GRj);
1611 vliw_wait_for_GR (cpu, out_GRk);
1612 handle_resource_wait (cpu);
1613 load_wait_for_GR (cpu, in_GRi);
1614 load_wait_for_GR (cpu, in_GRj);
1615 load_wait_for_GR (cpu, out_GRk);
1616 trace_vliw_wait_cycles (cpu);
1617 return 0;
1618 }
1619
1620 cycles = idesc->timing->units[unit_num].done;
1621
1622 /* The latency of GRk will depend on how long it takes to swap
1623 the the data from the cache or memory. */
1624 update_GR_latency_for_swap (cpu, out_GRk, cycles);
1625
1626 return cycles;
1627 }
1628
1629 int
1630 frvbf_model_fr550_u_fr2fr (SIM_CPU *cpu, const IDESC *idesc,
1631 int unit_num, int referenced,
1632 INT in_FRj, INT out_FRk)
1633 {
1634 int cycles;
1635
1636 if (model_insn == FRV_INSN_MODEL_PASS_1)
1637 {
1638 /* The entire VLIW insn must wait if there is a dependency on a register
1639 which is not ready yet.
1640 The latency of the registers may be less than previously recorded,
1641 depending on how they were used previously.
1642 See Table 14-15 in the LSI. */
1643 adjust_float_register_busy (cpu, -1, 1, in_FRj, 1, out_FRk, 1);
1644 vliw_wait_for_FR (cpu, in_FRj);
1645 vliw_wait_for_FR (cpu, out_FRk);
1646 handle_resource_wait (cpu);
1647 load_wait_for_FR (cpu, in_FRj);
1648 load_wait_for_FR (cpu, out_FRk);
1649 trace_vliw_wait_cycles (cpu);
1650 return 0;
1651 }
1652
1653 /* The latency of FRj is 2 cycles. */
1654 cycles = idesc->timing->units[unit_num].done;
1655 update_FR_latency (cpu, out_FRk, cycles + 2);
1656
1657 set_use_is_fr_complex_2 (cpu, out_FRk);
1658
1659 return cycles;
1660 }
1661
1662 int
1663 frvbf_model_fr550_u_fr2gr (SIM_CPU *cpu, const IDESC *idesc,
1664 int unit_num, int referenced,
1665 INT in_FRk, INT out_GRj)
1666 {
1667 int cycles;
1668
1669 if (model_insn == FRV_INSN_MODEL_PASS_1)
1670 {
1671 /* The entire VLIW insn must wait if there is a dependency on a register
1672 which is not ready yet.
1673 The latency of the registers may be less than previously recorded,
1674 depending on how they were used previously.
1675 See Table 14-15 in the LSI. */
1676 adjust_float_register_busy (cpu, in_FRk, 1, -1, 1, -1, 1);
1677 vliw_wait_for_FR (cpu, in_FRk);
1678 vliw_wait_for_GR (cpu, out_GRj);
1679 handle_resource_wait (cpu);
1680 load_wait_for_FR (cpu, in_FRk);
1681 load_wait_for_GR (cpu, out_GRj);
1682 trace_vliw_wait_cycles (cpu);
1683 return 0;
1684 }
1685
1686 /* The latency of GRj is 1 cycle. */
1687 cycles = idesc->timing->units[unit_num].done;
1688 update_GR_latency (cpu, out_GRj, cycles + 1);
1689
1690 return cycles;
1691 }
1692
1693 int
1694 frvbf_model_fr550_u_clrgr (SIM_CPU *cpu, const IDESC *idesc,
1695 int unit_num, int referenced,
1696 INT in_GRk)
1697 {
1698 /* Modelling for this unit is the same as for fr500. */
1699 return frvbf_model_fr500_u_clrgr (cpu, idesc, unit_num, referenced, in_GRk);
1700 }
1701
1702 int
1703 frvbf_model_fr550_u_clrfr (SIM_CPU *cpu, const IDESC *idesc,
1704 int unit_num, int referenced,
1705 INT in_FRk)
1706 {
1707 /* Modelling for this unit is the same as for fr500. */
1708 return frvbf_model_fr500_u_clrfr (cpu, idesc, unit_num, referenced, in_FRk);
1709 }
1710
1711 int
1712 frvbf_model_fr550_u_commit (SIM_CPU *cpu, const IDESC *idesc,
1713 int unit_num, int referenced,
1714 INT in_GRk, INT in_FRk)
1715 {
1716 /* Modelling for this unit is the same as for fr500. */
1717 return frvbf_model_fr500_u_commit (cpu, idesc, unit_num, referenced,
1718 in_GRk, in_FRk);
1719 }
1720
1721 int
1722 frvbf_model_fr550_u_media (SIM_CPU *cpu, const IDESC *idesc,
1723 int unit_num, int referenced,
1724 INT in_FRi, INT in_FRj, INT out_FRk)
1725 {
1726 int cycles;
1727 FRV_PROFILE_STATE *ps;
1728 FRV_VLIW *vliw;
1729 int slot;
1730
1731 if (model_insn == FRV_INSN_MODEL_PASS_1)
1732 return 0;
1733
1734 /* The preprocessing can execute right away. */
1735 cycles = idesc->timing->units[unit_num].done;
1736
1737 /* If the previous use of the registers was a media op,
1738 then their latency may be less than previously recorded.
1739 See Table 14-15 in the LSI. */
1740 adjust_float_register_busy_for_media (cpu, in_FRi, 1, in_FRj, 1, out_FRk, 1);
1741
1742 /* The post processing must wait if there is a dependency on a FR
1743 which is not ready yet. */
1744 ps = CPU_PROFILE_STATE (cpu);
1745 ps->post_wait = cycles;
1746 vliw = CPU_VLIW (cpu);
1747 slot = vliw->next_slot - 1;
1748 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
1749 post_wait_for_media (cpu, slot);
1750 post_wait_for_FR (cpu, in_FRi);
1751 post_wait_for_FR (cpu, in_FRj);
1752 post_wait_for_FR (cpu, out_FRk);
1753
1754 /* Restore the busy cycles of the registers we used. */
1755 restore_float_register_busy_for_media (cpu, in_FRi, 1, in_FRj, 1, out_FRk, 1);
1756
1757 /* The latency of tht output register will be at least the latency of the
1758 other inputs. Once initiated, post-processing will take 1 cycle. */
1759 if (out_FRk >= 0)
1760 {
1761 update_FR_latency (cpu, out_FRk, ps->post_wait);
1762 update_FR_ptime (cpu, out_FRk, 1);
1763 /* Mark this use of the register as a media op. */
1764 set_use_is_fr_complex_1 (cpu, out_FRk);
1765 }
1766
1767 /* the floating point unit resource has a latency of 3 cycles */
1768 update_float_resource_latency (cpu, slot, cycles + 3);
1769
1770 return cycles;
1771 }
1772
1773 int
1774 frvbf_model_fr550_u_media_quad (SIM_CPU *cpu, const IDESC *idesc,
1775 int unit_num, int referenced,
1776 INT in_FRi, INT in_FRj,
1777 INT out_FRk)
1778 {
1779 int cycles;
1780 INT dual_FRi;
1781 INT dual_FRj;
1782 INT dual_FRk;
1783 FRV_PROFILE_STATE *ps;
1784 FRV_VLIW *vliw;
1785 int slot;
1786
1787 if (model_insn == FRV_INSN_MODEL_PASS_1)
1788 return 0;
1789
1790 /* The preprocessing can execute right away. */
1791 cycles = idesc->timing->units[unit_num].done;
1792
1793 dual_FRi = DUAL_REG (in_FRi);
1794 dual_FRj = DUAL_REG (in_FRj);
1795 dual_FRk = DUAL_REG (out_FRk);
1796
1797 /* The latency of the registers may be less than previously recorded,
1798 depending on how they were used previously.
1799 See Table 14-15 in the LSI. */
1800 adjust_float_register_busy_for_media (cpu, in_FRi, 2, in_FRj, 2, out_FRk, 2);
1801
1802 /* The post processing must wait if there is a dependency on a FR
1803 which is not ready yet. */
1804 ps = CPU_PROFILE_STATE (cpu);
1805 ps->post_wait = cycles;
1806 vliw = CPU_VLIW (cpu);
1807 slot = vliw->next_slot - 1;
1808 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
1809 post_wait_for_media (cpu, slot);
1810 post_wait_for_FR (cpu, in_FRi);
1811 post_wait_for_FR (cpu, dual_FRi);
1812 post_wait_for_FR (cpu, in_FRj);
1813 post_wait_for_FR (cpu, dual_FRj);
1814 post_wait_for_FR (cpu, out_FRk);
1815 post_wait_for_FR (cpu, dual_FRk);
1816
1817 /* Restore the busy cycles of the registers we used. */
1818 restore_float_register_busy_for_media (cpu, in_FRi, 2, in_FRj, 2, out_FRk, 2);
1819
1820 /* The latency of the output register will be at least the latency of the
1821 other inputs. Once initiated, post-processing take 1 cycle. */
1822 update_FR_latency (cpu, out_FRk, ps->post_wait);
1823 update_FR_ptime (cpu, out_FRk, 1);
1824 set_use_is_fr_complex_1 (cpu, out_FRk);
1825
1826 if (dual_FRk >= 0)
1827 {
1828 update_FR_latency (cpu, dual_FRk, ps->post_wait);
1829 update_FR_ptime (cpu, dual_FRk, 1);
1830 set_use_is_fr_complex_1 (cpu, dual_FRk);
1831 }
1832
1833 /* the floating point unit resource has a latency of 3 cycles */
1834 update_float_resource_latency (cpu, slot, cycles + 3);
1835
1836 return cycles;
1837 }
1838
1839 int
1840 frvbf_model_fr550_u_media_dual_expand (SIM_CPU *cpu, const IDESC *idesc,
1841 int unit_num, int referenced,
1842 INT in_FRi, INT out_FRk)
1843 {
1844 int cycles;
1845 INT dual_FRk;
1846 FRV_PROFILE_STATE *ps;
1847 FRV_VLIW *vliw;
1848 int slot;
1849
1850 if (model_insn == FRV_INSN_MODEL_PASS_1)
1851 return 0;
1852
1853 /* The preprocessing can execute right away. */
1854 cycles = idesc->timing->units[unit_num].done;
1855
1856 /* If the previous use of the registers was a media op,
1857 then their latency will be less than previously recorded.
1858 See Table 14-15 in the LSI. */
1859 dual_FRk = DUAL_REG (out_FRk);
1860 adjust_float_register_busy_for_media (cpu, in_FRi, 1, -1, 1, out_FRk, 2);
1861
1862 /* The post processing must wait if there is a dependency on a FR
1863 which is not ready yet. */
1864 ps = CPU_PROFILE_STATE (cpu);
1865 ps->post_wait = cycles;
1866 vliw = CPU_VLIW (cpu);
1867 slot = vliw->next_slot - 1;
1868 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
1869 post_wait_for_media (cpu, slot);
1870 post_wait_for_FR (cpu, in_FRi);
1871 post_wait_for_FR (cpu, out_FRk);
1872 post_wait_for_FR (cpu, dual_FRk);
1873
1874 /* Restore the busy cycles of the registers we used. */
1875 restore_float_register_busy_for_media (cpu, in_FRi, 1, -1, 1, out_FRk, 2);
1876
1877 /* The latency of the output register will be at least the latency of the
1878 other inputs. Once initiated, post-processing will take 1 cycle. */
1879 update_FR_latency (cpu, out_FRk, ps->post_wait);
1880 update_FR_ptime (cpu, out_FRk, 1);
1881 set_use_is_fr_complex_1 (cpu, out_FRk);
1882
1883 if (dual_FRk >= 0)
1884 {
1885 update_FR_latency (cpu, dual_FRk, ps->post_wait);
1886 update_FR_ptime (cpu, dual_FRk, 1);
1887 set_use_is_fr_complex_1 (cpu, dual_FRk);
1888 }
1889
1890 /* the floating point unit resource has a latency of 3 cycles */
1891 update_float_resource_latency (cpu, slot, cycles + 3);
1892
1893 return cycles;
1894 }
1895
1896 int
1897 frvbf_model_fr550_u_media_3_dual (SIM_CPU *cpu, const IDESC *idesc,
1898 int unit_num, int referenced,
1899 INT in_FRi, INT out_FRk)
1900 {
1901 int cycles;
1902 INT dual_FRi;
1903 FRV_PROFILE_STATE *ps;
1904 FRV_VLIW *vliw;
1905 int slot;
1906
1907 if (model_insn == FRV_INSN_MODEL_PASS_1)
1908 return 0;
1909
1910 /* The preprocessing can execute right away. */
1911 cycles = idesc->timing->units[unit_num].done;
1912
1913 dual_FRi = DUAL_REG (in_FRi);
1914
1915 /* The latency of the registers may be less than previously recorded,
1916 depending on how they were used previously.
1917 See Table 14-15 in the LSI. */
1918 adjust_float_register_busy_for_media (cpu, in_FRi, 2, -1, 1, out_FRk, 1);
1919
1920 /* The post processing must wait if there is a dependency on a FR
1921 which is not ready yet. */
1922 ps = CPU_PROFILE_STATE (cpu);
1923 ps->post_wait = cycles;
1924 vliw = CPU_VLIW (cpu);
1925 slot = vliw->next_slot - 1;
1926 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
1927 post_wait_for_media (cpu, slot);
1928 post_wait_for_FR (cpu, in_FRi);
1929 post_wait_for_FR (cpu, dual_FRi);
1930 post_wait_for_FR (cpu, out_FRk);
1931
1932 /* Restore the busy cycles of the registers we used. */
1933 restore_float_register_busy_for_media (cpu, in_FRi, 2, -1, 1, out_FRk, 1);
1934
1935 /* The latency of the output register will be at least the latency of the
1936 other inputs. Once initiated, post-processing takes 1 cycle. */
1937 update_FR_latency (cpu, out_FRk, ps->post_wait);
1938 update_FR_ptime (cpu, out_FRk, 1);
1939
1940 set_use_is_fr_complex_1 (cpu, out_FRk);
1941
1942 /* the floating point unit resource has a latency of 3 cycles */
1943 update_float_resource_latency (cpu, slot, cycles + 3);
1944
1945 return cycles;
1946 }
1947
1948 int
1949 frvbf_model_fr550_u_media_3_acc (SIM_CPU *cpu, const IDESC *idesc,
1950 int unit_num, int referenced,
1951 INT in_FRj, INT in_ACC40Si,
1952 INT out_FRk)
1953 {
1954 int cycles;
1955 FRV_PROFILE_STATE *ps;
1956 FRV_VLIW *vliw;
1957 int slot;
1958
1959 if (model_insn == FRV_INSN_MODEL_PASS_1)
1960 return 0;
1961
1962 /* The preprocessing can execute right away. */
1963 cycles = idesc->timing->units[unit_num].done;
1964
1965 /* If the previous use of the registers was a media op,
1966 then their latency will be less than previously recorded.
1967 See Table 14-15 in the LSI. */
1968 adjust_float_register_busy_for_media (cpu, -1, 1, in_FRj, 1, out_FRk, 1);
1969
1970 /* The post processing must wait if there is a dependency on a FR
1971 which is not ready yet. */
1972 ps = CPU_PROFILE_STATE (cpu);
1973 ps->post_wait = cycles;
1974 vliw = CPU_VLIW (cpu);
1975 slot = vliw->next_slot - 1;
1976 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
1977 post_wait_for_media (cpu, slot);
1978 post_wait_for_FR (cpu, in_FRj);
1979 post_wait_for_FR (cpu, out_FRk);
1980 post_wait_for_ACC (cpu, in_ACC40Si);
1981
1982 /* Restore the busy cycles of the registers we used. */
1983 restore_float_register_busy_for_media (cpu, -1, 1, in_FRj, 1, out_FRk, 1);
1984
1985 /* The latency of tht output register will be at least the latency of the
1986 other inputs. Once initiated, post-processing will take 1 cycle. */
1987 update_FR_latency (cpu, out_FRk, ps->post_wait);
1988 update_FR_ptime (cpu, out_FRk, 1);
1989
1990 set_use_is_fr_complex_1 (cpu, out_FRk);
1991
1992 /* the floating point unit resource has a latency of 3 cycles */
1993 update_float_resource_latency (cpu, slot, cycles + 3);
1994
1995 return cycles;
1996 }
1997
1998 int
1999 frvbf_model_fr550_u_media_3_acc_dual (SIM_CPU *cpu, const IDESC *idesc,
2000 int unit_num, int referenced,
2001 INT in_ACC40Si, INT out_FRk)
2002 {
2003 int cycles;
2004 FRV_PROFILE_STATE *ps;
2005 INT ACC40Si_1;
2006 INT dual_FRk;
2007 FRV_VLIW *vliw;
2008 int slot;
2009
2010 if (model_insn == FRV_INSN_MODEL_PASS_1)
2011 return 0;
2012
2013 /* The preprocessing can execute right away. */
2014 cycles = idesc->timing->units[unit_num].done;
2015
2016 ACC40Si_1 = DUAL_REG (in_ACC40Si);
2017 dual_FRk = DUAL_REG (out_FRk);
2018
2019 /* If the previous use of the registers was a media op,
2020 then their latency will be less than previously recorded.
2021 See Table 14-15 in the LSI. */
2022 adjust_float_register_busy_for_media (cpu, -1, 1, -1, 1, out_FRk, 2);
2023
2024 /* The post processing must wait if there is a dependency on a FR
2025 which is not ready yet. */
2026 ps = CPU_PROFILE_STATE (cpu);
2027 ps->post_wait = cycles;
2028 vliw = CPU_VLIW (cpu);
2029 slot = vliw->next_slot - 1;
2030 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
2031 post_wait_for_media (cpu, slot);
2032 post_wait_for_ACC (cpu, in_ACC40Si);
2033 post_wait_for_ACC (cpu, ACC40Si_1);
2034 post_wait_for_FR (cpu, out_FRk);
2035 post_wait_for_FR (cpu, dual_FRk);
2036
2037 /* Restore the busy cycles of the registers we used. */
2038 restore_float_register_busy_for_media (cpu, -1, 1, -1, 1, out_FRk, 2);
2039
2040 /* The latency of the output register will be at least the latency of the
2041 other inputs. Once initiated, post-processing will take 1 cycle. */
2042 update_FR_latency (cpu, out_FRk, ps->post_wait);
2043 update_FR_ptime (cpu, out_FRk, 1);
2044 set_use_is_fr_complex_1 (cpu, out_FRk);
2045 if (dual_FRk >= 0)
2046 {
2047 update_FR_latency (cpu, dual_FRk, ps->post_wait);
2048 update_FR_ptime (cpu, dual_FRk, 1);
2049 set_use_is_fr_complex_1 (cpu, dual_FRk);
2050 }
2051
2052 /* the floating point unit resource has a latency of 3 cycles */
2053 update_float_resource_latency (cpu, slot, cycles + 3);
2054
2055 return cycles;
2056 }
2057
2058 int
2059 frvbf_model_fr550_u_media_3_wtacc (SIM_CPU *cpu, const IDESC *idesc,
2060 int unit_num, int referenced,
2061 INT in_FRi, INT out_ACC40Sk)
2062 {
2063 int cycles;
2064 FRV_PROFILE_STATE *ps;
2065 FRV_VLIW *vliw;
2066 int slot;
2067
2068 if (model_insn == FRV_INSN_MODEL_PASS_1)
2069 return 0;
2070
2071 /* The preprocessing can execute right away. */
2072 cycles = idesc->timing->units[unit_num].done;
2073
2074 ps = CPU_PROFILE_STATE (cpu);
2075
2076 /* The latency of the registers may be less than previously recorded,
2077 depending on how they were used previously.
2078 See Table 14-15 in the LSI. */
2079 adjust_float_register_busy_for_media (cpu, in_FRi, 1, -1, 1, -1, 1);
2080
2081 /* The post processing must wait if there is a dependency on a FR
2082 which is not ready yet. */
2083 ps->post_wait = cycles;
2084 vliw = CPU_VLIW (cpu);
2085 slot = vliw->next_slot - 1;
2086 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
2087 post_wait_for_media (cpu, slot);
2088 post_wait_for_FR (cpu, in_FRi);
2089 post_wait_for_ACC (cpu, out_ACC40Sk);
2090
2091 /* Restore the busy cycles of the registers we used. */
2092 restore_float_register_busy_for_media (cpu, in_FRi, 1, -1, 1, -1, 1);
2093
2094 /* The latency of the output register will be at least the latency of the
2095 other inputs. Once initiated, post-processing will take 1 cycle. */
2096 update_ACC_latency (cpu, out_ACC40Sk, ps->post_wait);
2097 update_ACC_ptime (cpu, out_ACC40Sk, 1);
2098 set_use_is_acc_mmac (cpu, out_ACC40Sk);
2099
2100 /* the floating point unit resource has a latency of 3 cycles */
2101 update_float_resource_latency (cpu, slot, cycles + 3);
2102
2103 return cycles;
2104 }
2105
2106 int
2107 frvbf_model_fr550_u_media_3_mclracc (SIM_CPU *cpu, const IDESC *idesc,
2108 int unit_num, int referenced)
2109 {
2110 int cycles;
2111 FRV_PROFILE_STATE *ps;
2112 FRV_VLIW *vliw;
2113 int slot;
2114 int i;
2115
2116 if (model_insn == FRV_INSN_MODEL_PASS_1)
2117 return 0;
2118
2119 /* The preprocessing can execute right away. */
2120 cycles = idesc->timing->units[unit_num].done;
2121
2122 ps = CPU_PROFILE_STATE (cpu);
2123
2124 /* The post processing must wait if there is a dependency on a FR
2125 which is not ready yet. */
2126 ps->post_wait = cycles;
2127 vliw = CPU_VLIW (cpu);
2128 slot = vliw->next_slot - 1;
2129 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
2130 post_wait_for_media (cpu, slot);
2131
2132 /* If A was 1 and the accumulator was ACC0, then we must check all
2133 accumulators. Otherwise just wait for the specified accumulator. */
2134 if (ps->mclracc_A && ps->mclracc_acc == 0)
2135 {
2136 for (i = 0; i < 8; ++i)
2137 post_wait_for_ACC (cpu, i);
2138 }
2139 else
2140 post_wait_for_ACC (cpu, ps->mclracc_acc);
2141
2142 /* The latency of the output registers will be at least the latency of the
2143 other inputs. Once initiated, post-processing will take 1 cycle. */
2144 if (ps->mclracc_A && ps->mclracc_acc == 0)
2145 {
2146 for (i = 0; i < 8; ++i)
2147 {
2148 update_ACC_latency (cpu, i, ps->post_wait);
2149 update_ACC_ptime (cpu, i, 1);
2150 set_use_is_acc_mmac (cpu, i);
2151 }
2152 }
2153 else
2154 {
2155 update_ACC_latency (cpu, ps->mclracc_acc, ps->post_wait);
2156 update_ACC_ptime (cpu, ps->mclracc_acc, 1);
2157 set_use_is_acc_mmac (cpu, ps->mclracc_acc);
2158 }
2159
2160 /* the floating point unit resource has a latency of 3 cycles */
2161 update_float_resource_latency (cpu, slot, cycles + 3);
2162
2163 return cycles;
2164 }
2165
2166 int
2167 frvbf_model_fr550_u_media_set (SIM_CPU *cpu, const IDESC *idesc,
2168 int unit_num, int referenced,
2169 INT out_FRk)
2170 {
2171 int cycles;
2172 FRV_PROFILE_STATE *ps;
2173 FRV_VLIW *vliw;
2174 int slot;
2175
2176 if (model_insn == FRV_INSN_MODEL_PASS_1)
2177 return 0;
2178
2179 /* The preprocessing can execute right away. */
2180 cycles = idesc->timing->units[unit_num].done;
2181
2182 /* If the previous use of the registers was a media op,
2183 then their latency will be less than previously recorded.
2184 See Table 14-15 in the LSI. */
2185 adjust_float_register_busy_for_media (cpu, -1, 1, -1, 1, out_FRk, 1);
2186
2187 /* The post processing must wait if there is a dependency on a FR
2188 which is not ready yet. */
2189 ps = CPU_PROFILE_STATE (cpu);
2190 ps->post_wait = cycles;
2191 vliw = CPU_VLIW (cpu);
2192 slot = vliw->next_slot - 1;
2193 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
2194 post_wait_for_media (cpu, slot);
2195 post_wait_for_FR (cpu, out_FRk);
2196
2197 /* Restore the busy cycles of the registers we used. */
2198 restore_float_register_busy_for_media (cpu, -1, 1, -1, 1, out_FRk, 1);
2199
2200 /* The latency of the output register will be at least the latency of the
2201 other inputs. Once initiated, post-processing takes 1 cycle. */
2202 update_FR_latency (cpu, out_FRk, ps->post_wait);
2203 update_FR_ptime (cpu, out_FRk, 1);
2204 fr550_reset_acc_flags (cpu, out_FRk);
2205
2206 /* the floating point unit resource has a latency of 3 cycles */
2207 update_float_resource_latency (cpu, slot, cycles + 3);
2208
2209 return cycles;
2210 }
2211
2212 int
2213 frvbf_model_fr550_u_media_4 (SIM_CPU *cpu, const IDESC *idesc,
2214 int unit_num, int referenced,
2215 INT in_FRi, INT in_FRj,
2216 INT out_ACC40Sk, INT out_ACC40Uk)
2217 {
2218 int cycles;
2219 INT dual_ACC40Sk;
2220 INT dual_ACC40Uk;
2221 FRV_PROFILE_STATE *ps;
2222 FRV_VLIW *vliw;
2223 int slot;
2224
2225 if (model_insn == FRV_INSN_MODEL_PASS_1)
2226 return 0;
2227
2228 /* The preprocessing can execute right away. */
2229 cycles = idesc->timing->units[unit_num].done;
2230
2231 ps = CPU_PROFILE_STATE (cpu);
2232 dual_ACC40Sk = DUAL_REG (out_ACC40Sk);
2233 dual_ACC40Uk = DUAL_REG (out_ACC40Uk);
2234
2235 /* The latency of the registers may be less than previously recorded,
2236 depending on how they were used previously.
2237 See Table 14-15 in the LSI. */
2238 adjust_acc_busy_for_mmac (cpu, -1, 1, out_ACC40Sk, 2);
2239 adjust_acc_busy_for_mmac (cpu, -1, 1, out_ACC40Uk, 2);
2240
2241 /* The post processing must wait if there is a dependency on a FR
2242 which is not ready yet. */
2243 ps->post_wait = cycles;
2244 vliw = CPU_VLIW (cpu);
2245 slot = vliw->next_slot - 1;
2246 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
2247 post_wait_for_media (cpu, slot);
2248 post_wait_for_FR (cpu, in_FRi);
2249 post_wait_for_FR (cpu, in_FRj);
2250 post_wait_for_ACC (cpu, out_ACC40Sk);
2251 post_wait_for_ACC (cpu, dual_ACC40Sk);
2252 post_wait_for_ACC (cpu, out_ACC40Uk);
2253 post_wait_for_ACC (cpu, dual_ACC40Uk);
2254
2255 /* Restore the busy cycles of the registers we used. */
2256 restore_acc_busy_for_mmac (cpu, -1, 1, out_ACC40Sk, 2);
2257 restore_acc_busy_for_mmac (cpu, -1, 1, out_ACC40Uk, 2);
2258
2259 /* The latency of the output register will be at least the latency of the
2260 other inputs. Once initiated, post-processing will take 1 cycles. */
2261 if (out_ACC40Sk >= 0)
2262 {
2263 update_ACC_latency (cpu, out_ACC40Sk, ps->post_wait + 1);
2264 set_use_is_acc_mmac (cpu, out_ACC40Sk);
2265 }
2266 if (dual_ACC40Sk >= 0)
2267 {
2268 update_ACC_latency (cpu, dual_ACC40Sk, ps->post_wait + 1);
2269 set_use_is_acc_mmac (cpu, dual_ACC40Sk);
2270 }
2271 if (out_ACC40Uk >= 0)
2272 {
2273 update_ACC_latency (cpu, out_ACC40Uk, ps->post_wait + 1);
2274 set_use_is_acc_mmac (cpu, out_ACC40Uk);
2275 }
2276 if (dual_ACC40Uk >= 0)
2277 {
2278 update_ACC_latency (cpu, dual_ACC40Uk, ps->post_wait + 1);
2279 set_use_is_acc_mmac (cpu, dual_ACC40Uk);
2280 }
2281
2282 /* the floating point unit resource has a latency of 3 cycles */
2283 update_float_resource_latency (cpu, slot, cycles + 3);
2284
2285 return cycles;
2286 }
2287
2288 int
2289 frvbf_model_fr550_u_media_4_acc (SIM_CPU *cpu, const IDESC *idesc,
2290 int unit_num, int referenced,
2291 INT in_ACC40Si, INT out_ACC40Sk)
2292 {
2293 int cycles;
2294 INT ACC40Si_1;
2295 FRV_PROFILE_STATE *ps;
2296 FRV_VLIW *vliw;
2297 int slot;
2298
2299 if (model_insn == FRV_INSN_MODEL_PASS_1)
2300 return 0;
2301
2302 /* The preprocessing can execute right away. */
2303 cycles = idesc->timing->units[unit_num].done;
2304
2305 ACC40Si_1 = DUAL_REG (in_ACC40Si);
2306
2307 ps = CPU_PROFILE_STATE (cpu);
2308 /* The latency of the registers may be less than previously recorded,
2309 depending on how they were used previously.
2310 See Table 14-15 in the LSI. */
2311 adjust_acc_busy_for_mmac (cpu, in_ACC40Si, 2, out_ACC40Sk, 1);
2312
2313 /* The post processing must wait if there is a dependency on a register
2314 which is not ready yet. */
2315 ps->post_wait = cycles;
2316 vliw = CPU_VLIW (cpu);
2317 slot = vliw->next_slot - 1;
2318 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
2319 post_wait_for_media (cpu, slot);
2320 post_wait_for_ACC (cpu, in_ACC40Si);
2321 post_wait_for_ACC (cpu, ACC40Si_1);
2322 post_wait_for_ACC (cpu, out_ACC40Sk);
2323
2324 /* Restore the busy cycles of the registers we used. */
2325 restore_acc_busy_for_mmac (cpu, in_ACC40Si, 2, out_ACC40Sk, 1);
2326
2327 /* The latency of the output register will be at least the latency of the
2328 other inputs. Once initiated, post-processing will take 1 cycle. */
2329 update_ACC_latency (cpu, out_ACC40Sk, ps->post_wait + 1);
2330 set_use_is_acc_mmac (cpu, out_ACC40Sk);
2331
2332 /* the floating point unit resource has a latency of 3 cycles */
2333 update_float_resource_latency (cpu, slot, cycles + 3);
2334
2335 return cycles;
2336 }
2337
2338 int
2339 frvbf_model_fr550_u_media_4_acc_dual (SIM_CPU *cpu, const IDESC *idesc,
2340 int unit_num, int referenced,
2341 INT in_ACC40Si, INT out_ACC40Sk)
2342 {
2343 int cycles;
2344 INT ACC40Si_1;
2345 INT ACC40Si_2;
2346 INT ACC40Si_3;
2347 INT ACC40Sk_1;
2348 FRV_PROFILE_STATE *ps;
2349 FRV_VLIW *vliw;
2350 int slot;
2351
2352 if (model_insn == FRV_INSN_MODEL_PASS_1)
2353 return 0;
2354
2355 /* The preprocessing can execute right away. */
2356 cycles = idesc->timing->units[unit_num].done;
2357
2358 ACC40Si_1 = DUAL_REG (in_ACC40Si);
2359 ACC40Si_2 = DUAL_REG (ACC40Si_1);
2360 ACC40Si_3 = DUAL_REG (ACC40Si_2);
2361 ACC40Sk_1 = DUAL_REG (out_ACC40Sk);
2362
2363 ps = CPU_PROFILE_STATE (cpu);
2364 /* The latency of the registers may be less than previously recorded,
2365 depending on how they were used previously.
2366 See Table 14-15 in the LSI. */
2367 adjust_acc_busy_for_mmac (cpu, in_ACC40Si, 4, out_ACC40Sk, 2);
2368
2369 /* The post processing must wait if there is a dependency on a register
2370 which is not ready yet. */
2371 ps->post_wait = cycles;
2372 vliw = CPU_VLIW (cpu);
2373 slot = vliw->next_slot - 1;
2374 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
2375 post_wait_for_media (cpu, slot);
2376 post_wait_for_ACC (cpu, in_ACC40Si);
2377 post_wait_for_ACC (cpu, ACC40Si_1);
2378 post_wait_for_ACC (cpu, ACC40Si_2);
2379 post_wait_for_ACC (cpu, ACC40Si_3);
2380 post_wait_for_ACC (cpu, out_ACC40Sk);
2381 post_wait_for_ACC (cpu, ACC40Sk_1);
2382
2383 /* Restore the busy cycles of the registers we used. */
2384 restore_acc_busy_for_mmac (cpu, in_ACC40Si, 4, out_ACC40Sk, 2);
2385
2386 /* The latency of the output register will be at least the latency of the
2387 other inputs. Once initiated, post-processing will take 1 cycle. */
2388 update_ACC_latency (cpu, out_ACC40Sk, ps->post_wait + 1);
2389 set_use_is_acc_mmac (cpu, out_ACC40Sk);
2390 if (ACC40Sk_1 >= 0)
2391 {
2392 update_ACC_latency (cpu, ACC40Sk_1, ps->post_wait + 1);
2393 set_use_is_acc_mmac (cpu, ACC40Sk_1);
2394 }
2395
2396 /* the floating point unit resource has a latency of 3 cycles */
2397 update_float_resource_latency (cpu, slot, cycles + 3);
2398
2399 return cycles;
2400 }
2401
2402 int
2403 frvbf_model_fr550_u_media_4_add_sub (SIM_CPU *cpu, const IDESC *idesc,
2404 int unit_num, int referenced,
2405 INT in_ACC40Si, INT out_ACC40Sk)
2406 {
2407 int cycles;
2408 INT ACC40Si_1;
2409 INT ACC40Sk_1;
2410 FRV_PROFILE_STATE *ps;
2411 FRV_VLIW *vliw;
2412 int slot;
2413
2414 if (model_insn == FRV_INSN_MODEL_PASS_1)
2415 return 0;
2416
2417 /* The preprocessing can execute right away. */
2418 cycles = idesc->timing->units[unit_num].done;
2419
2420 ACC40Si_1 = DUAL_REG (in_ACC40Si);
2421 ACC40Sk_1 = DUAL_REG (out_ACC40Sk);
2422
2423 ps = CPU_PROFILE_STATE (cpu);
2424 /* The latency of the registers may be less than previously recorded,
2425 depending on how they were used previously.
2426 See Table 14-15 in the LSI. */
2427 adjust_acc_busy_for_mmac (cpu, in_ACC40Si, 2, out_ACC40Sk, 2);
2428
2429 /* The post processing must wait if there is a dependency on a register
2430 which is not ready yet. */
2431 ps->post_wait = cycles;
2432 vliw = CPU_VLIW (cpu);
2433 slot = vliw->next_slot - 1;
2434 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
2435 post_wait_for_media (cpu, slot);
2436 post_wait_for_ACC (cpu, in_ACC40Si);
2437 post_wait_for_ACC (cpu, ACC40Si_1);
2438 post_wait_for_ACC (cpu, out_ACC40Sk);
2439 post_wait_for_ACC (cpu, ACC40Sk_1);
2440
2441 /* Restore the busy cycles of the registers we used. */
2442 restore_acc_busy_for_mmac (cpu, in_ACC40Si, 2, out_ACC40Sk, 2);
2443
2444 /* The latency of the output register will be at least the latency of the
2445 other inputs. Once initiated, post-processing will take 1 cycle. */
2446 update_ACC_latency (cpu, out_ACC40Sk, ps->post_wait + 1);
2447 set_use_is_acc_mmac (cpu, out_ACC40Sk);
2448 if (ACC40Sk_1 >= 0)
2449 {
2450 update_ACC_latency (cpu, ACC40Sk_1, ps->post_wait + 1);
2451 set_use_is_acc_mmac (cpu, ACC40Sk_1);
2452 }
2453
2454 /* the floating point unit resource has a latency of 3 cycles */
2455 update_float_resource_latency (cpu, slot, cycles + 3);
2456
2457 return cycles;
2458 }
2459
2460 int
2461 frvbf_model_fr550_u_media_4_add_sub_dual (SIM_CPU *cpu, const IDESC *idesc,
2462 int unit_num, int referenced,
2463 INT in_ACC40Si, INT out_ACC40Sk)
2464 {
2465 int cycles;
2466 INT ACC40Si_1;
2467 INT ACC40Si_2;
2468 INT ACC40Si_3;
2469 INT ACC40Sk_1;
2470 INT ACC40Sk_2;
2471 INT ACC40Sk_3;
2472 FRV_PROFILE_STATE *ps;
2473 FRV_VLIW *vliw;
2474 int slot;
2475
2476 if (model_insn == FRV_INSN_MODEL_PASS_1)
2477 return 0;
2478
2479 /* The preprocessing can execute right away. */
2480 cycles = idesc->timing->units[unit_num].done;
2481
2482 ACC40Si_1 = DUAL_REG (in_ACC40Si);
2483 ACC40Si_2 = DUAL_REG (ACC40Si_1);
2484 ACC40Si_3 = DUAL_REG (ACC40Si_2);
2485 ACC40Sk_1 = DUAL_REG (out_ACC40Sk);
2486 ACC40Sk_2 = DUAL_REG (ACC40Sk_1);
2487 ACC40Sk_3 = DUAL_REG (ACC40Sk_2);
2488
2489 ps = CPU_PROFILE_STATE (cpu);
2490 /* The latency of the registers may be less than previously recorded,
2491 depending on how they were used previously.
2492 See Table 14-15 in the LSI. */
2493 adjust_acc_busy_for_mmac (cpu, in_ACC40Si, 4, out_ACC40Sk, 4);
2494
2495 /* The post processing must wait if there is a dependency on a register
2496 which is not ready yet. */
2497 ps->post_wait = cycles;
2498 vliw = CPU_VLIW (cpu);
2499 slot = vliw->next_slot - 1;
2500 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
2501 post_wait_for_media (cpu, slot);
2502 post_wait_for_ACC (cpu, in_ACC40Si);
2503 post_wait_for_ACC (cpu, ACC40Si_1);
2504 post_wait_for_ACC (cpu, ACC40Si_2);
2505 post_wait_for_ACC (cpu, ACC40Si_3);
2506 post_wait_for_ACC (cpu, out_ACC40Sk);
2507 post_wait_for_ACC (cpu, ACC40Sk_1);
2508 post_wait_for_ACC (cpu, ACC40Sk_2);
2509 post_wait_for_ACC (cpu, ACC40Sk_3);
2510
2511 /* Restore the busy cycles of the registers we used. */
2512 restore_acc_busy_for_mmac (cpu, in_ACC40Si, 4, out_ACC40Sk, 4);
2513
2514 /* The latency of the output register will be at least the latency of the
2515 other inputs. Once initiated, post-processing will take 1 cycle. */
2516 update_ACC_latency (cpu, out_ACC40Sk, ps->post_wait + 1);
2517 set_use_is_acc_mmac (cpu, out_ACC40Sk);
2518 if (ACC40Sk_1 >= 0)
2519 {
2520 update_ACC_latency (cpu, ACC40Sk_1, ps->post_wait + 1);
2521 set_use_is_acc_mmac (cpu, ACC40Sk_1);
2522 }
2523 if (ACC40Sk_2 >= 0)
2524 {
2525 update_ACC_latency (cpu, ACC40Sk_2, ps->post_wait + 1);
2526 set_use_is_acc_mmac (cpu, ACC40Sk_2);
2527 }
2528 if (ACC40Sk_3 >= 0)
2529 {
2530 update_ACC_latency (cpu, ACC40Sk_3, ps->post_wait + 1);
2531 set_use_is_acc_mmac (cpu, ACC40Sk_3);
2532 }
2533
2534 /* the floating point unit resource has a latency of 3 cycles */
2535 update_float_resource_latency (cpu, slot, cycles + 3);
2536
2537 return cycles;
2538 }
2539
2540 int
2541 frvbf_model_fr550_u_media_4_quad (SIM_CPU *cpu, const IDESC *idesc,
2542 int unit_num, int referenced,
2543 INT in_FRi, INT in_FRj,
2544 INT out_ACC40Sk, INT out_ACC40Uk)
2545 {
2546 int cycles;
2547 INT dual_FRi;
2548 INT dual_FRj;
2549 INT ACC40Sk_1;
2550 INT ACC40Sk_2;
2551 INT ACC40Sk_3;
2552 INT ACC40Uk_1;
2553 INT ACC40Uk_2;
2554 INT ACC40Uk_3;
2555 FRV_PROFILE_STATE *ps;
2556 FRV_VLIW *vliw;
2557 int slot;
2558
2559 if (model_insn == FRV_INSN_MODEL_PASS_1)
2560 return 0;
2561
2562 /* The preprocessing can execute right away. */
2563 cycles = idesc->timing->units[unit_num].done;
2564
2565 dual_FRi = DUAL_REG (in_FRi);
2566 dual_FRj = DUAL_REG (in_FRj);
2567 ACC40Sk_1 = DUAL_REG (out_ACC40Sk);
2568 ACC40Sk_2 = DUAL_REG (ACC40Sk_1);
2569 ACC40Sk_3 = DUAL_REG (ACC40Sk_2);
2570 ACC40Uk_1 = DUAL_REG (out_ACC40Uk);
2571 ACC40Uk_2 = DUAL_REG (ACC40Uk_1);
2572 ACC40Uk_3 = DUAL_REG (ACC40Uk_2);
2573
2574 ps = CPU_PROFILE_STATE (cpu);
2575 /* The latency of the registers may be less than previously recorded,
2576 depending on how they were used previously.
2577 See Table 14-15 in the LSI. */
2578 adjust_float_register_busy_for_media (cpu, in_FRi, 2, in_FRj, 2, -1, 1);
2579 adjust_acc_busy_for_mmac (cpu, -1, 1, out_ACC40Sk, 4);
2580 adjust_acc_busy_for_mmac (cpu, -1, 1, out_ACC40Uk, 4);
2581
2582 /* The post processing must wait if there is a dependency on a FR
2583 which is not ready yet. */
2584 ps->post_wait = cycles;
2585 vliw = CPU_VLIW (cpu);
2586 slot = vliw->next_slot - 1;
2587 slot = (*vliw->current_vliw)[slot] - UNIT_FM0;
2588 post_wait_for_media (cpu, slot);
2589 post_wait_for_FR (cpu, in_FRi);
2590 post_wait_for_FR (cpu, dual_FRi);
2591 post_wait_for_FR (cpu, in_FRj);
2592 post_wait_for_FR (cpu, dual_FRj);
2593 post_wait_for_ACC (cpu, out_ACC40Sk);
2594 post_wait_for_ACC (cpu, ACC40Sk_1);
2595 post_wait_for_ACC (cpu, ACC40Sk_2);
2596 post_wait_for_ACC (cpu, ACC40Sk_3);
2597 post_wait_for_ACC (cpu, out_ACC40Uk);
2598 post_wait_for_ACC (cpu, ACC40Uk_1);
2599 post_wait_for_ACC (cpu, ACC40Uk_2);
2600 post_wait_for_ACC (cpu, ACC40Uk_3);
2601
2602 /* Restore the busy cycles of the registers we used. */
2603 restore_float_register_busy_for_media (cpu, in_FRi, 2, in_FRj, 2, -1, 1);
2604 restore_acc_busy_for_mmac (cpu, -1, 1, out_ACC40Sk, 4);
2605 restore_acc_busy_for_mmac (cpu, -1, 1, out_ACC40Uk, 4);
2606
2607 /* The latency of the output register will be at least the latency of the
2608 other inputs. Once initiated, post-processing will take 1 cycle. */
2609 if (out_ACC40Sk >= 0)
2610 {
2611 update_ACC_latency (cpu, out_ACC40Sk, ps->post_wait + 1);
2612
2613 set_use_is_acc_mmac (cpu, out_ACC40Sk);
2614 if (ACC40Sk_1 >= 0)
2615 {
2616 update_ACC_latency (cpu, ACC40Sk_1, ps->post_wait + 1);
2617
2618 set_use_is_acc_mmac (cpu, ACC40Sk_1);
2619 }
2620 if (ACC40Sk_2 >= 0)
2621 {
2622 update_ACC_latency (cpu, ACC40Sk_2, ps->post_wait + 1);
2623
2624 set_use_is_acc_mmac (cpu, ACC40Sk_2);
2625 }
2626 if (ACC40Sk_3 >= 0)
2627 {
2628 update_ACC_latency (cpu, ACC40Sk_3, ps->post_wait + 1);
2629
2630 set_use_is_acc_mmac (cpu, ACC40Sk_3);
2631 }
2632 }
2633 else if (out_ACC40Uk >= 0)
2634 {
2635 update_ACC_latency (cpu, out_ACC40Uk, ps->post_wait + 1);
2636
2637 set_use_is_acc_mmac (cpu, out_ACC40Uk);
2638 if (ACC40Uk_1 >= 0)
2639 {
2640 update_ACC_latency (cpu, ACC40Uk_1, ps->post_wait + 1);
2641
2642 set_use_is_acc_mmac (cpu, ACC40Uk_1);
2643 }
2644 if (ACC40Uk_2 >= 0)
2645 {
2646 update_ACC_latency (cpu, ACC40Uk_2, ps->post_wait + 1);
2647
2648 set_use_is_acc_mmac (cpu, ACC40Uk_2);
2649 }
2650 if (ACC40Uk_3 >= 0)
2651 {
2652 update_ACC_latency (cpu, ACC40Uk_3, ps->post_wait + 1);
2653
2654 set_use_is_acc_mmac (cpu, ACC40Uk_3);
2655 }
2656 }
2657
2658 /* the floating point unit resource has a latency of 3 cycles */
2659 update_float_resource_latency (cpu, slot, cycles + 3);
2660
2661 return cycles;
2662 }
2663
2664 #endif /* WITH_PROFILE_MODEL_P */