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

Subversion Repositories or1k

[/] [or1k/] [tags/] [nog_patch_47/] [or1ksim/] [debug/] [debug_unit.c] - Blame information for rev 378

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

Line No. Rev Author Line
1 221 markom
/* debug_unit.c -- Simulation of Or1k debug unit
2
   Copyright (C) 2001 Chris Ziomkowski, chris@asics.ws
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
  This is an architectural level simulation of the Or1k debug
22
  unit as described in OpenRISC 1000 System Architecture Manual,
23
  v. 0.1 on 22 April, 2001. This unit is described in Section 13.
24
 
25
  Every attempt has been made to be as accurate as possible with
26
  respect to the registers and the behavior. There are no known
27
  limitations at this time.
28
*/
29
 
30
#include <stdlib.h>
31
#include <stdio.h>
32
#include <string.h>
33
#include <inttypes.h>
34
 
35
#include "debug_unit.h"
36
#include "sim-config.h"
37
#include "except.h"
38
#include "arch.h"
39
#include "abstract.h"
40
#include "parse.h"
41
#include "trace.h"
42
#include "sprs.h"
43
#include "../gdb.h"
44
#include "../cpu/or1k/except.h"
45
#include "opcode/or32.h"
46
 
47
DebugUnit debug_unit;
48
DevelopmentInterface development;
49
 
50
typedef enum {
51
  false = 0,
52
  true = 1,
53
} Boolean;
54
static void ExecuteInducedInstruction(unsigned long);
55
 
56
/* External STALL signal to debug interface */
57
int cpu_stalled = false;
58
int in_reset = false;
59
 
60
/* An induced instruction has been written to the DIR register */
61
static Boolean induced = false;
62
static unsigned long induced_insn;
63
 
64
/* A flag to indicate that we must perform an ic mmu cycle */
65
static Boolean lookup_physical_address = false;
66
 
67
/* Variables for implementing ExecuteInducedInstruction */
68
extern unsigned long pc;
69
extern unsigned long pcnext;
70
extern unsigned long  pcdelay;
71
extern unsigned long pc_phy;
72
extern int delay_insn;
73
static void GetIQueueEntry(struct iqueue_entry*);
74
 
75
static int CalculateWatchpoints(void);
76
 
77
static  int watchpoint[10];
78
 
79
/* This function returns true if an induced instruction has
80
   been inserted into the instruction stream. It will remove
81
   that instruction and return the result. This function is
82
   called from the fetch() routine. */
83
int OverrideFetch(unsigned long* insn)
84
{
85
  int valid = induced;
86
  induced = false;
87
 
88
  if(valid)
89
    *insn = induced_insn;
90
  return valid;
91
}
92
 
93
void InduceImmediateInstruction(unsigned long insn)
94
{
95
  induced = true;
96
  induced_insn = insn;
97
 
98
  if(in_reset)
99
    return;
100
 
101
  if(cpu_stalled)
102
    {
103
      ExecuteInducedInstruction(insn);
104
      induced_insn = 0;
105
      induced = false;
106
    }
107
}
108
 
109
void SetCPUStallState(int state)
110
{
111
  if(debug_unit.DMR1.DXFW) /* If debugger disabled */
112
    state = false;
113
 
114
  if(state == cpu_stalled)
115
    return;
116
 
117
  if(state && induced)
118
    {
119
      ExecuteInducedInstruction(induced_insn);
120
      induced_insn = 0;
121
      induced = false;
122
    }
123
 
124
  cpu_stalled = state;
125
}
126
 
127
void ResetDebugUnit()
128
{
129
  memset(&debug_unit,'\0',sizeof(DebugUnit));
130
  cpu_stalled = 0;
131
}
132
 
