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

Subversion Repositories or1k

[/] [or1k/] [tags/] [nog_patch_47/] [or1ksim/] [testbench/] [except_test.c] - Blame information for rev 608

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

Line No. Rev Author Line
1 516 markom
/* This is exception test for OpenRISC 1200 */
2
 
3
#include "spr_defs.h"
4
#include "support.h"
5
#include "int.h"
6
 
7
/* Define RAM physical location and size
8
   Bottom half will be used for this program, the rest
9
   will be used for testing */
10
#define FLASH_START 0x00000000
11
#define FLASH_SIZE  0x00200000
12 608 simons
#define RAM_START   0x80000000
13 516 markom
#define RAM_SIZE    0x00200000
14
 
15
/* MMU page size */
16
#define PAGE_SIZE 8192
17
 
18
/* Number of DTLB sets used (power of 2, max is 256) */
19
#define DTLB_SETS 32
20
 
21
/* Number of DTLB ways (2, 2, 3 etc., max is 4). */
22
#define DTLB_WAYS 1
23
 
24
/* Number of ITLB sets used (power of 2, max is 256) */
25
#define ITLB_SETS 32
26
 
27
/* Number of ITLB ways (1, 2, 3 etc., max is 4). */
28
#define ITLB_WAYS 1
29
 
30
/* TLB mode codes */
31
#define TLB_CODE_ONE_TO_ONE     0x00000000
32
#define TLB_CODE_PLUS_ONE_PAGE  0x10000000
33
#define TLB_CODE_MINUS_ONE_PAGE 0x20000000
34
 
35
#define TLB_TEXT_SET_NB 6
36
#define TLB_DATA_SET_NB 2
37
 
38
#define TLB_CODE_MASK   0xfffff000
39
#define TLB_PR_MASK     0x00000fff
40
#define DTLB_PR_NOLIMIT  ( SPR_DTLBTR_CI   | \
41
                          SPR_DTLBTR_URE  | \
42
                          SPR_DTLBTR_UWE  | \
43
                          SPR_DTLBTR_SRE  | \
44
                          SPR_DTLBTR_SWE  )
45
 
46
#define ITLB_PR_NOLIMIT  ( SPR_ITLBTR_CI   | \
47
                          SPR_ITLBTR_SXE  | \
48
                          SPR_ITLBTR_UXE  )
49
 
50
/* fails if x is false */
51
#define ASSERT(x) ((x)?1: fail (__FUNCTION__, __LINE__))
52
 
53
/* Exception vectors */
54
#define V_RESET       1
55
#define V_BERR        2
56
#define V_DPF         3
57
#define V_IPF         4
58 600 simons
#define V_TICK        5
59 516 markom
#define V_ALIGN       6
60
#define V_ILLINSN     7
61 600 simons
#define V_INT         8
62 516 markom
#define V_DTLB_MISS   9
63
#define V_ITLB_MISS   10
64
#define V_RANGE       11
65
#define V_SYS         12
66
#define V_TRAP        14
67
 
68
#if 1
69
#define debug printf
70
#else
71
#define debug
72
#endif
73
 
74
/* Extern functions */
75
extern void lo_dmmu_en (void);
76
extern void lo_immu_en (void);
77
extern unsigned long call (unsigned long add, unsigned long val);
78
extern unsigned long call_with_int (unsigned long add, unsigned long val);
79
extern void trap (void);
80
extern void b_trap (void);
81
extern void range (void);
82
extern void b_range (void);
83
extern int except_basic (void);
84
extern void (*test)(void);
85
extern int load_acc_32 (unsigned long add);
86
extern int load_acc_16 (unsigned long add);
87
extern int store_acc_32 (unsigned long add);
88
extern int store_acc_16 (unsigned long add);
89
extern int load_b_acc_32 (unsigned long add);
90
extern int int_trigger (void);
91
extern int int_loop (void);
92
extern int jump_back (void);
93
 
94
/* Local functions prototypes */
95
void dmmu_disable (void);
96
void immu_disable (void);
97
 
98
/* DTLB mode status */
99
volatile unsigned long dtlb_val;
100
 
101
/* ITLB mode status */
102
volatile unsigned long itlb_val;
103
 
104
/* Exception counter */
105
volatile int except_count;
106
 
107
/* Exception mask */
108
volatile unsigned long except_mask;
109
 
110
/* Exception efective address */
111
volatile unsigned long except_ea;
112
 
113
/* Eception PC */
114
volatile unsigned long except_pc;
115
 
116
void fail (char *func, int line)
117
{
118
#ifndef __FUNCTION__
119
#define __FUNCTION__ "?"
120
#endif
121
 
122
  immu_disable ();
123
  dmmu_disable ();
124
 
125
  debug("Test failed in %s:%i\n", func, line);
126
  report (0xeeeeeeee);
127
  exit (1);
128
}
129
 
130
void test_dummy (void)
131
{
132
        asm("_test:");
133
        asm("l.addi\t\tr3,r3,1") ;
134
        asm("l.nop" : :);
135
}
136
 
137
void copy_test (unsigned long phy_add)
138
{
139
        memcpy((void *)phy_add, (void *)&test, 8);
140
}
141
 
142
/* Bus error handler */
143
void bus_err_handler (void)
144
{
145
 
146
  except_mask |= 1 << V_BERR;
147
  except_count++;
148
}
149
 
150
/* Illegal insn handler */
151
void ill_insn_handler (void)
152
{
153
 
154
  except_mask |= 1 << V_ILLINSN;
155
  except_count++;
156
}
157
 
158
/* Low priority interrupt handler */
159 600 simons
void tick_handler (void)
160 516 markom
{
161
 
162
  /* Disable interrupt recognition */
163 600 simons
  mtspr(SPR_ESR_BASE, mfspr(SPR_ESR_BASE) & ~SPR_SR_TEE);
164 516 markom
 
165 600 simons
  except_mask |= 1 << V_TICK;
166 516 markom
  except_count++;
167
}
168
 
