OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [tags/] [rel-0-3-0-rc1/] [or1ksim/] [cpu/] [or32/] [op.c] - Blame information for rev 1692

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 1452 nogj
/* op.c -- Micro operations for the recompiler
2
   Copyright (C) 2005 György `nog' Jeney, nog@sdf.lonestar.org
3
 
4
This file is part of OpenRISC 1000 Architectural Simulator.
5
 
6
This program is free software; you can redistribute it and/or modify
7
it under the terms of the GNU General Public License as published by
8
the Free Software Foundation; either version 2 of the License, or
9
(at your option) any later version.
10
 
11
This program is distributed in the hope that it will be useful,
12
but WITHOUT ANY WARRANTY; without even the implied warranty of
13
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
GNU General Public License for more details.
15
 
16
You should have received a copy of the GNU General Public License
17
along with this program; if not, write to the Free Software
18
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
19
 
20
 
21
#include <stdio.h>
22
#include <stdint.h>
23
#include <stdlib.h>
24
 
25
#include "config.h"
26
 
27
#ifdef HAVE_INTTYPES_H
28
#include <inttypes.h>
29
#endif
30
 
31
#include "port.h"
32
#include "arch.h"
33
#include "spr_defs.h"
34
#include "opcode/or32.h"
35
#include "sim-config.h"
36
#include "except.h"
37
#include "abstract.h"
38
#include "execute.h"
39
#include "sprs.h"
40
#include "sched.h"
41
 
42
#include "op_support.h"
43
 
44
#include "i386_regs.h"
45
 
46
#include "dyn_rec.h"
47
 
48
register struct cpu_state *env asm(CPU_STATE_REG);
49
 
50
#include "op_i386.h"
51
 
52
/*
53 1549 nogj
 * WARNING: Before going of and wildly editing everything in this file remember
54 1452 nogj
 * the following about its contents:
55
 * 1) The `functions' don't EVER return.  In otherwords haveing return state-
56
 *    ments _anywere_ in this file is likely not to work.  This is because
57
 *    dyngen just strips away the ret from the end of the function and just uses
58
 *    the function `body'.  If a ret statement is executed _anyware_ inside the
59
 *    dynamicly generated code, then it is undefined were we shall jump to.
60
 * 2) Because of 1), try not to have overly complicated functions.  In too
61
 *    complicated functions, gcc may decide to generate premature `exits'.  This
62
 *    is what passing the -fno-reorder-blocks command line switch to gcc helps
63
 *    with.  This is ofcourse not desired and is rather flaky as we don't (and
64
 *    can't) control the kind of code that gcc generates: It may work for one
65
 *    and break for another.  The less branches there are the less likely it is
66
 *    that a premature return shall occur.
67
 * 3) If gcc decides that it is going to be a basterd then it will optimise a
68
 *    very simple condition (if/switch) with a premature exit.  But gcc can't
69
 *    fuck ME over!  Just stick a FORCE_RET; at the END of the offending
70
 *    function.
71
 * 4) All operations must start with `op_'.  dyngen ignores all other functions.
72
 * 5) Local variables are depriciated: They hinder performance.
73
 * 6) Function calls are expensive as the stack has to be shifted (twice).
74
 */
75
 
76
/*#define __or_dynop __attribute__((noreturn))*/
77
#define __or_dynop
78
 
79
/* Temporaries to hold the (simulated) registers in */
80
register uint32_t t0 asm(T0_REG);
81
register uint32_t t1 asm(T1_REG);
82
register uint32_t t2 asm(T2_REG);
83
 
84
#define OP_PARAM1 ((uorreg_t)(&__op_param1))
85
#define OP_PARAM2 ((uorreg_t)(&__op_param2))
86
#define OP_PARAM3 ((uorreg_t)(&__op_param3))
87
 
88
extern uorreg_t __op_param1;
89
extern uorreg_t __op_param2;
90
extern uorreg_t __op_param3;
91
 
92
 
93 1678 nogj
static inline void save_t_bound(oraddr_t pc)
94 1452 nogj
{
95 1678 nogj
  int reg;
96
 
97
  pc = (pc & config.immu.page_offset_mask) / 4;
98
  reg = env->curr_page->ts_bound[pc];
99
 
100
  if(reg & 0x1f)
101
    env->reg[reg & 0x1f] = t0;
102
 
103
  if((reg >> 5) & 0x1f)
104
    env->reg[(reg >> 5) & 0x1f] = t1;
105
 
106
  if((reg >> 10) & 0x1f)
107
    env->reg[(reg >> 10) & 0x1f] = t2;
108 1452 nogj
}
109
 
