source: trunk/src/binutils/opcodes/fr30-ibld.c@ 1036

Last change on this file since 1036 was 610, checked in by bird, 22 years ago

This commit was generated by cvs2svn to compensate for changes in r609,
which included commits to RCS files with non-trunk default branches.

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