[ include/opcode/ChangeLog ]
[deliverable/binutils-gdb.git] / opcodes / fr30-ibld.c
CommitLineData
252b5132
RH
1/* Instruction building/extraction support for fr30. -*- C -*-
2
3THIS FILE IS MACHINE GENERATED WITH CGEN: Cpu tools GENerator.
4- the resultant file is machine generated, cgen-ibld.in isn't
5
060d22b0 6Copyright 1996, 1997, 1998, 1999, 2000, 2001 Free Software Foundation, Inc.
252b5132
RH
7
8This file is part of the GNU Binutils and GDB, the GNU debugger.
9
10This program is free software; you can redistribute it and/or modify
11it under the terms of the GNU General Public License as published by
12the Free Software Foundation; either version 2, or (at your option)
13any later version.
14
15This program is distributed in the hope that it will be useful,
16but WITHOUT ANY WARRANTY; without even the implied warranty of
17MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18GNU General Public License for more details.
19
20You should have received a copy of the GNU General Public License
21along with this program; if not, write to the Free Software Foundation, Inc.,
2259 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
23
24/* ??? Eventually more and more of this stuff can go to cpu-independent files.
25 Keep that in mind. */
26
27#include "sysdep.h"
252b5132
RH
28#include <stdio.h>
29#include "ansidecl.h"
30#include "dis-asm.h"
31#include "bfd.h"
32#include "symcat.h"
33#include "fr30-desc.h"
34#include "fr30-opc.h"
35#include "opintl.h"
37111cc7 36#include "safe-ctype.h"
252b5132
RH
37
38#undef min
39#define min(a,b) ((a) < (b) ? (a) : (b))
40#undef max
41#define max(a,b) ((a) > (b) ? (a) : (b))
42
43/* Used by the ifield rtx function. */
44#define FLD(f) (fields->f)
45
46static const char * insert_normal
47 PARAMS ((CGEN_CPU_DESC, long, unsigned int, unsigned int, unsigned int,
48 unsigned int, unsigned int, unsigned int, CGEN_INSN_BYTES_PTR));
49static const char * insert_insn_normal
50 PARAMS ((CGEN_CPU_DESC, const CGEN_INSN *,
51 CGEN_FIELDS *, CGEN_INSN_BYTES_PTR, bfd_vma));
252b5132
RH
52static int extract_normal
53 PARAMS ((CGEN_CPU_DESC, CGEN_EXTRACT_INFO *, CGEN_INSN_INT,
54 unsigned int, unsigned int, unsigned int, unsigned int,
55 unsigned int, unsigned int, bfd_vma, long *));
56static int extract_insn_normal
57 PARAMS ((CGEN_CPU_DESC, const CGEN_INSN *, CGEN_EXTRACT_INFO *,
58 CGEN_INSN_INT, CGEN_FIELDS *, bfd_vma));
d5b2f4d6 59#if CGEN_INT_INSN_P
6bb95a0f
DB
60static void put_insn_int_value
61 PARAMS ((CGEN_CPU_DESC, CGEN_INSN_BYTES_PTR, int, int, CGEN_INSN_INT));
d5b2f4d6 62#endif
0e2ee3ca 63#if ! CGEN_INT_INSN_P
d5b2f4d6
NC
64static CGEN_INLINE void insert_1
65 PARAMS ((CGEN_CPU_DESC, unsigned long, int, int, int, unsigned char *));
0e2ee3ca
NC
66static CGEN_INLINE int fill_cache
67 PARAMS ((CGEN_CPU_DESC, CGEN_EXTRACT_INFO *, int, int, bfd_vma));
68static CGEN_INLINE long extract_1
69 PARAMS ((CGEN_CPU_DESC, CGEN_EXTRACT_INFO *, int, int, int,
70 unsigned char *, bfd_vma));
71#endif
252b5132
RH
72\f
73/* Operand insertion. */
74
75#if ! CGEN_INT_INSN_P
76
77/* Subroutine of insert_normal. */
78
79static CGEN_INLINE void
80insert_1 (cd, value, start, length, word_length, bufp)
81 CGEN_CPU_DESC cd;
82 unsigned long value;
83 int start,length,word_length;
84 unsigned char *bufp;
85{
86 unsigned long x,mask;
87 int shift;
252b5132 88
0e2ee3ca 89 x = cgen_get_insn_value (cd, bufp, word_length);
252b5132
RH
90
91 /* Written this way to avoid undefined behaviour. */
92 mask = (((1L << (length - 1)) - 1) << 1) | 1;
93 if (CGEN_INSN_LSB0_P)
94 shift = (start + 1) - length;
95 else
96 shift = (word_length - (start + length));
97 x = (x & ~(mask << shift)) | ((value & mask) << shift);
98
0e2ee3ca 99 cgen_put_insn_value (cd, bufp, word_length, (bfd_vma) x);
252b5132
RH
100}
101
102#endif /* ! CGEN_INT_INSN_P */
103
104/* Default insertion routine.
105
106 ATTRS is a mask of the boolean attributes.
107 WORD_OFFSET is the offset in bits from the start of the insn of the value.
108 WORD_LENGTH is the length of the word in bits in which the value resides.
109 START is the starting bit number in the word, architecture origin.
110 LENGTH is the length of VALUE in bits.
111 TOTAL_LENGTH is the total length of the insn in bits.
112
113 The result is an error message or NULL if success. */
114
115/* ??? This duplicates functionality with bfd's howto table and
116 bfd_install_relocation. */
117/* ??? This doesn't handle bfd_vma's. Create another function when
118 necessary. */
119
120static const char *
121insert_normal (cd, value, attrs, word_offset, start, length, word_length,
122 total_length, buffer)
123 CGEN_CPU_DESC cd;
124 long value;
125 unsigned int attrs;
126 unsigned int word_offset, start, length, word_length, total_length;
127 CGEN_INSN_BYTES_PTR buffer;
128{
129 static char errbuf[100];
130 /* Written this way to avoid undefined behaviour. */
131 unsigned long mask = (((1L << (length - 1)) - 1) << 1) | 1;
132
133 /* If LENGTH is zero, this operand doesn't contribute to the value. */
134 if (length == 0)
135 return NULL;
136
6bb95a0f 137#if 0
252b5132
RH
138 if (CGEN_INT_INSN_P
139 && word_offset != 0)
140 abort ();
6bb95a0f 141#endif
252b5132
RH
142
143 if (word_length > 32)
144 abort ();
145
146 /* For architectures with insns smaller than the base-insn-bitsize,
147 word_length may be too big. */
148 if (cd->min_insn_bitsize < cd->base_insn_bitsize)
149 {
150 if (word_offset == 0
151 && word_length > total_length)
152 word_length = total_length;
153 }
154
155 /* Ensure VALUE will fit. */
fc7bc883
RH
156 if (CGEN_BOOL_ATTR (attrs, CGEN_IFLD_SIGN_OPT))
157 {
158 long minval = - (1L << (length - 1));
159 unsigned long maxval = mask;
160
161 if ((value > 0 && (unsigned long) value > maxval)
162 || value < minval)
163 {
164 /* xgettext:c-format */
165 sprintf (errbuf,
166 _("operand out of range (%ld not between %ld and %lu)"),
167 value, minval, maxval);
168 return errbuf;
169 }
170 }
171 else if (! CGEN_BOOL_ATTR (attrs, CGEN_IFLD_SIGNED))
252b5132
RH
172 {
173 unsigned long maxval = mask;
6bb95a0f 174
252b5132
RH
175 if ((unsigned long) value > maxval)
176 {
177 /* xgettext:c-format */
178 sprintf (errbuf,
179 _("operand out of range (%lu not between 0 and %lu)"),
180 value, maxval);
181 return errbuf;
182 }
183 }
184 else
185 {
6bb95a0f 186 if (! cgen_signed_overflow_ok_p (cd))
252b5132 187 {
6bb95a0f
DB
188 long minval = - (1L << (length - 1));
189 long maxval = (1L << (length - 1)) - 1;
190
191 if (value < minval || value > maxval)
192 {
193 sprintf
194 /* xgettext:c-format */
195 (errbuf, _("operand out of range (%ld not between %ld and %ld)"),
196 value, minval, maxval);
197 return errbuf;
198 }
252b5132
RH
199 }
200 }
201
202#if CGEN_INT_INSN_P
203
204 {
205 int shift;
206
207 if (CGEN_INSN_LSB0_P)
6bb95a0f 208 shift = (word_offset + start + 1) - length;
252b5132 209 else
6bb95a0f 210 shift = total_length - (word_offset + start + length);
252b5132
RH
211 *buffer = (*buffer & ~(mask << shift)) | ((value & mask) << shift);
212 }
213
214#else /* ! CGEN_INT_INSN_P */
215
216 {
217 unsigned char *bufp = (unsigned char *) buffer + word_offset / 8;
218
219 insert_1 (cd, value, start, length, word_length, bufp);
220 }
221
222#endif /* ! CGEN_INT_INSN_P */
223
224 return NULL;
225}
226
227/* Default insn builder (insert handler).
fc7bc883
RH
228 The instruction is recorded in CGEN_INT_INSN_P byte order (meaning
229 that if CGEN_INSN_BYTES_PTR is an int * and thus, the value is
230 recorded in host byte order, otherwise BUFFER is an array of bytes
231 and the value is recorded in target byte order).
252b5132
RH
232 The result is an error message or NULL if success. */
233
234static const char *
235insert_insn_normal (cd, insn, fields, buffer, pc)
236 CGEN_CPU_DESC cd;
237 const CGEN_INSN * insn;
238 CGEN_FIELDS * fields;
239 CGEN_INSN_BYTES_PTR buffer;
240 bfd_vma pc;
241{
242 const CGEN_SYNTAX *syntax = CGEN_INSN_SYNTAX (insn);
243 unsigned long value;
b3466c39 244 const CGEN_SYNTAX_CHAR_TYPE * syn;
252b5132
RH
245
246 CGEN_INIT_INSERT (cd);
247 value = CGEN_INSN_BASE_VALUE (insn);
248
249 /* If we're recording insns as numbers (rather than a string of bytes),
250 target byte order handling is deferred until later. */
251
252#if CGEN_INT_INSN_P
253
6bb95a0f
DB
254 put_insn_int_value (cd, buffer, cd->base_insn_bitsize,
255 CGEN_FIELDS_BITSIZE (fields), value);
252b5132
RH
256
257#else
258
0e2ee3ca 259 cgen_put_insn_value (cd, buffer, min ((unsigned) cd->base_insn_bitsize,
d5b2f4d6 260 (unsigned) CGEN_FIELDS_BITSIZE (fields)),
252b5132
RH
261 value);
262
263#endif /* ! CGEN_INT_INSN_P */
264
265 /* ??? It would be better to scan the format's fields.
266 Still need to be able to insert a value based on the operand though;
267 e.g. storing a branch displacement that got resolved later.
268 Needs more thought first. */
269
b3466c39 270 for (syn = CGEN_SYNTAX_STRING (syntax); * syn; ++ syn)
252b5132
RH
271 {
272 const char *errmsg;
273
274 if (CGEN_SYNTAX_CHAR_P (* syn))
275 continue;
276
277 errmsg = (* cd->insert_operand) (cd, CGEN_SYNTAX_FIELD (*syn),
278 fields, buffer, pc);
279 if (errmsg)
280 return errmsg;
281 }
282
283 return NULL;
284}
6bb95a0f 285
d5b2f4d6 286#if CGEN_INT_INSN_P
6bb95a0f
DB
287/* Cover function to store an insn value into an integral insn. Must go here
288 because it needs <prefix>-desc.h for CGEN_INT_INSN_P. */
289
290static void
291put_insn_int_value (cd, buf, length, insn_length, value)
fc7bc883 292 CGEN_CPU_DESC cd ATTRIBUTE_UNUSED;
6bb95a0f
DB
293 CGEN_INSN_BYTES_PTR buf;
294 int length;
295 int insn_length;
296 CGEN_INSN_INT value;
297{
298 /* For architectures with insns smaller than the base-insn-bitsize,
299 length may be too big. */
300 if (length > insn_length)
301 *buf = value;
302 else
303 {
304 int shift = insn_length - length;
305 /* Written this way to avoid undefined behaviour. */
306 CGEN_INSN_INT mask = (((1L << (length - 1)) - 1) << 1) | 1;
307 *buf = (*buf & ~(mask << shift)) | ((value & mask) << shift);
308 }
309}
d5b2f4d6 310#endif
252b5132
RH
311\f
312/* Operand extraction. */
313
314#if ! CGEN_INT_INSN_P
315
316/* Subroutine of extract_normal.
317 Ensure sufficient bytes are cached in EX_INFO.
318 OFFSET is the offset in bytes from the start of the insn of the value.
319 BYTES is the length of the needed value.
320 Returns 1 for success, 0 for failure. */
321
322static CGEN_INLINE int
323fill_cache (cd, ex_info, offset, bytes, pc)
d5b2f4d6 324 CGEN_CPU_DESC cd ATTRIBUTE_UNUSED;
252b5132
RH
325 CGEN_EXTRACT_INFO *ex_info;
326 int offset, bytes;
327 bfd_vma pc;
328{
329 /* It's doubtful that the middle part has already been fetched so
330 we don't optimize that case. kiss. */
d5b2f4d6 331 unsigned int mask;
252b5132
RH
332 disassemble_info *info = (disassemble_info *) ex_info->dis_info;
333
334 /* First do a quick check. */
335 mask = (1 << bytes) - 1;
336 if (((ex_info->valid >> offset) & mask) == mask)
337 return 1;
338
339 /* Search for the first byte we need to read. */
340 for (mask = 1 << offset; bytes > 0; --bytes, ++offset, mask <<= 1)
341 if (! (mask & ex_info->valid))
342 break;
343
344 if (bytes)
345 {
346 int status;
347
348 pc += offset;
349 status = (*info->read_memory_func)
350 (pc, ex_info->insn_bytes + offset, bytes, info);
351
352 if (status != 0)
353 {
354 (*info->memory_error_func) (status, pc, info);
355 return 0;
356 }
357
358 ex_info->valid |= ((1 << bytes) - 1) << offset;
359 }
360
361 return 1;
362}
363
364/* Subroutine of extract_normal. */
365
366static CGEN_INLINE long
367extract_1 (cd, ex_info, start, length, word_length, bufp, pc)
368 CGEN_CPU_DESC cd;
d5b2f4d6 369 CGEN_EXTRACT_INFO *ex_info ATTRIBUTE_UNUSED;
252b5132
RH
370 int start,length,word_length;
371 unsigned char *bufp;
d5b2f4d6 372 bfd_vma pc ATTRIBUTE_UNUSED;
252b5132 373{
b3466c39 374 unsigned long x;
252b5132 375 int shift;
0e2ee3ca 376#if 0
252b5132 377 int big_p = CGEN_CPU_INSN_ENDIAN (cd) == CGEN_ENDIAN_BIG;
0e2ee3ca 378#endif
e333d2c4
NC
379 x = cgen_get_insn_value (cd, bufp, word_length);
380
252b5132
RH
381 if (CGEN_INSN_LSB0_P)
382 shift = (start + 1) - length;
383 else
384 shift = (word_length - (start + length));
b3466c39 385 return x >> shift;
252b5132
RH
386}
387
388#endif /* ! CGEN_INT_INSN_P */
389
390/* Default extraction routine.
391
392 INSN_VALUE is the first base_insn_bitsize bits of the insn in host order,
393 or sometimes less for cases like the m32r where the base insn size is 32
394 but some insns are 16 bits.
395 ATTRS is a mask of the boolean attributes. We only need `SIGNED',
396 but for generality we take a bitmask of all of them.
397 WORD_OFFSET is the offset in bits from the start of the insn of the value.
398 WORD_LENGTH is the length of the word in bits in which the value resides.
399 START is the starting bit number in the word, architecture origin.
400 LENGTH is the length of VALUE in bits.
401 TOTAL_LENGTH is the total length of the insn in bits.
402
403 Returns 1 for success, 0 for failure. */
404
405/* ??? The return code isn't properly used. wip. */
406
407/* ??? This doesn't handle bfd_vma's. Create another function when
408 necessary. */
409
410static int
411extract_normal (cd, ex_info, insn_value, attrs, word_offset, start, length,
412 word_length, total_length, pc, valuep)
413 CGEN_CPU_DESC cd;
6bb95a0f 414#if ! CGEN_INT_INSN_P
252b5132 415 CGEN_EXTRACT_INFO *ex_info;
6bb95a0f
DB
416#else
417 CGEN_EXTRACT_INFO *ex_info ATTRIBUTE_UNUSED;
418#endif
252b5132
RH
419 CGEN_INSN_INT insn_value;
420 unsigned int attrs;
421 unsigned int word_offset, start, length, word_length, total_length;
6bb95a0f 422#if ! CGEN_INT_INSN_P
252b5132 423 bfd_vma pc;
6bb95a0f
DB
424#else
425 bfd_vma pc ATTRIBUTE_UNUSED;
426#endif
252b5132
RH
427 long *valuep;
428{
fc7bc883 429 long value, mask;
252b5132
RH
430
431 /* If LENGTH is zero, this operand doesn't contribute to the value
432 so give it a standard value of zero. */
433 if (length == 0)
434 {
435 *valuep = 0;
436 return 1;
437 }
438
6bb95a0f 439#if 0
252b5132
RH
440 if (CGEN_INT_INSN_P
441 && word_offset != 0)
442 abort ();
6bb95a0f 443#endif
252b5132
RH
444
445 if (word_length > 32)
446 abort ();
447
448 /* For architectures with insns smaller than the insn-base-bitsize,
449 word_length may be too big. */
450 if (cd->min_insn_bitsize < cd->base_insn_bitsize)
451 {
452 if (word_offset == 0
453 && word_length > total_length)
454 word_length = total_length;
455 }
456
fc7bc883 457 /* Does the value reside in INSN_VALUE, and at the right alignment? */
252b5132 458
fc7bc883 459 if (CGEN_INT_INSN_P || (word_offset == 0 && word_length == total_length))
252b5132 460 {
252b5132 461 if (CGEN_INSN_LSB0_P)
6bb95a0f 462 value = insn_value >> ((word_offset + start + 1) - length);
252b5132 463 else
6bb95a0f 464 value = insn_value >> (total_length - ( word_offset + start + length));
252b5132
RH
465 }
466
467#if ! CGEN_INT_INSN_P
468
469 else
470 {
471 unsigned char *bufp = ex_info->insn_bytes + word_offset / 8;
472
473 if (word_length > 32)
474 abort ();
475
476 if (fill_cache (cd, ex_info, word_offset / 8, word_length / 8, pc) == 0)
477 return 0;
478
479 value = extract_1 (cd, ex_info, start, length, word_length, bufp, pc);
480 }
481
482#endif /* ! CGEN_INT_INSN_P */
483
b3466c39
DB
484 /* Written this way to avoid undefined behaviour. */
485 mask = (((1L << (length - 1)) - 1) << 1) | 1;
486
487 value &= mask;
488 /* sign extend? */
489 if (CGEN_BOOL_ATTR (attrs, CGEN_IFLD_SIGNED)
490 && (value & (1L << (length - 1))))
491 value |= ~mask;
492
252b5132
RH
493 *valuep = value;
494
495 return 1;
496}
497
498/* Default insn extractor.
499
500 INSN_VALUE is the first base_insn_bitsize bits, translated to host order.
501 The extracted fields are stored in FIELDS.
502 EX_INFO is used to handle reading variable length insns.
503 Return the length of the insn in bits, or 0 if no match,
504 or -1 if an error occurs fetching data (memory_error_func will have
505 been called). */
506
507static int
508extract_insn_normal (cd, insn, ex_info, insn_value, fields, pc)
509 CGEN_CPU_DESC cd;
510 const CGEN_INSN *insn;
511 CGEN_EXTRACT_INFO *ex_info;
512 CGEN_INSN_INT insn_value;
513 CGEN_FIELDS *fields;
514 bfd_vma pc;
515{
516 const CGEN_SYNTAX *syntax = CGEN_INSN_SYNTAX (insn);
b3466c39 517 const CGEN_SYNTAX_CHAR_TYPE *syn;
252b5132
RH
518
519 CGEN_FIELDS_BITSIZE (fields) = CGEN_INSN_BITSIZE (insn);
520
521 CGEN_INIT_EXTRACT (cd);
522
523 for (syn = CGEN_SYNTAX_STRING (syntax); *syn; ++syn)
524 {
525 int length;
526
527 if (CGEN_SYNTAX_CHAR_P (*syn))
528 continue;
529
530 length = (* cd->extract_operand) (cd, CGEN_SYNTAX_FIELD (*syn),
531 ex_info, insn_value, fields, pc);
532 if (length <= 0)
533 return length;
534 }
535
536 /* We recognized and successfully extracted this insn. */
537 return CGEN_INSN_BITSIZE (insn);
538}
539\f
540/* machine generated code added here */
541
0e2ee3ca
NC
542const char * fr30_cgen_insert_operand
543 PARAMS ((CGEN_CPU_DESC, int, CGEN_FIELDS *, CGEN_INSN_BYTES_PTR, bfd_vma));
544
252b5132
RH
545/* Main entry point for operand insertion.
546
547 This function is basically just a big switch statement. Earlier versions
548 used tables to look up the function to use, but
549 - if the table contains both assembler and disassembler functions then
550 the disassembler contains much of the assembler and vice-versa,
551 - there's a lot of inlining possibilities as things grow,
552 - using a switch statement avoids the function call overhead.
553
554 This function could be moved into `parse_insn_normal', but keeping it
555 separate makes clear the interface between `parse_insn_normal' and each of
556 the handlers. It's also needed by GAS to insert operands that couldn't be
9a2e995d 557 resolved during parsing. */
252b5132
RH
558
559const char *
560fr30_cgen_insert_operand (cd, opindex, fields, buffer, pc)
561 CGEN_CPU_DESC cd;
562 int opindex;
563 CGEN_FIELDS * fields;
564 CGEN_INSN_BYTES_PTR buffer;
0e2ee3ca 565 bfd_vma pc ATTRIBUTE_UNUSED;
252b5132 566{
eb1b03df 567 const char * errmsg = NULL;
252b5132
RH
568 unsigned int total_length = CGEN_FIELDS_BITSIZE (fields);
569
570 switch (opindex)
571 {
572 case FR30_OPERAND_CRI :
573 errmsg = insert_normal (cd, fields->f_CRi, 0, 16, 12, 4, 16, total_length, buffer);
574 break;
575 case FR30_OPERAND_CRJ :
576 errmsg = insert_normal (cd, fields->f_CRj, 0, 16, 8, 4, 16, total_length, buffer);
577 break;
578 case FR30_OPERAND_R13 :
252b5132
RH
579 break;
580 case FR30_OPERAND_R14 :
252b5132
RH
581 break;
582 case FR30_OPERAND_R15 :
252b5132
RH
583 break;
584 case FR30_OPERAND_RI :
585 errmsg = insert_normal (cd, fields->f_Ri, 0, 0, 12, 4, 16, total_length, buffer);
586 break;
587 case FR30_OPERAND_RIC :
588 errmsg = insert_normal (cd, fields->f_Ric, 0, 16, 12, 4, 16, total_length, buffer);
589 break;
590 case FR30_OPERAND_RJ :
591 errmsg = insert_normal (cd, fields->f_Rj, 0, 0, 8, 4, 16, total_length, buffer);
592 break;
593 case FR30_OPERAND_RJC :
594 errmsg = insert_normal (cd, fields->f_Rjc, 0, 16, 8, 4, 16, total_length, buffer);
595 break;
596 case FR30_OPERAND_RS1 :
597 errmsg = insert_normal (cd, fields->f_Rs1, 0, 0, 8, 4, 16, total_length, buffer);
598 break;
599 case FR30_OPERAND_RS2 :
600 errmsg = insert_normal (cd, fields->f_Rs2, 0, 0, 12, 4, 16, total_length, buffer);
601 break;
602 case FR30_OPERAND_CC :
603 errmsg = insert_normal (cd, fields->f_cc, 0, 0, 4, 4, 16, total_length, buffer);
604 break;
605 case FR30_OPERAND_CCC :
606 errmsg = insert_normal (cd, fields->f_ccc, 0, 16, 0, 8, 16, total_length, buffer);
607 break;
608 case FR30_OPERAND_DIR10 :
609 {
610 long value = fields->f_dir10;
611 value = ((unsigned int) (value) >> (2));
612 errmsg = insert_normal (cd, value, 0, 0, 8, 8, 16, total_length, buffer);
613 }
614 break;
615 case FR30_OPERAND_DIR8 :
616 errmsg = insert_normal (cd, fields->f_dir8, 0, 0, 8, 8, 16, total_length, buffer);
617 break;
618 case FR30_OPERAND_DIR9 :
619 {
620 long value = fields->f_dir9;
621 value = ((unsigned int) (value) >> (1));
622 errmsg = insert_normal (cd, value, 0, 0, 8, 8, 16, total_length, buffer);
623 }
624 break;
625 case FR30_OPERAND_DISP10 :
626 {
627 long value = fields->f_disp10;
628 value = ((int) (value) >> (2));
629 errmsg = insert_normal (cd, value, 0|(1<<CGEN_IFLD_SIGNED), 0, 4, 8, 16, total_length, buffer);
630 }
631 break;
632 case FR30_OPERAND_DISP8 :
633 errmsg = insert_normal (cd, fields->f_disp8, 0|(1<<CGEN_IFLD_SIGNED), 0, 4, 8, 16, total_length, buffer);
634 break;
635 case FR30_OPERAND_DISP9 :
636 {
637 long value = fields->f_disp9;
638 value = ((int) (value) >> (1));
639 errmsg = insert_normal (cd, value, 0|(1<<CGEN_IFLD_SIGNED), 0, 4, 8, 16, total_length, buffer);
640 }
641 break;
642 case FR30_OPERAND_I20 :
643 {
644{
645 FLD (f_i20_4) = ((unsigned int) (FLD (f_i20)) >> (16));
646 FLD (f_i20_16) = ((FLD (f_i20)) & (65535));
647}
648 errmsg = insert_normal (cd, fields->f_i20_4, 0, 0, 8, 4, 16, total_length, buffer);
649 if (errmsg)
650 break;
651 errmsg = insert_normal (cd, fields->f_i20_16, 0, 16, 0, 16, 16, total_length, buffer);
652 if (errmsg)
653 break;
654 }
655 break;
656 case FR30_OPERAND_I32 :
657 errmsg = insert_normal (cd, fields->f_i32, 0|(1<<CGEN_IFLD_SIGN_OPT), 16, 0, 32, 32, total_length, buffer);
658 break;
659 case FR30_OPERAND_I8 :
660 errmsg = insert_normal (cd, fields->f_i8, 0, 0, 4, 8, 16, total_length, buffer);
661 break;
662 case FR30_OPERAND_LABEL12 :
663 {
664 long value = fields->f_rel12;
665 value = ((int) (((value) - (((pc) + (2))))) >> (1));
666 errmsg = insert_normal (cd, value, 0|(1<<CGEN_IFLD_SIGNED)|(1<<CGEN_IFLD_PCREL_ADDR), 0, 5, 11, 16, total_length, buffer);
667 }
668 break;
669 case FR30_OPERAND_LABEL9 :
670 {
671 long value = fields->f_rel9;
672 value = ((int) (((value) - (((pc) + (2))))) >> (1));
673 errmsg = insert_normal (cd, value, 0|(1<<CGEN_IFLD_SIGNED)|(1<<CGEN_IFLD_PCREL_ADDR), 0, 8, 8, 16, total_length, buffer);
674 }
675 break;
676 case FR30_OPERAND_M4 :
677 {
678 long value = fields->f_m4;
679 value = ((value) & (15));
680 errmsg = insert_normal (cd, value, 0, 0, 8, 4, 16, total_length, buffer);
681 }
682 break;
683 case FR30_OPERAND_PS :
252b5132
RH
684 break;
685 case FR30_OPERAND_REGLIST_HI_LD :
686 errmsg = insert_normal (cd, fields->f_reglist_hi_ld, 0, 0, 8, 8, 16, total_length, buffer);
687 break;
688 case FR30_OPERAND_REGLIST_HI_ST :
689 errmsg = insert_normal (cd, fields->f_reglist_hi_st, 0, 0, 8, 8, 16, total_length, buffer);
690 break;
691 case FR30_OPERAND_REGLIST_LOW_LD :
692 errmsg = insert_normal (cd, fields->f_reglist_low_ld, 0, 0, 8, 8, 16, total_length, buffer);
693 break;
694 case FR30_OPERAND_REGLIST_LOW_ST :
695 errmsg = insert_normal (cd, fields->f_reglist_low_st, 0, 0, 8, 8, 16, total_length, buffer);
696 break;
697 case FR30_OPERAND_S10 :
698 {
699 long value = fields->f_s10;
700 value = ((int) (value) >> (2));
701 errmsg = insert_normal (cd, value, 0|(1<<CGEN_IFLD_SIGNED), 0, 8, 8, 16, total_length, buffer);
702 }
703 break;
704 case FR30_OPERAND_U10 :
705 {
706 long value = fields->f_u10;
707 value = ((unsigned int) (value) >> (2));
708 errmsg = insert_normal (cd, value, 0, 0, 8, 8, 16, total_length, buffer);
709 }
710 break;
711 case FR30_OPERAND_U4 :
712 errmsg = insert_normal (cd, fields->f_u4, 0, 0, 8, 4, 16, total_length, buffer);
713 break;
714 case FR30_OPERAND_U4C :
715 errmsg = insert_normal (cd, fields->f_u4c, 0, 0, 12, 4, 16, total_length, buffer);
716 break;
717 case FR30_OPERAND_U8 :
718 errmsg = insert_normal (cd, fields->f_u8, 0, 0, 8, 8, 16, total_length, buffer);
719 break;
720 case FR30_OPERAND_UDISP6 :
721 {
722 long value = fields->f_udisp6;
723 value = ((unsigned int) (value) >> (2));
724 errmsg = insert_normal (cd, value, 0, 0, 8, 4, 16, total_length, buffer);
725 }
726 break;
727
728 default :
729 /* xgettext:c-format */
730 fprintf (stderr, _("Unrecognized field %d while building insn.\n"),
731 opindex);
732 abort ();
733 }
734
735 return errmsg;
736}
737
0e2ee3ca
NC
738int fr30_cgen_extract_operand
739 PARAMS ((CGEN_CPU_DESC, int, CGEN_EXTRACT_INFO *, CGEN_INSN_INT,
740 CGEN_FIELDS *, bfd_vma));
741
252b5132 742/* Main entry point for operand extraction.
eb1b03df
DE
743 The result is <= 0 for error, >0 for success.
744 ??? Actual values aren't well defined right now.
252b5132
RH
745
746 This function is basically just a big switch statement. Earlier versions
747 used tables to look up the function to use, but
748 - if the table contains both assembler and disassembler functions then
749 the disassembler contains much of the assembler and vice-versa,
750 - there's a lot of inlining possibilities as things grow,
751 - using a switch statement avoids the function call overhead.
752
753 This function could be moved into `print_insn_normal', but keeping it
754 separate makes clear the interface between `print_insn_normal' and each of
9a2e995d 755 the handlers. */
252b5132
RH
756
757int
758fr30_cgen_extract_operand (cd, opindex, ex_info, insn_value, fields, pc)
759 CGEN_CPU_DESC cd;
760 int opindex;
761 CGEN_EXTRACT_INFO *ex_info;
762 CGEN_INSN_INT insn_value;
763 CGEN_FIELDS * fields;
764 bfd_vma pc;
765{
eb1b03df
DE
766 /* Assume success (for those operands that are nops). */
767 int length = 1;
252b5132
RH
768 unsigned int total_length = CGEN_FIELDS_BITSIZE (fields);
769
770 switch (opindex)
771 {
772 case FR30_OPERAND_CRI :
773 length = extract_normal (cd, ex_info, insn_value, 0, 16, 12, 4, 16, total_length, pc, & fields->f_CRi);
774 break;
775 case FR30_OPERAND_CRJ :
776 length = extract_normal (cd, ex_info, insn_value, 0, 16, 8, 4, 16, total_length, pc, & fields->f_CRj);
777 break;
778 case FR30_OPERAND_R13 :
252b5132
RH
779 break;
780 case FR30_OPERAND_R14 :
252b5132
RH
781 break;
782 case FR30_OPERAND_R15 :
252b5132
RH
783 break;
784 case FR30_OPERAND_RI :
785 length = extract_normal (cd, ex_info, insn_value, 0, 0, 12, 4, 16, total_length, pc, & fields->f_Ri);
786 break;
787 case FR30_OPERAND_RIC :
788 length = extract_normal (cd, ex_info, insn_value, 0, 16, 12, 4, 16, total_length, pc, & fields->f_Ric);
789 break;
790 case FR30_OPERAND_RJ :
791 length = extract_normal (cd, ex_info, insn_value, 0, 0, 8, 4, 16, total_length, pc, & fields->f_Rj);
792 break;
793 case FR30_OPERAND_RJC :
794 length = extract_normal (cd, ex_info, insn_value, 0, 16, 8, 4, 16, total_length, pc, & fields->f_Rjc);
795 break;
796 case FR30_OPERAND_RS1 :
797 length = extract_normal (cd, ex_info, insn_value, 0, 0, 8, 4, 16, total_length, pc, & fields->f_Rs1);
798 break;
799 case FR30_OPERAND_RS2 :
800 length = extract_normal (cd, ex_info, insn_value, 0, 0, 12, 4, 16, total_length, pc, & fields->f_Rs2);
801 break;
802 case FR30_OPERAND_CC :
803 length = extract_normal (cd, ex_info, insn_value, 0, 0, 4, 4, 16, total_length, pc, & fields->f_cc);
804 break;
805 case FR30_OPERAND_CCC :
806 length = extract_normal (cd, ex_info, insn_value, 0, 16, 0, 8, 16, total_length, pc, & fields->f_ccc);
807 break;
808 case FR30_OPERAND_DIR10 :
809 {
810 long value;
811 length = extract_normal (cd, ex_info, insn_value, 0, 0, 8, 8, 16, total_length, pc, & value);
812 value = ((value) << (2));
813 fields->f_dir10 = value;
814 }
815 break;
816 case FR30_OPERAND_DIR8 :
817 length = extract_normal (cd, ex_info, insn_value, 0, 0, 8, 8, 16, total_length, pc, & fields->f_dir8);
818 break;
819 case FR30_OPERAND_DIR9 :
820 {
821 long value;
822 length = extract_normal (cd, ex_info, insn_value, 0, 0, 8, 8, 16, total_length, pc, & value);
823 value = ((value) << (1));
824 fields->f_dir9 = value;
825 }
826 break;
827 case FR30_OPERAND_DISP10 :
828 {
829 long value;
830 length = extract_normal (cd, ex_info, insn_value, 0|(1<<CGEN_IFLD_SIGNED), 0, 4, 8, 16, total_length, pc, & value);
831 value = ((value) << (2));
832 fields->f_disp10 = value;
833 }
834 break;
835 case FR30_OPERAND_DISP8 :
836 length = extract_normal (cd, ex_info, insn_value, 0|(1<<CGEN_IFLD_SIGNED), 0, 4, 8, 16, total_length, pc, & fields->f_disp8);
837 break;
838 case FR30_OPERAND_DISP9 :
839 {
840 long value;
841 length = extract_normal (cd, ex_info, insn_value, 0|(1<<CGEN_IFLD_SIGNED), 0, 4, 8, 16, total_length, pc, & value);
842 value = ((value) << (1));
843 fields->f_disp9 = value;
844 }
845 break;
846 case FR30_OPERAND_I20 :
847 {
848 length = extract_normal (cd, ex_info, insn_value, 0, 0, 8, 4, 16, total_length, pc, & fields->f_i20_4);
6bb95a0f 849 if (length <= 0) break;
252b5132 850 length = extract_normal (cd, ex_info, insn_value, 0, 16, 0, 16, 16, total_length, pc, & fields->f_i20_16);
6bb95a0f 851 if (length <= 0) break;
252b5132
RH
852{
853 FLD (f_i20) = ((((FLD (f_i20_4)) << (16))) | (FLD (f_i20_16)));
854}
855 }
856 break;
857 case FR30_OPERAND_I32 :
858 length = extract_normal (cd, ex_info, insn_value, 0|(1<<CGEN_IFLD_SIGN_OPT), 16, 0, 32, 32, total_length, pc, & fields->f_i32);
859 break;
860 case FR30_OPERAND_I8 :
861 length = extract_normal (cd, ex_info, insn_value, 0, 0, 4, 8, 16, total_length, pc, & fields->f_i8);
862 break;
863 case FR30_OPERAND_LABEL12 :
864 {
865 long value;
866 length = extract_normal (cd, ex_info, insn_value, 0|(1<<CGEN_IFLD_SIGNED)|(1<<CGEN_IFLD_PCREL_ADDR), 0, 5, 11, 16, total_length, pc, & value);
867 value = ((((value) << (1))) + (((pc) + (2))));
868 fields->f_rel12 = value;
869 }
870 break;
871 case FR30_OPERAND_LABEL9 :
872 {
873 long value;
874 length = extract_normal (cd, ex_info, insn_value, 0|(1<<CGEN_IFLD_SIGNED)|(1<<CGEN_IFLD_PCREL_ADDR), 0, 8, 8, 16, total_length, pc, & value);
875 value = ((((value) << (1))) + (((pc) + (2))));
876 fields->f_rel9 = value;
877 }
878 break;
879 case FR30_OPERAND_M4 :
880 {
881 long value;
882 length = extract_normal (cd, ex_info, insn_value, 0, 0, 8, 4, 16, total_length, pc, & value);
883 value = ((value) | (((-1) << (4))));
884 fields->f_m4 = value;
885 }
886 break;
887 case FR30_OPERAND_PS :
252b5132
RH
888 break;
889 case FR30_OPERAND_REGLIST_HI_LD :
890 length = extract_normal (cd, ex_info, insn_value, 0, 0, 8, 8, 16, total_length, pc, & fields->f_reglist_hi_ld);
891 break;
892 case FR30_OPERAND_REGLIST_HI_ST :
893 length = extract_normal (cd, ex_info, insn_value, 0, 0, 8, 8, 16, total_length, pc, & fields->f_reglist_hi_st);
894 break;
895 case FR30_OPERAND_REGLIST_LOW_LD :
896 length = extract_normal (cd, ex_info, insn_value, 0, 0, 8, 8, 16, total_length, pc, & fields->f_reglist_low_ld);
897 break;
898 case FR30_OPERAND_REGLIST_LOW_ST :
899 length = extract_normal (cd, ex_info, insn_value, 0, 0, 8, 8, 16, total_length, pc, & fields->f_reglist_low_st);
900 break;
901 case FR30_OPERAND_S10 :
902 {
903 long value;
904 length = extract_normal (cd, ex_info, insn_value, 0|(1<<CGEN_IFLD_SIGNED), 0, 8, 8, 16, total_length, pc, & value);
905 value = ((value) << (2));
906 fields->f_s10 = value;
907 }
908 break;
909 case FR30_OPERAND_U10 :
910 {
911 long value;
912 length = extract_normal (cd, ex_info, insn_value, 0, 0, 8, 8, 16, total_length, pc, & value);
913 value = ((value) << (2));
914 fields->f_u10 = value;
915 }
916 break;
917 case FR30_OPERAND_U4 :
918 length = extract_normal (cd, ex_info, insn_value, 0, 0, 8, 4, 16, total_length, pc, & fields->f_u4);
919 break;
920 case FR30_OPERAND_U4C :
921 length = extract_normal (cd, ex_info, insn_value, 0, 0, 12, 4, 16, total_length, pc, & fields->f_u4c);
922 break;
923 case FR30_OPERAND_U8 :
924 length = extract_normal (cd, ex_info, insn_value, 0, 0, 8, 8, 16, total_length, pc, & fields->f_u8);
925 break;
926 case FR30_OPERAND_UDISP6 :
927 {
928 long value;
929 length = extract_normal (cd, ex_info, insn_value, 0, 0, 8, 4, 16, total_length, pc, & value);
930 value = ((value) << (2));
931 fields->f_udisp6 = value;
932 }
933 break;
934
935 default :
936 /* xgettext:c-format */
937 fprintf (stderr, _("Unrecognized field %d while decoding insn.\n"),
938 opindex);
939 abort ();
940 }
941
942 return length;
943}
944
945cgen_insert_fn * const fr30_cgen_insert_handlers[] =
946{
947 insert_insn_normal,
948};
949
950cgen_extract_fn * const fr30_cgen_extract_handlers[] =
951{
952 extract_insn_normal,
953};
954
0e2ee3ca
NC
955int fr30_cgen_get_int_operand
956 PARAMS ((CGEN_CPU_DESC, int, const CGEN_FIELDS *));
957bfd_vma fr30_cgen_get_vma_operand
958 PARAMS ((CGEN_CPU_DESC, int, const CGEN_FIELDS *));
959
252b5132
RH
960/* Getting values from cgen_fields is handled by a collection of functions.
961 They are distinguished by the type of the VALUE argument they return.
962 TODO: floating point, inlining support, remove cases where result type
963 not appropriate. */
964
965int
966fr30_cgen_get_int_operand (cd, opindex, fields)
d5b2f4d6 967 CGEN_CPU_DESC cd ATTRIBUTE_UNUSED;
252b5132
RH
968 int opindex;
969 const CGEN_FIELDS * fields;
970{
971 int value;
972
973 switch (opindex)
974 {
975 case FR30_OPERAND_CRI :
976 value = fields->f_CRi;
977 break;
978 case FR30_OPERAND_CRJ :
979 value = fields->f_CRj;
980 break;
981 case FR30_OPERAND_R13 :
eb1b03df 982 value = 0;
252b5132
RH
983 break;
984 case FR30_OPERAND_R14 :
eb1b03df 985 value = 0;
252b5132
RH
986 break;
987 case FR30_OPERAND_R15 :
eb1b03df 988 value = 0;
252b5132
RH
989 break;
990 case FR30_OPERAND_RI :
991 value = fields->f_Ri;
992 break;
993 case FR30_OPERAND_RIC :
994 value = fields->f_Ric;
995 break;
996 case FR30_OPERAND_RJ :
997 value = fields->f_Rj;
998 break;
999 case FR30_OPERAND_RJC :
1000 value = fields->f_Rjc;
1001 break;
1002 case FR30_OPERAND_RS1 :
1003 value = fields->f_Rs1;
1004 break;
1005 case FR30_OPERAND_RS2 :
1006 value = fields->f_Rs2;
1007 break;
1008 case FR30_OPERAND_CC :
1009 value = fields->f_cc;
1010 break;
1011 case FR30_OPERAND_CCC :
1012 value = fields->f_ccc;
1013 break;
1014 case FR30_OPERAND_DIR10 :
1015 value = fields->f_dir10;
1016 break;
1017 case FR30_OPERAND_DIR8 :
1018 value = fields->f_dir8;
1019 break;
1020 case FR30_OPERAND_DIR9 :
1021 value = fields->f_dir9;
1022 break;
1023 case FR30_OPERAND_DISP10 :
1024 value = fields->f_disp10;
1025 break;
1026 case FR30_OPERAND_DISP8 :
1027 value = fields->f_disp8;
1028 break;
1029 case FR30_OPERAND_DISP9 :
1030 value = fields->f_disp9;
1031 break;
1032 case FR30_OPERAND_I20 :
1033 value = fields->f_i20;
1034 break;
1035 case FR30_OPERAND_I32 :
1036 value = fields->f_i32;
1037 break;
1038 case FR30_OPERAND_I8 :
1039 value = fields->f_i8;
1040 break;
1041 case FR30_OPERAND_LABEL12 :
1042 value = fields->f_rel12;
1043 break;
1044 case FR30_OPERAND_LABEL9 :
1045 value = fields->f_rel9;
1046 break;
1047 case FR30_OPERAND_M4 :
1048 value = fields->f_m4;
1049 break;
1050 case FR30_OPERAND_PS :
eb1b03df 1051 value = 0;
252b5132
RH
1052 break;
1053 case FR30_OPERAND_REGLIST_HI_LD :
1054 value = fields->f_reglist_hi_ld;
1055 break;
1056 case FR30_OPERAND_REGLIST_HI_ST :
1057 value = fields->f_reglist_hi_st;
1058 break;
1059 case FR30_OPERAND_REGLIST_LOW_LD :
1060 value = fields->f_reglist_low_ld;
1061 break;
1062 case FR30_OPERAND_REGLIST_LOW_ST :
1063 value = fields->f_reglist_low_st;
1064 break;
1065 case FR30_OPERAND_S10 :
1066 value = fields->f_s10;
1067 break;
1068 case FR30_OPERAND_U10 :
1069 value = fields->f_u10;
1070 break;
1071 case FR30_OPERAND_U4 :
1072 value = fields->f_u4;
1073 break;
1074 case FR30_OPERAND_U4C :
1075 value = fields->f_u4c;
1076 break;
1077 case FR30_OPERAND_U8 :
1078 value = fields->f_u8;
1079 break;
1080 case FR30_OPERAND_UDISP6 :
1081 value = fields->f_udisp6;
1082 break;
1083
1084 default :
1085 /* xgettext:c-format */
1086 fprintf (stderr, _("Unrecognized field %d while getting int operand.\n"),
1087 opindex);
1088 abort ();
1089 }
1090
1091 return value;
1092}
1093
1094bfd_vma
1095fr30_cgen_get_vma_operand (cd, opindex, fields)
d5b2f4d6 1096 CGEN_CPU_DESC cd ATTRIBUTE_UNUSED;
252b5132
RH
1097 int opindex;
1098 const CGEN_FIELDS * fields;
1099{
1100 bfd_vma value;
1101
1102 switch (opindex)
1103 {
1104 case FR30_OPERAND_CRI :
1105 value = fields->f_CRi;
1106 break;
1107 case FR30_OPERAND_CRJ :
1108 value = fields->f_CRj;
1109 break;
1110 case FR30_OPERAND_R13 :
eb1b03df 1111 value = 0;
252b5132
RH
1112 break;
1113 case FR30_OPERAND_R14 :
eb1b03df 1114 value = 0;
252b5132
RH
1115 break;
1116 case FR30_OPERAND_R15 :
eb1b03df 1117 value = 0;
252b5132
RH
1118 break;
1119 case FR30_OPERAND_RI :
1120 value = fields->f_Ri;
1121 break;
1122 case FR30_OPERAND_RIC :
1123 value = fields->f_Ric;
1124 break;
1125 case FR30_OPERAND_RJ :
1126 value = fields->f_Rj;
1127 break;
1128 case FR30_OPERAND_RJC :
1129 value = fields->f_Rjc;
1130 break;
1131 case FR30_OPERAND_RS1 :
1132 value = fields->f_Rs1;
1133 break;
1134 case FR30_OPERAND_RS2 :
1135 value = fields->f_Rs2;
1136 break;
1137 case FR30_OPERAND_CC :
1138 value = fields->f_cc;
1139 break;
1140 case FR30_OPERAND_CCC :
1141 value = fields->f_ccc;
1142 break;
1143 case FR30_OPERAND_DIR10 :
1144 value = fields->f_dir10;
1145 break;
1146 case FR30_OPERAND_DIR8 :
1147 value = fields->f_dir8;
1148 break;
1149 case FR30_OPERAND_DIR9 :
1150 value = fields->f_dir9;
1151 break;
1152 case FR30_OPERAND_DISP10 :
1153 value = fields->f_disp10;
1154 break;
1155 case FR30_OPERAND_DISP8 :
1156 value = fields->f_disp8;
1157 break;
1158 case FR30_OPERAND_DISP9 :
1159 value = fields->f_disp9;
1160 break;
1161 case FR30_OPERAND_I20 :
1162 value = fields->f_i20;
1163 break;
1164 case FR30_OPERAND_I32 :
1165 value = fields->f_i32;
1166 break;
1167 case FR30_OPERAND_I8 :
1168 value = fields->f_i8;
1169 break;
1170 case FR30_OPERAND_LABEL12 :
1171 value = fields->f_rel12;
1172 break;
1173 case FR30_OPERAND_LABEL9 :
1174 value = fields->f_rel9;
1175 break;
1176 case FR30_OPERAND_M4 :
1177 value = fields->f_m4;
1178 break;
1179 case FR30_OPERAND_PS :
eb1b03df 1180 value = 0;
252b5132
RH
1181 break;
1182 case FR30_OPERAND_REGLIST_HI_LD :
1183 value = fields->f_reglist_hi_ld;
1184 break;
1185 case FR30_OPERAND_REGLIST_HI_ST :
1186 value = fields->f_reglist_hi_st;
1187 break;
1188 case FR30_OPERAND_REGLIST_LOW_LD :
1189 value = fields->f_reglist_low_ld;
1190 break;
1191 case FR30_OPERAND_REGLIST_LOW_ST :
1192 value = fields->f_reglist_low_st;
1193 break;
1194 case FR30_OPERAND_S10 :
1195 value = fields->f_s10;
1196 break;
1197 case FR30_OPERAND_U10 :
1198 value = fields->f_u10;
1199 break;
1200 case FR30_OPERAND_U4 :
1201 value = fields->f_u4;
1202 break;
1203 case FR30_OPERAND_U4C :
1204 value = fields->f_u4c;
1205 break;
1206 case FR30_OPERAND_U8 :
1207 value = fields->f_u8;
1208 break;
1209 case FR30_OPERAND_UDISP6 :
1210 value = fields->f_udisp6;
1211 break;
1212
1213 default :
1214 /* xgettext:c-format */
1215 fprintf (stderr, _("Unrecognized field %d while getting vma operand.\n"),
1216 opindex);
1217 abort ();
1218 }
1219
1220 return value;
1221}
1222
0e2ee3ca
NC
1223void fr30_cgen_set_int_operand
1224 PARAMS ((CGEN_CPU_DESC, int, CGEN_FIELDS *, int));
1225void fr30_cgen_set_vma_operand
1226 PARAMS ((CGEN_CPU_DESC, int, CGEN_FIELDS *, bfd_vma));
1227
252b5132
RH
1228/* Stuffing values in cgen_fields is handled by a collection of functions.
1229 They are distinguished by the type of the VALUE argument they accept.
1230 TODO: floating point, inlining support, remove cases where argument type
1231 not appropriate. */
1232
1233void
1234fr30_cgen_set_int_operand (cd, opindex, fields, value)
d5b2f4d6 1235 CGEN_CPU_DESC cd ATTRIBUTE_UNUSED;
252b5132
RH
1236 int opindex;
1237 CGEN_FIELDS * fields;
1238 int value;
1239{
1240 switch (opindex)
1241 {
1242 case FR30_OPERAND_CRI :
1243 fields->f_CRi = value;
1244 break;
1245 case FR30_OPERAND_CRJ :
1246 fields->f_CRj = value;
1247 break;
1248 case FR30_OPERAND_R13 :
252b5132
RH
1249 break;
1250 case FR30_OPERAND_R14 :
252b5132
RH
1251 break;
1252 case FR30_OPERAND_R15 :
252b5132
RH
1253 break;
1254 case FR30_OPERAND_RI :
1255 fields->f_Ri = value;
1256 break;
1257 case FR30_OPERAND_RIC :
1258 fields->f_Ric = value;
1259 break;
1260 case FR30_OPERAND_RJ :
1261 fields->f_Rj = value;
1262 break;
1263 case FR30_OPERAND_RJC :
1264 fields->f_Rjc = value;
1265 break;
1266 case FR30_OPERAND_RS1 :
1267 fields->f_Rs1 = value;
1268 break;
1269 case FR30_OPERAND_RS2 :
1270 fields->f_Rs2 = value;
1271 break;
1272 case FR30_OPERAND_CC :
1273 fields->f_cc = value;
1274 break;
1275 case FR30_OPERAND_CCC :
1276 fields->f_ccc = value;
1277 break;
1278 case FR30_OPERAND_DIR10 :
1279 fields->f_dir10 = value;
1280 break;
1281 case FR30_OPERAND_DIR8 :
1282 fields->f_dir8 = value;
1283 break;
1284 case FR30_OPERAND_DIR9 :
1285 fields->f_dir9 = value;
1286 break;
1287 case FR30_OPERAND_DISP10 :
1288 fields->f_disp10 = value;
1289 break;
1290 case FR30_OPERAND_DISP8 :
1291 fields->f_disp8 = value;
1292 break;
1293 case FR30_OPERAND_DISP9 :
1294 fields->f_disp9 = value;
1295 break;
1296 case FR30_OPERAND_I20 :
1297 fields->f_i20 = value;
1298 break;
1299 case FR30_OPERAND_I32 :
1300 fields->f_i32 = value;
1301 break;
1302 case FR30_OPERAND_I8 :
1303 fields->f_i8 = value;
1304 break;
1305 case FR30_OPERAND_LABEL12 :
1306 fields->f_rel12 = value;
1307 break;
1308 case FR30_OPERAND_LABEL9 :
1309 fields->f_rel9 = value;
1310 break;
1311 case FR30_OPERAND_M4 :
1312 fields->f_m4 = value;
1313 break;
1314 case FR30_OPERAND_PS :
252b5132
RH
1315 break;
1316 case FR30_OPERAND_REGLIST_HI_LD :
1317 fields->f_reglist_hi_ld = value;
1318 break;
1319 case FR30_OPERAND_REGLIST_HI_ST :
1320 fields->f_reglist_hi_st = value;
1321 break;
1322 case FR30_OPERAND_REGLIST_LOW_LD :
1323 fields->f_reglist_low_ld = value;
1324 break;
1325 case FR30_OPERAND_REGLIST_LOW_ST :
1326 fields->f_reglist_low_st = value;
1327 break;
1328 case FR30_OPERAND_S10 :
1329 fields->f_s10 = value;
1330 break;
1331 case FR30_OPERAND_U10 :
1332 fields->f_u10 = value;
1333 break;
1334 case FR30_OPERAND_U4 :
1335 fields->f_u4 = value;
1336 break;
1337 case FR30_OPERAND_U4C :
1338 fields->f_u4c = value;
1339 break;
1340 case FR30_OPERAND_U8 :
1341 fields->f_u8 = value;
1342 break;
1343 case FR30_OPERAND_UDISP6 :
1344 fields->f_udisp6 = value;
1345 break;
1346
1347 default :
1348 /* xgettext:c-format */
1349 fprintf (stderr, _("Unrecognized field %d while setting int operand.\n"),
1350 opindex);
1351 abort ();
1352 }
1353}
1354
1355void
1356fr30_cgen_set_vma_operand (cd, opindex, fields, value)
d5b2f4d6 1357 CGEN_CPU_DESC cd ATTRIBUTE_UNUSED;
252b5132
RH
1358 int opindex;
1359 CGEN_FIELDS * fields;
1360 bfd_vma value;
1361{
1362 switch (opindex)
1363 {
1364 case FR30_OPERAND_CRI :
1365 fields->f_CRi = value;
1366 break;
1367 case FR30_OPERAND_CRJ :
1368 fields->f_CRj = value;
1369 break;
1370 case FR30_OPERAND_R13 :
252b5132
RH
1371 break;
1372 case FR30_OPERAND_R14 :
252b5132
RH
1373 break;
1374 case FR30_OPERAND_R15 :
252b5132
RH
1375 break;
1376 case FR30_OPERAND_RI :
1377 fields->f_Ri = value;
1378 break;
1379 case FR30_OPERAND_RIC :
1380 fields->f_Ric = value;
1381 break;
1382 case FR30_OPERAND_RJ :
1383 fields->f_Rj = value;
1384 break;
1385 case FR30_OPERAND_RJC :
1386 fields->f_Rjc = value;
1387 break;
1388 case FR30_OPERAND_RS1 :
1389 fields->f_Rs1 = value;
1390 break;
1391 case FR30_OPERAND_RS2 :
1392 fields->f_Rs2 = value;
1393 break;
1394 case FR30_OPERAND_CC :
1395 fields->f_cc = value;
1396 break;
1397 case FR30_OPERAND_CCC :
1398 fields->f_ccc = value;
1399 break;
1400 case FR30_OPERAND_DIR10 :
1401 fields->f_dir10 = value;
1402 break;
1403 case FR30_OPERAND_DIR8 :
1404 fields->f_dir8 = value;
1405 break;
1406 case FR30_OPERAND_DIR9 :
1407 fields->f_dir9 = value;
1408 break;
1409 case FR30_OPERAND_DISP10 :
1410 fields->f_disp10 = value;
1411 break;
1412 case FR30_OPERAND_DISP8 :
1413 fields->f_disp8 = value;
1414 break;
1415 case FR30_OPERAND_DISP9 :
1416 fields->f_disp9 = value;
1417 break;
1418 case FR30_OPERAND_I20 :
1419 fields->f_i20 = value;
1420 break;
1421 case FR30_OPERAND_I32 :
1422 fields->f_i32 = value;
1423 break;
1424 case FR30_OPERAND_I8 :
1425 fields->f_i8 = value;
1426 break;
1427 case FR30_OPERAND_LABEL12 :
1428 fields->f_rel12 = value;
1429 break;
1430 case FR30_OPERAND_LABEL9 :
1431 fields->f_rel9 = value;
1432 break;
1433 case FR30_OPERAND_M4 :
1434 fields->f_m4 = value;
1435 break;
1436 case FR30_OPERAND_PS :
252b5132
RH
1437 break;
1438 case FR30_OPERAND_REGLIST_HI_LD :
1439 fields->f_reglist_hi_ld = value;
1440 break;
1441 case FR30_OPERAND_REGLIST_HI_ST :
1442 fields->f_reglist_hi_st = value;
1443 break;
1444 case FR30_OPERAND_REGLIST_LOW_LD :
1445 fields->f_reglist_low_ld = value;
1446 break;
1447 case FR30_OPERAND_REGLIST_LOW_ST :
1448 fields->f_reglist_low_st = value;
1449 break;
1450 case FR30_OPERAND_S10 :
1451 fields->f_s10 = value;
1452 break;
1453 case FR30_OPERAND_U10 :
1454 fields->f_u10 = value;
1455 break;
1456 case FR30_OPERAND_U4 :
1457 fields->f_u4 = value;
1458 break;
1459 case FR30_OPERAND_U4C :
1460 fields->f_u4c = value;
1461 break;
1462 case FR30_OPERAND_U8 :
1463 fields->f_u8 = value;
1464 break;
1465 case FR30_OPERAND_UDISP6 :
1466 fields->f_udisp6 = value;
1467 break;
1468
1469 default :
1470 /* xgettext:c-format */
1471 fprintf (stderr, _("Unrecognized field %d while setting vma operand.\n"),
1472 opindex);
1473 abort ();
1474 }
1475}
1476
1477/* Function to call before using the instruction builder tables. */
1478
1479void
1480fr30_cgen_init_ibld_table (cd)
1481 CGEN_CPU_DESC cd;
1482{
1483 cd->insert_handlers = & fr30_cgen_insert_handlers[0];
1484 cd->extract_handlers = & fr30_cgen_extract_handlers[0];
1485
1486 cd->insert_operand = fr30_cgen_insert_operand;
1487 cd->extract_operand = fr30_cgen_extract_operand;
1488
1489 cd->get_int_operand = fr30_cgen_get_int_operand;
1490 cd->set_int_operand = fr30_cgen_set_int_operand;
1491 cd->get_vma_operand = fr30_cgen_get_vma_operand;
1492 cd->set_vma_operand = fr30_cgen_set_vma_operand;
1493}
This page took 0.159961 seconds and 4 git commands to generate.