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

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [gnu-stable/] [gdb-7.2/] [sim/] [common/] [sim-core.c] - Blame information for rev 841

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 330 jeremybenn
/* The common simulator framework for GDB, the GNU Debugger.
2
 
3
   Copyright 2002, 2007, 2008, 2009, 2010 Free Software Foundation, Inc.
4
 
5
   Contributed by Andrew Cagney and Red Hat.
6
 
7
   This file is part of GDB.
8
 
9
   This program is free software; you can redistribute it and/or modify
10
   it under the terms of the GNU General Public License as published by
11
   the Free Software Foundation; either version 3 of the License, or
12
   (at your option) any later version.
13
 
14
   This program is distributed in the hope that it will be useful,
15
   but WITHOUT ANY WARRANTY; without even the implied warranty of
16
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17
   GNU General Public License for more details.
18
 
19
   You should have received a copy of the GNU General Public License
20
   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
21
 
22
 
23
#ifndef SIM_CORE_C
24
#define SIM_CORE_C
25
 
26
#include "sim-main.h"
27
#include "sim-assert.h"
28
 
29
#if (WITH_HW)
30
#include "sim-hw.h"
31
#endif
32
 
33
/* "core" module install handler.
34
 
35
   This is called via sim_module_install to install the "core"
36
   subsystem into the simulator.  */
37
 
38
#if EXTERN_SIM_CORE_P
39
static MODULE_INIT_FN sim_core_init;
40
static MODULE_UNINSTALL_FN sim_core_uninstall;
41
#endif
42
 
43
#if EXTERN_SIM_CORE_P
44
SIM_RC
45
sim_core_install (SIM_DESC sd)
46
{
47
  SIM_ASSERT (STATE_MAGIC (sd) == SIM_MAGIC_NUMBER);
48
 
49
  /* establish the other handlers */
50
  sim_module_add_uninstall_fn (sd, sim_core_uninstall);
51
  sim_module_add_init_fn (sd, sim_core_init);
52
 
53
  /* establish any initial data structures - none */
54
  return SIM_RC_OK;
55
}
56
#endif
57
 
58
 
59
/* Uninstall the "core" subsystem from the simulator.  */
60
 
61
#if EXTERN_SIM_CORE_P
62
static void
63
sim_core_uninstall (SIM_DESC sd)
64
{
65
  sim_core *core = STATE_CORE(sd);
66
  unsigned map;
67
  /* blow away any mappings */
68
  for (map = 0; map < nr_maps; map++) {
69
    sim_core_mapping *curr = core->common.map[map].first;
70
    while (curr != NULL) {
71
      sim_core_mapping *tbd = curr;
72
      curr = curr->next;
73
      if (tbd->free_buffer != NULL) {
74
        SIM_ASSERT(tbd->buffer != NULL);
75
        zfree(tbd->free_buffer);
76
      }
77
      zfree(tbd);
78
    }
79
    core->common.map[map].first = NULL;
80
  }
81
}
82
#endif
83
 
84
 
85
#if EXTERN_SIM_CORE_P
86
static SIM_RC
87
sim_core_init (SIM_DESC sd)
88
{
89
  /* Nothing to do */
90
  return SIM_RC_OK;
91
}
92
#endif
93
 
94
 
95
 
96
#ifndef SIM_CORE_SIGNAL
97
#define SIM_CORE_SIGNAL(SD,CPU,CIA,MAP,NR_BYTES,ADDR,TRANSFER,ERROR) \
98
sim_core_signal ((SD), (CPU), (CIA), (MAP), (NR_BYTES), (ADDR), (TRANSFER), (ERROR))
99
#endif
100
 
101
#if EXTERN_SIM_CORE_P
102
void
103
sim_core_signal (SIM_DESC sd,
104
                 sim_cpu *cpu,
105
                 sim_cia cia,
106
                 unsigned map,
107
                 int nr_bytes,
108
                 address_word addr,
109
                 transfer_type transfer,
110
                 sim_core_signals sig)
