* gdb.base/d10vovly.c (D10VTranslate): Map IMAP0 to low 128k of
[deliverable/binutils-gdb.git] / gdb / testsuite / gdb.base / d10vovly.c
1
2 /*
3 * Ovlymgr.c -- Runtime Overlay Manager for the Mitsubishi D10V
4 */
5
6 #include "ovlymgr.h"
7
8 /* Local functions and data: */
9
10 extern unsigned long _ovly_table[][4], _novlys;
11 enum ovly_index { VMA, SIZE, LMA, MAPPED };
12 enum ovly_direction { IN, OUT };
13
14 static void D10VCopy (unsigned long dst, unsigned long src, long size);
15
16 /* OverlayLoad:
17 * Copy the overlay into its runtime region,
18 * and mark the overlay as "mapped".
19 */
20
21 void
22 OverlayLoad (int ovlyno)
23 {
24 int i;
25
26 if (ovlyno < 0 || ovlyno >= _novlys)
27 exit (-1); /* fail, bad ovly number */
28
29 if (_ovly_table[ovlyno][MAPPED])
30 return; /* this overlay already mapped -- nothing to do! */
31
32 for (i = 0; i < _novlys; i++)
33 if (i == ovlyno)
34 _ovly_table[i][MAPPED] = 1; /* this one now mapped */
35 else if (_ovly_table[i][VMA] == _ovly_table[ovlyno][VMA])
36 _ovly_table[i][MAPPED] = 0; /* this one now un-mapped */
37
38 /* copy overlay using D10V DMAP register */
39 D10VCopy (_ovly_table[ovlyno][VMA], _ovly_table[ovlyno][LMA],
40 _ovly_table[ovlyno][SIZE]);
41 }
42
43 /* OverlayUnload:
44 * Copy the overlay back into its "load" region.
45 * Does NOT mark overlay as "unmapped", therefore may be called
46 * more than once for the same mapped overlay.
47 */
48
49 void
50 OverlayUnload (int ovlyno)
51 {
52 if (ovlyno < 0 || ovlyno >= _novlys)
53 exit (-1); /* fail, bad ovly number */
54
55 if (!_ovly_table[ovlyno][MAPPED])
56 exit (-1); /* error, can't copy out a segment that's not "in" */
57
58 D10VCopy (_ovly_table[ovlyno][LMA], _ovly_table[ovlyno][VMA],
59 _ovly_table[ovlyno][SIZE]);
60 }
61
62 /* D10VCopy:
63 * Copy a region of memory from src to dest.
64 * Like memcpy, but can copy anywhere in Universal, Data or Instruction memory.
65 */
66
67 #define IMAP0 (*(int *)(0xff00))
68 #define IMAP1 (*(int *)(0xff02))
69 #define DMAP (*(int *)(0xff04))
70
71 static void
72 D10VTranslate (unsigned long logical,
73 short *dmap,
74 unsigned long **addr)
75 {
76 unsigned long physical;
77 unsigned long seg;
78 unsigned long off;
79 int err = 0;
80 /* to access data, we use the following mapping
81 0x00xxxxxx: Logical data address segment (DMAP translated memory)
82 0x01xxxxxx: Logical instruction address segment (IMAP translated memory)
83 0x10xxxxxx: Physical data memory segment (On-chip data memory)
84 0x11xxxxxx: Physical instruction memory segment (On-chip insn memory)
85 0x12xxxxxx: Phisical unified memory segment (Unified memory)
86 */
87
88 /* Addresses must be correctly aligned */
89 if (logical & (sizeof (**addr) - 1))
90 exit (-1);
91
92 /* If the address is in one of the two logical address spaces, it is
93 first translated into a physical address */
94 seg = (logical >> 24);
95 off = (logical & 0xffffffL);
96 switch (seg)
97 {
98 case 0x00: /* in logical data address segment */
99 if (off <= 0x7fffL)
100 physical = (0x10L << 24) + off;
101 else
102 /* Logical address out side of on-chip segment, not
103 supported */
104 exit (-1);
105 break;
106 case 0x01: /* in logical instruction address segment */
107 {
108 short map;
109 if (off <= 0x1ffffL)
110 map = IMAP0;
111 else if (off <= 0x3ffffL)
112 map = IMAP1;
113 else
114 /* Logical address outside of IMAP[01] segment, not
115 supported */
116 exit (-1);
117 if (map & 0x1000L)
118 {
119 /* Instruction memory */
120 physical = (0x11L << 24) | off;
121 }
122 else
123 {
124 /* Unified memory */
125 physical = ((map & 0x7fL) << 17) + (off & 0x1ffffL);
126 if (physical > 0xffffffL)
127 /* Address outside of unified address segment */
128 exit (-1);
129 physical |= (0x12L << 24);
130 }
131 break;
132 }
133 case 0x10:
134 case 0x11:
135 case 0x12:
136 physical = logical;
137 break;
138 default:
139 exit (-1); /* error */
140 }
141
142 seg = (physical >> 24);
143 off = (physical & 0xffffffL);
144 switch (seg)
145 {
146 case 0x10: /* dst is a 15 bit offset into the on-chip memory */
147 *dmap = 0;
148 *addr = (long *) (0x0000 + ((int)off & 0x7fff));
149 break;
150 case 0x11: /* dst is an 18-bit offset into the on-chip
151 instruction memory */
152 *dmap = 0x1000L | ((off & 0x3ffffL) >> 14);
153 *addr = (long *) (0x8000 + ((int)off & 0x3fff));
154 break;
155 case 0x12: /* dst is a 24-bit offset into unified memory */
156 *dmap = off >> 14;
157 *addr = (long *) (0x8000 + ((int)off & 0x3fff));
158 break;
159 default:
160 exit (-1); /* error */
161 }
162
163 #if 0
164 printf ("D10VTranslate: logical = %08lx, dmap = %04x, addr = %04x\n",
165 logical, *dmap, *addr);
166 #endif
167 }
168
169 static void
170 D10VCopy (unsigned long dst, unsigned long src, long size)
171 {
172 unsigned long *s, *d, tmp;
173 short dmap_src, dmap_dst;
174 short dmap_save;
175
176 #if 0
177 printf ("D10VCopy: dst = %08lx, src = %08lx, size = %ld\n",
178 dst, src, size);
179 #endif
180
181 /* all section sizes should by multiples of 4 bytes */
182 dmap_save = DMAP;
183
184 D10VTranslate (src, &dmap_src, &s);
185 D10VTranslate (dst, &dmap_dst, &d);
186
187 while (size > 0)
188 {
189 /* NB: Transfer 4 byte (long) quantites, problems occure
190 when only two bytes are transfered */
191 DMAP = dmap_src;
192 tmp = *s;
193 DMAP = dmap_dst;
194 *d = tmp;
195 d++;
196 s++;
197 size -= sizeof (tmp);
198 src += sizeof (tmp);
199 dst += sizeof (tmp);
200 if ((src & 0x3fff) == 0)
201 D10VTranslate (src, &dmap_src, &s);
202 if ((dst & 0x3fff) == 0)
203 D10VTranslate (dst, &dmap_dst, &d);
204 }
205 DMAP = dmap_save;
206 }
207
This page took 0.033486 seconds and 5 git commands to generate.