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 1691

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 1481 nogj
 
138 1483 nogj
  addr &= config.immu.pagesize - 1;
139 1481 nogj
  addr >>= 2;
140
 
141 1678 nogj
  if(addr)
142
    reg = dp->ts_bound[addr - 1];
143 1481 nogj
 
144 1691 nogj
  t0 = cpu_state.reg[reg & 0x1f];
145
  t1 = cpu_state.reg[(reg >> 5) & 0x1f];
146 1481 nogj
 
147 1691 nogj
  /* Don't we all love gcc?  For some heavenly reason gcc 3.2 _knows_ that if I
148
   * don't put a condition around the assignment of t2, _all_ the assignments to
149
   * t{0,1,2} are useless and not needed.  I'm pleasently happy that gcc is so
150
   * bright, but on the other hand, t{0,1,2} are globals (!) how can you assume
151
   * that the value of a global won't be used in a function further up or
152
   * further down the stack?? */
153
  if(addr)
154 1481 nogj
    t2 = cpu_state.reg[(reg >> 10) & 0x1f];
155
 
156
  or_longjmp(dp->locs[addr]);
157
}
158
 
159 1452 nogj
 
160 1481 nogj
__or_dynop void op_set_pc_pc_delay(void)
161 1452 nogj
{
162 1687 nogj
  env->sprs[SPR_PPC] = env->pc;
163 1481 nogj
  /* pc_delay is pulled back 4 since imediatly after this is run, the scheduler
164
   * runs which also increments it by 4 */
165 1687 nogj
  env->pc = env->pc_delay - 4;
166 1452 nogj
}
167
 
168
__or_dynop void op_set_pc_delay_imm(void)
169
{
170 1687 nogj
  env->pc_delay = env->pc + (orreg_t)OP_PARAM1;
171 1452 nogj
  env->delay_insn = 1;
172
}
173
 
174
__or_dynop void op_set_pc_delay_pc(void)
175
{
176 1687 nogj
  env->pc_delay = env->pc;
177 1452 nogj
  env->delay_insn = 1;
178
}
179
 
180
__or_dynop void op_clear_pc_delay(void)
181
{
182
  env->pc_delay = 0;
183
  env->delay_insn = 1;
184
}
185
 
186
__or_dynop void op_do_jump(void)
187
{
188 1687 nogj
  do_jump(env->pc);
189 1481 nogj
}
190
 
191
__or_dynop void op_do_jump_delay(void)
192
{
193 1452 nogj
  do_jump(env->pc_delay);
194
}
195
 
196 1481 nogj
__or_dynop void op_clear_delay_insn(void)
197 1452 nogj
{
198 1481 nogj
  env->delay_insn = 0;
199 1452 nogj
}
200
 
201 1481 nogj
__or_dynop void op_set_delay_insn(void)
202 1452 nogj
{
203 1481 nogj
  env->delay_insn = 1;
204 1452 nogj
}
205
 
206 1481 nogj
__or_dynop void op_check_delay_slot(void)
207 1452 nogj
{
208 1481 nogj
  if(!env->delay_insn)
209
    OP_JUMP(OP_PARAM1);
210 1452 nogj
}
211
 
212
__or_dynop void op_jmp_imm(void)
213
{
214
  OP_JUMP(OP_PARAM1);
215
}
216
 
217
__or_dynop void op_set_flag(void)
218
{
219
  env->sprs[SPR_SR] |= SPR_SR_F;
220
}
221
 
222
__or_dynop void op_clear_flag(void)
223
{
224
  env->sprs[SPR_SR] &= ~SPR_SR_F;
225
}
226
 
227 1481 nogj
/* Used for the l.bf instruction.  Therefore if the flag is not set, jump over
228
 * all the jumping stuff */
229 1452 nogj
__or_dynop void op_check_flag(void)
230
{
231 1481 nogj
  if(!(env->sprs[SPR_SR] & SPR_SR_F)) {
232 1687 nogj
    SPEEDY_CALL(do_sched_wrap);
233 1481 nogj
    OP_JUMP(OP_PARAM1);
234
  }
235
}
236
 