111
{
112
  const char *copy = (transfer == read_transfer ? "read" : "write");
113
  address_word ip = CIA_ADDR (cia);
114
  switch (sig)
115
    {
116
    case sim_core_unmapped_signal:
117
      sim_io_eprintf (sd, "core: %d byte %s to unmapped address 0x%lx at 0x%lx\n",
118
                      nr_bytes, copy, (unsigned long) addr, (unsigned long) ip);
119
      sim_engine_halt (sd, cpu, NULL, cia, sim_stopped, SIM_SIGSEGV);
120
      break;
121
    case sim_core_unaligned_signal:
122
      sim_io_eprintf (sd, "core: %d byte misaligned %s to address 0x%lx at 0x%lx\n",
123
                      nr_bytes, copy, (unsigned long) addr, (unsigned long) ip);
124
      sim_engine_halt (sd, cpu, NULL, cia, sim_stopped, SIM_SIGBUS);
125
      break;
126
    default:
127
      sim_engine_abort (sd, cpu, cia,
128
                        "sim_core_signal - internal error - bad switch");
129
    }
130
}
131
#endif
132
 
133
 
134
#if EXTERN_SIM_CORE_P
135
static sim_core_mapping *
136
new_sim_core_mapping (SIM_DESC sd,
137
                      int level,
138
                      int space,
139
                      address_word addr,
140
                      address_word nr_bytes,
141
                      unsigned modulo,
142
#if WITH_HW
143
                      struct hw *device,
144
#else
145
                      device *device,
146
#endif
147
                      void *buffer,
148
                      void *free_buffer)
149
{
150
  sim_core_mapping *new_mapping = ZALLOC(sim_core_mapping);
151
  /* common */
152
  new_mapping->level = level;
153
  new_mapping->space = space;
154
  new_mapping->base = addr;
155
  new_mapping->nr_bytes = nr_bytes;
156
  new_mapping->bound = addr + (nr_bytes - 1);
157
  if (modulo == 0)
158
    new_mapping->mask = (unsigned) 0 - 1;
159
  else
160
    new_mapping->mask = modulo - 1;
161
  new_mapping->buffer = buffer;
162
  new_mapping->free_buffer = free_buffer;
163
  new_mapping->device = device;
164
  return new_mapping;
165
}
166
#endif
167
 
168
 
169
#if EXTERN_SIM_CORE_P
170
static void
171
sim_core_map_attach (SIM_DESC sd,
172
                     sim_core_map *access_map,
173
                     int level,
174
                     int space,
175
                     address_word addr,
176
                     address_word nr_bytes,
177
                     unsigned modulo,
178
#if WITH_HW
179
                     struct hw *client, /*callback/default*/
180
#else
181
                     device *client, /*callback/default*/
182
#endif
183
                     void *buffer, /*raw_memory*/
184
                     void *free_buffer) /*raw_memory*/