133
#ifdef DEBUGMOD_OFF
134
#define CheckDebugUnit(x,y) 0
135
#else
136
inline int CheckDebugUnit(DebugUnitAction action,unsigned long udata)
137
{
138
  int i;
139
  DCR_CT_Settings condition = DCR_CT_Disabled;
140
  long data = (long)udata;
141
  int match;
142
 
143 269 markom
  if(DEBUG_ENABLED || in_reset)
144 221 markom
    return 0;
145
 
146
  /* If we're single stepping, always stop */
147
  if(debug_unit.DMR1.ST && action == DebugInstructionFetch)
148
    return 1;
149
 
150
  switch(action)
151
    {
152
    case DebugInstructionFetch:   condition = DCR_CT_InsnAddress;   break;
153
    case DebugLoadAddress:        condition = DCR_CT_LoadAddress;   break;
154
    case DebugStoreAddress:       condition = DCR_CT_StoreAddress;  break;
155
    case DebugLoadData:           condition = DCR_CT_LoadData;      break;
156
    case DebugStoreData:          condition = DCR_CT_StoreData;     break;
157
    }
158
 
159
  for(i=0;i<8;i++)
160
    {
161
      if(debug_unit.DCR[i].DP == DCR_DP_Absent)
162
        continue;
163
 
164
      if(debug_unit.DCR[i].CT == condition)
165
        {
166
          if(debug_unit.DCR[i].SC == DCR_SC_Signed)
167
            {
168
              switch(debug_unit.DCR[i].CC)
169
                {
170
                case DCR_CC_Equal:        match = data == (int)debug_unit.DVR[i];   break;
171
                case DCR_CC_LessThan:     match = data < (int)debug_unit.DVR[i];    break;
172
                case DCR_CC_LessEqual:    match = data <= (int)debug_unit.DVR[i];   break;
173
                case DCR_CC_GreaterThan:  match = data > (int)debug_unit.DVR[i];    break;
174
                case DCR_CC_GreaterEqual: match = data >= (int)debug_unit.DVR[i];   break;
175
                case DCR_CC_NotEqual:     match = data != (int)debug_unit.DVR[i];   break;
176
                default:                  match = 0;                                break;
177
                }
178
            }
179
          else
180
            {
181
              switch(debug_unit.DCR[i].CC)
182
                {
183
                case DCR_CC_Equal:        match = udata == debug_unit.DVR[i];   break;
184
                case DCR_CC_LessThan:     match = udata < debug_unit.DVR[i];    break;
185
                case DCR_CC_LessEqual:    match = udata <= debug_unit.DVR[i];   break;
186
                case DCR_CC_GreaterThan:  match = udata > debug_unit.DVR[i];    break;
187
                case DCR_CC_GreaterEqual: match = udata >= debug_unit.DVR[i];   break;
188
                case DCR_CC_NotEqual:     match = udata != debug_unit.DVR[i];   break;
189
                default:                  match = 0;                            break;
190
                }
191
            }
192
        }
193
      match <<= i;
194
      debug_unit.DCR_hit &= ~match;      /* Clear DCR compare if it has changed */
195
      debug_unit.DCR_hit |= match;  /* Save the state of each DCR compare */
196
    }
197
 
198
  return CalculateWatchpoints();
199
}
200
#endif
201
 