237
/* Used for l.bf if the delay slot instruction is on another page */
238
__or_dynop void op_check_flag_delay(void)
239
{
240 1452 nogj
  if(env->sprs[SPR_SR] & SPR_SR_F) {
241 1481 nogj
    env->delay_insn = 1;
242 1687 nogj
    env->pc_delay = env->pc + (orreg_t)OP_PARAM1;
243 1452 nogj
  }
244
}
245
 
246 1481 nogj
/* Used for the l.bnf instruction.  Therefore if the flag is set, jump over all
247
 * the jumping stuff */
248 1452 nogj
__or_dynop void op_check_not_flag(void)
249
{
250 1481 nogj
  if(env->sprs[SPR_SR] & SPR_SR_F) {
251 1687 nogj
    SPEEDY_CALL(do_sched_wrap);
252 1481 nogj
    OP_JUMP(OP_PARAM1);
253
  }
254
}
255
 
256
/* Used for l.bnf if the delay slot instruction is on another page */
257
__or_dynop void op_check_not_flag_delay(void)
258
{
259 1452 nogj
  if(!(env->sprs[SPR_SR] & SPR_SR_F)) {
260 1481 nogj
    env->delay_insn = 1;
261 1687 nogj
    env->pc_delay = env->pc + (orreg_t)OP_PARAM1;
262 1452 nogj
  }
263
}
264
 
265 1481 nogj
__or_dynop void op_add_pc(void)
266 1452 nogj
{
267 1687 nogj
  env->pc += OP_PARAM1;
268 1452 nogj
}
269
 
270
__or_dynop void op_nop_exit(void)
271
{
272
  op_support_nop_exit();
273
  FORCE_RET;
274
}
275
 
276
__or_dynop void op_nop_reset(void)
277
{
278
  op_support_nop_reset();
279 1481 nogj
  do_jump(EXCEPT_RESET);
280 1452 nogj
}
281
 
282
__or_dynop void op_nop_printf(void)
283
{
284
  op_support_nop_printf();
285
  FORCE_RET;
286
}
287
 
288
__or_dynop void op_nop_report(void)
289
{
290
  op_support_nop_report();
291
  FORCE_RET;
292
}
293
 
294
__or_dynop void op_nop_report_imm(void)
295
{
296
  op_support_nop_report_imm(OP_PARAM1);
297
}
298
 
299 1657 nogj
__or_dynop void op_analysis(void)
300 1452 nogj
{
301 1657 nogj
  op_support_analysis();
302
  FORCE_RET;
303 1452 nogj
}
304
 
305 1657 nogj
__or_dynop void op_move_gpr1_pc_delay(void)
306
{
307
  env->pc_delay = env->reg[1];
308
  env->delay_insn = 1;
309
}
310 1452 nogj
 
311 1657 nogj
__or_dynop void op_move_gpr2_pc_delay(void)
312 1452 nogj
{
313 1657 nogj
  env->pc_delay = env->reg[2];
314
  env->delay_insn = 1;
315 1452 nogj
}
316
 
317 1657 nogj
__or_dynop void op_move_gpr3_pc_delay(void)
318 1452 nogj
{
319 1657 nogj
  env->pc_delay = env->reg[3];
320
  env->delay_insn = 1;
321 1452 nogj
}
322
 
323 1657 nogj
__or_dynop void op_move_gpr4_pc_delay(void)
324
{
325
  env->pc_delay = env->reg[4];
326
  env->delay_insn = 1;
327
}
328 1452 nogj
 
329 1657 nogj
__or_dynop void op_move_gpr5_pc_delay(void)
330 1452 nogj
{
331 1657 nogj
  env->pc_delay = env->reg[5];
332
  env->delay_insn = 1;
333 1452 nogj
}
334
 
335 1657 nogj
__or_dynop void op_move_gpr6_pc_delay(void)
336 1452 nogj
{
337 1657 nogj
  env->pc_delay = env->reg[6];
338
  env->delay_insn = 1;
339 1452 nogj
}
340
 
341 1657 nogj
__or_dynop void op_move_gpr7_pc_delay(void)
342 1452 nogj
{
343 1657 nogj
  env->pc_delay = env->reg[7];
344
  env->delay_insn = 1;
345 1452 nogj
}
346
 
347 1657 nogj
__or_dynop void op_move_gpr8_pc_delay(void)
348 1452 nogj
{
349 1657 nogj
  env->pc_delay = env->reg[8];
350
  env->delay_insn = 1;
351 1452 nogj
}
352
 
