]> git.ipfire.org Git - thirdparty/binutils-gdb.git/blob - sim/mips/m16e.igen
Update copyright year range in header of all files managed by GDB
[thirdparty/binutils-gdb.git] / sim / mips / m16e.igen
1 // -*- C -*-
2
3 // Simulator definition for the MIPS16e instructions.
4 // Copyright (C) 2005-2024 Free Software Foundation, Inc.
5 // Contributed by Nigel Stephens (nigel@mips.com) and
6 // David Ung (davidu@mips.com) of MIPS Technologies.
7 //
8 // This file is part of GDB, the GNU debugger.
9 //
10 // This program is free software; you can redistribute it and/or modify
11 // it under the terms of the GNU General Public License as published by
12 // the Free Software Foundation; either version 3 of the License, or
13 // (at your option) any later version.
14 //
15 // This program is distributed in the hope that it will be useful,
16 // but WITHOUT ANY WARRANTY; without even the implied warranty of
17 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 // GNU General Public License for more details.
19 //
20 // You should have received a copy of the GNU General Public License
21 // along with this program. If not, see <http://www.gnu.org/licenses/>.
22
23
24 11101,3.RX,100,10001:RR:16::SEB
25 "seb r<TRX>"
26 *mips16e:
27 {
28 TRACE_ALU_INPUT1 (GPR[TRX]);
29 GPR[TRX] = EXTEND8 (GPR[TRX]);
30 TRACE_ALU_RESULT (GPR[TRX]);
31 }
32
33
34 11101,3.RX,101,10001:RR:16::SEH
35 "seh r<TRX>"
36 *mips16e:
37 {
38 TRACE_ALU_INPUT1 (GPR[TRX]);
39 GPR[TRX] = EXTEND16 (GPR[TRX]);
40 TRACE_ALU_RESULT (GPR[TRX]);
41 }
42
43 11101,3.RX,110,10001:RR:16::SEW
44 "sew r<TRX>"
45 *mips16e:
46 {
47 check_u64 (SD_, instruction_0);
48 TRACE_ALU_INPUT1 (GPR[TRX]);
49 GPR[TRX] = EXTEND32 (GPR[TRX]);
50 TRACE_ALU_RESULT (GPR[TRX]);
51 }
52
53 11101,3.RX,000,10001:RR:16::ZEB
54 "zeb r<TRX>"
55 *mips16e:
56 {
57 TRACE_ALU_INPUT1 (GPR[TRX]);
58 GPR[TRX] = (unsigned_word)(uint8_t)(GPR[TRX]);
59 TRACE_ALU_RESULT (GPR[TRX]);
60 }
61
62 11101,3.RX,001,10001:RR:16::ZEH
63 "zeh r<TRX>"
64 *mips16e:
65 {
66 TRACE_ALU_INPUT1 (GPR[TRX]);
67 GPR[TRX] = (unsigned_word)(uint16_t)(GPR[TRX]);
68 TRACE_ALU_RESULT (GPR[TRX]);
69 }
70
71 11101,3.RX,010,10001:RR:16::ZEW
72 "zew r<TRX>"
73 *mips16e:
74 {
75 check_u64 (SD_, instruction_0);
76 TRACE_ALU_INPUT1 (GPR[TRX]);
77 GPR[TRX] = (unsigned_word)(uint32_t)(GPR[TRX]);
78 TRACE_ALU_RESULT (GPR[TRX]);
79 }
80
81
82 11101,3.RX,100,00000:RR:16::JRC
83 "jrc r<TRX>"
84 *mips16e:
85 {
86 NIA = GPR[TRX];
87 }
88
89
90 11101,000,101,00000:RR:16::JRCRA
91 "jrc ra"
92 *mips16e:
93 {
94 NIA = RA;
95 }
96
97
98 11101,3.RX,110,00000:RR:16::JALRC
99 "jalrc r<TRX>"
100 *mips16e:
101 {
102 RA = NIA;
103 NIA = GPR[TRX];
104 }
105
106
107 // format routines for save/restore
108 :%s::::RAS:int ras
109 *mips16e
110 {
111 static char buf[10];
112 buf[0] = '\0';
113 if (ras & 4)
114 strcat (buf,"ra,");
115 if (ras & 2)
116 strcat (buf,"s0,");
117 if (ras & 1)
118 strcat (buf,"s1,");
119 return (buf);
120 }
121
122 :%s::::XSREGS:int xsregs
123 *mips16e
124 {
125 if (xsregs > 6)
126 return "s2,s3,s4,s5,s6,s7,s8,";
127 if (xsregs > 5)
128 return "s2,s3,s4,s5,s6,s7,";
129 if (xsregs > 4)
130 return "s2,s3,s4,s5,s6,";
131 if (xsregs > 3)
132 return "s2,s3,s4,s5,";
133 if (xsregs > 2)
134 return "s2,s3,s4,";
135 if (xsregs > 1)
136 return "s2,s3,";
137 if (xsregs > 0)
138 return "s2,";
139 return "";
140 }
141
142 :%s::::AREGS:int aregs
143 *mips16e
144 {
145 // Fixme: how is the arg/static distinction made by the assembler?
146 static const char * const aregstr[16] = {
147 "",
148 "A3,",
149 "A2,A3,",
150 "A1,A2,A3,",
151 "A0,A1,A2,A3,",
152 "a0,",
153 "a0,A3,",
154 "a0,A2,A3,",
155 "a0,A1,A2,A3,",
156 "a0,a1,",
157 "a0,a1,A3,",
158 "a0,a1,A2,A3,",
159 "a0,a1,a2,",
160 "a0,a1,a2,A3,",
161 "?,"
162 };
163 return aregstr[aregs];
164 }
165
166 :compute:::int:SFRAME:FS:((FS == 0) ? 128 \: (FS << 3))
167 :compute:::int:BFRAME:FSHI,FSLO:(((FSHI << 4) | FSLO) << 3)
168
169 :function:::void:do_save:int xsregs, int aregs, int ras0s1, int framesize
170 {
171 unsigned_word temp;
172 int args, astatic;
173
174 temp = GPR[29];
175
176 /* writes are in the same order as the hardware description... */
177 switch (aregs) {
178 case 0: case 1: case 2: case 3: case 11:
179 args = 0;
180 break;
181 case 4: case 5: case 6: case 7:
182 args = 1;
183 break;
184 case 8: case 9: case 10:
185 args = 2;
186 break;
187 case 12: case 13:
188 args = 3;
189 break;
190 case 14:
191 args = 4;
192 break;
193 default:
194 sim_engine_abort (SD, CPU, CIA, "save: aregs=%d causes unpredictable results\n", aregs);
195 }
196 if (args > 0) {
197 do_store (SD_, AccessLength_WORD, temp, 0, GPR[4]);
198 if (args > 1) {
199 do_store (SD_,AccessLength_WORD, temp, 4 , GPR[5]);
200 if (args > 2) {
201 do_store (SD_,AccessLength_WORD, temp, 8 , GPR[6]);
202 if (args > 3) {
203 do_store (SD_,AccessLength_WORD, temp, 12, GPR[7]);
204 }
205 }
206 }
207 }
208
209 if (ras0s1 & 4)
210 do_store (SD_,AccessLength_WORD, temp -= 4, 0, GPR[31]);
211
212 switch (xsregs) {
213 case 7:
214 do_store (SD_,AccessLength_WORD, temp -= 4, 0, GPR[30]);
215 ATTRIBUTE_FALLTHROUGH;
216 case 6:
217 do_store (SD_,AccessLength_WORD, temp -= 4, 0, GPR[23]);
218 ATTRIBUTE_FALLTHROUGH;
219 case 5:
220 do_store (SD_,AccessLength_WORD, temp -= 4, 0, GPR[22]);
221 ATTRIBUTE_FALLTHROUGH;
222 case 4:
223 do_store (SD_,AccessLength_WORD, temp -= 4, 0, GPR[21]);
224 ATTRIBUTE_FALLTHROUGH;
225 case 3:
226 do_store (SD_,AccessLength_WORD, temp -= 4, 0, GPR[20]);
227 ATTRIBUTE_FALLTHROUGH;
228 case 2:
229 do_store (SD_,AccessLength_WORD, temp -= 4, 0, GPR[19]);
230 ATTRIBUTE_FALLTHROUGH;
231 case 1:
232 do_store (SD_,AccessLength_WORD, temp -= 4, 0, GPR[18]);
233 }
234
235 if (ras0s1 & 1)
236 do_store (SD_,AccessLength_WORD, temp -= 4, 0, GPR[17]);
237 if (ras0s1 & 2)
238 do_store (SD_,AccessLength_WORD, temp -= 4, 0, GPR[16]);
239
240 switch (aregs) {
241 case 0: case 4: case 8: case 12: case 14:
242 astatic = 0;
243 break;
244 case 1: case 5: case 9: case 13:
245 astatic = 1;
246 break;
247 case 2: case 6: case 10:
248 astatic = 2;
249 break;
250 case 3: case 7:
251 astatic = 3;
252 break;
253 case 11:
254 astatic = 4;
255 break;
256 default:
257 sim_engine_abort (SD, CPU, CIA, "save: aregs=%d causes unpredictable results\n", aregs);
258 }
259 if (astatic > 0) {
260 do_store (SD_, AccessLength_WORD, temp -= 4, 0, GPR[7]);
261 if (astatic > 1) {
262 do_store (SD_, AccessLength_WORD, temp -= 4, 0, GPR[6]);
263 if (astatic > 2) {
264 do_store (SD_, AccessLength_WORD, temp -= 4, 0, GPR[5]);
265 if (astatic > 3) {
266 do_store (SD_, AccessLength_WORD, temp -= 4, 0, GPR[4]);
267 }
268 }
269 }
270 }
271
272 GPR[29] -= framesize;
273 }
274
275 01100,100,1,3.RAS,4.FS:I8:16::SAVE
276 "save %s<RAS>,<SFRAME>"
277 *mips16e
278 {
279 do_save (SD_, 0, 0, RAS, SFRAME);
280 }
281
282
283 11110,3.XSREGS,4.FSHI,4.AREGS + 01100,100,1,3.RAS,4.FSLO:EXT-I8:16::SAVE
284 "save %s<RAS>%s<XSREGS>%s<AREGS><BFRAME>"
285 *mips16e
286 {
287 do_save (SD_, XSREGS, AREGS, RAS, BFRAME);
288 }
289
290
291 :function:::void:do_restore:int xsregs, int aregs, int ras0s1, int framesize
292 *mips16e
293 {
294 unsigned_word temp, temp2;
295 int astatic;
296
297 temp = GPR[29] + framesize;
298 temp2 = temp;
299
300 /* reads are in the same order as the hardware description... */
301
302 if (ras0s1 & 4)
303 GPR[31] = EXTEND32 (do_load(SD_, AccessLength_WORD, temp -= 4, 0));
304
305 switch (xsregs) {
306 case 7:
307 GPR[30] = EXTEND32 (do_load (SD_,AccessLength_WORD, temp -= 4, 0));
308 case 6:
309 GPR[23] = EXTEND32 (do_load (SD_,AccessLength_WORD, temp -= 4, 0));
310 case 5:
311 GPR[22] = EXTEND32 (do_load (SD_,AccessLength_WORD, temp -= 4, 0));
312 case 4:
313 GPR[21] = EXTEND32 (do_load (SD_,AccessLength_WORD, temp -= 4, 0));
314 case 3:
315 GPR[20] = EXTEND32 (do_load (SD_,AccessLength_WORD, temp -= 4, 0));
316 case 2:
317 GPR[19] = EXTEND32 (do_load (SD_,AccessLength_WORD, temp -= 4, 0));
318 case 1:
319 GPR[18] = EXTEND32 (do_load (SD_,AccessLength_WORD, temp -= 4, 0));
320 }
321
322 if (ras0s1 & 1)
323 GPR[17] = EXTEND32 (do_load (SD_,AccessLength_WORD, temp -= 4, 0));
324 if (ras0s1 & 2)
325 GPR[16] = EXTEND32 (do_load (SD_,AccessLength_WORD, temp -= 4, 0));
326
327 switch (aregs) {
328 case 0: case 4: case 8: case 12: case 14:
329 astatic = 0;
330 break;
331 case 1: case 5: case 9: case 13:
332 astatic = 1;
333 break;
334 case 2: case 6: case 10:
335 astatic = 2;
336 break;
337 case 3: case 7:
338 astatic = 3;
339 break;
340 case 11:
341 astatic = 4;
342 break;
343 default:
344 sim_engine_abort (SD, CPU, CIA, "save: aregs=%d causes unpredictable results\n", aregs);
345 }
346 if (astatic > 0) {
347 GPR[7] = EXTEND32 (do_load (SD_,AccessLength_WORD, temp -= 4, 0));
348 if (astatic > 1) {
349 GPR[6] = EXTEND32 (do_load (SD_,AccessLength_WORD, temp -= 4, 0));
350 if (astatic > 2) {
351 GPR[5] = EXTEND32 (do_load (SD_,AccessLength_WORD, temp -= 4, 0));
352 if (astatic > 3) {
353 GPR[4] = EXTEND32 (do_load (SD_,AccessLength_WORD, temp -= 4, 0));
354 }
355 }
356 }
357 }
358
359 GPR[29] = temp2;
360 }
361
362 01100,100,0,3.RAS,4.FS:I8:16::RESTORE
363 "restore %s<RAS>,<SFRAME>"
364 *mips16e
365 {
366 do_restore (SD_,0,0,RAS,SFRAME);
367 }
368
369 11110,3.XSREGS,4.FSHI,4.AREGS + 01100,100,0,3.RAS,4.FSLO:EXT-I8:16::RESTORE
370 "restore %s<RAS>%s<XSREGS>%s<AREGS><BFRAME>"
371 *mips16e
372 {
373 do_restore (SD_,XSREGS,AREGS,RAS,BFRAME);
374 }