185
{
186
  /* find the insertion point for this additional mapping and then
187
     insert */
188
  sim_core_mapping *next_mapping;
189
  sim_core_mapping **last_mapping;
190
 
191
  SIM_ASSERT ((client == NULL) != (buffer == NULL));
192
  SIM_ASSERT ((client == NULL) >= (free_buffer != NULL));
193
 
194
  /* actually do occasionally get a zero size map */
195
  if (nr_bytes == 0)
196
    {
197
#if (WITH_DEVICES)
198
      device_error(client, "called on sim_core_map_attach with size zero");
199
#endif
200
#if (WITH_HW)
201
      sim_hw_abort (sd, client, "called on sim_core_map_attach with size zero");
202
#endif
203
      sim_io_error (sd, "called on sim_core_map_attach with size zero");
204
    }
205
 
206
  /* find the insertion point (between last/next) */
207
  next_mapping = access_map->first;
208
  last_mapping = &access_map->first;
209
  while(next_mapping != NULL
210
        && (next_mapping->level < level
211
            || (next_mapping->level == level
212
                && next_mapping->bound < addr)))
213
    {
214
      /* provided levels are the same */
215
      /* assert: next_mapping->base > all bases before next_mapping */
216
      /* assert: next_mapping->bound >= all bounds before next_mapping */
217
      last_mapping = &next_mapping->next;
218
      next_mapping = next_mapping->next;
219
    }
220
 
221
  /* check insertion point correct */
222
  SIM_ASSERT (next_mapping == NULL || next_mapping->level >= level);
223
  if (next_mapping != NULL && next_mapping->level == level
224
      && next_mapping->base < (addr + (nr_bytes - 1)))
225
    {
226
#if (WITH_DEVICES)
227
      device_error (client, "memory map %d:0x%lx..0x%lx (%ld bytes) overlaps %d:0x%lx..0x%lx (%ld bytes)",
228
                    space,
229
                    (long) addr,
230
                    (long) (addr + nr_bytes - 1),
231
                    (long) nr_bytes,
232
                    next_mapping->space,
233
                    (long) next_mapping->base,
234
                    (long) next_mapping->bound,
235
                    (long) next_mapping->nr_bytes);
236
#endif
237
#if WITH_HW
238
      sim_hw_abort (sd, client, "memory map %d:0x%lx..0x%lx (%ld bytes) overlaps %d:0x%lx..0x%lx (%ld bytes)",
239
                    space,
240
                    (long) addr,
241
                    (long) (addr + (nr_bytes - 1)),
242
                    (long) nr_bytes,
243
                    next_mapping->space,
244
                    (long) next_mapping->base,
245
                    (long) next_mapping->bound,
246
                    (long) next_mapping->nr_bytes);
247
#endif
248
      sim_io_error (sd, "memory map %d:0x%lx..0x%lx (%ld bytes) overlaps %d:0x%lx..0x%lx (%ld bytes)",
249
                    space,
250
                    (long) addr,
251
                    (long) (addr + (nr_bytes - 1)),
252
                    (long) nr_bytes,
253
                    next_mapping->space,
254
                    (long) next_mapping->base,
255
                    (long) next_mapping->bound,
256
                    (long) next_mapping->nr_bytes);
257
  }
258
 
259
  /* create/insert the new mapping */
260
  *last_mapping = new_sim_core_mapping(sd,
261
                                       level,
262
                                       space, addr, nr_bytes, modulo,
263
                                       client, buffer, free_buffer);
264
  (*last_mapping)->next = next_mapping;
265
}
266
#endif
267
 
268
 
269
/* Attach memory or a memory mapped device to the simulator.
270
   See sim-core.h for a full description.  */
271
 
272
#if EXTERN_SIM_CORE_P
273
void
274
sim_core_attach (SIM_DESC sd,
275
                 sim_cpu *cpu,
276
                 int level,
277
                 unsigned mapmask,
278
                 int space,
279
                 address_word addr,
280
                 address_word nr_bytes,
281
                 unsigned modulo,
282
#if WITH_HW
283
                 struct hw *client,
284
#else
285
                 device *client,
286
#endif
287
                 void *optional_buffer)