202
static int CalculateWatchpoints()
203
{
204
  int spec[11];
205
  int breakpoint = 0;
206
  int i,bit;
207
 
208
  spec[0] = debug_unit.DMR1.CW0;
209
  spec[1] = debug_unit.DMR1.CW1;
210
  spec[2] = debug_unit.DMR1.CW2;
211
  spec[3] = debug_unit.DMR1.CW3;
212
  spec[4] = debug_unit.DMR1.CW4;
213
  spec[5] = debug_unit.DMR1.CW5;
214
  spec[6] = debug_unit.DMR1.CW6;
215
  spec[7] = debug_unit.DMR1.CW7;
216
  spec[8] = debug_unit.DMR1.CW8;
217
  spec[9] = debug_unit.DMR1.CW9;
218
  spec[10] = debug_unit.DMR1.CW10;
219
 
220
  for(i=0,bit=1;i<11;i++,bit<<=1)
221
    {
222
      int chain1,chain2;
223
      int match = 0;
224
 
225
      switch(i)
226
        {
227
        case 0:
228
          chain1 = chain2 = debug_unit.DCR_hit & 0x01;
229
          break;
230
        case 8:
231
          chain1 = debug_unit.DWCR[0].COUNT == debug_unit.DWCR[0].MATCH;
232
          chain2 = debug_unit.watchpoint & (1 << 7);
233
          break;
234
        case 9:
235
          chain1 = debug_unit.DWCR[1].COUNT == debug_unit.DWCR[1].MATCH;
236
          chain2 = debug_unit.watchpoint & (1 << 8);
237
          break;
238
        case 10:
239
          chain1 = debug_unit.DCR_hit & 0x100; /* External hit */
240
          chain2 = debug_unit.watchpoint & (1 << 9);
241
          break;
242
        default:
243
          chain1 = debug_unit.DCR_hit & bit;
244
          chain2 = debug_unit.watchpoint & (bit >> 1);
245
          break;
246
        }
247
 
248
      switch(spec[i])
249
        {
250
        case 0:  match = chain1;           break;
251
        case 1: match = chain1 && chain2; break;
252
        case 2: match = chain1 || chain2; break;
253
        default:
254
          break;
255
        }
256
 
257
      if(match & !(debug_unit.watchpoint & bit))
258
        {
259
          int counter = (debug_unit.DMR2.AWPC & bit) ? 1 : 0;
260
          int enabled = counter ? debug_unit.DMR2.WCE1 : debug_unit.DMR2.WCE0;
261
 
262
          if(enabled)
263
            debug_unit.DWCR[counter].COUNT++;
264
 
265
          if(debug_unit.DMR2.WGB & bit)
266
            breakpoint = 1;
267
        }
268
 
269
      debug_unit.watchpoint &= ~bit;
270
      debug_unit.watchpoint |= bit;
271
    }
272
 
273
  return breakpoint;
274
}
275
 
276
static void GetIQueueEntry(struct iqueue_entry* iq_entry)
277
{
278
  iq_entry->insn = induced_insn;
279
  iq_entry->insn_index = insn_decode(induced_insn);
280
  iq_entry->insn_addr = pc_phy;
281
  iq_entry->op[0] = 0;
282
  iq_entry->op[MAX_OPERANDS] = OPTYPE_LAST;
283
}
284
 
285
static void ExecuteInducedInstruction(unsigned long insn)
286
{
287
  struct iqueue_entry iq_entry;
288
  unsigned long pc_saved = pc;
289
  unsigned long pcnext_saved = pcnext;
290
  unsigned long pcdelay_saved = pcdelay;
291
  unsigned long pc_phy_saved = pc_phy;
292
 
293
  GetIQueueEntry(&iq_entry);
294
  decode_execute(&iq_entry);
295
 
296
  pc = pc_saved;
297
  pcnext = pcnext_saved;
298
  pcdelay = pcdelay_saved;
299
  pc_phy = pc_phy_saved;
300
}
301
 
302
static DebugScanChainIDs current_scan_chain = JTAG_CHAIN_GLOBAL;
303
 
304
int DebugGetRegister(unsigned int address,int32_t* data)
305
{
306
  int err;
307
#ifdef DEBUG_JTAG
308
  printf("Debug get register %x\n",address);
309
  fflush(stdout);
310
#endif
311
  switch(current_scan_chain)
312
    {
313
    case JTAG_CHAIN_DEBUG_UNIT:
314
      err = GetDebugUnitRegister(address,data);
315
      break;
316
    case JTAG_CHAIN_TRACE:
317
      *data = 0;  /* Scan chain not yet implemented */
318
      err = 0;
319
      break;
320
    case JTAG_CHAIN_DEVELOPMENT:
321
      err = GetDevelopmentInterfaceRegister(address,data);
322
      break;
323
    case JTAG_CHAIN_WISHBONE:
324
      err = GetWishboneMemory(address,data);
325
      break;
326
    }
327
#ifdef DEBUG_JTAG
328
  printf("!get reg %x\n", *data);
329
  fflush(stdout);
330
#endif
331
  return err;
332
}
333
 
334
int DebugSetRegister(unsigned int address,int32_t data)
335
{
336
  int err;
337
#ifdef DEBUG_JTAG
338
  printf("Debug set register %x <- %x\n",address, data);
339
  fflush(stdout);
340
#endif
341
  switch(current_scan_chain)
342
    {
343
    case JTAG_CHAIN_DEBUG_UNIT:
344
      err = SetDebugUnitRegister(address,data);
345
      break;
346
    case JTAG_CHAIN_TRACE:
347
      err = JTAG_PROXY_ACCESS_EXCEPTION;
348
      break;
349
    case JTAG_CHAIN_DEVELOPMENT:
350
      err = SetDevelopmentInterfaceRegister(address,data);
351
      break;
352
    case JTAG_CHAIN_WISHBONE:
353
      err = SetWishboneMemory(address,data);
354
      break;
355
    }
356
#ifdef DEBUG_JTAG
357
  printf("!set reg\n");
358
  fflush(stdout);
359
#endif
360
  return err;
361
}
362
 