169
/* High priority interrupt handler */
170 600 simons
void int_handler (void)
171 516 markom
{
172
 
173
  /* Disable interrupt recognition */
174 600 simons
  mtspr(SPR_ESR_BASE, mfspr(SPR_ESR_BASE) & ~SPR_SR_IEE);
175 516 markom
 
176 600 simons
  except_mask |= 1 << V_INT;
177 516 markom
  except_count++;
178
}
179
 
180
/* Trap handler */
181
void trap_handler (void)
182
{
183
 
184
  except_mask |= 1 << V_TRAP;
185
  except_count++;
186
}
187
 
188
/* Align handler */
189
void align_handler (void)
190
{
191
 
192
  except_mask |= 1 << V_ALIGN;
193
  except_count++;
194
}
195
 
196
/* Range handler */
197
void range_handler (void)
198
{
199
  /* Disable range exception */
200
  mtspr (SPR_ESR_BASE, mfspr (SPR_ESR_BASE) & ~SPR_SR_OVE);
201
 
202
  except_mask |= 1 << V_RANGE;
203
  except_count++;
204
}
205
 
206
/* DTLB miss exception handler */
207
void dtlb_miss_handler (void)
208
{
209
  unsigned long ea;
210
  int set, way = 0;
211
  int i;
212
 
213
  /* Get EA that cause the exception */
214
  ea = mfspr (SPR_EEAR_BASE);
215
 
216
  /* Find TLB set and LRU way */
217
  set = (ea / PAGE_SIZE) % DTLB_SETS;
218
  for (i = 0; i < DTLB_WAYS; i++) {
219
    if ((mfspr (SPR_DTLBMR_BASE(i) + set) & SPR_DTLBMR_LRU) == 0) {
220
      way = i;
221
      break;
222
    }
223
  }
224
 
225
  mtspr (SPR_DTLBMR_BASE(way) + set, (ea & SPR_DTLBMR_VPN) | SPR_DTLBMR_V);
226
  mtspr (SPR_DTLBTR_BASE(way) + set, (ea & SPR_DTLBTR_PPN) | dtlb_val);
227
 
228
  except_mask |= 1 << V_DTLB_MISS;
229
  except_count++;
230
}
231
 
232
/* ITLB miss exception handler */
233
void itlb_miss_handler (void)
234
{
235
  unsigned long ea;
236
  int set, way = 0;
237
  int i;
238
 
239
  /* Get EA that cause the exception */
240
  ea = mfspr (SPR_EEAR_BASE);
241
 
242
  /* Find TLB set and LRU way */
243
  set = (ea / PAGE_SIZE) % ITLB_SETS;
244
  for (i = 0; i < ITLB_WAYS; i++) {
245
    if ((mfspr (SPR_ITLBMR_BASE(i) + set) & SPR_ITLBMR_LRU) == 0) {
246
      way = i;
247
      break;
248
    }
249
  }
250
 
251
  mtspr (SPR_ITLBMR_BASE(way) + set, (ea & SPR_ITLBMR_VPN) | SPR_ITLBMR_V);
252
  mtspr (SPR_ITLBTR_BASE(way) + set, (ea & SPR_ITLBTR_PPN) | itlb_val);
253
  except_mask |= 1 << V_ITLB_MISS;
254
  except_count++;
255
}
256
 
257
/* Data page fault exception handler */
258
void dpage_fault_handler (void)
259
{
260
  unsigned long ea;
261
  int set, way = 0;
262
  int i;
263
 
264
  /* Get EA that cause the exception */
265
  ea = mfspr (SPR_EEAR_BASE);
266
 
267
  /* Find TLB set and way */
268
  set = (ea / PAGE_SIZE) % DTLB_SETS;
269
  for (i = 0; i < DTLB_WAYS; i++) {
270
    if ((mfspr (SPR_DTLBMR_BASE(i) + set) & SPR_DTLBMR_VPN) == (ea & SPR_DTLBMR_VPN)) {
271
      way = i;
272
      break;
273
    }
274
  }
275
 
276
  /* Give permission */
277
  mtspr (SPR_DTLBTR_BASE(way) + set, (mfspr (SPR_DTLBTR_BASE(way) + set) & ~DTLB_PR_NOLIMIT) | dtlb_val);
278
 
279
  except_mask |= 1 << V_DPF;
280
  except_count++;
281
}
282
 
283
/* Intstruction page fault exception handler */
284
void ipage_fault_handler (void)
285
{
286
  unsigned long ea;
287
  int set, way = 0;
288
  int i;
289
 
290
  /* Get EA that cause the exception */
291
  ea = mfspr (SPR_EEAR_BASE);
292
 
293
  /* Find TLB set and way */
294
  set = (ea / PAGE_SIZE) % ITLB_SETS;
295
  for (i = 0; i < ITLB_WAYS; i++) {
296
    if ((mfspr (SPR_ITLBMR_BASE(i) + set) & SPR_ITLBMR_VPN) == (ea & SPR_ITLBMR_VPN)) {
297
      way = i;
298
      break;
299
    }
300
  }
301
 
302
  /* Give permission */
303
  mtspr (SPR_ITLBTR_BASE(way) + set, (mfspr (SPR_ITLBTR_BASE(way) + set) & ~ITLB_PR_NOLIMIT) | itlb_val);
304
 
305
  except_mask |= 1 << V_IPF;
306
  except_count++;
307
}
308
 
309
/*Enable DMMU */
310
void dmmu_enable (void)
311
{
312
  /* Enable DMMU */
313
  lo_dmmu_en ();
314
}
315
 
316
/* Disable DMMU */
317
void dmmu_disable (void)
318
{
319
  mtspr (SPR_SR, mfspr (SPR_SR) & ~SPR_SR_DME);
320
}
321
 
322
/* Enable IMMU */
323
void immu_enable (void)
324
{
325
  /* Enable IMMU */
326
  lo_immu_en ();
327
}
328
 