110
void do_sched_wrap(void)
111
{
112 1687 nogj
  env->pc += 4;
113
  //runtime.cpu.instructions++;
114
  runtime.sim.cycles -= env->cycles_dec;
115
  scheduler.job_queue->time += env->cycles_dec;
116
  if(scheduler.job_queue->time <= 0) {
117
    save_t_bound(env->pc - 4);
118
    do_scheduler();
119
  }
120 1452 nogj
}
121
 
122 1481 nogj
/* do_scheduler wrapper for instructions that are in the delay slot */
123
void do_sched_wrap_delay(void)
124
{
125 1687 nogj
  /* FIXME: Can't this be eliminated? */
126
  env->pc += 4;
127
  //runtime.cpu.instructions++;
128
  runtime.sim.cycles -= env->cycles_dec;
129
  scheduler.job_queue->time += env->cycles_dec;
130
  if(scheduler.job_queue->time <= 0)
131
    do_scheduler();
132 1481 nogj
}
133
 
134
void enter_dyn_code(oraddr_t addr, struct dyn_page *dp)
135
{
136 1678 nogj
  uint16_t reg = 0;
137 1692 nogj
  uint32_t t0_reg = t0, t1_reg = t1, t2_reg = t2;
138
  struct cpu_state *cpu_reg = env;
139 1481 nogj
 
140 1483 nogj
  addr &= config.immu.pagesize - 1;
141 1481 nogj
  addr >>= 2;
142
 
143 1678 nogj
  if(addr)
144
    reg = dp->ts_bound[addr - 1];
145 1481 nogj
 
146 1691 nogj
  t0 = cpu_state.reg[reg & 0x1f];
147
  t1 = cpu_state.reg[(reg >> 5) & 0x1f];
148 1481 nogj
 
149 1691 nogj
  /* Don't we all love gcc?  For some heavenly reason gcc 3.2 _knows_ that if I
150
   * don't put a condition around the assignment of t2, _all_ the assignments to
151
   * t{0,1,2} are useless and not needed.  I'm pleasently happy that gcc is so
152
   * bright, but on the other hand, t{0,1,2} are globals (!) how can you assume
153
   * that the value of a global won't be used in a function further up or
154
   * further down the stack?? */
155
  if(addr)
156 1481 nogj
    t2 = cpu_state.reg[(reg >> 10) & 0x1f];
157
 
158 1692 nogj
  env = &cpu_state;
159
 
160
  ((gen_code_ent *)dp->locs)[addr]();
161
  t0 = t0_reg;
162
  t1 = t1_reg;
163
  t2 = t2_reg;
164
  env = (struct cpu_state *)cpu_reg;
165 1481 nogj
}
166
 
167
__or_dynop void op_set_pc_pc_delay(void)
168 1452 nogj
{
169 1687 nogj
  env->sprs[SPR_PPC] = env->pc;
170 1481 nogj
  /* pc_delay is pulled back 4 since imediatly after this is run, the scheduler
171
   * runs which also increments it by 4 */
172 1687 nogj
  env->pc = env->pc_delay - 4;
173 1452 nogj
}
174
 
175
__or_dynop void op_set_pc_delay_imm(void)
176
{
177 1687 nogj
  env->pc_delay = env->pc + (orreg_t)OP_PARAM1;
178 1452 nogj
  env->delay_insn = 1;
179
}
180
 
181
__or_dynop void op_set_pc_delay_pc(void)
182
{
183 1687 nogj
  env->pc_delay = env->pc;
184 1452 nogj
  env->delay_insn = 1;
185
}
186
 
187
__or_dynop void op_clear_pc_delay(void)
188
{
189
  env->pc_delay = 0;
190
  env->delay_insn = 1;
191
}
192
 
193
__or_dynop void op_do_jump(void)
194
{
195 1692 nogj
  RET_FROM_DYN_CODE;
196 1481 nogj
}
197
 
198
__or_dynop void op_do_jump_delay(void)
199
{
200 1692 nogj
  env->pc = env->pc_delay;
201
  RET_FROM_DYN_CODE;
202 1452 nogj
}
203
 
204 1481 nogj
__or_dynop void op_clear_delay_insn(void)
205 1452 nogj
{
206 1481 nogj
  env->delay_insn = 0;
207 1452 nogj
}
208
 
209 1481 nogj
__or_dynop void op_set_delay_insn(void)
210 1452 nogj
{
211 1481 nogj
  env->delay_insn = 1;
212 1452 nogj
}
213
 
214 1481 nogj
__or_dynop void op_check_delay_slot(void)
215 1452 nogj
{
216 1481 nogj
  if(!env->delay_insn)
217
    OP_JUMP(OP_PARAM1);
218 1452 nogj
}
219
 
220
__or_dynop void op_jmp_imm(void)
221
{
222
  OP_JUMP(OP_PARAM1);
223
}
224
 