363
int DebugSetChain(int chain)
364
{
365
#ifdef DEBUG_JTAG
366
  printf("Debug set chain %x\n",chain);
367
  fflush(stdout);
368
#endif
369
  switch(chain)
370
    {
371
    case JTAG_CHAIN_DEBUG_UNIT:
372
    case JTAG_CHAIN_TRACE:
373
    case JTAG_CHAIN_DEVELOPMENT:
374
    case JTAG_CHAIN_WISHBONE:
375
      current_scan_chain = chain;
376
      break;
377
    default: /* All other chains not implemented */
378
      return JTAG_PROXY_INVALID_CHAIN;
379
    }
380
 
381
#ifdef DEBUG_JTAG
382
  printf("!set chain\n");
383
  fflush(stdout);
384
#endif
385
  return 0;
386
}
387
 
388
/* Nearly all compilers today store these bit fields as a packed structure
389
   in network byte order (Big Endian). If you happen to be unlucky enough
390
   to be working in a non standard environment, you may need to rewrite
391
   this routine or the SET_REG32 macro. */
392
int SetDevelopmentInterfaceRegister(unsigned int address,uint32_t data)
393
{
394
  int err = 0;
395
  uint32_t value = data;
396
  int old_value;
397
  char *t_ptr = (char*)&development.RISCOP;
398
 
399
  switch(address)
400
    {
401
    case DEVELOPINT_MODER:
402
      SET_REG32(development.MODER,value);
403
      break;
404
    case DEVELOPINT_TSEL:
405
      SET_REG32(development.TSEL,value);
406
      break;
407
    case DEVELOPINT_QSEL:
408
      SET_REG32(development.QSEL,value);
409
      break;
410
    case DEVELOPINT_SSEL:
411
      SET_REG32(development.SSEL,value);
412
      break;
413
    case DEVELOPINT_RISCOP:
414
      old_value = development.RISCOP.RESET;
415
      SET_REG32(development.RISCOP,value);
416
 
417
      in_reset = development.RISCOP.RESET;
418
 
419
      /* Reset the cpu on the negative edge of RESET */
420
      if(old_value && !development.RISCOP.RESET)
421
        {
422
          uart_reset();
423
          tick_reset();
424
          pm_reset();
425
          pic_reset();
426
          reset(); /* Old or new mode */
427
        }
428
 
429
      SetCPUStallState(development.RISCOP.RISCSTALL);
430
      break;
431
    case DEVELOPINT_RECWP0:
432
    case DEVELOPINT_RECWP1:
433
    case DEVELOPINT_RECWP2:
434
    case DEVELOPINT_RECWP3:
435
    case DEVELOPINT_RECWP4:
436
    case DEVELOPINT_RECWP5:
437
    case DEVELOPINT_RECWP6:
438
    case DEVELOPINT_RECWP7:
439
    case DEVELOPINT_RECWP8:
440
    case DEVELOPINT_RECWP9:
441
    case DEVELOPINT_RECWP10:
442
      SET_REG32(development.RECWP[address-DEVELOPINT_RECWP0],value);
443
      break;
444
    case DEVELOPINT_RECBP0:
445
      SET_REG32(development.RECBP[0],value);
446
      break;
447
    default:
448
      err = JTAG_PROXY_INVALID_ADDRESS;
449
      break;
450
    }
451
  return err;
452
}
453
 