353 1657 nogj
__or_dynop void op_move_gpr9_pc_delay(void)
354
{
355
  env->pc_delay = env->reg[9];
356
  env->delay_insn = 1;
357
}
358
 
359
__or_dynop void op_move_gpr10_pc_delay(void)
360
{
361
  env->pc_delay = env->reg[10];
362
  env->delay_insn = 1;
363
}
364
 
365
__or_dynop void op_move_gpr11_pc_delay(void)
366
{
367
  env->pc_delay = env->reg[11];
368
  env->delay_insn = 1;
369
}
370
 
371
__or_dynop void op_move_gpr12_pc_delay(void)
372
{
373
  env->pc_delay = env->reg[12];
374
  env->delay_insn = 1;
375
}
376
 
377
__or_dynop void op_move_gpr13_pc_delay(void)
378
{
379
  env->pc_delay = env->reg[13];
380
  env->delay_insn = 1;
381
}
382
 
383
__or_dynop void op_move_gpr14_pc_delay(void)
384
{
385
  env->pc_delay = env->reg[14];
386
  env->delay_insn = 1;
387
}
388
 
389
__or_dynop void op_move_gpr15_pc_delay(void)
390
{
391
  env->pc_delay = env->reg[15];
392
  env->delay_insn = 1;
393
}
394
 
395
__or_dynop void op_move_gpr16_pc_delay(void)
396
{
397
  env->pc_delay = env->reg[16];
398
  env->delay_insn = 1;
399
}
400
 
401
__or_dynop void op_move_gpr17_pc_delay(void)
402
{
403
  env->pc_delay = env->reg[17];
404
  env->delay_insn = 1;
405
}
406
 
407
__or_dynop void op_move_gpr18_pc_delay(void)
408
{
409
  env->pc_delay = env->reg[18];
410
  env->delay_insn = 1;
411
}
412
 
413
__or_dynop void op_move_gpr19_pc_delay(void)
414
{
415
  env->pc_delay = env->reg[19];
416
  env->delay_insn = 1;
417
}
418
 
419
__or_dynop void op_move_gpr20_pc_delay(void)
420
{
421
  env->pc_delay = env->reg[20];
422
  env->delay_insn = 1;
423
}
424
 
425
__or_dynop void op_move_gpr21_pc_delay(void)
426
{
427
  env->pc_delay = env->reg[21];
428
  env->delay_insn = 1;
429
}
430
 
431
__or_dynop void op_move_gpr22_pc_delay(void)
432
{
433
  env->pc_delay = env->reg[22];
434
  env->delay_insn = 1;
435
}
436
 
437
__or_dynop void op_move_gpr23_pc_delay(void)
438
{
439
  env->pc_delay = env->reg[23];
440
  env->delay_insn = 1;
441
}
442
 
443
__or_dynop void op_move_gpr24_pc_delay(void)
444
{
445
  env->pc_delay = env->reg[24];
446
  env->delay_insn = 1;
447
}
448
 
449
__or_dynop void op_move_gpr25_pc_delay(void)
450
{
451
  env->pc_delay = env->reg[25];
452
  env->delay_insn = 1;
453
}
454
 
455
__or_dynop void op_move_gpr26_pc_delay(void)
456
{
457
  env->pc_delay = env->reg[26];
458
  env->delay_insn = 1;
459
}
460
 
461
__or_dynop void op_move_gpr27_pc_delay(void)
462
{
463
  env->pc_delay = env->reg[27];
464
  env->delay_insn = 1;
465
}
466
 
467
__or_dynop void op_move_gpr28_pc_delay(void)
468
{
469
  env->pc_delay = env->reg[28];
470
  env->delay_insn = 1;
471
}
472
 
473
__or_dynop void op_move_gpr29_pc_delay(void)
474
{
475
  env->pc_delay = env->reg[29];
476
  env->delay_insn = 1;
477
}
478
 
479
__or_dynop void op_move_gpr30_pc_delay(void)
480
{
481
  env->pc_delay = env->reg[30];
482
  env->delay_insn = 1;
483
}
484
 
485
__or_dynop void op_move_gpr31_pc_delay(void)
486
{
487
  env->pc_delay = env->reg[31];
488
  env->delay_insn = 1;
489
}
490
 