225
__or_dynop void op_set_flag(void)
226
{
227
  env->sprs[SPR_SR] |= SPR_SR_F;
228
}
229
 
230
__or_dynop void op_clear_flag(void)
231
{
232
  env->sprs[SPR_SR] &= ~SPR_SR_F;
233
}
234
 
235 1481 nogj
/* Used for the l.bf instruction.  Therefore if the flag is not set, jump over
236
 * all the jumping stuff */
237 1452 nogj
__or_dynop void op_check_flag(void)
238
{
239 1481 nogj
  if(!(env->sprs[SPR_SR] & SPR_SR_F)) {
240 1687 nogj
    SPEEDY_CALL(do_sched_wrap);
241 1481 nogj
    OP_JUMP(OP_PARAM1);
242
  }
243
}
244
 
245
/* Used for l.bf if the delay slot instruction is on another page */
246
__or_dynop void op_check_flag_delay(void)
247
{
248 1452 nogj
  if(env->sprs[SPR_SR] & SPR_SR_F) {
249 1481 nogj
    env->delay_insn = 1;
250 1687 nogj
    env->pc_delay = env->pc + (orreg_t)OP_PARAM1;
251 1452 nogj
  }
252
}
253
 
254 1481 nogj
/* Used for the l.bnf instruction.  Therefore if the flag is set, jump over all
255
 * the jumping stuff */
256 1452 nogj
__or_dynop void op_check_not_flag(void)
257
{
258 1481 nogj
  if(env->sprs[SPR_SR] & SPR_SR_F) {
259 1687 nogj
    SPEEDY_CALL(do_sched_wrap);
260 1481 nogj
    OP_JUMP(OP_PARAM1);
261
  }
262
}
263
 
264
/* Used for l.bnf if the delay slot instruction is on another page */
265
__or_dynop void op_check_not_flag_delay(void)
266
{
267 1452 nogj
  if(!(env->sprs[SPR_SR] & SPR_SR_F)) {
268 1481 nogj
    env->delay_insn = 1;
269 1687 nogj
    env->pc_delay = env->pc + (orreg_t)OP_PARAM1;
270 1452 nogj
  }
271
}
272
 
273 1481 nogj
__or_dynop void op_add_pc(void)
274 1452 nogj
{
275 1687 nogj
  env->pc += OP_PARAM1;
276 1452 nogj
}
277
 
278
__or_dynop void op_nop_exit(void)
279
{
280
  op_support_nop_exit();
281
  FORCE_RET;
282
}
283
 
284
__or_dynop void op_nop_reset(void)
285
{
286
  op_support_nop_reset();
287 1692 nogj
  env->pc = EXCEPT_RESET;
288
  RET_FROM_DYN_CODE;
289 1452 nogj
}
290
 
291
__or_dynop void op_nop_printf(void)
292
{
293
  op_support_nop_printf();
294
  FORCE_RET;
295
}
296
 
297
__or_dynop void op_nop_report(void)
298
{
299
  op_support_nop_report();
300
  FORCE_RET;
301
}
302
 
303
__or_dynop void op_nop_report_imm(void)
304
{
305
  op_support_nop_report_imm(OP_PARAM1);
306
}
307
 
308 1657 nogj
__or_dynop void op_analysis(void)
309 1452 nogj
{
310 1657 nogj
  op_support_analysis();
311
  FORCE_RET;
312 1452 nogj
}
313
 
314 1657 nogj
__or_dynop void op_move_gpr1_pc_delay(void)
315
{
316
  env->pc_delay = env->reg[1];
317
  env->delay_insn = 1;
318
}
319 1452 nogj
 
320 1657 nogj
__or_dynop void op_move_gpr2_pc_delay(void)
321 1452 nogj
{
322 1657 nogj
  env->pc_delay = env->reg[2];
323
  env->delay_insn = 1;
324 1452 nogj
}
325
 
326 1657 nogj
__or_dynop void op_move_gpr3_pc_delay(void)
327 1452 nogj
{
328 1657 nogj
  env->pc_delay = env->reg[3];
329
  env->delay_insn = 1;
330 1452 nogj
}
331
 
332 1657 nogj
__or_dynop void op_move_gpr4_pc_delay(void)
333
{
334
  env->pc_delay = env->reg[4];
335
  env->delay_insn = 1;
336
}
337 1452 nogj
 
338 1657 nogj
__or_dynop void op_move_gpr5_pc_delay(void)
339 1452 nogj
{
340 1657 nogj
  env->pc_delay = env->reg[5];
341
  env->delay_insn = 1;
342 1452 nogj
}
343
 