329
/* Disable IMMU */
330
void immu_disable (void)
331
{
332
  mtspr (SPR_SR, mfspr (SPR_SR) & ~SPR_SR_IME);
333
}
334
 
335
/* Tick timer init */
336
void tick_init (int period, int hp_int)
337
{
338 600 simons
  /* Disable tick timer exception recognition */
339
  mtspr(SPR_SR, mfspr(SPR_SR) & ~SPR_SR_TEE);
340 516 markom
 
341
  /* Set period of one cycle, restartable mode */
342
  mtspr(SPR_TTMR, SPR_TTMR_IE | SPR_TTMR_RT | (period & SPR_TTMR_PERIOD));
343
 
344
  /* Reset counter */
345
  mtspr(SPR_TTCR, 0);
346
}
347
 
348
/* Interrupt test */
349
int interrupt_test (void)
350
{
351
  unsigned long ret;
352
  int i;
353
 
354
  /* Init tick timer */
355
  tick_init (1, 1);
356
 
357
  /* Reset except counter */
358
  except_count = 0;
359
  except_mask = 0;
360
  except_pc = 0;
361
  except_ea = 0;
362
 
363
  /* Test normal high priority interrupt trigger */
364
  ret = call ((unsigned long)&int_trigger, 0);
365
  ASSERT(except_count == 1);
366 600 simons
  ASSERT(except_mask == (1 << V_TICK));
367 516 markom
  ASSERT(ret == 0);
368
  ASSERT(except_pc == (unsigned long)int_trigger + 16);
369
 
370
  /* Reset except counter */
371
  except_count = 0;
372
  except_mask = 0;
373
  except_pc = 0;
374
  except_ea = 0;
375
 
376
  /* Test inetrrupt in delay slot */
377
  tick_init (10, 1);
378
 
379
  /* Hopefully we will have interrupt recognition between branch insn and delay slot */
380
  except_pc = (unsigned long)&int_loop;
381
  for (i = 0; i < 10; i++) {
382
    call_with_int (except_pc, RAM_START);
383
    ASSERT(except_pc == (unsigned long)&int_loop);
384
  }
385
 
386
  return 0;
387
}
388
 
389
/* ITLB miss test */
390
int itlb_test (void)
391
{
392
  int i, j, ret;
393
  unsigned long ea, ta;
394
 
395
  /* Invalidate all entries in ITLB */
396
  for (i = 0; i < ITLB_WAYS; i++) {
397
    for (j = 0; j < ITLB_SETS; j++) {
398
      mtspr (SPR_ITLBMR_BASE(i) + j, 0);
399
      mtspr (SPR_ITLBTR_BASE(i) + j, 0);
400
    }
401
  }
402
 
403
  /* Set one to one translation for the use of this program */
404
  for (i = 0; i < TLB_TEXT_SET_NB; i++) {
405
    ea = FLASH_START + (i*PAGE_SIZE);
406
    ta = FLASH_START + (i*PAGE_SIZE);
407
    mtspr (SPR_ITLBMR_BASE(0) + i, ea | SPR_ITLBMR_V);
408
    mtspr (SPR_ITLBTR_BASE(0) + i, ta | ITLB_PR_NOLIMIT);
409
  }
410
 
411
  /* Set dtlb no permisions */
412
  itlb_val = SPR_ITLBTR_CI;
413
 
414
  /* Reset except counter */
415
  except_count = 0;
416
  except_mask = 0;
417
  except_pc = 0;
418
  except_ea = 0;
419
 
420
  /* Enable IMMU */
421
  immu_enable ();
422
 
423
  /* Copy jump instruction to last location of a page */
424
  ea = RAM_START + (RAM_SIZE/2) + ((TLB_TEXT_SET_NB + 1)*PAGE_SIZE) - 8;
425
  memcpy((void *)ea, (void *)&jump_back, 12);
426
 
427
  /* Check if there was ITLB miss exception */
428
  ret = call (ea, 0);
429
  ASSERT(except_count == 1);
430
  ASSERT(except_mask == (1 << V_ITLB_MISS));
431
  ASSERT(except_pc == ea);
432
  ASSERT(ret == 0);
433
 
434
  /* Set dtlb no permisions */
435
  itlb_val = SPR_ITLBTR_CI | SPR_ITLBTR_SXE;
436
 
437
  /* Reset except counter */
438
  except_count = 0;
439
  except_mask = 0;
440
  except_pc = 0;
441
  except_ea = 0;
442
 
443
  /* Check if there was IPF miss exception */
444
  ret = call (ea, 0);
445
  ASSERT(except_count == 1);
446
  ASSERT(except_mask == (1 << V_IPF));
447
  ASSERT(except_pc == ea);
448
  ASSERT(ret == 0);
449
 
450
  /* Set dtlb no permisions */
451
  itlb_val = SPR_ITLBTR_CI;
452
 
453
  /* Reset except counter */
454
  except_count = 0;
455
  except_mask = 0;
456
  except_pc = 0;
457
  except_ea = 0;
458
 
459
  /* Check if there was ITLB miss exception */
460
  ret = call (ea, 0);
461
  ASSERT(except_count == 1);
462
  ASSERT(except_mask == (1 << V_ITLB_MISS));
463
  ASSERT(except_pc == ea + 4);
464
  ASSERT(ret == 0);
465
 
466
  /* Set dtlb no permisions */
467
  itlb_val = SPR_ITLBTR_CI | SPR_ITLBTR_SXE;
468
 
469
  /* Reset except counter */
470
  except_count = 0;
471
  except_mask = 0;
472
  except_pc = 0;
473
  except_ea = 0;
474
 
475
  /* Check if there was IPF exception */
476
  ret = call (ea, 0);
477
  ASSERT(except_count == 1);
478
  ASSERT(except_mask == (1 << V_IPF));
479
  ASSERT(except_pc == ea + 4);
480
  ASSERT(ret == 0);
481
 
482
  /* Reset except counter */
483
  except_count = 0;
484
  except_mask = 0;
485
  except_pc = 0;
486
  except_ea = 0;
487
 
488
  ret = call (ea, 0);
489
  ASSERT(except_count == 0);
490
  ASSERT(ret == 1);
491
 
492
  /* Disable IMMU */
493
  immu_disable ();
494
 
495
  return 0;
496
}
497
 