288
{
289
  sim_core *memory = STATE_CORE(sd);
290
  unsigned map;
291
  void *buffer;
292
  void *free_buffer;
293
 
294
  /* check for for attempt to use unimplemented per-processor core map */
295
  if (cpu != NULL)
296
    sim_io_error (sd, "sim_core_map_attach - processor specific memory map not yet supported");
297
 
298
  /* verify modulo memory */
299
  if (!WITH_MODULO_MEMORY && modulo != 0)
300
    {
301
#if (WITH_DEVICES)
302
      device_error (client, "sim_core_attach - internal error - modulo memory disabled");
303
#endif
304
#if (WITH_HW)
305
      sim_hw_abort (sd, client, "sim_core_attach - internal error - modulo memory disabled");
306
#endif
307
      sim_io_error (sd, "sim_core_attach - internal error - modulo memory disabled");
308
    }
309
  if (client != NULL && modulo != 0)
310
    {
311
#if (WITH_DEVICES)
312
      device_error (client, "sim_core_attach - internal error - modulo and callback memory conflict");
313
#endif
314
#if (WITH_HW)
315
      sim_hw_abort (sd, client, "sim_core_attach - internal error - modulo and callback memory conflict");
316
#endif
317
      sim_io_error (sd, "sim_core_attach - internal error - modulo and callback memory conflict");
318
    }
319
  if (modulo != 0)
320
    {
321
      unsigned mask = modulo - 1;
322
      /* any zero bits */
323
      while (mask >= sizeof (unsigned64)) /* minimum modulo */
324
        {
325
          if ((mask & 1) == 0)
326
            mask = 0;
327
          else
328
            mask >>= 1;
329
        }
330
      if (mask != sizeof (unsigned64) - 1)
331
        {
332
#if (WITH_DEVICES)
333
          device_error (client, "sim_core_attach - internal error - modulo %lx not power of two", (long) modulo);
334
#endif
335
#if (WITH_HW)
336
          sim_hw_abort (sd, client, "sim_core_attach - internal error - modulo %lx not power of two", (long) modulo);
337
#endif
338
          sim_io_error (sd, "sim_core_attach - internal error - modulo %lx not power of two", (long) modulo);
339
        }
340
    }
341
 
342
  /* verify consistency between device and buffer */
343
  if (client != NULL && optional_buffer != NULL)
344
    {
345
#if (WITH_DEVICES)
346
      device_error (client, "sim_core_attach - internal error - conflicting buffer and attach arguments");
347
#endif
348
#if (WITH_HW)
349
      sim_hw_abort (sd, client, "sim_core_attach - internal error - conflicting buffer and attach arguments");
350
#endif
351
      sim_io_error (sd, "sim_core_attach - internal error - conflicting buffer and attach arguments");
352
    }
353
  if (client == NULL)
354
    {
355
      if (optional_buffer == NULL)
356
        {
357
          int padding = (addr % sizeof (unsigned64));
358
          unsigned long bytes = (modulo == 0 ? nr_bytes : modulo) + padding;
359
          free_buffer = zalloc (bytes);
360
          buffer = (char*) free_buffer + padding;
361
        }
362
      else
363
        {
364
          buffer = optional_buffer;
365
          free_buffer = NULL;
366
        }
367
    }
368
  else
369
    {
370
      /* a device */
371
      buffer = NULL;
372
      free_buffer = NULL;
373
    }
374
 
375
  /* attach the region to all applicable access maps */
376
  for (map = 0;
377
       map < nr_maps;
378
       map++)
379
    {
380
      if (mapmask & (1 << map))
381
        {
382
          sim_core_map_attach (sd, &memory->common.map[map],
383
                               level, space, addr, nr_bytes, modulo,
384
                               client, buffer, free_buffer);
385
          free_buffer = NULL;
386
        }
387
    }
388
 
389
  /* Just copy this map to each of the processor specific data structures.
390
     FIXME - later this will be replaced by true processor specific
391
     maps. */
392
  {
393
    int i;
394
    for (i = 0; i < MAX_NR_PROCESSORS; i++)
395
      {
396
        CPU_CORE (STATE_CPU (sd, i))->common = STATE_CORE (sd)->common;
397
      }
398
  }
399
}
400
#endif
401
 
402
 
403
/* Remove any memory reference related to this address */
404
#if EXTERN_SIM_CORE_P
405
static void
406
sim_core_map_detach (SIM_DESC sd,
407
                     sim_core_map *access_map,
408
                     int level,
409
                     int space,
410
                     address_word addr)
411
{
412
  sim_core_mapping **entry;
413
  for (entry = &access_map->first;
414
       (*entry) != NULL;
415
       entry = &(*entry)->next)
416
    {
417
      if ((*entry)->base == addr
418
          && (*entry)->level == level
419
          && (*entry)->space == space)
420
        {
421
          sim_core_mapping *dead = (*entry);
422
          (*entry) = dead->next;
423
          if (dead->free_buffer != NULL)
424
            zfree (dead->free_buffer);
425
          zfree (dead);
426
          return;
427
        }
428
    }
429
}
430
#endif
431
 