344 1657 nogj
__or_dynop void op_move_gpr6_pc_delay(void)
345 1452 nogj
{
346 1657 nogj
  env->pc_delay = env->reg[6];
347
  env->delay_insn = 1;
348 1452 nogj
}
349
 
350 1657 nogj
__or_dynop void op_move_gpr7_pc_delay(void)
351 1452 nogj
{
352 1657 nogj
  env->pc_delay = env->reg[7];
353
  env->delay_insn = 1;
354 1452 nogj
}
355
 
356 1657 nogj
__or_dynop void op_move_gpr8_pc_delay(void)
357 1452 nogj
{
358 1657 nogj
  env->pc_delay = env->reg[8];
359
  env->delay_insn = 1;
360 1452 nogj
}
361
 
362 1657 nogj
__or_dynop void op_move_gpr9_pc_delay(void)
363
{
364
  env->pc_delay = env->reg[9];
365
  env->delay_insn = 1;
366
}
367
 
368
__or_dynop void op_move_gpr10_pc_delay(void)
369
{
370
  env->pc_delay = env->reg[10];
371
  env->delay_insn = 1;
372
}
373
 
374
__or_dynop void op_move_gpr11_pc_delay(void)
375
{
376
  env->pc_delay = env->reg[11];
377
  env->delay_insn = 1;
378
}
379
 
380
__or_dynop void op_move_gpr12_pc_delay(void)
381
{
382
  env->pc_delay = env->reg[12];
383
  env->delay_insn = 1;
384
}
385
 
386
__or_dynop void op_move_gpr13_pc_delay(void)
387
{
388
  env->pc_delay = env->reg[13];
389
  env->delay_insn = 1;
390
}
391
 
392
__or_dynop void op_move_gpr14_pc_delay(void)
393
{
394
  env->pc_delay = env->reg[14];
395
  env->delay_insn = 1;
396
}
397
 
398
__or_dynop void op_move_gpr15_pc_delay(void)
399
{
400
  env->pc_delay = env->reg[15];
401
  env->delay_insn = 1;
402
}
403
 
404
__or_dynop void op_move_gpr16_pc_delay(void)
405
{
406
  env->pc_delay = env->reg[16];
407
  env->delay_insn = 1;
408
}
409
 
410
__or_dynop void op_move_gpr17_pc_delay(void)
411
{
412
  env->pc_delay = env->reg[17];
413
  env->delay_insn = 1;
414
}
415
 
416
__or_dynop void op_move_gpr18_pc_delay(void)
417
{
418
  env->pc_delay = env->reg[18];
419
  env->delay_insn = 1;
420
}
421
 
422
__or_dynop void op_move_gpr19_pc_delay(void)
423
{
424
  env->pc_delay = env->reg[19];
425
  env->delay_insn = 1;
426
}
427
 
428
__or_dynop void op_move_gpr20_pc_delay(void)
429
{
430
  env->pc_delay = env->reg[20];
431
  env->delay_insn = 1;
432
}
433
 
434
__or_dynop void op_move_gpr21_pc_delay(void)
435
{
436
  env->pc_delay = env->reg[21];
437
  env->delay_insn = 1;
438
}
439
 
440
__or_dynop void op_move_gpr22_pc_delay(void)
441
{
442
  env->pc_delay = env->reg[22];
443
  env->delay_insn = 1;
444
}
445
 
446
__or_dynop void op_move_gpr23_pc_delay(void)
447
{
448
  env->pc_delay = env->reg[23];
449
  env->delay_insn = 1;
450
}
451
 
452
__or_dynop void op_move_gpr24_pc_delay(void)
453
{
454
  env->pc_delay = env->reg[24];
455
  env->delay_insn = 1;
456
}
457
 
458
__or_dynop void op_move_gpr25_pc_delay(void)
459
{
460
  env->pc_delay = env->reg[25];
461
  env->delay_insn = 1;
462
}
463
 
464
__or_dynop void op_move_gpr26_pc_delay(void)
465
{
466
  env->pc_delay = env->reg[26];
467
  env->delay_insn = 1;
468
}
469
 
470
__or_dynop void op_move_gpr27_pc_delay(void)
471
{
472
  env->pc_delay = env->reg[27];
473
  env->delay_insn = 1;
474
}
475
 
476
__or_dynop void op_move_gpr28_pc_delay(void)
477
{
478
  env->pc_delay = env->reg[28];
479
  env->delay_insn = 1;
480
}
481
 
482
__or_dynop void op_move_gpr29_pc_delay(void)
483
{
484
  env->pc_delay = env->reg[29];
485
  env->delay_insn = 1;
486
}
487
 
488
__or_dynop void op_move_gpr30_pc_delay(void)
489
{
490
  env->pc_delay = env->reg[30];
491
  env->delay_insn = 1;
492
}
493
 