491
#define OP_FILE "op_1t_op.h"
492
#include "op_1t.h"
493
#undef OP_FILE
494 1658 nogj
 
495
#define OP_FILE "op_2t_op.h"
496
#include "op_2t.h"
497
#undef OP_FILE
498 1660 nogj
 
499
#define OP_FILE "op_3t_op.h"
500
#include "op_3t.h"
501
#undef OP_FILE
502
 
503 1661 nogj
#define OP_FILE "op_arith_op.h"
504 1452 nogj
#define OP_EXTRA
505
 
506
#define OP /
507 1661 nogj
#define OP_CAST(x) (orreg_t)(x)
508 1452 nogj
#define OP_NAME div
509 1661 nogj
#include "op_3t.h"
510 1452 nogj
#undef OP_NAME
511
#undef OP_CAST
512
#undef OP
513
 
514
#define OP /
515 1661 nogj
#define OP_CAST(x) (x)
516 1452 nogj
#define OP_NAME divu
517 1661 nogj
#include "op_3t.h"
518 1452 nogj
#undef OP_NAME
519
#undef OP_CAST
520
#undef OP
521
 
522
#define OP *
523 1661 nogj
#define OP_CAST(x) (x)
524 1452 nogj
#define OP_NAME mulu
525 1661 nogj
#include "op_3t.h"
526 1452 nogj
#undef OP_NAME
527
#undef OP_CAST
528
#undef OP
529
 
530
#define OP -
531 1661 nogj
#define OP_CAST(x) (orreg_t)(x)
532 1452 nogj
#define OP_NAME sub
533 1661 nogj
#include "op_3t.h"
534 1452 nogj
#undef OP_NAME
535
#undef OP_CAST
536
#undef OP
537
 
538
#undef OP_EXTRA
539
 
540
#define OP_EXTRA + ((env->sprs[SPR_SR] & SPR_SR_CY) >> 10)
541
#define OP +
542 1661 nogj
#define OP_CAST(x) (orreg_t)(x)
543 1452 nogj
#define OP_NAME addc
544 1661 nogj
#include "op_3t.h"
545
#include "op_2t.h"
546 1452 nogj
#undef OP_NAME
547
#undef OP_CAST
548
#undef OP
549
 
550
#undef OP_EXTRA
551
#define OP_EXTRA
552
 
553
#define OP +
554 1661 nogj
#define OP_CAST(x) (orreg_t)(x)
555 1452 nogj
#define OP_NAME add
556 1661 nogj
#include "op_3t.h"
557
#include "op_2t.h"
558 1452 nogj
#undef OP_NAME
559
#undef OP_CAST
560
#undef OP
561
 
562
#define OP &
563 1661 nogj
#define OP_CAST(x) (x)
564 1452 nogj
#define OP_NAME and
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) (orreg_t)(x)
573 1452 nogj
#define OP_NAME mul
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) (x)
582 1452 nogj
#define OP_NAME or
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 sll
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) (orreg_t)(x)
600 1452 nogj
#define OP_NAME sra
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) (x)
609 1452 nogj
#define OP_NAME srl
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 xor
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
#undef OP_EXTRA
626 1661 nogj
#undef OP_FILE
627 1452 nogj
 
628 1662 nogj
#define OP_FILE "op_extend_op.h"
629
 
630 1452 nogj
#define EXT_NAME extbs
631
#define EXT_TYPE int8_t
632
#define EXT_CAST (orreg_t)
633 1662 nogj
#include "op_2t.h"
634 1452 nogj
#undef EXT_CAST
635
#undef EXT_TYPE
636
#undef EXT_NAME
637
 
638
#define EXT_NAME extbz
639
#define EXT_TYPE uint8_t
640
#define EXT_CAST (uorreg_t)
641 1662 nogj
#include "op_2t.h"
642 1452 nogj
#undef EXT_CAST
643
#undef EXT_TYPE
644
#undef EXT_NAME
645
 
646
#define EXT_NAME exths
647
#define EXT_TYPE int16_t
648
#define EXT_CAST (orreg_t)
649 1662 nogj
#include "op_2t.h"
650 1452 nogj
#undef EXT_CAST
651
#undef EXT_TYPE
652
#undef EXT_NAME
653
 