432
#if EXTERN_SIM_CORE_P
433
void
434
sim_core_detach (SIM_DESC sd,
435
                 sim_cpu *cpu,
436
                 int level,
437
                 int address_space,
438
                 address_word addr)
439
{
440
  sim_core *memory = STATE_CORE (sd);
441
  unsigned map;
442
  for (map = 0; map < nr_maps; map++)
443
    {
444
      sim_core_map_detach (sd, &memory->common.map[map],
445
                           level, address_space, addr);
446
    }
447
  /* Just copy this update to each of the processor specific data
448
     structures.  FIXME - later this will be replaced by true
449
     processor specific maps. */
450
  {
451
    int i;
452
    for (i = 0; i < MAX_NR_PROCESSORS; i++)
453
      {
454
        CPU_CORE (STATE_CPU (sd, i))->common = STATE_CORE (sd)->common;
455
      }
456
  }
457
}
458
#endif
459
 
460
 
461
STATIC_INLINE_SIM_CORE\
462
(sim_core_mapping *)
463
sim_core_find_mapping(sim_core_common *core,
464
                      unsigned map,
465
                      address_word addr,
466
                      unsigned nr_bytes,
467
                      transfer_type transfer,
468
                      int abort, /*either 0 or 1 - hint to inline/-O */
469
                      sim_cpu *cpu, /* abort => cpu != NULL */
470
                      sim_cia cia)
471
{
472
  sim_core_mapping *mapping = core->map[map].first;
473
  ASSERT ((addr & (nr_bytes - 1)) == 0); /* must be aligned */
474
  ASSERT ((addr + (nr_bytes - 1)) >= addr); /* must not wrap */
475
  ASSERT (!abort || cpu != NULL); /* abort needs a non null CPU */
476
  while (mapping != NULL)
477
    {
478
      if (addr >= mapping->base
479
          && (addr + (nr_bytes - 1)) <= mapping->bound)
480
        return mapping;
481
      mapping = mapping->next;
482
    }
483
  if (abort)
484
    {
485
      SIM_CORE_SIGNAL (CPU_STATE (cpu), cpu, cia, map, nr_bytes, addr, transfer,
486
                       sim_core_unmapped_signal);
487
    }
488
  return NULL;
489
}
490
 
491
 
492
STATIC_INLINE_SIM_CORE\
493
(void *)
494
sim_core_translate (sim_core_mapping *mapping,
495
                    address_word addr)
496
{
497
  if (WITH_MODULO_MEMORY)
498
    return (void *)((unsigned8 *) mapping->buffer
499
                    + ((addr - mapping->base) & mapping->mask));
500
  else
501
    return (void *)((unsigned8 *) mapping->buffer
502
                    + addr - mapping->base);
503
}
504
 
505
 
506
#if EXTERN_SIM_CORE_P
507
unsigned
508
sim_core_read_buffer (SIM_DESC sd,
509
                      sim_cpu *cpu,
510
                      unsigned map,
511
                      void *buffer,
512
                      address_word addr,
513
                      unsigned len)