494
__or_dynop void op_move_gpr31_pc_delay(void)
495
{
496
  env->pc_delay = env->reg[31];
497
  env->delay_insn = 1;
498
}
499
 
500
#define OP_FILE "op_1t_op.h"
501
#include "op_1t.h"
502
#undef OP_FILE
503 1658 nogj
 
504
#define OP_FILE "op_2t_op.h"
505
#include "op_2t.h"
506
#undef OP_FILE
507 1660 nogj
 
508
#define OP_FILE "op_3t_op.h"
509
#include "op_3t.h"
510
#undef OP_FILE
511
 
512 1661 nogj
#define OP_FILE "op_arith_op.h"
513 1452 nogj
#define OP_EXTRA
514
 
515
#define OP /
516 1661 nogj
#define OP_CAST(x) (orreg_t)(x)
517 1452 nogj
#define OP_NAME div
518 1661 nogj
#include "op_3t.h"
519 1452 nogj
#undef OP_NAME
520
#undef OP_CAST
521
#undef OP
522
 
523
#define OP /
524 1661 nogj
#define OP_CAST(x) (x)
525 1452 nogj
#define OP_NAME divu
526 1661 nogj
#include "op_3t.h"
527 1452 nogj
#undef OP_NAME
528
#undef OP_CAST
529
#undef OP
530
 
531
#define OP *
532 1661 nogj
#define OP_CAST(x) (x)
533 1452 nogj
#define OP_NAME mulu
534 1661 nogj
#include "op_3t.h"
535 1452 nogj
#undef OP_NAME
536
#undef OP_CAST
537
#undef OP
538
 
539
#define OP -
540 1661 nogj
#define OP_CAST(x) (orreg_t)(x)
541 1452 nogj
#define OP_NAME sub
542 1661 nogj
#include "op_3t.h"
543 1452 nogj
#undef OP_NAME
544
#undef OP_CAST
545
#undef OP
546
 
547
#undef OP_EXTRA
548
 
549
#define OP_EXTRA + ((env->sprs[SPR_SR] & SPR_SR_CY) >> 10)
550
#define OP +
551 1661 nogj
#define OP_CAST(x) (orreg_t)(x)
552 1452 nogj
#define OP_NAME addc
553 1661 nogj
#include "op_3t.h"
554
#include "op_2t.h"
555 1452 nogj
#undef OP_NAME
556
#undef OP_CAST
557
#undef OP
558
 
559
#undef OP_EXTRA
560
#define OP_EXTRA
561
 
562
#define OP +
563 1661 nogj
#define OP_CAST(x) (orreg_t)(x)
564 1452 nogj
#define OP_NAME add
565 1661 nogj
#include "op_3t.h"
566
#include "op_2t.h"
567 1452 nogj
#undef OP_NAME
568
#undef OP_CAST
569
#undef OP
570
 
571
#define OP &
572 1661 nogj
#define OP_CAST(x) (x)
573 1452 nogj
#define OP_NAME and
574 1661 nogj
#include "op_3t.h"
575
#include "op_2t.h"
576 1452 nogj
#undef OP_NAME
577
#undef OP_CAST
578
#undef OP
579
 
580
#define OP *
581 1661 nogj
#define OP_CAST(x) (orreg_t)(x)
582 1452 nogj
#define OP_NAME mul
583 1661 nogj
#include "op_3t.h"
584
#include "op_2t.h"
585 1452 nogj
#undef OP_NAME
586
#undef OP_CAST
587
#undef OP
588
 
589
#define OP |
590 1661 nogj
#define OP_CAST(x) (x)
591 1452 nogj
#define OP_NAME or
592 1661 nogj
#include "op_3t.h"
593
#include "op_2t.h"
594 1452 nogj
#undef OP_NAME
595
#undef OP_CAST
596
#undef OP
597
 
598
#define OP <<
599 1661 nogj
#define OP_CAST(x) (x)
600 1452 nogj
#define OP_NAME sll
601 1661 nogj
#include "op_3t.h"
602
#include "op_2t.h"
603 1452 nogj
#undef OP_NAME
604
#undef OP_CAST
605
#undef OP
606
 
607
#define OP >>
608 1661 nogj
#define OP_CAST(x) (orreg_t)(x)
609 1452 nogj
#define OP_NAME sra
610 1661 nogj
#include "op_3t.h"
611
#include "op_2t.h"
612 1452 nogj
#undef OP_NAME
613
#undef OP_CAST
614
#undef OP
615
 
616
#define OP >>
617 1661 nogj
#define OP_CAST(x) (x)
618 1452 nogj
#define OP_NAME srl
619 1661 nogj
#include "op_3t.h"
620
#include "op_2t.h"
621 1452 nogj
#undef OP_NAME
622
#undef OP_CAST
623
#undef OP
624
 