498
/* DTLB miss test */
499
int dtlb_test (void)
500
{
501
  int i, j, ret;
502
  unsigned long ea, ta;
503
 
504
  /* Invalidate all entries in DTLB */
505
  for (i = 0; i < DTLB_WAYS; i++) {
506
    for (j = 0; j < DTLB_SETS; j++) {
507
      mtspr (SPR_DTLBMR_BASE(i) + j, 0);
508
      mtspr (SPR_DTLBTR_BASE(i) + j, 0);
509
    }
510
  }
511
 
512
  /* Set one to one translation for the use of this program */
513
  for (i = 0; i < TLB_DATA_SET_NB; i++) {
514
    ea = RAM_START + (i*PAGE_SIZE);
515
    ta = RAM_START + (i*PAGE_SIZE);
516
    mtspr (SPR_DTLBMR_BASE(0) + i, ea | SPR_ITLBMR_V);
517
    mtspr (SPR_DTLBTR_BASE(0) + i, ta | DTLB_PR_NOLIMIT);
518
  }
519
 
520
  /* Set dtlb no permisions */
521
  dtlb_val = SPR_DTLBTR_CI;
522
 
523
  /* Reset except counter */
524
  except_count = 0;
525
  except_mask = 0;
526
  except_pc = 0;
527
  except_ea = 0;
528
 
529
  /* Set pattern */
530
  ea = RAM_START + (RAM_SIZE/2) + ((TLB_DATA_SET_NB)*PAGE_SIZE);
531
  REG32(ea) = 0x87654321;
532
 
533
  /* Enable DMMU */
534
  dmmu_enable ();
535
 
536
  /* Check if there was DTLB miss exception */
537
  ret = call ((unsigned long)&load_b_acc_32, ea);
538
  ASSERT(except_count == 1);
539
  ASSERT(except_mask == (1 << V_DTLB_MISS));
540
  ASSERT(except_pc == (unsigned long)load_b_acc_32 + 8);
541
  ASSERT(except_ea == ea);
542
  ASSERT(ret == 0x12345678);
543
 
544
  /* Set dtlb no permisions */
545
  dtlb_val = SPR_DTLBTR_CI | SPR_DTLBTR_SRE;
546
 
547
  /* Reset except counter */
548
  except_count = 0;
549
  except_mask = 0;
550
  except_pc = 0;
551
  except_ea = 0;
552
 
553
  /* Check if there was DPF miss exception */
554
  ret = call ((unsigned long)&load_b_acc_32, ea);
555
  ASSERT(except_count == 1);
556
  ASSERT(except_mask == (1 << V_DPF));
557
  ASSERT(except_pc == (unsigned long)load_b_acc_32 + 8);
558
  ASSERT(except_ea == ea);
559
  ASSERT(ret == 0x12345678);
560
 
561
  /* Reset except counter */
562
  except_count = 0;
563
  except_mask = 0;
564
  except_pc = 0;
565
  except_ea = 0;
566
 
567
  ret = call ((unsigned long)&load_b_acc_32, ea);
568
  ASSERT(except_count == 0);
569
  ASSERT(ret == 0x87654321);
570
 
571
  /* Disable DMMU */
572
  dmmu_disable ();
573
 
574
  return 0;
575
}
576
 