454
int GetDevelopmentInterfaceRegister(unsigned int address,uint32_t *data)
455
{
456
  int err = 0;
457
  uint32_t value = 0;
458
 
459
  switch(address)
460
    {
461
    case DEVELOPINT_MODER:    GET_REG32(development.MODER,value);      break;
462
    case DEVELOPINT_TSEL:     GET_REG32(development.TSEL,value);       break;
463
    case DEVELOPINT_QSEL:     GET_REG32(development.QSEL,value);       break;
464
    case DEVELOPINT_SSEL:     GET_REG32(development.SSEL,value);       break;
465
    case DEVELOPINT_RISCOP:   GET_REG32(development.RISCOP,value);     break;
466
    case DEVELOPINT_RECWP0:
467
    case DEVELOPINT_RECWP1:
468
    case DEVELOPINT_RECWP2:
469
    case DEVELOPINT_RECWP3:
470
    case DEVELOPINT_RECWP4:
471
    case DEVELOPINT_RECWP5:
472
    case DEVELOPINT_RECWP6:
473
    case DEVELOPINT_RECWP7:
474
    case DEVELOPINT_RECWP8:
475
    case DEVELOPINT_RECWP9:
476
    case DEVELOPINT_RECWP10:  GET_REG32(development.RECWP[address-DEVELOPINT_RECWP0],value); break;
477
    case DEVELOPINT_RECBP0:   GET_REG32(development.RECBP[0],value);   break;
478
    default:                  err = JTAG_PROXY_INVALID_ADDRESS;        break;
479
    }
480
 
481
  *data = value;
482
  return err;
483
}
484
 
485
/* Nearly all compilers today store these bit fields as a packed structure
486
   in network byte order (Big Endian). If you happen to be unlucky enough
487
   to be working in a non standard environment, you may need to rewrite
488
   this routine or the SET_REG32 macro. */
489
int SetDebugUnitRegister(unsigned int address,uint32_t data)
490
{
491
  int err = 0;
492
  uint32_t value = data;
493
  int old_value;
494
  int group = address >> 11;
495
 
496
  address &= 0x07FF;
497
 
498
  /*****************************************************/
499
  /*  TEMPORARY!!!!                                    */
500
  /*****************************************************/
501
  if(group == 6)
502
    address -= 32;
503
 
504
  if(group == 6)
505
    {
506
      switch(address)
507
        {
508
        case DEBUGINT_DVR0:
509
        case DEBUGINT_DVR1:
510
        case DEBUGINT_DVR2:
511
        case DEBUGINT_DVR3:
512
        case DEBUGINT_DVR4:
513
        case DEBUGINT_DVR5:
514
        case DEBUGINT_DVR6:
515
        case DEBUGINT_DVR7:
516
          printf("DVR %d set to 0x%08x\n",address-DEBUGINT_DVR0,value);
517
          SET_REG32(debug_unit.DVR[address-DEBUGINT_DVR0],value);
518
          break;
519
        case DEBUGINT_DCR0:
520
        case DEBUGINT_DCR1:
521
        case DEBUGINT_DCR2:
522
        case DEBUGINT_DCR3:
523
        case DEBUGINT_DCR4:
524
        case DEBUGINT_DCR5:
525
        case DEBUGINT_DCR6:
526
        case DEBUGINT_DCR7:
527
          printf("DCR %d set to 0x%08x\n",address-DEBUGINT_DCR0,value);
528
          SET_REG32(debug_unit.DCR[address-DEBUGINT_DCR0],value);
529
          break;
530
        case DEBUGINT_DMR1:
531
          SET_REG32(debug_unit.DMR1,value);
532
          break;
533
        case DEBUGINT_DMR2:
534
          SET_REG32(debug_unit.DMR2,value);
535
          break;
536
        case DEBUGINT_DWCR0:
537
          SET_REG32(debug_unit.DWCR[0],value);
538
          break;
539
        case DEBUGINT_DWCR1:
540
          SET_REG32(debug_unit.DWCR[1],value);
541
          break;
542
        case DEBUGINT_DSR:
543
          SET_REG32(debug_unit.DSR,value);
544
          break;
545
        case DEBUGINT_DRR:
546
          SET_REG32(debug_unit.DRR,value);
547
          break;
548
        case DEBUGINT_DIR:
549
          InduceImmediateInstruction(value);
550
          break;
551
        default:
552
          err = JTAG_PROXY_INVALID_ADDRESS;
553
          break;
554
        }
555
    }
556
  else if(group == 0)
557
    {
558
      extern unsigned long reg[32];
559
 
560
      if(!address)
561
        err = JTAG_PROXY_ACCESS_EXCEPTION;
562
      else if(address < 32)
563
        {
564
          /* Assume that a write to the PC implies
565
             that the debugging software has recognized
566
             the exception and wants to do something
567
             else instead. */
568
 
569 378 markom
          if(address == SPR_NPC)
570 221 markom
            {
571
              ClearPendingException();
572
              ClearPreparedPCState();
573
            }
574
          mtspr(address,data);
575
        }
576
      else if(address >= 0x0400 && address < 0x0420)
577
        reg[address - 0x0400] = data;
578
      else if(address < 0x0600 || address >= 0x0620)
579
        err = JTAG_PROXY_INVALID_ADDRESS;
580
    }
581
  else
582
    err = JTAG_PROXY_INVALID_ADDRESS;
583
 
584
  return err;
585
}
586
 