625
#define OP ^
626 1661 nogj
#define OP_CAST(x) (x)
627 1452 nogj
#define OP_NAME xor
628 1661 nogj
#include "op_3t.h"
629
#include "op_2t.h"
630 1452 nogj
#undef OP_NAME
631
#undef OP_CAST
632
#undef OP
633
 
634
#undef OP_EXTRA
635 1661 nogj
#undef OP_FILE
636 1452 nogj
 
637 1662 nogj
#define OP_FILE "op_extend_op.h"
638
 
639 1452 nogj
#define EXT_NAME extbs
640
#define EXT_TYPE int8_t
641
#define EXT_CAST (orreg_t)
642 1662 nogj
#include "op_2t.h"
643 1452 nogj
#undef EXT_CAST
644
#undef EXT_TYPE
645
#undef EXT_NAME
646
 
647
#define EXT_NAME extbz
648
#define EXT_TYPE uint8_t
649
#define EXT_CAST (uorreg_t)
650 1662 nogj
#include "op_2t.h"
651 1452 nogj
#undef EXT_CAST
652
#undef EXT_TYPE
653
#undef EXT_NAME
654
 
655
#define EXT_NAME exths
656
#define EXT_TYPE int16_t
657
#define EXT_CAST (orreg_t)
658 1662 nogj
#include "op_2t.h"
659 1452 nogj
#undef EXT_CAST
660
#undef EXT_TYPE
661
#undef EXT_NAME
662
 
663
#define EXT_NAME exthz
664
#define EXT_TYPE uint16_t
665
#define EXT_CAST (uorreg_t)
666 1662 nogj
#include "op_2t.h"
667 1452 nogj
#undef EXT_CAST
668
#undef EXT_TYPE
669
#undef EXT_NAME
670
 
671 1662 nogj
#undef OP_FILE
672
 
673 1663 nogj
#define OP_FILE "op_comp_op.h"
674
 
675 1452 nogj
#define COMP ==
676
#define COMP_NAME sfeq
677 1663 nogj
#define COMP_CAST(x) (x)
678
#include "op_2t.h"
679
#include "op_1t.h"
680 1452 nogj
#undef COMP_CAST
681
#undef COMP_NAME
682
#undef COMP
683
 
684
#define COMP !=
685
#define COMP_NAME sfne
686 1663 nogj
#define COMP_CAST(x) (x)
687
#include "op_2t.h"
688
#include "op_1t.h"
689 1452 nogj
#undef COMP_CAST
690
#undef COMP_NAME
691
#undef COMP
692
 
693
#define COMP >
694
#define COMP_NAME sfgtu
695 1663 nogj
#define COMP_CAST(x) (x)
696
#include "op_2t.h"
697
#include "op_1t.h"
698 1452 nogj
#undef COMP_CAST
699
#undef COMP_NAME
700
#undef COMP
701
 
702
#define COMP >=
703
#define COMP_NAME sfgeu
704 1663 nogj
#define COMP_CAST(x) (x)
705
#include "op_2t.h"
706
#include "op_1t.h"
707 1452 nogj
#undef COMP_CAST
708
#undef COMP_NAME
709
#undef COMP
710
 
711
#define COMP <
712
#define COMP_NAME sfltu
713 1663 nogj
#define COMP_CAST(x) (x)
714
#include "op_2t.h"
715
#include "op_1t.h"
716 1452 nogj
#undef COMP_CAST
717
#undef COMP_NAME
718
#undef COMP
719
 
720
#define COMP <=
721
#define COMP_NAME sfleu
722 1663 nogj
#define COMP_CAST(x) (x)
723
#include "op_2t.h"
724
#include "op_1t.h"
725 1452 nogj
#undef COMP_CAST
726
#undef COMP_NAME
727
#undef COMP
728
 
729
#define COMP >
730
#define COMP_NAME sfgts
731 1663 nogj
#define COMP_CAST(x) (orreg_t)(x)
732
#include "op_2t.h"
733
#include "op_1t.h"
734 1452 nogj
#undef COMP_CAST
735
#undef COMP_NAME
736
#undef COMP
737
 
738
#define COMP >=
739
#define COMP_NAME sfges
740 1663 nogj
#define COMP_CAST(x) (orreg_t)(x)
741
#include "op_2t.h"
742
#include "op_1t.h"
743 1452 nogj
#undef COMP_CAST
744
#undef COMP_NAME
745
#undef COMP
746
 