577
/* Bus error test */
578
int buserr_test (void)
579
{
580
  int i, j, ret;
581
  unsigned long ea, ta;
582
 
583
  /* Invalidate all entries in ITLB */
584
  for (i = 0; i < ITLB_WAYS; i++) {
585
    for (j = 0; j < ITLB_SETS; j++) {
586
      mtspr (SPR_ITLBMR_BASE(i) + j, 0);
587
      mtspr (SPR_ITLBTR_BASE(i) + j, 0);
588
    }
589
  }
590
 
591
  /* Set one to one translation for the use of this program */
592
  for (i = 0; i < TLB_TEXT_SET_NB; i++) {
593
    ea = FLASH_START + (i*PAGE_SIZE);
594
    ta = FLASH_START + (i*PAGE_SIZE);
595
    mtspr (SPR_ITLBMR_BASE(0) + i, ea | SPR_ITLBMR_V);
596
    mtspr (SPR_ITLBTR_BASE(0) + i, ta | ITLB_PR_NOLIMIT);
597
  }
598
 
599
  /* Invalidate all entries in DTLB */
600
  for (i = 0; i < DTLB_WAYS; i++) {
601
    for (j = 0; j < DTLB_SETS; j++) {
602
      mtspr (SPR_DTLBMR_BASE(i) + j, 0);
603
      mtspr (SPR_DTLBTR_BASE(i) + j, 0);
604
    }
605
  }
606
 
607
  /* Set one to one translation for the use of this program */
608
  for (i = 0; i < TLB_DATA_SET_NB; i++) {
609
    ea = RAM_START + (i*PAGE_SIZE);
610
    ta = RAM_START + (i*PAGE_SIZE);
611
    mtspr (SPR_DTLBMR_BASE(0) + i, ea | SPR_ITLBMR_V);
612
    mtspr (SPR_DTLBTR_BASE(0) + i, ta | DTLB_PR_NOLIMIT);
613
  }
614
 
615
  /* Reset except counter */
616
  except_count = 0;
617
  except_mask = 0;
618
  except_pc = 0;
619
  except_ea = 0;
620
 
621
  /* Set IMMU translation */
622
  ea = RAM_START + (RAM_SIZE) + ((TLB_TEXT_SET_NB)*PAGE_SIZE);
623
  itlb_val = SPR_ITLBTR_CI | SPR_ITLBTR_SXE;
624
  mtspr (SPR_ITLBMR_BASE(0) + TLB_TEXT_SET_NB, (ea & SPR_ITLBMR_VPN) | SPR_ITLBMR_V);
625
  mtspr (SPR_ITLBTR_BASE(0) + TLB_TEXT_SET_NB, ((ea + PAGE_SIZE) & SPR_ITLBTR_PPN) | itlb_val);
626
 
627
  /* Enable IMMU */
628
  immu_enable ();
629
 
630
  /* Check if there was bus error exception */
631
  ret = call (ea, 0);
632
  ASSERT(except_count == 1);
633
  ASSERT(except_mask == (1 << V_BERR));
634
  ASSERT(except_pc == ea);
635 525 simons
  ASSERT(except_ea == ea);
636 516 markom
 
637
  /* Disable IMMU */
638
  immu_disable ();
639
 
640
  /* Reset except counter */
641
  except_count = 0;
642
  except_mask = 0;
643
  except_pc = 0;
644
  except_ea = 0;
645
 
646
  /* Copy jump instruction to last location of RAM */
647
  ea = RAM_START + RAM_SIZE - 8;
648
  memcpy((void *)ea, (void *)&jump_back, 8);
649
 
650
  /* Check if there was bus error exception */
651
  ret = call (ea, 0);
652
  ASSERT(except_count == 1);
653
  ASSERT(except_mask == (1 << V_BERR));
654
  ASSERT(except_pc == ea + 4);
655
  ASSERT(except_ea == ea + 8);
656
 
657
  /* Reset except counter */
658
  except_count = 0;
659
  except_mask = 0;
660
  except_pc = 0;
661
  except_ea = 0;
662
 
663
  /* Set DMMU translation */
664
  ea = RAM_START + (RAM_SIZE) + ((TLB_DATA_SET_NB)*PAGE_SIZE);
665
  dtlb_val = SPR_DTLBTR_CI | SPR_DTLBTR_SRE;
666
  mtspr (SPR_DTLBMR_BASE(0) + TLB_DATA_SET_NB, (ea & SPR_DTLBMR_VPN) | SPR_DTLBMR_V);
667
  mtspr (SPR_DTLBTR_BASE(0) + TLB_DATA_SET_NB, ((ea + PAGE_SIZE) & SPR_DTLBTR_PPN) | dtlb_val);
668
 
669
  /* Enable DMMU */
670
  dmmu_enable ();
671
 
672
  /* Check if there was bus error exception */
673
  ret = call ((unsigned long)&load_acc_32, ea );
674
  ASSERT(except_count == 1);
675
  ASSERT(except_mask == (1 << V_BERR));
676
  ASSERT(except_pc == (unsigned long)load_acc_32 + 8);
677 525 simons
  ASSERT(except_ea == ea);
678 516 markom
  ASSERT(ret == 0x12345678);
679
 
680
  /* Disable DMMU */
681
  dmmu_disable ();
682
 
683
  /* Reset except counter */
684
  except_count = 0;
685
  except_mask = 0;
686
  except_pc = 0;
687
  except_ea = 0;
688
 
689
  /* Check if there was bus error exception */
690
  ret = call ((unsigned long)&load_b_acc_32, ea );
691
  ASSERT(except_count == 1);
692
  ASSERT(except_mask == (1 << V_BERR));
693
  ASSERT(except_pc == (unsigned long)load_b_acc_32 + 8);
694
  ASSERT(except_ea == ea);
695
  ASSERT(ret == 0x12345678);
696
 
697
  return 0;
698
}
699
 
700
/* Illegal instruction test */
701
int illegal_insn_test (void)
702
{
703
  int ret;
704
 
705
  /* Reset except counter */
706
  except_count = 0;
707
  except_mask = 0;
708
  except_pc = 0;
709
  except_ea = 0;
710
 
711
  /* Set illegal insn */
712
  REG32(RAM_START + 0) = REG32((unsigned long)jump_back + 4);
713
  REG32(RAM_START + 4) = 0xffffffff;
714
 
715
  /* Check if there was illegal insn exception */
716
  ret = call (RAM_START + 4, 0 );
717
  ASSERT(except_count == 1);
718
  ASSERT(except_mask == (1 << V_ILLINSN));
719
  ASSERT(except_pc == RAM_START + 4);
720
 
721
  /* Reset except counter */
722
  except_count = 0;
723
  except_mask = 0;
724
  except_pc = 0;
725
  except_ea = 0;
726
 
727
  /* Check if there was illegal insn exception */
728
  ret = call (RAM_START, 0 );
729
  ASSERT(except_count == 1);
730
  ASSERT(except_mask == (1 << V_ILLINSN));
731
  ASSERT(except_pc == RAM_START);
732
 
733
  return 0;
734
}
735
 
736
/* Align test */
737
int align_test (void)
738
{
739
  int ret;
740
 
741
  /* Reset except counter */
742
  except_count = 0;
743
  except_mask = 0;
744
  except_pc = 0;
745
  except_ea = 0;
746
 
747
  /* Check if there was alignment exception on read insn */
748
  ret = call ((unsigned long)&load_acc_32, RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE) + 1);
749
  ASSERT(except_count == 1);
750
  ASSERT(except_mask == (1 << V_ALIGN));
751
  ASSERT(ret == 0x12345678);
752
  ASSERT(except_pc == ((unsigned long)(load_acc_32) + 8));
753
  ASSERT(except_ea == (RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE + 1)));
754
 
755
  ret = call ((unsigned long)&load_acc_32, RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE) + 2);
756
  ASSERT(except_count == 2);
757
  ASSERT(except_mask == (1 << V_ALIGN));
758
  ASSERT(ret == 0x12345678);
759
  ASSERT(except_pc == ((unsigned long)(load_acc_32) + 8));
760
  ASSERT(except_ea == (RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE + 2)));
761
 
762
  ret = call ((unsigned long)&load_acc_32, RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE) + 3);
763
  ASSERT(except_count == 3);