587
int GetDebugUnitRegister(unsigned int address,uint32_t *data)
588
{
589
  int err = 0;
590
  uint32_t value = 0;
591
  int group = address >> 11;
592
 
593
  address &= 0x07FF;
594
 
595
  /*****************************************************/
596
  /*  TEMPORARY!!!!                                    */
597
  /*****************************************************/
598
  if(group == 6)
599
    address -= 32;
600
 
601
  if(group == 6)
602
    {
603
      switch(address)
604
        {
605
        case DEBUGINT_DVR0:
606
        case DEBUGINT_DVR1:
607
        case DEBUGINT_DVR2:
608
        case DEBUGINT_DVR3:
609
        case DEBUGINT_DVR4:
610
        case DEBUGINT_DVR5:
611
        case DEBUGINT_DVR6:
612
        case DEBUGINT_DVR7:    GET_REG32(debug_unit.DVR[address-DEBUGINT_DVR0],value);  break;
613
        case DEBUGINT_DCR0:
614
        case DEBUGINT_DCR1:
615
        case DEBUGINT_DCR2:
616
        case DEBUGINT_DCR3:
617
        case DEBUGINT_DCR4:
618
        case DEBUGINT_DCR5:
619
        case DEBUGINT_DCR6:
620
        case DEBUGINT_DCR7:    GET_REG32(debug_unit.DCR[address-DEBUGINT_DCR0],value);  break;
621
        case DEBUGINT_DMR1:    GET_REG32(debug_unit.DMR1,value);         break;
622
        case DEBUGINT_DMR2:    GET_REG32(debug_unit.DMR2,value);         break;
623
        case DEBUGINT_DWCR0:   GET_REG32(debug_unit.DWCR[0],value);        break;
624
        case DEBUGINT_DWCR1:   GET_REG32(debug_unit.DWCR[1],value);        break;
625
        case DEBUGINT_DSR:     GET_REG32(debug_unit.DSR,value);          break;
626
        case DEBUGINT_DRR:     GET_REG32(debug_unit.DRR,value);          break;
627
        case DEBUGINT_DIR:     err = JTAG_PROXY_ACCESS_EXCEPTION;        break;
628
        default:               err = JTAG_PROXY_INVALID_ADDRESS;         break;
629
        }
630
    }
631
  else if(group == 0)
632
    {
633
      extern unsigned long reg[32];
634
 
635
      if(address < 32)
636
        value = mfspr(address);
637
      else if(address >= 0x0400 && address < 0x0420)
638
        value = reg[address - 0x400];
639
      else if(address >= 0x0600 && address < 0x0620)
640
        value = 0;
641
      else
642
        err = JTAG_PROXY_INVALID_ADDRESS;
643
    }
644
  else
645
    err = JTAG_PROXY_INVALID_ADDRESS;
646
 
647
  *data = value;
648
  return err;
649
}
650
 
651
/* Nearly all compilers today store these bit fields as a packed structure
652
   in network byte order (Big Endian). If you happen to be unlucky enough
653
   to be working in a non standard environment, you may need to rewrite
654
   this routine or the SET_REG32 macro. */