747
#define COMP <
748
#define COMP_NAME sflts
749 1663 nogj
#define COMP_CAST(x) (orreg_t)(x)
750
#include "op_2t.h"
751
#include "op_1t.h"
752 1452 nogj
#undef COMP_CAST
753
#undef COMP_NAME
754
#undef COMP
755
 
756
#define COMP <=
757
#define COMP_NAME sfles
758 1663 nogj
#define COMP_CAST(x) (orreg_t)(x)
759
#include "op_2t.h"
760
#include "op_1t.h"
761 1452 nogj
#undef COMP_CAST
762
#undef COMP_NAME
763
#undef COMP
764
 
765 1663 nogj
#undef OP_FILE
766
 
767 1657 nogj
#define OP_FILE "op_t_reg_mov_op.h"
768
#include "op_1t.h"
769
#undef OP_FILE
770 1452 nogj
 
771 1664 nogj
#define OP_FILE "op_mftspr_op.h"
772
#include "op_1t.h"
773
#include "op_2t.h"
774
#undef OP_FILE
775 1452 nogj
#include "op_mftspr_op.h"
776
 
777 1665 nogj
#define OP_FILE "op_mac_op.h"
778 1452 nogj
 
779
#define OP +=
780
#define OP_NAME mac
781 1665 nogj
#include "op_2t.h"
782 1452 nogj
#undef OP_NAME
783
#undef OP
784
 
785
#define OP -=
786
#define OP_NAME msb
787 1665 nogj
#include "op_2t.h"
788 1452 nogj
#undef OP_NAME
789
#undef OP
790
 
791 1665 nogj
#undef OP_FILE
792
 
793 1666 nogj
#define OP_FILE "op_lwhb_op.h"
794
 
795 1452 nogj
#define LS_OP_NAME lbz
796
#define LS_OP_CAST
797
#define LS_OP_FUNC eval_mem8
798 1666 nogj
#include "op_2t.h"
799
#include "op_1t.h"
800 1452 nogj
#undef LS_OP_FUNC
801
#undef LS_OP_CAST
802
#undef LS_OP_NAME
803
 
804
#define LS_OP_NAME lbs
805
#define LS_OP_CAST (int8_t)
806
#define LS_OP_FUNC eval_mem8
807 1666 nogj
#include "op_2t.h"
808
#include "op_1t.h"
809 1452 nogj
#undef LS_OP_FUNC
810
#undef LS_OP_CAST
811
#undef LS_OP_NAME
812
 
813
#define LS_OP_NAME lhz
814
#define LS_OP_CAST
815
#define LS_OP_FUNC eval_mem16
816 1666 nogj
#include "op_2t.h"
817
#include "op_1t.h"
818 1452 nogj
#undef LS_OP_FUNC
819
#undef LS_OP_CAST
820
#undef LS_OP_NAME
821
 
822
#define LS_OP_NAME lhs
823
#define LS_OP_CAST (int16_t)
824
#define LS_OP_FUNC eval_mem16
825 1666 nogj
#include "op_2t.h"
826
#include "op_1t.h"
827 1452 nogj
#undef LS_OP_FUNC
828
#undef LS_OP_CAST
829
#undef LS_OP_NAME
830
 
831
#define LS_OP_NAME lwz
832
#define LS_OP_CAST
833
#define LS_OP_FUNC eval_mem32
834 1666 nogj
#include "op_2t.h"
835
#include "op_1t.h"
836 1452 nogj
#undef LS_OP_FUNC
837
#undef LS_OP_CAST
838
#undef LS_OP_NAME
839
 
840
#define LS_OP_NAME lws
841
#define LS_OP_CAST (int32_t)
842
#define LS_OP_FUNC eval_mem32
843 1666 nogj
#include "op_2t.h"
844
#include "op_1t.h"
845 1452 nogj
#undef LS_OP_FUNC
846
#undef LS_OP_CAST
847
#undef LS_OP_NAME
848
 
849 1666 nogj
#undef OP_FILE
850
 
851 1667 nogj
#define OP_FILE "op_swhb_op.h"
852
 
853 1452 nogj
#define S_OP_NAME sb
854
#define S_FUNC set_mem8
855
#include "op_swhb_op.h"
856 1667 nogj
#include "op_2t.h"
857
#include "op_1t.h"
858 1452 nogj
#undef S_FUNC
859
#undef S_OP_NAME
860
 
861
#define S_OP_NAME sh
862
#define S_FUNC set_mem16
863
#include "op_swhb_op.h"
864 1667 nogj
#include "op_2t.h"
865
#include "op_1t.h"
866 1452 nogj
#undef S_FUNC
867
#undef S_OP_NAME
868
 
869
#define S_OP_NAME sw
870
#define S_FUNC set_mem32
871
#include "op_swhb_op.h"
872 1667 nogj
#include "op_2t.h"
873
#include "op_1t.h"
874 1452 nogj
#undef S_FUNC
875
#undef S_OP_NAME
876
 