654
#define EXT_NAME exthz
655
#define EXT_TYPE uint16_t
656
#define EXT_CAST (uorreg_t)
657 1662 nogj
#include "op_2t.h"
658 1452 nogj
#undef EXT_CAST
659
#undef EXT_TYPE
660
#undef EXT_NAME
661
 
662 1662 nogj
#undef OP_FILE
663
 
664 1663 nogj
#define OP_FILE "op_comp_op.h"
665
 
666 1452 nogj
#define COMP ==
667
#define COMP_NAME sfeq
668 1663 nogj
#define COMP_CAST(x) (x)
669
#include "op_2t.h"
670
#include "op_1t.h"
671 1452 nogj
#undef COMP_CAST
672
#undef COMP_NAME
673
#undef COMP
674
 
675
#define COMP !=
676
#define COMP_NAME sfne
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 sfgtu
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 sfgeu
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 sfltu
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 sfleu
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 sfgts
722 1663 nogj
#define COMP_CAST(x) (orreg_t)(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 sfges
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 sflts
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 sfles
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 1663 nogj
#undef OP_FILE
757
 
758 1657 nogj
#define OP_FILE "op_t_reg_mov_op.h"
759
#include "op_1t.h"
760
#undef OP_FILE
761 1452 nogj
 
762 1664 nogj
#define OP_FILE "op_mftspr_op.h"
763
#include "op_1t.h"
764
#include "op_2t.h"
765
#undef OP_FILE
766 1452 nogj
#include "op_mftspr_op.h"
767
 
768 1665 nogj
#define OP_FILE "op_mac_op.h"
769 1452 nogj
 
770
#define OP +=
771
#define OP_NAME mac
772 1665 nogj
#include "op_2t.h"
773 1452 nogj
#undef OP_NAME
774
#undef OP
775
 
776
#define OP -=
777
#define OP_NAME msb
778 1665 nogj
#include "op_2t.h"
779 1452 nogj
#undef OP_NAME
780
#undef OP
781
 
782 1665 nogj
#undef OP_FILE
783
 
784 1666 nogj
#define OP_FILE "op_lwhb_op.h"
785
 
786 1452 nogj
#define LS_OP_NAME lbz
787
#define LS_OP_CAST
788
#define LS_OP_FUNC eval_mem8
789 1666 nogj
#include "op_2t.h"
790
#include "op_1t.h"
791 1452 nogj
#undef LS_OP_FUNC
792
#undef LS_OP_CAST
793
#undef LS_OP_NAME
794
 
795
#define LS_OP_NAME lbs
796
#define LS_OP_CAST (int8_t)
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 lhz
805
#define LS_OP_CAST
806
#define LS_OP_FUNC eval_mem16
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 lhs
814
#define LS_OP_CAST (int16_t)
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 lwz
823
#define LS_OP_CAST
824
#define LS_OP_FUNC eval_mem32
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 lws
832
#define LS_OP_CAST (int32_t)
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 1666 nogj
#undef OP_FILE
841
 
842 1667 nogj
#define OP_FILE "op_swhb_op.h"
843
 
844 1452 nogj
#define S_OP_NAME sb
845
#define S_FUNC set_mem8
846
#include "op_swhb_op.h"
847 1667 nogj
#include "op_2t.h"
848
#include "op_1t.h"
849 1452 nogj
#undef S_FUNC
850
#undef S_OP_NAME
851
 
852
#define S_OP_NAME sh
853
#define S_FUNC set_mem16
854
#include "op_swhb_op.h"
855 1667 nogj
#include "op_2t.h"
856
#include "op_1t.h"
857 1452 nogj
#undef S_FUNC
858
#undef S_OP_NAME
859
 
860
#define S_OP_NAME sw
861
#define S_FUNC set_mem32
862
#include "op_swhb_op.h"
863 1667 nogj
#include "op_2t.h"
864
#include "op_1t.h"
865 1452 nogj
#undef S_FUNC
866
#undef S_OP_NAME
867
 
868
__or_dynop void op_join_mem_cycles(void)
869
{
870 1687 nogj
  runtime.sim.cycles += runtime.sim.mem_cycles;
871
  scheduler.job_queue->time -= runtime.sim.mem_cycles;
872
  runtime.sim.mem_cycles = 0;
873 1452 nogj
}
874
 