764
  ASSERT(except_mask == (1 << V_ALIGN));
765
  ASSERT(ret == 0x12345678);
766
  ASSERT(except_pc == ((unsigned long)(load_acc_32) + 8));
767
  ASSERT(except_ea == (RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE + 3)));
768
 
769
  ret = call ((unsigned long)&load_acc_16, RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE) + 1);
770
  ASSERT(except_count == 4);
771
  ASSERT(except_mask == (1 << V_ALIGN));
772
  ASSERT(ret == 0x12345678);
773
  ASSERT(except_pc == ((unsigned long)(load_acc_16) + 8));
774
  ASSERT(except_ea == (RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE + 1)));
775
 
776
  /* Check alignment exception on write  insn */
777
  call ((unsigned long)&store_acc_32, RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE) + 1);
778
  ASSERT(except_count == 5);
779
  ASSERT(except_mask == (1 << V_ALIGN));
780
  ASSERT(except_pc == ((unsigned long)(store_acc_32) + 8));
781
  ASSERT(except_ea == (RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE + 1)));
782
 
783
  call ((unsigned long)&store_acc_32, RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE) + 2);
784
  ASSERT(except_count == 6);
785
  ASSERT(except_mask == (1 << V_ALIGN));
786
  ASSERT(except_pc == ((unsigned long)(store_acc_32) + 8));
787
  ASSERT(except_ea == (RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE + 2)));
788
 
789
  call ((unsigned long)&store_acc_32, RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE) + 3);
790
  ASSERT(except_count == 7);
791
  ASSERT(except_mask == (1 << V_ALIGN));
792
  ASSERT(except_pc == ((unsigned long)(store_acc_32) + 8));
793
  ASSERT(except_ea == (RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE + 3)));
794
 
795
  call ((unsigned long)&store_acc_16, RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE) + 1);
796
  ASSERT(except_count == 8);
797
  ASSERT(except_mask == (1 << V_ALIGN));
798
  ASSERT(except_pc == ((unsigned long)(store_acc_16) + 8));
799
  ASSERT(except_ea == (RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE + 1)));
800
 
801
 
802
  ret = call ((unsigned long)&load_b_acc_32, RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE) + 1);
803
  ASSERT(except_count == 9);
804
  ASSERT(except_mask == (1 << V_ALIGN));
805
  ASSERT(ret == 0x12345678);
806
  ASSERT(except_pc == ((unsigned long)(load_b_acc_32) + 8));
807
  ASSERT(except_ea == (RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE + 1)));
808
 
809
 
810
  return 0;
811
}
812
 
813
/* Trap test */
814
int trap_test (void)
815
{
816
  /* Reset except counter */
817
  except_count = 0;
818
  except_mask = 0;
819
  except_pc = 0;
820
  except_ea = 0;
821
 
822
  /* Check if there was trap exception */
823
  call ((unsigned long)&trap, 0);
824
  ASSERT(except_count == 1);
825
  ASSERT(except_mask == (1 << V_TRAP));
826
  ASSERT(except_pc == (unsigned long)(trap));
827
  ASSERT(except_ea == 0);
828
 
829
  /* Check if there was trap exception */
830
  call ((unsigned long)&b_trap, 0);
831
  ASSERT(except_count == 2);
832
  ASSERT(except_mask == (1 << V_TRAP));
833
  ASSERT(except_pc == (unsigned long)(b_trap));
834
  ASSERT(except_ea == 0);
835
 
836
  return 0;
837
}
838
 
839
/* Range test */
840
int range_test (void)
841
{
842
  /* Reset except counter */
843
  except_count = 0;
844
  except_mask = 0;
845
  except_pc = 0;
846
  except_ea = 0;
847
 
848
  /* Check if there was range exception */
849
  mtspr (SPR_SR, mfspr (SPR_SR) | SPR_SR_OVE);
850
  call ((unsigned long)&range, 0);
851
  ASSERT(except_count == 1);
852
  ASSERT(except_mask == (1 << V_RANGE));
853
  ASSERT(except_pc == (unsigned long)(range));
854
  ASSERT(except_ea == 0);
855
 
856
  /* Check if there was range exception */
857
  mtspr (SPR_SR, mfspr (SPR_SR) | SPR_SR_OVE);
858
  call ((unsigned long)&b_range, 0);
859
  ASSERT(except_count == 2);
860
  ASSERT(except_mask == (1 << V_RANGE));
861
  ASSERT(except_pc == (unsigned long)(b_range));
862
  ASSERT(except_ea == 0);
863
 
864
  return 0;
865
}
866
 