655
int SetWishboneMemory(unsigned int address,uint32_t data)
656
{
657
  int err = 0;
658
  uint32_t value = data;
659
  int old_value;
660
  int group = address >> 11;
661
 
662
  address <<= 2;
663
 
664
  if(!verify_memoryarea(address))
665
          err = JTAG_PROXY_INVALID_ADDRESS;
666
  else
667
        {
668
          unsigned char t_data[4];
669
          int *tmp = (int*)t_data;
670
          extern char null_str[1];  /* From cpu/common/parse.c */
671
          int i;
672
 
673
          *tmp = htonl(data); /* We have already converted to host order */
674
 
675
          setsim_mem8(address++, t_data[0]); /* Back to network byte order */
676
          setsim_mem8(address++, t_data[1]);
677
          setsim_mem8(address++, t_data[2]);
678
          setsim_mem8(address++, t_data[3]);
679
        }
680
  return err;
681
}
682
 
683
int GetWishboneMemory(unsigned int address,uint32_t *data)
684
{
685
  int err = 0;
686
  uint32_t value = 0;
687
  int group = address >> 11;
688
 
689
  address <<= 2;
690
 
691
  if(!verify_memoryarea(address))
692
          err = JTAG_PROXY_INVALID_ADDRESS;
693
  else
694
        {
695
          unsigned char t_data[4];
696
          int *tmp = (int*)t_data;
697
          int bp;
698
 
699
          t_data[0] = evalsim_mem8(address++);
700
          t_data[1] = evalsim_mem8(address++);
701
          t_data[2] = evalsim_mem8(address++);
702
          t_data[3] = evalsim_mem8(address++); /* Already in network byte order */
703
 
704
          *data = ntohl(*tmp);  /* But we assume it is in host order later */
705
        }
706
  return err;
707
}
708
 
709
/* DebugCheckException returns 1 if the exception should be ignored.
710
   Currently, this is true only if the exception is a breakpoint
711
   exception and debug_unit.DMR1.ST is set. Sorry, this is a quick
712
   hack to disable processing of breakpoint exceptions on single
713
   stepping. Just one of those historical accidents. Feel free
714
   to rewrite the behavior. */
715
int DebugCheckException(int exception)
716
{
717
  int result = 0;
718
 
719
  switch(exception)
720
    {
721
    case EXCEPT_RESET:     result = debug_unit.DRR.RSTE   = debug_unit.DSR.RSTE;   break;
722
    case EXCEPT_BUSERR:    result = debug_unit.DRR.BUSEE  = debug_unit.DSR.BUSEE;  break;
723
    case EXCEPT_DPF:       result = debug_unit.DRR.DPFE   = debug_unit.DSR.DPFE;   break;
724
    case EXCEPT_IPF:       result = debug_unit.DRR.IPFE   = debug_unit.DSR.IPFE;   break;
725
    case EXCEPT_LPINT:     result = debug_unit.DRR.LPINTE = debug_unit.DSR.LPINTE; break;
726
    case EXCEPT_ALIGN:     result = debug_unit.DRR.AE     = debug_unit.DSR.AE;     break;
727
    case EXCEPT_ILLEGAL:   result = debug_unit.DRR.IIE    = debug_unit.DSR.IIE;    break;
728
    case EXCEPT_HPINT:     result = debug_unit.DRR.HPINTE = debug_unit.DSR.HPINTE; break;
729
    case EXCEPT_DTLBMISS:  result = debug_unit.DRR.DME    = debug_unit.DSR.DME;    break;
730
    case EXCEPT_ITLBMISS:  result = debug_unit.DRR.IME    = debug_unit.DSR.IME;    break;
731
    case EXCEPT_RANGE:     result = debug_unit.DRR.RE     = debug_unit.DSR.RE;     break;
732
    case EXCEPT_SYSCALL:   result = debug_unit.DRR.SCE    = debug_unit.DSR.SCE;    break;
733
    case EXCEPT_BREAK:     result = debug_unit.DRR.BE     = debug_unit.DSR.BE;     break;
734
    case EXCEPT_TRAP:      result = debug_unit.DRR.TE     = debug_unit.DSR.TE;     break;
735
    default:
736
      break;
737
    }
738
 
739
  if(result)
740
    SetCPUStallState(true);
741
 
742
  return (debug_unit.DMR1.ST && exception == EXCEPT_BREAK);
743
}

powered by: WebSVN 2.1.0

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