875
__or_dynop void op_store_link_addr_gpr(void)
876
{
877 1687 nogj
  env->reg[LINK_REGNO] = env->pc + 8;
878 1452 nogj
}
879
 
880
__or_dynop void op_prep_rfe(void)
881
{
882
  env->sprs[SPR_SR] = env->sprs[SPR_ESR_BASE] | SPR_SR_FO;
883 1687 nogj
  env->sprs[SPR_PPC] = env->pc;
884
  env->pc = env->sprs[SPR_EPCR_BASE] - 4;
885 1452 nogj
}
886
 
887
static inline void prep_except(oraddr_t epcr_base)
888
{
889
  env->sprs[SPR_EPCR_BASE] = epcr_base;
890
 
891
  env->sprs[SPR_ESR_BASE] = env->sprs[SPR_SR];
892
 
893
  /* Address translation is always disabled when starting exception. */
894
  env->sprs[SPR_SR] &= ~SPR_SR_DME;
895
  env->sprs[SPR_SR] &= ~SPR_SR_IME;
896
 
897
  env->sprs[SPR_SR] &= ~SPR_SR_OVE;   /* Disable overflow flag exception. */
898
 
899
  env->sprs[SPR_SR] |= SPR_SR_SM;     /* SUPV mode */
900
  env->sprs[SPR_SR] &= ~(SPR_SR_IEE | SPR_SR_TEE);    /* Disable interrupts. */
901
}
902
 
903
__or_dynop void op_set_except_pc(void)
904
{
905 1687 nogj
  env->pc = OP_PARAM1;
906 1452 nogj
}
907
 
908
/* Before the code in op_{sys,trap}{,_delay} gets run, the scheduler runs.
909
 * Therefore the pc will point to the instruction after the l.sys or l.trap
910
 * instruction */
911
__or_dynop void op_prep_sys_delay(void)
912
{
913
  env->delay_insn = 0;
914 1687 nogj
  prep_except(env->pc - 4);
915
  env->pc = EXCEPT_SYSCALL - 4;
916 1452 nogj
}
917
 
918
__or_dynop void op_prep_sys(void)
919
{
920 1687 nogj
  prep_except(env->pc + 4);
921
  env->pc = EXCEPT_SYSCALL - 4;
922 1452 nogj
}
923
 
924
__or_dynop void op_prep_trap_delay(void)
925
{
926
  env->delay_insn = 0;
927 1687 nogj
  prep_except(env->pc - 4);
928
  env->pc = EXCEPT_TRAP - 4;
929 1452 nogj
}
930
 
931
__or_dynop void op_prep_trap(void)
932
{
933 1687 nogj
  prep_except(env->pc);
934
  env->pc = EXCEPT_TRAP - 4;
935 1452 nogj
}
936
 
937
/* FIXME: This `instruction' should be split up like the l.trap and l.sys
938
 * instructions are done */
939
__or_dynop void op_illegal_delay(void)
940
{
941
  env->delay_insn = 0;
942 1687 nogj
  env->sprs[SPR_EEAR_BASE] = env->pc - 4;
943 1481 nogj
  do_jump(EXCEPT_ILLEGAL - 4);
944 1452 nogj
}
945
 
946
__or_dynop void op_illegal(void)
947
{
948 1687 nogj
  env->sprs[SPR_EEAR_BASE] = env->pc;
949 1481 nogj
  do_jump(EXCEPT_ILLEGAL);
950 1452 nogj
}
951
 
952
__or_dynop void op_do_sched(void)
953
{
954 1687 nogj
  SPEEDY_CALL(do_sched_wrap);
955 1452 nogj
}
956
 
957 1481 nogj
__or_dynop void op_do_sched_delay(void)
958
{
959 1687 nogj
  SPEEDY_CALL(do_sched_wrap_delay);
960 1481 nogj
}
961
 
962 1452 nogj
__or_dynop void op_macc(void)
963
{
964
  env->sprs[SPR_MACLO] = 0;
965
  env->sprs[SPR_MACHI] = 0;
966
}
967
 
968
__or_dynop void op_store_insn_ea(void)
969
{
970
  env->insn_ea = OP_PARAM1;
971
}
972
 

powered by: WebSVN 2.1.0

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