877
__or_dynop void op_join_mem_cycles(void)
878
{
879 1687 nogj
  runtime.sim.cycles += runtime.sim.mem_cycles;
880
  scheduler.job_queue->time -= runtime.sim.mem_cycles;
881
  runtime.sim.mem_cycles = 0;
882 1452 nogj
}
883
 
884
__or_dynop void op_store_link_addr_gpr(void)
885
{
886 1687 nogj
  env->reg[LINK_REGNO] = env->pc + 8;
887 1452 nogj
}
888
 
889
__or_dynop void op_prep_rfe(void)
890
{
891
  env->sprs[SPR_SR] = env->sprs[SPR_ESR_BASE] | SPR_SR_FO;
892 1687 nogj
  env->sprs[SPR_PPC] = env->pc;
893
  env->pc = env->sprs[SPR_EPCR_BASE] - 4;
894 1452 nogj
}
895
 
896
static inline void prep_except(oraddr_t epcr_base)
897
{
898
  env->sprs[SPR_EPCR_BASE] = epcr_base;
899
 
900
  env->sprs[SPR_ESR_BASE] = env->sprs[SPR_SR];
901
 
902
  /* Address translation is always disabled when starting exception. */
903
  env->sprs[SPR_SR] &= ~SPR_SR_DME;
904
  env->sprs[SPR_SR] &= ~SPR_SR_IME;
905
 
906
  env->sprs[SPR_SR] &= ~SPR_SR_OVE;   /* Disable overflow flag exception. */
907
 
908
  env->sprs[SPR_SR] |= SPR_SR_SM;     /* SUPV mode */
909
  env->sprs[SPR_SR] &= ~(SPR_SR_IEE | SPR_SR_TEE);    /* Disable interrupts. */
910
}
911
 
912
__or_dynop void op_set_except_pc(void)
913
{
914 1687 nogj
  env->pc = OP_PARAM1;
915 1452 nogj
}
916
 
917
/* Before the code in op_{sys,trap}{,_delay} gets run, the scheduler runs.
918
 * Therefore the pc will point to the instruction after the l.sys or l.trap
919
 * instruction */
920
__or_dynop void op_prep_sys_delay(void)
921
{
922
  env->delay_insn = 0;
923 1687 nogj
  prep_except(env->pc - 4);
924
  env->pc = EXCEPT_SYSCALL - 4;
925 1452 nogj
}
926
 
927
__or_dynop void op_prep_sys(void)
928
{
929 1687 nogj
  prep_except(env->pc + 4);
930
  env->pc = EXCEPT_SYSCALL - 4;
931 1452 nogj
}
932
 
933
__or_dynop void op_prep_trap_delay(void)
934
{
935
  env->delay_insn = 0;
936 1687 nogj
  prep_except(env->pc - 4);
937
  env->pc = EXCEPT_TRAP - 4;
938 1452 nogj
}
939
 
940
__or_dynop void op_prep_trap(void)
941
{
942 1687 nogj
  prep_except(env->pc);
943
  env->pc = EXCEPT_TRAP - 4;
944 1452 nogj
}
945
 
946
/* FIXME: This `instruction' should be split up like the l.trap and l.sys
947
 * instructions are done */
948
__or_dynop void op_illegal_delay(void)
949
{
950
  env->delay_insn = 0;
951 1687 nogj
  env->sprs[SPR_EEAR_BASE] = env->pc - 4;
952 1692 nogj
  env->pc = EXCEPT_ILLEGAL - 4;
953
  RET_FROM_DYN_CODE;
954 1452 nogj
}
955
 
956
__or_dynop void op_illegal(void)
957
{
958 1687 nogj
  env->sprs[SPR_EEAR_BASE] = env->pc;
959 1692 nogj
  env->pc = EXCEPT_ILLEGAL;
960
  RET_FROM_DYN_CODE;
961 1452 nogj
}
962
 
963
__or_dynop void op_do_sched(void)
964
{
965 1687 nogj
  SPEEDY_CALL(do_sched_wrap);
966 1452 nogj
}
967
 
968 1481 nogj
__or_dynop void op_do_sched_delay(void)
969
{
970 1687 nogj
  SPEEDY_CALL(do_sched_wrap_delay);
971 1481 nogj
}
972
 
973 1452 nogj
__or_dynop void op_macc(void)
974
{
975
  env->sprs[SPR_MACLO] = 0;
976
  env->sprs[SPR_MACHI] = 0;
977
}
978
 
979
__or_dynop void op_store_insn_ea(void)
980
{
981
  env->insn_ea = OP_PARAM1;
982
}
983
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.