514
{
515
  sim_core_common *core = (cpu == NULL ? &STATE_CORE (sd)->common : &CPU_CORE (cpu)->common);
516
  unsigned count = 0;
517
  while (count < len)
518
 {
519
    address_word raddr = addr + count;
520
    sim_core_mapping *mapping =
521
      sim_core_find_mapping (core, map,
522
                            raddr, /*nr-bytes*/1,
523
                            read_transfer,
524
 
525
    if (mapping == NULL)
526
      break;
527
#if (WITH_DEVICES)
528
    if (mapping->device != NULL)
529
      {
530
        int nr_bytes = len - count;
531
        sim_cia cia = cpu ? CIA_GET (cpu) : NULL_CIA;
532
        if (raddr + nr_bytes - 1> mapping->bound)
533
          nr_bytes = mapping->bound - raddr + 1;
534
        if (device_io_read_buffer (mapping->device,
535
                                   (unsigned_1*)buffer + count,
536
                                   mapping->space,
537
                                   raddr,
538
                                   nr_bytes,
539
                                   sd,
540
                                   cpu,
541
                                   cia) != nr_bytes)
542
          break;
543
        count += nr_bytes;
544
        continue;
545
      }
546
#endif
547
#if (WITH_HW)
548
    if (mapping->device != NULL)
549
      {
550
        int nr_bytes = len - count;
551
        if (raddr + nr_bytes - 1> mapping->bound)
552
          nr_bytes = mapping->bound - raddr + 1;
553
        if (sim_hw_io_read_buffer (sd, mapping->device,
554
                                   (unsigned_1*)buffer + count,
555
                                   mapping->space,
556
                                   raddr,
557
                                   nr_bytes) != nr_bytes)
558
          break;
559
        count += nr_bytes;
560
        continue;
561
      }
562
#endif
563
    ((unsigned_1*)buffer)[count] =
564
      *(unsigned_1*)sim_core_translate(mapping, raddr);
565
    count += 1;
566
 }
567
  return count;
568
}
569
#endif
570
 
571
 
572
#if EXTERN_SIM_CORE_P
573
unsigned
574
sim_core_write_buffer (SIM_DESC sd,
575
                       sim_cpu *cpu,
576
                       unsigned map,
577
                       const void *buffer,
578
                       address_word addr,
579
                       unsigned len)
580
{
581
  sim_core_common *core = (cpu == NULL ? &STATE_CORE (sd)->common : &CPU_CORE (cpu)->common);
582
  unsigned count = 0;
583
  while (count < len)
584
    {
585
      address_word raddr = addr + count;
586
      sim_core_mapping *mapping =
587
        sim_core_find_mapping (core, map,
588
                               raddr, /*nr-bytes*/1,
589
                               write_transfer,
590
 
591
      if (mapping == NULL)
592
        break;
593
#if (WITH_DEVICES)
594
      if (WITH_CALLBACK_MEMORY
595
          && mapping->device != NULL)
596
        {
597
          int nr_bytes = len - count;
598
          sim_cia cia = cpu ? CIA_GET (cpu) : NULL_CIA;
599
          if (raddr + nr_bytes - 1 > mapping->bound)
600
            nr_bytes = mapping->bound - raddr + 1;
601
          if (device_io_write_buffer (mapping->device,
602
                                      (unsigned_1*)buffer + count,
603
                                      mapping->space,
604
                                      raddr,
605
                                      nr_bytes,
606
                                      sd,
607
                                      cpu,
608
                                      cia) != nr_bytes)
609
            break;
610
          count += nr_bytes;
611
          continue;
612
        }
613
#endif
614
#if (WITH_HW)
615
      if (WITH_CALLBACK_MEMORY
616
          && mapping->device != NULL)
617
        {
618
          int nr_bytes = len - count;
619
          if (raddr + nr_bytes - 1 > mapping->bound)
620
            nr_bytes = mapping->bound - raddr + 1;
621
          if (sim_hw_io_write_buffer (sd, mapping->device,
622
                                      (unsigned_1*)buffer + count,
623
                                      mapping->space,
624
                                      raddr,
625
                                      nr_bytes) != nr_bytes)
626
            break;
627
          count += nr_bytes;
628
          continue;
629
        }
630
#endif
631
      *(unsigned_1*)sim_core_translate(mapping, raddr) =
632
        ((unsigned_1*)buffer)[count];
633
      count += 1;
634
    }
635
  return count;
636
}
637
#endif
638
 
639
 
640
#if EXTERN_SIM_CORE_P
641
void
642
sim_core_set_xor (SIM_DESC sd,
643
                  sim_cpu *cpu,
644
                  int is_xor)
645
{
646
  /* set up the XOR map if required. */
647
  if (WITH_XOR_ENDIAN) {
648
    {
649
      sim_core *core = STATE_CORE (sd);
650
      sim_cpu_core *cpu_core = (cpu != NULL ? CPU_CORE (cpu) : NULL);
651
      if (cpu_core != NULL)
652
        {
653
          int i = 1;
654
          unsigned mask;
655
          if (is_xor)
656
            mask = WITH_XOR_ENDIAN - 1;
657
          else
658
            mask = 0;
659
          while (i - 1 < WITH_XOR_ENDIAN)
660
            {
661
              cpu_core->xor[i-1] = mask;
662
              mask = (mask << 1) & (WITH_XOR_ENDIAN - 1);
663
              i = (i << 1);
664
            }
665
        }
666
      else
667
        {
668
          if (is_xor)
669
            core->byte_xor = WITH_XOR_ENDIAN - 1;
670
          else
671
            core->byte_xor = 0;
672
        }
673
    }
674
  }
675
  else {
676
    if (is_xor)
677
      sim_engine_abort (sd, NULL, NULL_CIA,
678
                        "Attempted to enable xor-endian mode when permenantly disabled.");
679
  }
680
}
681
#endif
682
 
683
 
684
#if EXTERN_SIM_CORE_P
685
static void
686
reverse_n (unsigned_1 *dest,
687
           const unsigned_1 *src,
688
           int nr_bytes)
689
{
690
  int i;
691
  for (i = 0; i < nr_bytes; i++)
692
    {
693
      dest [nr_bytes - i - 1] = src [i];
694
    }
695
}
696
#endif
697
 
698
 
699
#if EXTERN_SIM_CORE_P
700
unsigned
701
sim_core_xor_read_buffer (SIM_DESC sd,
702
                          sim_cpu *cpu,
703
                          unsigned map,
704
                          void *buffer,
705
                          address_word addr,
706
                          unsigned nr_bytes)
707
{
708
  address_word byte_xor = (cpu == NULL ? STATE_CORE (sd)->byte_xor : CPU_CORE (cpu)->xor[0]);
709
  if (!WITH_XOR_ENDIAN || !byte_xor)
710
    return sim_core_read_buffer (sd, cpu, map, buffer, addr, nr_bytes);
711
  else
712
    /* only break up transfers when xor-endian is both selected and enabled */
713
    {
714
      unsigned_1 x[WITH_XOR_ENDIAN + 1]; /* +1 to avoid zero-sized array */
715
      unsigned nr_transfered = 0;
716
      address_word start = addr;
717
      unsigned nr_this_transfer = (WITH_XOR_ENDIAN - (addr & ~(WITH_XOR_ENDIAN - 1)));
718
      address_word stop;
719
      /* initial and intermediate transfers are broken when they cross
720
         an XOR endian boundary */
721
      while (nr_transfered + nr_this_transfer < nr_bytes)
722
        /* initial/intermediate transfers */
723
        {
724
          /* since xor-endian is enabled stop^xor defines the start
725
             address of the transfer */
726
          stop = start + nr_this_transfer - 1;
727
          SIM_ASSERT (start <= stop);
728
          SIM_ASSERT ((stop ^ byte_xor) <= (start ^ byte_xor));
729
          if (sim_core_read_buffer (sd, cpu, map, x, stop ^ byte_xor, nr_this_transfer)
730
              != nr_this_transfer)
731
            return nr_transfered;
732
          reverse_n (&((unsigned_1*)buffer)[nr_transfered], x, nr_this_transfer);
733
          nr_transfered += nr_this_transfer;
734
          nr_this_transfer = WITH_XOR_ENDIAN;
735
          start = stop + 1;
736
        }
737
      /* final transfer */
738
      nr_this_transfer = nr_bytes - nr_transfered;
739
      stop = start + nr_this_transfer - 1;
740
      SIM_ASSERT (stop == (addr + nr_bytes - 1));
741
      if (sim_core_read_buffer (sd, cpu, map, x, stop ^ byte_xor, nr_this_transfer)
742
          != nr_this_transfer)
743
        return nr_transfered;
744
      reverse_n (&((unsigned_1*)buffer)[nr_transfered], x, nr_this_transfer);
745
      return nr_bytes;
746
    }
747
}
748
#endif
749
 
750
 
751
#if EXTERN_SIM_CORE_P
752
unsigned
753
sim_core_xor_write_buffer (SIM_DESC sd,
754
                           sim_cpu *cpu,
755
                           unsigned map,
756
                           const void *buffer,
757
                           address_word addr,
758
                           unsigned nr_bytes)
759
{
760
  address_word byte_xor = (cpu == NULL ? STATE_CORE (sd)->byte_xor : CPU_CORE (cpu)->xor[0]);
761
  if (!WITH_XOR_ENDIAN || !byte_xor)
762
    return sim_core_write_buffer (sd, cpu, map, buffer, addr, nr_bytes);
763
  else
764
    /* only break up transfers when xor-endian is both selected and enabled */
765
    {
766
      unsigned_1 x[WITH_XOR_ENDIAN + 1]; /* +1 to avoid zero sized array */
767
      unsigned nr_transfered = 0;
768
      address_word start = addr;
769
      unsigned nr_this_transfer = (WITH_XOR_ENDIAN - (addr & ~(WITH_XOR_ENDIAN - 1)));
770
      address_word stop;
771
      /* initial and intermediate transfers are broken when they cross
772
         an XOR endian boundary */
773
      while (nr_transfered + nr_this_transfer < nr_bytes)
774
        /* initial/intermediate transfers */
775
        {
776
          /* since xor-endian is enabled stop^xor defines the start
777
             address of the transfer */
778
          stop = start + nr_this_transfer - 1;
779
          SIM_ASSERT (start <= stop);
780
          SIM_ASSERT ((stop ^ byte_xor) <= (start ^ byte_xor));
781
          reverse_n (x, &((unsigned_1*)buffer)[nr_transfered], nr_this_transfer);
782
          if (sim_core_read_buffer (sd, cpu, map, x, stop ^ byte_xor, nr_this_transfer)
783
              != nr_this_transfer)
784
            return nr_transfered;
785
          nr_transfered += nr_this_transfer;
786
          nr_this_transfer = WITH_XOR_ENDIAN;
787
          start = stop + 1;
788
        }
789
      /* final transfer */
790
      nr_this_transfer = nr_bytes - nr_transfered;
791
      stop = start + nr_this_transfer - 1;
792
      SIM_ASSERT (stop == (addr + nr_bytes - 1));
793
      reverse_n (x, &((unsigned_1*)buffer)[nr_transfered], nr_this_transfer);
794
      if (sim_core_read_buffer (sd, cpu, map, x, stop ^ byte_xor, nr_this_transfer)
795
          != nr_this_transfer)
796
        return nr_transfered;
797
      return nr_bytes;
798
    }
799
}
800
#endif
801
 
802
#if EXTERN_SIM_CORE_P
803
void *
804
sim_core_trans_addr (SIM_DESC sd,
805
                     sim_cpu *cpu,
806
                     unsigned map,
807
                     address_word addr)
808
{
809
  sim_core_common *core = (cpu == NULL ? &STATE_CORE (sd)->common : &CPU_CORE (cpu)->common);
810
  sim_core_mapping *mapping =
811
    sim_core_find_mapping (core, map,
812
                           addr, /*nr-bytes*/1,
813
                           write_transfer,
814
 
815
  if (mapping == NULL)
816
    return NULL;
817
  return sim_core_translate(mapping, addr);
818
}
819
#endif
820
 
821
 
822
 
823
/* define the read/write 1/2/4/8/16/word functions */
824
 
825
#define N 16
826
#include "sim-n-core.h"
827
 
828
#define N 8
829
#include "sim-n-core.h"
830
 
831
#define N 7
832
#define M 8
833
#include "sim-n-core.h"
834
 
835
#define N 6
836
#define M 8
837
#include "sim-n-core.h"
838
 
839
#define N 5
840
#define M 8
841
#include "sim-n-core.h"
842
 
843
#define N 4
844
#include "sim-n-core.h"
845
 
846
#define N 3
847
#define M 4
848
#include "sim-n-core.h"
849
 
850
#define N 2
851
#include "sim-n-core.h"
852
 
853
#define N 1
854
#include "sim-n-core.h"
855
 
856
#endif

powered by: WebSVN 2.1.0

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