867
/* Exception priority test */
868
void except_priority_test (void)
869
{
870
  int i, j;
871
  unsigned long ea, ta, ret;
872
 
873
  /* Invalidate all entries in ITLB */
874
  for (i = 0; i < ITLB_WAYS; i++) {
875
    for (j = 0; j < ITLB_SETS; j++) {
876
      mtspr (SPR_ITLBMR_BASE(i) + j, 0);
877
      mtspr (SPR_ITLBTR_BASE(i) + j, 0);
878
    }
879
  }
880
 
881
  /* Set one to one translation for the use of this program */
882
  for (i = 0; i < TLB_TEXT_SET_NB; i++) {
883
    ea = FLASH_START + (i*PAGE_SIZE);
884
    ta = FLASH_START + (i*PAGE_SIZE);
885
    mtspr (SPR_ITLBMR_BASE(0) + i, ea | SPR_ITLBMR_V);
886
    mtspr (SPR_ITLBTR_BASE(0) + i, ta | ITLB_PR_NOLIMIT);
887
  }
888
 
889
  /* Set dtlb no permisions */
890
  itlb_val = SPR_ITLBTR_CI;
891
 
892
  /* Invalidate all entries in DTLB */
893
  for (i = 0; i < DTLB_WAYS; i++) {
894
    for (j = 0; j < DTLB_SETS; j++) {
895
      mtspr (SPR_DTLBMR_BASE(i) + j, 0);
896
      mtspr (SPR_DTLBTR_BASE(i) + j, 0);
897
    }
898
  }
899
 
900
  /* Set one to one translation for the use of this program */
901
  for (i = 0; i < TLB_DATA_SET_NB; i++) {
902
    ea = RAM_START + (i*PAGE_SIZE);
903
    ta = RAM_START + (i*PAGE_SIZE);
904
    mtspr (SPR_DTLBMR_BASE(0) + i, ea | SPR_ITLBMR_V);
905
    mtspr (SPR_DTLBTR_BASE(0) + i, ta | DTLB_PR_NOLIMIT);
906
  }
907
 
908
  /* Init tick timer */
909
  tick_init (1, 1);
910
 
911
  /* Set dtlb no permisions */
912
  dtlb_val = SPR_DTLBTR_CI;
913
 
914
  /* Reset except counter */
915
  except_count = 0;
916
  except_mask = 0;
917
  except_pc = 0;
918
  except_ea = 0;
919
 
920
  /* Enable IMMU */
921
  immu_enable ();
922
 
923
  /* Check if there was INT exception */
924
  call_with_int (RAM_START + (RAM_SIZE) + (TLB_TEXT_SET_NB*PAGE_SIZE), 0);
925
  ASSERT(except_count == 1);
926 600 simons
  ASSERT(except_mask == (1 << V_TICK));
927 516 markom
  ASSERT(except_pc == (RAM_START + (RAM_SIZE) + (TLB_TEXT_SET_NB*PAGE_SIZE)));
928
  ASSERT(except_ea == 0);
929
 
930
  /* Reset except counter */
931
  except_count = 0;
932
  except_mask = 0;
933
  except_pc = 0;
934
  except_ea = 0;
935
 
936
  /* Check if there was ITLB exception */
937
  call (RAM_START + (RAM_SIZE) + (TLB_TEXT_SET_NB*PAGE_SIZE), 0);
938
  ASSERT(except_count == 1);
939
  ASSERT(except_mask == (1 << V_ITLB_MISS));
940
  ASSERT(except_pc == (RAM_START + (RAM_SIZE) + (TLB_TEXT_SET_NB*PAGE_SIZE)));
941
  ASSERT(except_ea == (RAM_START + (RAM_SIZE) + (TLB_TEXT_SET_NB*PAGE_SIZE)));
942
 
943
  /* Set dtlb permisions */
944
  itlb_val |= SPR_ITLBTR_SXE;
945
 
946
  /* Reset except counter */
947
  except_count = 0;
948
  except_mask = 0;
949
  except_pc = 0;
950
  except_ea = 0;
951
 
952
  /* Check if there was IPF exception */
953
  call (RAM_START + (RAM_SIZE) + (TLB_TEXT_SET_NB*PAGE_SIZE), 0);
954
  ASSERT(except_count == 1);
955
  ASSERT(except_mask == (1 << V_IPF));
956
  ASSERT(except_pc == (RAM_START + (RAM_SIZE) + (TLB_TEXT_SET_NB*PAGE_SIZE)));
957
  ASSERT(except_ea == (RAM_START + (RAM_SIZE) + (TLB_TEXT_SET_NB*PAGE_SIZE)));
958
 
959
  /* Reset except counter */
960
  except_count = 0;
961
  except_mask = 0;
962
  except_pc = 0;
963
  except_ea = 0;
964
 
965
  /* Check if there was bus error exception */
966
  call (RAM_START + (RAM_SIZE) + (TLB_TEXT_SET_NB*PAGE_SIZE), 0);
967
  ASSERT(except_count == 1);
968
  ASSERT(except_mask == (1 << V_BERR));
969
  ASSERT(except_pc == (RAM_START + (RAM_SIZE) + (TLB_TEXT_SET_NB*PAGE_SIZE)));
970
  ASSERT(except_ea == (RAM_START + (RAM_SIZE) + (TLB_TEXT_SET_NB*PAGE_SIZE)));
971
 
972
  /* Reset except counter */
973
  except_count = 0;
974
  except_mask = 0;
975
  except_pc = 0;
976
  except_ea = 0;
977
 
978
  /* Disable MMU */
979
  immu_disable ();
980
 
981
  /* Set illegal instruction */
982
  REG32(RAM_START + (RAM_SIZE/2) + (TLB_TEXT_SET_NB*PAGE_SIZE) + 0) = 0x00000000;
983
  REG32(RAM_START + (RAM_SIZE/2) + (TLB_TEXT_SET_NB*PAGE_SIZE) + 4) = 0xffffffff;
984
  REG32(RAM_START + (RAM_SIZE/2) + (TLB_TEXT_SET_NB*PAGE_SIZE) + 8) = 0x00000000;
985
 
986
  /* Check if there was illegal insn exception */
987
  call (RAM_START + (RAM_SIZE/2) + (TLB_TEXT_SET_NB*PAGE_SIZE) + 4, 0);
988
  ASSERT(except_count == 1);
989
  ASSERT(except_mask == (1 << V_ILLINSN));
990
  ASSERT(except_pc == (RAM_START + (RAM_SIZE/2) + (TLB_TEXT_SET_NB*PAGE_SIZE) + 4));
991
  ASSERT(except_ea == (RAM_START + (RAM_SIZE/2) + (TLB_TEXT_SET_NB*PAGE_SIZE) + 4 ));
992
 
993
  /* Reset except counter */
994
  except_count = 0;
995
  except_mask = 0;
996
  except_pc = 0;
997
  except_ea = 0;
998
 
999
  /* Enable DMMU */
1000
  dmmu_enable ();
1001
 
1002
  /* Check if there was alignment exception on read insn */
1003
  ret = call ((unsigned long)&load_acc_32, RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE) + 1);
1004
  ASSERT(except_count == 1);
1005
  ASSERT(except_mask == (1 << V_ALIGN));
1006
  ASSERT(ret == 0x12345678);
1007
  ASSERT(except_pc == ((unsigned long)(load_acc_32) + 8));
1008
  ASSERT(except_ea == (RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE + 1)));
1009
 
1010
  /* Reset except counter */
1011
  except_count = 0;
1012
  except_mask = 0;
1013
  except_pc = 0;
1014
  except_ea = 0;
1015
 
1016
  /* Check if there was DTLB exception */
1017
  ret = call ((unsigned long)&load_acc_32, RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE));
1018
  ASSERT(except_count == 1);
1019
  ASSERT(except_mask == (1 << V_DTLB_MISS));
1020
  ASSERT(ret == 0x12345678);
1021
  ASSERT(except_pc == ((unsigned long)(load_acc_32) + 8));
1022
  ASSERT(except_ea == (RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE)));
1023
 
1024
  /* Reset except counter */
1025
  except_count = 0;
1026
  except_mask = 0;
1027
  except_pc = 0;
1028
  except_ea = 0;
1029
 
1030
  /* Set dtlb permisions */
1031
  dtlb_val |= SPR_DTLBTR_SRE;
1032
 
1033
  /* Check if there was DPF exception */
1034
  ret = call ((unsigned long)&load_acc_32, RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE));
1035
  ASSERT(except_count == 1);
1036
  ASSERT(except_mask == (1 << V_DPF));
1037
  ASSERT(ret == 0x12345678);
1038
  ASSERT(except_pc == ((unsigned long)(load_acc_32) + 8));
1039
  ASSERT(except_ea == (RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE)));
1040
 
1041
  /* Reset except counter */
1042
  except_count = 0;
1043
  except_mask = 0;
1044
  except_pc = 0;
1045
  except_ea = 0;
1046
 
1047
  /* Check if there was bus error exception */
1048
  ret = call ((unsigned long)&load_acc_32, RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE));
1049
  ASSERT(except_count == 1);
1050
  ASSERT(except_mask == (1 << V_BERR));
1051
  ASSERT(ret == 0x12345678);
1052
  ASSERT(except_pc == ((unsigned long)(load_acc_32) + 8));
1053
  ASSERT(except_ea == (RAM_START + (RAM_SIZE) + (TLB_DATA_SET_NB*PAGE_SIZE)));
1054
 
1055
  /* Reset except counter */
1056
  except_count = 0;
1057
  except_mask = 0;
1058
  except_pc = 0;
1059
  except_ea = 0;
1060
 
1061
  /* Check if there was trap exception */
1062
  call ((unsigned long)&trap, 0);
1063
  ASSERT(except_count == 1);
1064
  ASSERT(except_mask == (1 << V_TRAP));
1065
  ASSERT(except_pc == (unsigned long)(trap));
1066
  ASSERT(except_ea == 0);
1067
 
1068 608 simons
#if 0
1069 516 markom
  /* Reset except counter */
1070
  except_count = 0;
1071
  except_mask = 0;
1072
  except_pc = 0;
1073
  except_ea = 0;
1074
 
1075
  /* Check if there was range exception */
1076
  mtspr (SPR_SR, mfspr (SPR_SR) | SPR_SR_OVE);
1077
  call ((unsigned long)&range, 0);
1078
  ASSERT(except_count == 1);
1079
  ASSERT(except_mask == (1 << V_RANGE));
1080
  ASSERT(except_pc == (unsigned long)(range));
1081
  ASSERT(except_ea == 0);
1082 608 simons
#endif
1083 516 markom
}
1084
 
1085
int main (void)
1086
{
1087
  int ret;
1088
 
1089 520 simons
  printf("except_test\n");
1090
 
1091 516 markom
  /* Register bus error handler */
1092
  excpt_buserr = (unsigned long)bus_err_handler;
1093
 
1094
  /* Register illegal insn handler */
1095
  excpt_illinsn = (unsigned long)ill_insn_handler;
1096
 
1097 600 simons
  /* Register tick timer exception handler */
1098
  excpt_tick = (unsigned long)tick_handler;
1099 516 markom
 
1100 600 simons
  /* Register external interrupt handler */
1101
  excpt_int = (unsigned long)int_handler;
1102 516 markom
 
1103
  /* Register ITLB miss handler */
1104
  excpt_itlbmiss = (unsigned long)itlb_miss_handler;
1105
 
1106
  /* Register instruction page fault handler */
1107
  excpt_ipfault = (unsigned long)ipage_fault_handler;
1108
 
1109
  /* Register DTLB miss handler */
1110
  excpt_dtlbmiss = (unsigned long)dtlb_miss_handler;
1111
 
1112
  /* Register data page fault handler */
1113
  excpt_dpfault = (unsigned long)dpage_fault_handler;
1114
 
1115
  /* Register trap handler */
1116
  excpt_trap = (unsigned long)trap_handler;
1117
 
1118
  /* Register align handler */
1119
  excpt_align = (unsigned long)align_handler;
1120
 
1121
  /* Register range handler */
1122
  excpt_range = (unsigned long)range_handler;
1123
 
1124
  /* Exception basic test */
1125
  ret = except_basic ();
1126
  ASSERT(ret == 0);
1127
 
1128
  /* Interrupt exception test */
1129
  interrupt_test ();
1130
 
1131
  /* ITLB exception test */
1132
  itlb_test ();
1133
 
1134
  /* DTLB exception test */
1135
  dtlb_test ();
1136
 
1137
  /* Bus error exception test */
1138
  buserr_test ();
1139
 
1140
  /* Illegal insn test */
1141
  illegal_insn_test ();
1142
 
1143
  /* Alignment test */
1144
  align_test ();
1145
 
1146
  /* Trap test */
1147
  trap_test ();
1148
 
1149
  /* Range test */
1150 520 simons
//  range_test ();
1151 516 markom
 
1152
  /* Exception priority test */
1153
  except_priority_test ();
1154
 
1155
  report (0xdeaddead);
1156
  exit (0);
1157
 
1158
  return 0;
1159
}
1160
 

powered by: WebSVN 2.1.0

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