1 /* tc-c30.c -- Assembly code for the Texas Instruments TMS320C30
2    Copyright 1998, 1999, 2000, 2001, 2002 Free Software Foundation, Inc.
3    Contributed by Steven Haworth (steve@pm.cse.rmit.edu.au)
4 
5    This file is part of GAS, the GNU Assembler.
6 
7    GAS is free software; you can redistribute it and/or modify
8    it under the terms of the GNU General Public License as published by
9    the Free Software Foundation; either version 2, or (at your option)
10    any later version.
11 
12    GAS is distributed in the hope that it will be useful,
13    but WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15    GNU General Public License for more details.
16 
17    You should have received a copy of the GNU General Public License
18    along with GAS; see the file COPYING.  If not, write to the Free
19    Software Foundation, 59 Temple Place - Suite 330, Boston, MA
20    02111-1307, USA.  */
21 
22 /* Texas Instruments TMS320C30 machine specific gas.
23    Written by Steven Haworth (steve@pm.cse.rmit.edu.au).
24    Bugs & suggestions are completely welcome.  This is free software.
25    Please help us make it better.  */
26 
27 #include "as.h"
28 #include "safe-ctype.h"
29 #include "opcode/tic30.h"
30 #ifdef ANSI_PROTOTYPES
31 #include <stdarg.h>
32 #else
33 #include <varargs.h>
34 #endif
35 
36 /* Put here all non-digit non-letter characters that may occur in an
37    operand.  */
38 static char operand_special_chars[] = "%$-+(,)*._~/<>&^!:[@]";
39 static char *ordinal_names[] = {
40   "first", "second", "third", "fourth", "fifth"
41 };
42 
43 const int md_reloc_size = 0;
44 
45 const char comment_chars[] = ";";
46 const char line_comment_chars[] = "*";
47 const char line_separator_chars[] = "";
48 
49 const char *md_shortopts = "";
50 struct option md_longopts[] = {
51   {NULL, no_argument, NULL, 0}
52 };
53 
54 size_t md_longopts_size = sizeof (md_longopts);
55 
56 /* Chars that mean this number is a floating point constant.  */
57 /* As in 0f12.456 */
58 /* or    0d1.2345e12 */
59 const char FLT_CHARS[] = "fFdDxX";
60 
61 /* Chars that can be used to separate mant from exp in floating point
62    nums.  */
63 const char EXP_CHARS[] = "eE";
64 
65 /* tables for lexical analysis */
66 static char opcode_chars[256];
67 static char register_chars[256];
68 static char operand_chars[256];
69 static char space_chars[256];
70 static char identifier_chars[256];
71 static char digit_chars[256];
72 
73 /* lexical macros */
74 #define is_opcode_char(x) (opcode_chars[(unsigned char) x])
75 #define is_operand_char(x) (operand_chars[(unsigned char) x])
76 #define is_register_char(x) (register_chars[(unsigned char) x])
77 #define is_space_char(x) (space_chars[(unsigned char) x])
78 #define is_identifier_char(x) (identifier_chars[(unsigned char) x])
79 #define is_digit_char(x) (digit_chars[(unsigned char) x])
80 
81 const pseudo_typeS md_pseudo_table[] = {
82   {0, 0, 0}
83 };
84 
85 int debug PARAMS ((const char *string, ...));
86 
87 int
debug(const char * string,...)88 debug VPARAMS ((const char *string, ...))
89 {
90   if (flag_debug)
91     {
92       char str[100];
93 
94       VA_OPEN (argptr, string);
95       VA_FIXEDARG (argptr, const char *, string);
96       vsprintf (str, string, argptr);
97       VA_CLOSE (argptr);
98       if (str[0] == '\0')
99 	return (0);
100       fputs (str, USE_STDOUT ? stdout : stderr);
101       return strlen (str);
102     }
103   else
104     return 0;
105 }
106 
107 /* hash table for opcode lookup */
108 static struct hash_control *op_hash;
109 /* hash table for parallel opcode lookup */
110 static struct hash_control *parop_hash;
111 /* hash table for register lookup */
112 static struct hash_control *reg_hash;
113 /* hash table for indirect addressing lookup */
114 static struct hash_control *ind_hash;
115 
116 void
md_begin()117 md_begin ()
118 {
119   const char *hash_err;
120   debug ("In md_begin()\n");
121   op_hash = hash_new ();
122   {
123     const template *current_optab = tic30_optab;
124     for (; current_optab < tic30_optab_end; current_optab++)
125       {
126 	hash_err = hash_insert (op_hash, current_optab->name, (char *) current_optab);
127 	if (hash_err)
128 	  as_fatal ("Internal Error: Can't Hash %s: %s", current_optab->name, hash_err);
129       }
130   }
131   parop_hash = hash_new ();
132   {
133     const partemplate *current_parop = tic30_paroptab;
134     for (; current_parop < tic30_paroptab_end; current_parop++)
135       {
136 	hash_err = hash_insert (parop_hash, current_parop->name, (char *) current_parop);
137 	if (hash_err)
138 	  as_fatal ("Internal Error: Can't Hash %s: %s", current_parop->name, hash_err);
139       }
140   }
141   reg_hash = hash_new ();
142   {
143     const reg *current_reg = tic30_regtab;
144     for (; current_reg < tic30_regtab_end; current_reg++)
145       {
146 	hash_err = hash_insert (reg_hash, current_reg->name, (char *) current_reg);
147 	if (hash_err)
148 	  as_fatal ("Internal Error: Can't Hash %s: %s", current_reg->name, hash_err);
149       }
150   }
151   ind_hash = hash_new ();
152   {
153     const ind_addr_type *current_ind = tic30_indaddr_tab;
154     for (; current_ind < tic30_indaddrtab_end; current_ind++)
155       {
156 	hash_err = hash_insert (ind_hash, current_ind->syntax, (char *) current_ind);
157 	if (hash_err)
158 	  as_fatal ("Internal Error: Can't Hash %s: %s", current_ind->syntax, hash_err);
159       }
160   }
161   /* fill in lexical tables:  opcode_chars, operand_chars, space_chars */
162   {
163     register int c;
164     register char *p;
165 
166     for (c = 0; c < 256; c++)
167       {
168 	if (ISLOWER (c) || ISDIGIT (c))
169 	  {
170 	    opcode_chars[c] = c;
171 	    register_chars[c] = c;
172 	  }
173 	else if (ISUPPER (c))
174 	  {
175 	    opcode_chars[c] = TOLOWER (c);
176 	    register_chars[c] = opcode_chars[c];
177 	  }
178 	else if (c == ')' || c == '(')
179 	  {
180 	    register_chars[c] = c;
181 	  }
182 	if (ISUPPER (c) || ISLOWER (c) || ISDIGIT (c))
183 	  operand_chars[c] = c;
184 	if (ISDIGIT (c) || c == '-')
185 	  digit_chars[c] = c;
186 	if (ISALPHA (c) || c == '_' || c == '.' || ISDIGIT (c))
187 	  identifier_chars[c] = c;
188 	if (c == ' ' || c == '\t')
189 	  space_chars[c] = c;
190 	if (c == '_')
191 	  opcode_chars[c] = c;
192       }
193     for (p = operand_special_chars; *p != '\0'; p++)
194       operand_chars[(unsigned char) *p] = *p;
195   }
196 }
197 
198 /* Address Mode OR values */
199 #define AM_Register  0x00000000
200 #define AM_Direct    0x00200000
201 #define AM_Indirect  0x00400000
202 #define AM_Immediate 0x00600000
203 #define AM_NotReq    0xFFFFFFFF
204 
205 /* PC Relative OR values */
206 #define PC_Register 0x00000000
207 #define PC_Relative 0x02000000
208 
209 typedef struct {
210   unsigned op_type;
211   struct {
212     int resolved;
213     unsigned address;
214     char *label;
215     expressionS direct_expr;
216   } direct;
217   struct {
218     unsigned mod;
219     int ARnum;
220     unsigned char disp;
221   } indirect;
222   struct {
223     unsigned opcode;
224   } reg;
225   struct {
226     int resolved;
227     int decimal_found;
228     float f_number;
229     int s_number;
230     unsigned int u_number;
231     char *label;
232     expressionS imm_expr;
233   } immediate;
234 } operand;
235 
236 int tic30_parallel_insn PARAMS ((char *));
237 operand *tic30_operand PARAMS ((char *));
238 char *tic30_find_parallel_insn PARAMS ((char *, char *));
239 
240 template *opcode;
241 
242 struct tic30_insn {
243   template *tm;			/* Template of current instruction */
244   unsigned opcode;		/* Final opcode */
245   unsigned int operands;	/* Number of given operands */
246   /* Type of operand given in instruction */
247   operand *operand_type[MAX_OPERANDS];
248   unsigned addressing_mode;	/* Final addressing mode of instruction */
249 };
250 
251 struct tic30_insn insn;
252 static int found_parallel_insn;
253 
254 void
md_assemble(line)255 md_assemble (line)
256      char *line;
257 {
258   template *opcode;
259   char *current_posn;
260   char *token_start;
261   char save_char;
262   unsigned int count;
263 
264   debug ("In md_assemble() with argument %s\n", line);
265   memset (&insn, '\0', sizeof (insn));
266   if (found_parallel_insn)
267     {
268       debug ("Line is second part of parallel instruction\n\n");
269       found_parallel_insn = 0;
270       return;
271     }
272   if ((current_posn = tic30_find_parallel_insn (line, input_line_pointer + 1)) == NULL)
273     current_posn = line;
274   else
275     found_parallel_insn = 1;
276   while (is_space_char (*current_posn))
277     current_posn++;
278   token_start = current_posn;
279   if (!is_opcode_char (*current_posn))
280     {
281       as_bad ("Invalid character %s in opcode", output_invalid (*current_posn));
282       return;
283     }
284   /* Check if instruction is a parallel instruction by seeing if the first
285      character is a q.  */
286   if (*token_start == 'q')
287     {
288       if (tic30_parallel_insn (token_start))
289 	{
290 	  if (found_parallel_insn)
291 	    free (token_start);
292 	  return;
293 	}
294     }
295   while (is_opcode_char (*current_posn))
296     current_posn++;
297   {				/* Find instruction */
298     save_char = *current_posn;
299     *current_posn = '\0';
300     opcode = (template *) hash_find (op_hash, token_start);
301     if (opcode)
302       {
303 	debug ("Found instruction %s\n", opcode->name);
304 	insn.tm = opcode;
305       }
306     else
307       {
308 	debug ("Didn't find insn\n");
309 	as_bad ("Unknown TMS320C30 instruction: %s", token_start);
310 	return;
311       }
312     *current_posn = save_char;
313   }
314   if (*current_posn != END_OF_INSN)
315     {				/* Find operands */
316       int paren_not_balanced;
317       int expecting_operand = 0;
318       int this_operand;
319       do
320 	{
321 	  /* skip optional white space before operand */
322 	  while (!is_operand_char (*current_posn) && *current_posn != END_OF_INSN)
323 	    {
324 	      if (!is_space_char (*current_posn))
325 		{
326 		  as_bad ("Invalid character %s before %s operand",
327 			  output_invalid (*current_posn),
328 			  ordinal_names[insn.operands]);
329 		  return;
330 		}
331 	      current_posn++;
332 	    }
333 	  token_start = current_posn;	/* after white space */
334 	  paren_not_balanced = 0;
335 	  while (paren_not_balanced || *current_posn != ',')
336 	    {
337 	      if (*current_posn == END_OF_INSN)
338 		{
339 		  if (paren_not_balanced)
340 		    {
341 		      as_bad ("Unbalanced parenthesis in %s operand.",
342 			      ordinal_names[insn.operands]);
343 		      return;
344 		    }
345 		  else
346 		    break;	/* we are done */
347 		}
348 	      else if (!is_operand_char (*current_posn) && !is_space_char (*current_posn))
349 		{
350 		  as_bad ("Invalid character %s in %s operand",
351 			  output_invalid (*current_posn),
352 			  ordinal_names[insn.operands]);
353 		  return;
354 		}
355 	      if (*current_posn == '(')
356 		++paren_not_balanced;
357 	      if (*current_posn == ')')
358 		--paren_not_balanced;
359 	      current_posn++;
360 	    }
361 	  if (current_posn != token_start)
362 	    {			/* yes, we've read in another operand */
363 	      this_operand = insn.operands++;
364 	      if (insn.operands > MAX_OPERANDS)
365 		{
366 		  as_bad ("Spurious operands; (%d operands/instruction max)",
367 			  MAX_OPERANDS);
368 		  return;
369 		}
370 	      /* now parse operand adding info to 'insn' as we go along */
371 	      save_char = *current_posn;
372 	      *current_posn = '\0';
373 	      insn.operand_type[this_operand] = tic30_operand (token_start);
374 	      *current_posn = save_char;
375 	      if (insn.operand_type[this_operand] == NULL)
376 		return;
377 	    }
378 	  else
379 	    {
380 	      if (expecting_operand)
381 		{
382 		  as_bad ("Expecting operand after ','; got nothing");
383 		  return;
384 		}
385 	      if (*current_posn == ',')
386 		{
387 		  as_bad ("Expecting operand before ','; got nothing");
388 		  return;
389 		}
390 	    }
391 	  /* now *current_posn must be either ',' or END_OF_INSN */
392 	  if (*current_posn == ',')
393 	    {
394 	      if (*++current_posn == END_OF_INSN)
395 		{		/* just skip it, if it's \n complain */
396 		  as_bad ("Expecting operand after ','; got nothing");
397 		  return;
398 		}
399 	      expecting_operand = 1;
400 	    }
401 	}
402       while (*current_posn != END_OF_INSN);	/* until we get end of insn */
403     }
404   debug ("Number of operands found: %d\n", insn.operands);
405   /* Check that number of operands is correct */
406   if (insn.operands != insn.tm->operands)
407     {
408       unsigned int i;
409       unsigned int numops = insn.tm->operands;
410       /* If operands are not the same, then see if any of the operands are not
411          required.  Then recheck with number of given operands.  If they are still not
412          the same, then give an error, otherwise carry on.  */
413       for (i = 0; i < insn.tm->operands; i++)
414 	if (insn.tm->operand_types[i] & NotReq)
415 	  numops--;
416       if (insn.operands != numops)
417 	{
418 	  as_bad ("Incorrect number of operands given");
419 	  return;
420 	}
421     }
422   insn.addressing_mode = AM_NotReq;
423   for (count = 0; count < insn.operands; count++)
424     {
425       if (insn.operand_type[count]->op_type & insn.tm->operand_types[count])
426 	{
427 	  debug ("Operand %d matches\n", count + 1);
428 	  /* If instruction has two operands and has an AddressMode modifier then set
429 	     addressing mode type for instruction */
430 	  if (insn.tm->opcode_modifier == AddressMode)
431 	    {
432 	      int addr_insn = 0;
433 	      /* Store instruction uses the second operand for the address mode.  */
434 	      if ((insn.tm->operand_types[1] & (Indirect | Direct)) == (Indirect | Direct))
435 		addr_insn = 1;
436 	      if (insn.operand_type[addr_insn]->op_type & (AllReg))
437 		insn.addressing_mode = AM_Register;
438 	      else if (insn.operand_type[addr_insn]->op_type & Direct)
439 		insn.addressing_mode = AM_Direct;
440 	      else if (insn.operand_type[addr_insn]->op_type & Indirect)
441 		insn.addressing_mode = AM_Indirect;
442 	      else
443 		insn.addressing_mode = AM_Immediate;
444 	    }
445 	}
446       else
447 	{
448 	  as_bad ("The %s operand doesn't match", ordinal_names[count]);
449 	  return;
450 	}
451     }
452   /* Now set the addressing mode for 3 operand instructions.  */
453   if ((insn.tm->operand_types[0] & op3T1) && (insn.tm->operand_types[1] & op3T2))
454     {
455       /* Set the addressing mode to the values used for 2 operand instructions in the
456          G addressing field of the opcode.  */
457       char *p;
458       switch (insn.operand_type[0]->op_type)
459 	{
460 	case Rn:
461 	case ARn:
462 	case DPReg:
463 	case OtherReg:
464 	  if (insn.operand_type[1]->op_type & (AllReg))
465 	    insn.addressing_mode = AM_Register;
466 	  else if (insn.operand_type[1]->op_type & Indirect)
467 	    insn.addressing_mode = AM_Direct;
468 	  else
469 	    {
470 	      /* Shouldn't make it to this stage */
471 	      as_bad ("Incompatible first and second operands in instruction");
472 	      return;
473 	    }
474 	  break;
475 	case Indirect:
476 	  if (insn.operand_type[1]->op_type & (AllReg))
477 	    insn.addressing_mode = AM_Indirect;
478 	  else if (insn.operand_type[1]->op_type & Indirect)
479 	    insn.addressing_mode = AM_Immediate;
480 	  else
481 	    {
482 	      /* Shouldn't make it to this stage */
483 	      as_bad ("Incompatible first and second operands in instruction");
484 	      return;
485 	    }
486 	  break;
487 	}
488       /* Now make up the opcode for the 3 operand instructions.  As in parallel
489          instructions, there will be no unresolved values, so they can be fully formed
490          and added to the frag table.  */
491       insn.opcode = insn.tm->base_opcode;
492       if (insn.operand_type[0]->op_type & Indirect)
493 	{
494 	  insn.opcode |= (insn.operand_type[0]->indirect.ARnum);
495 	  insn.opcode |= (insn.operand_type[0]->indirect.mod << 3);
496 	}
497       else
498 	insn.opcode |= (insn.operand_type[0]->reg.opcode);
499       if (insn.operand_type[1]->op_type & Indirect)
500 	{
501 	  insn.opcode |= (insn.operand_type[1]->indirect.ARnum << 8);
502 	  insn.opcode |= (insn.operand_type[1]->indirect.mod << 11);
503 	}
504       else
505 	insn.opcode |= (insn.operand_type[1]->reg.opcode << 8);
506       if (insn.operands == 3)
507 	insn.opcode |= (insn.operand_type[2]->reg.opcode << 16);
508       insn.opcode |= insn.addressing_mode;
509       p = frag_more (INSN_SIZE);
510       md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
511     }
512   else
513     {				/* Not a three operand instruction */
514       char *p;
515       int am_insn = -1;
516       insn.opcode = insn.tm->base_opcode;
517       /* Create frag for instruction - all instructions are 4 bytes long.  */
518       p = frag_more (INSN_SIZE);
519       if ((insn.operands > 0) && (insn.tm->opcode_modifier == AddressMode))
520 	{
521 	  insn.opcode |= insn.addressing_mode;
522 	  if (insn.addressing_mode == AM_Indirect)
523 	    {
524 	      /* Determine which operand gives the addressing mode */
525 	      if (insn.operand_type[0]->op_type & Indirect)
526 		am_insn = 0;
527 	      if ((insn.operands > 1) && (insn.operand_type[1]->op_type & Indirect))
528 		am_insn = 1;
529 	      insn.opcode |= (insn.operand_type[am_insn]->indirect.disp);
530 	      insn.opcode |= (insn.operand_type[am_insn]->indirect.ARnum << 8);
531 	      insn.opcode |= (insn.operand_type[am_insn]->indirect.mod << 11);
532 	      if (insn.operands > 1)
533 		insn.opcode |= (insn.operand_type[!am_insn]->reg.opcode << 16);
534 	      md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
535 	    }
536 	  else if (insn.addressing_mode == AM_Register)
537 	    {
538 	      insn.opcode |= (insn.operand_type[0]->reg.opcode);
539 	      if (insn.operands > 1)
540 		insn.opcode |= (insn.operand_type[1]->reg.opcode << 16);
541 	      md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
542 	    }
543 	  else if (insn.addressing_mode == AM_Direct)
544 	    {
545 	      if (insn.operand_type[0]->op_type & Direct)
546 		am_insn = 0;
547 	      if ((insn.operands > 1) && (insn.operand_type[1]->op_type & Direct))
548 		am_insn = 1;
549 	      if (insn.operands > 1)
550 		insn.opcode |= (insn.operand_type[!am_insn]->reg.opcode << 16);
551 	      if (insn.operand_type[am_insn]->direct.resolved == 1)
552 		{
553 		  /* Resolved values can be placed straight into instruction word, and output */
554 		  insn.opcode |= (insn.operand_type[am_insn]->direct.address & 0x0000FFFF);
555 		  md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
556 		}
557 	      else
558 		{		/* Unresolved direct addressing mode instruction */
559 		  md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
560 		  fix_new_exp (frag_now, p + 2 - (frag_now->fr_literal), 2, &insn.operand_type[am_insn]->direct.direct_expr, 0, 0);
561 		}
562 	    }
563 	  else if (insn.addressing_mode == AM_Immediate)
564 	    {
565 	      if (insn.operand_type[0]->immediate.resolved == 1)
566 		{
567 		  char *keeploc;
568 		  int size;
569 		  if (insn.operands > 1)
570 		    insn.opcode |= (insn.operand_type[1]->reg.opcode << 16);
571 		  switch (insn.tm->imm_arg_type)
572 		    {
573 		    case Imm_Float:
574 		      debug ("Floating point first operand\n");
575 		      md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
576 		      keeploc = input_line_pointer;
577 		      input_line_pointer = insn.operand_type[0]->immediate.label;
578 		      if (md_atof ('f', p + 2, &size) != 0)
579 			{
580 			  as_bad ("invalid short form floating point immediate operand");
581 			  return;
582 			}
583 		      input_line_pointer = keeploc;
584 		      break;
585 		    case Imm_UInt:
586 		      debug ("Unsigned int first operand\n");
587 		      if (insn.operand_type[0]->immediate.decimal_found)
588 			as_warn ("rounding down first operand float to unsigned int");
589 		      if (insn.operand_type[0]->immediate.u_number > 0xFFFF)
590 			as_warn ("only lower 16-bits of first operand are used");
591 		      insn.opcode |= (insn.operand_type[0]->immediate.u_number & 0x0000FFFFL);
592 		      md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
593 		      break;
594 		    case Imm_SInt:
595 		      debug ("Int first operand\n");
596 		      if (insn.operand_type[0]->immediate.decimal_found)
597 			as_warn ("rounding down first operand float to signed int");
598 		      if (insn.operand_type[0]->immediate.s_number < -32768 ||
599 			  insn.operand_type[0]->immediate.s_number > 32767)
600 			{
601 			  as_bad ("first operand is too large for 16-bit signed int");
602 			  return;
603 			}
604 		      insn.opcode |= (insn.operand_type[0]->immediate.s_number & 0x0000FFFFL);
605 		      md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
606 		      break;
607 		    }
608 		}
609 	      else
610 		{		/* Unresolved immediate label */
611 		  if (insn.operands > 1)
612 		    insn.opcode |= (insn.operand_type[1]->reg.opcode << 16);
613 		  md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
614 		  fix_new_exp (frag_now, p + 2 - (frag_now->fr_literal), 2, &insn.operand_type[0]->immediate.imm_expr, 0, 0);
615 		}
616 	    }
617 	}
618       else if (insn.tm->opcode_modifier == PCRel)
619 	{
620 	  /* Conditional Branch and Call instructions */
621 	  if ((insn.tm->operand_types[0] & (AllReg | Disp)) == (AllReg | Disp))
622 	    {
623 	      if (insn.operand_type[0]->op_type & (AllReg))
624 		{
625 		  insn.opcode |= (insn.operand_type[0]->reg.opcode);
626 		  insn.opcode |= PC_Register;
627 		  md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
628 		}
629 	      else
630 		{
631 		  insn.opcode |= PC_Relative;
632 		  if (insn.operand_type[0]->immediate.resolved == 1)
633 		    {
634 		      insn.opcode |= (insn.operand_type[0]->immediate.s_number & 0x0000FFFF);
635 		      md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
636 		    }
637 		  else
638 		    {
639 		      md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
640 		      fix_new_exp (frag_now, p + 2 - (frag_now->fr_literal), 2, &insn.operand_type[0]->immediate.imm_expr, 1, 0);
641 		    }
642 		}
643 	    }
644 	  else if ((insn.tm->operand_types[0] & ARn) == ARn)
645 	    {
646 	      /* Decrement and Branch instructions */
647 	      insn.opcode |= ((insn.operand_type[0]->reg.opcode - 0x08) << 22);
648 	      if (insn.operand_type[1]->op_type & (AllReg))
649 		{
650 		  insn.opcode |= (insn.operand_type[1]->reg.opcode);
651 		  insn.opcode |= PC_Register;
652 		  md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
653 		}
654 	      else if (insn.operand_type[1]->immediate.resolved == 1)
655 		{
656 		  if (insn.operand_type[0]->immediate.decimal_found)
657 		    {
658 		      as_bad ("first operand is floating point");
659 		      return;
660 		    }
661 		  if (insn.operand_type[0]->immediate.s_number < -32768 ||
662 		      insn.operand_type[0]->immediate.s_number > 32767)
663 		    {
664 		      as_bad ("first operand is too large for 16-bit signed int");
665 		      return;
666 		    }
667 		  insn.opcode |= (insn.operand_type[1]->immediate.s_number);
668 		  insn.opcode |= PC_Relative;
669 		  md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
670 		}
671 	      else
672 		{
673 		  insn.opcode |= PC_Relative;
674 		  md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
675 		  fix_new_exp (frag_now, p + 2 - frag_now->fr_literal, 2, &insn.operand_type[1]->immediate.imm_expr, 1, 0);
676 		}
677 	    }
678 	}
679       else if (insn.tm->operand_types[0] == IVector)
680 	{
681 	  /* Trap instructions */
682 	  if (insn.operand_type[0]->op_type & IVector)
683 	    insn.opcode |= (insn.operand_type[0]->immediate.u_number);
684 	  else
685 	    {			/* Shouldn't get here */
686 	      as_bad ("interrupt vector for trap instruction out of range");
687 	      return;
688 	    }
689 	  md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
690 	}
691       else if (insn.tm->opcode_modifier == StackOp || insn.tm->opcode_modifier == Rotate)
692 	{
693 	  /* Push, Pop and Rotate instructions */
694 	  insn.opcode |= (insn.operand_type[0]->reg.opcode << 16);
695 	  md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
696 	}
697       else if ((insn.tm->operand_types[0] & (Abs24 | Direct)) == (Abs24 | Direct))
698 	{
699 	  /* LDP Instruction needs to be tested for before the next section */
700 	  if (insn.operand_type[0]->op_type & Direct)
701 	    {
702 	      if (insn.operand_type[0]->direct.resolved == 1)
703 		{
704 		  /* Direct addressing uses lower 8 bits of direct address */
705 		  insn.opcode |= (insn.operand_type[0]->direct.address & 0x00FF0000) >> 16;
706 		  md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
707 		}
708 	      else
709 		{
710 		  fixS *fix;
711 		  md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
712 		  fix = fix_new_exp (frag_now, p + 3 - (frag_now->fr_literal), 1, &insn.operand_type[0]->direct.direct_expr, 0, 0);
713 		  /* Ensure that the assembler doesn't complain about fitting a 24-bit
714 		     address into 8 bits.  */
715 		  fix->fx_no_overflow = 1;
716 		}
717 	    }
718 	  else
719 	    {
720 	      if (insn.operand_type[0]->immediate.resolved == 1)
721 		{
722 		  /* Immediate addressing uses upper 8 bits of address */
723 		  if (insn.operand_type[0]->immediate.u_number > 0x00FFFFFF)
724 		    {
725 		      as_bad ("LDP instruction needs a 24-bit operand");
726 		      return;
727 		    }
728 		  insn.opcode |= ((insn.operand_type[0]->immediate.u_number & 0x00FF0000) >> 16);
729 		  md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
730 		}
731 	      else
732 		{
733 		  fixS *fix;
734 		  md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
735 		  fix = fix_new_exp (frag_now, p + 3 - (frag_now->fr_literal), 1, &insn.operand_type[0]->immediate.imm_expr, 0, 0);
736 		  fix->fx_no_overflow = 1;
737 		}
738 	    }
739 	}
740       else if (insn.tm->operand_types[0] & (Imm24))
741 	{
742 	  /* Unconditional Branch and Call instructions */
743 	  if (insn.operand_type[0]->immediate.resolved == 1)
744 	    {
745 	      if (insn.operand_type[0]->immediate.u_number > 0x00FFFFFF)
746 		as_warn ("first operand is too large for a 24-bit displacement");
747 	      insn.opcode |= (insn.operand_type[0]->immediate.u_number & 0x00FFFFFF);
748 	      md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
749 	    }
750 	  else
751 	    {
752 	      md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
753 	      fix_new_exp (frag_now, p + 1 - (frag_now->fr_literal), 3, &insn.operand_type[0]->immediate.imm_expr, 0, 0);
754 	    }
755 	}
756       else if (insn.tm->operand_types[0] & NotReq)
757 	{
758 	  /* Check for NOP instruction without arguments.  */
759 	  md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
760 	}
761       else if (insn.tm->operands == 0)
762 	{
763 	  /* Check for instructions without operands.  */
764 	  md_number_to_chars (p, (valueT) insn.opcode, INSN_SIZE);
765 	}
766     }
767   debug ("Addressing mode: %08X\n", insn.addressing_mode);
768   {
769     unsigned int i;
770     for (i = 0; i < insn.operands; i++)
771       {
772 	if (insn.operand_type[i]->immediate.label)
773 	  free (insn.operand_type[i]->immediate.label);
774 	free (insn.operand_type[i]);
775       }
776   }
777   debug ("Final opcode: %08X\n", insn.opcode);
778   debug ("\n");
779 }
780 
781 struct tic30_par_insn {
782   partemplate *tm;		/* Template of current parallel instruction */
783   unsigned operands[2];		/* Number of given operands for each insn */
784   /* Type of operand given in instruction */
785   operand *operand_type[2][MAX_OPERANDS];
786   int swap_operands;		/* Whether to swap operands around.  */
787   unsigned p_field;		/* Value of p field in multiply add/sub instructions */
788   unsigned opcode;		/* Final opcode */
789 };
790 
791 struct tic30_par_insn p_insn;
792 
793 int
tic30_parallel_insn(char * token)794 tic30_parallel_insn (char *token)
795 {
796   static partemplate *p_opcode;
797   char *current_posn = token;
798   char *token_start;
799   char save_char;
800 
801   debug ("In tic30_parallel_insn with %s\n", token);
802   memset (&p_insn, '\0', sizeof (p_insn));
803   while (is_opcode_char (*current_posn))
804     current_posn++;
805   {				/* Find instruction */
806     save_char = *current_posn;
807     *current_posn = '\0';
808     p_opcode = (partemplate *) hash_find (parop_hash, token);
809     if (p_opcode)
810       {
811 	debug ("Found instruction %s\n", p_opcode->name);
812 	p_insn.tm = p_opcode;
813       }
814     else
815       {
816 	char first_opcode[6] =
817 	{0};
818 	char second_opcode[6] =
819 	{0};
820 	unsigned int i;
821 	int current_opcode = -1;
822 	int char_ptr = 0;
823 
824 	for (i = 0; i < strlen (token); i++)
825 	  {
826 	    char ch = *(token + i);
827 	    if (ch == '_' && current_opcode == -1)
828 	      {
829 		current_opcode = 0;
830 		continue;
831 	      }
832 	    if (ch == '_' && current_opcode == 0)
833 	      {
834 		current_opcode = 1;
835 		char_ptr = 0;
836 		continue;
837 	      }
838 	    switch (current_opcode)
839 	      {
840 	      case 0:
841 		first_opcode[char_ptr++] = ch;
842 		break;
843 	      case 1:
844 		second_opcode[char_ptr++] = ch;
845 		break;
846 	      }
847 	  }
848 	debug ("first_opcode = %s\n", first_opcode);
849 	debug ("second_opcode = %s\n", second_opcode);
850 	sprintf (token, "q_%s_%s", second_opcode, first_opcode);
851 	p_opcode = (partemplate *) hash_find (parop_hash, token);
852 	if (p_opcode)
853 	  {
854 	    debug ("Found instruction %s\n", p_opcode->name);
855 	    p_insn.tm = p_opcode;
856 	    p_insn.swap_operands = 1;
857 	  }
858 	else
859 	  return 0;
860       }
861     *current_posn = save_char;
862   }
863   {				/* Find operands */
864     int paren_not_balanced;
865     int expecting_operand = 0;
866     int found_separator = 0;
867     do
868       {
869 	/* skip optional white space before operand */
870 	while (!is_operand_char (*current_posn) && *current_posn != END_OF_INSN)
871 	  {
872 	    if (!is_space_char (*current_posn) && *current_posn != PARALLEL_SEPARATOR)
873 	      {
874 		as_bad ("Invalid character %s before %s operand",
875 			output_invalid (*current_posn),
876 			ordinal_names[insn.operands]);
877 		return 1;
878 	      }
879 	    if (*current_posn == PARALLEL_SEPARATOR)
880 	      found_separator = 1;
881 	    current_posn++;
882 	  }
883 	token_start = current_posn;	/* after white space */
884 	paren_not_balanced = 0;
885 	while (paren_not_balanced || *current_posn != ',')
886 	  {
887 	    if (*current_posn == END_OF_INSN)
888 	      {
889 		if (paren_not_balanced)
890 		  {
891 		    as_bad ("Unbalanced parenthesis in %s operand.",
892 			    ordinal_names[insn.operands]);
893 		    return 1;
894 		  }
895 		else
896 		  break;	/* we are done */
897 	      }
898 	    else if (*current_posn == PARALLEL_SEPARATOR)
899 	      {
900 		while (is_space_char (*(current_posn - 1)))
901 		  current_posn--;
902 		break;
903 	      }
904 	    else if (!is_operand_char (*current_posn) && !is_space_char (*current_posn))
905 	      {
906 		as_bad ("Invalid character %s in %s operand",
907 			output_invalid (*current_posn),
908 			ordinal_names[insn.operands]);
909 		return 1;
910 	      }
911 	    if (*current_posn == '(')
912 	      ++paren_not_balanced;
913 	    if (*current_posn == ')')
914 	      --paren_not_balanced;
915 	    current_posn++;
916 	  }
917 	if (current_posn != token_start)
918 	  {			/* yes, we've read in another operand */
919 	    p_insn.operands[found_separator]++;
920 	    if (p_insn.operands[found_separator] > MAX_OPERANDS)
921 	      {
922 		as_bad ("Spurious operands; (%d operands/instruction max)",
923 			MAX_OPERANDS);
924 		return 1;
925 	      }
926 	    /* now parse operand adding info to 'insn' as we go along */
927 	    save_char = *current_posn;
928 	    *current_posn = '\0';
929 	    p_insn.operand_type[found_separator][p_insn.operands[found_separator] - 1] =
930 	      tic30_operand (token_start);
931 	    *current_posn = save_char;
932 	    if (!p_insn.operand_type[found_separator][p_insn.operands[found_separator] - 1])
933 	      return 1;
934 	  }
935 	else
936 	  {
937 	    if (expecting_operand)
938 	      {
939 		as_bad ("Expecting operand after ','; got nothing");
940 		return 1;
941 	      }
942 	    if (*current_posn == ',')
943 	      {
944 		as_bad ("Expecting operand before ','; got nothing");
945 		return 1;
946 	      }
947 	  }
948 	/* now *current_posn must be either ',' or END_OF_INSN */
949 	if (*current_posn == ',')
950 	  {
951 	    if (*++current_posn == END_OF_INSN)
952 	      {			/* just skip it, if it's \n complain */
953 		as_bad ("Expecting operand after ','; got nothing");
954 		return 1;
955 	      }
956 	    expecting_operand = 1;
957 	  }
958       }
959     while (*current_posn != END_OF_INSN);	/* until we get end of insn */
960   }
961   if (p_insn.swap_operands)
962     {
963       int temp_num, i;
964       operand *temp_op;
965 
966       temp_num = p_insn.operands[0];
967       p_insn.operands[0] = p_insn.operands[1];
968       p_insn.operands[1] = temp_num;
969       for (i = 0; i < MAX_OPERANDS; i++)
970 	{
971 	  temp_op = p_insn.operand_type[0][i];
972 	  p_insn.operand_type[0][i] = p_insn.operand_type[1][i];
973 	  p_insn.operand_type[1][i] = temp_op;
974 	}
975     }
976   if (p_insn.operands[0] != p_insn.tm->operands_1)
977     {
978       as_bad ("incorrect number of operands given in the first instruction");
979       return 1;
980     }
981   if (p_insn.operands[1] != p_insn.tm->operands_2)
982     {
983       as_bad ("incorrect number of operands given in the second instruction");
984       return 1;
985     }
986   debug ("Number of operands in first insn: %d\n", p_insn.operands[0]);
987   debug ("Number of operands in second insn: %d\n", p_insn.operands[1]);
988   {				/* Now check if operands are correct */
989     int count;
990     int num_rn = 0;
991     int num_ind = 0;
992     for (count = 0; count < 2; count++)
993       {
994 	unsigned int i;
995 	for (i = 0; i < p_insn.operands[count]; i++)
996 	  {
997 	    if ((p_insn.operand_type[count][i]->op_type &
998 		 p_insn.tm->operand_types[count][i]) == 0)
999 	      {
1000 		as_bad ("%s instruction, operand %d doesn't match", ordinal_names[count], i + 1);
1001 		return 1;
1002 	      }
1003 	    /* Get number of R register and indirect reference contained within the first
1004 	       two operands of each instruction.  This is required for the multiply
1005 	       parallel instructions which require two R registers and two indirect
1006 	       references, but not in any particular place.  */
1007 	    if ((p_insn.operand_type[count][i]->op_type & Rn) && i < 2)
1008 	      num_rn++;
1009 	    else if ((p_insn.operand_type[count][i]->op_type & Indirect) && i < 2)
1010 	      num_ind++;
1011 	  }
1012       }
1013     if ((p_insn.tm->operand_types[0][0] & (Indirect | Rn)) == (Indirect | Rn))
1014       {
1015 	/* Check for the multiply instructions */
1016 	if (num_rn != 2)
1017 	  {
1018 	    as_bad ("incorrect format for multiply parallel instruction");
1019 	    return 1;
1020 	  }
1021 	if (num_ind != 2)
1022 	  {			/* Shouldn't get here */
1023 	    as_bad ("incorrect format for multiply parallel instruction");
1024 	    return 1;
1025 	  }
1026 	if ((p_insn.operand_type[0][2]->reg.opcode != 0x00) &&
1027 	    (p_insn.operand_type[0][2]->reg.opcode != 0x01))
1028 	  {
1029 	    as_bad ("destination for multiply can only be R0 or R1");
1030 	    return 1;
1031 	  }
1032 	if ((p_insn.operand_type[1][2]->reg.opcode != 0x02) &&
1033 	    (p_insn.operand_type[1][2]->reg.opcode != 0x03))
1034 	  {
1035 	    as_bad ("destination for add/subtract can only be R2 or R3");
1036 	    return 1;
1037 	  }
1038 	/* Now determine the P field for the instruction */
1039 	if (p_insn.operand_type[0][0]->op_type & Indirect)
1040 	  {
1041 	    if (p_insn.operand_type[0][1]->op_type & Indirect)
1042 	      p_insn.p_field = 0x00000000;	/* Ind * Ind, Rn  +/- Rn  */
1043 	    else if (p_insn.operand_type[1][0]->op_type & Indirect)
1044 	      p_insn.p_field = 0x01000000;	/* Ind * Rn,  Ind +/- Rn  */
1045 	    else
1046 	      p_insn.p_field = 0x03000000;	/* Ind * Rn,  Rn  +/- Ind */
1047 	  }
1048 	else
1049 	  {
1050 	    if (p_insn.operand_type[0][1]->op_type & Rn)
1051 	      p_insn.p_field = 0x02000000;	/* Rn  * Rn,  Ind +/- Ind */
1052 	    else if (p_insn.operand_type[1][0]->op_type & Indirect)
1053 	      {
1054 		operand *temp;
1055 		p_insn.p_field = 0x01000000;	/* Rn  * Ind, Ind +/- Rn  */
1056 		/* Need to swap the two multiply operands around so that everything is in
1057 		   its place for the opcode makeup ie so Ind * Rn, Ind +/- Rn */
1058 		temp = p_insn.operand_type[0][0];
1059 		p_insn.operand_type[0][0] = p_insn.operand_type[0][1];
1060 		p_insn.operand_type[0][1] = temp;
1061 	      }
1062 	    else
1063 	      {
1064 		operand *temp;
1065 		p_insn.p_field = 0x03000000;	/* Rn  * Ind, Rn  +/- Ind */
1066 		temp = p_insn.operand_type[0][0];
1067 		p_insn.operand_type[0][0] = p_insn.operand_type[0][1];
1068 		p_insn.operand_type[0][1] = temp;
1069 	      }
1070 	  }
1071       }
1072   }
1073   debug ("P field: %08X\n", p_insn.p_field);
1074   /* Finalise opcode.  This is easier for parallel instructions as they have to be
1075      fully resolved, there are no memory addresses allowed, except through indirect
1076      addressing, so there are no labels to resolve.  */
1077   {
1078     p_insn.opcode = p_insn.tm->base_opcode;
1079     switch (p_insn.tm->oporder)
1080       {
1081       case OO_4op1:
1082 	p_insn.opcode |= (p_insn.operand_type[0][0]->indirect.ARnum);
1083 	p_insn.opcode |= (p_insn.operand_type[0][0]->indirect.mod << 3);
1084 	p_insn.opcode |= (p_insn.operand_type[1][1]->indirect.ARnum << 8);
1085 	p_insn.opcode |= (p_insn.operand_type[1][1]->indirect.mod << 11);
1086 	p_insn.opcode |= (p_insn.operand_type[1][0]->reg.opcode << 16);
1087 	p_insn.opcode |= (p_insn.operand_type[0][1]->reg.opcode << 22);
1088 	break;
1089       case OO_4op2:
1090 	p_insn.opcode |= (p_insn.operand_type[0][0]->indirect.ARnum);
1091 	p_insn.opcode |= (p_insn.operand_type[0][0]->indirect.mod << 3);
1092 	p_insn.opcode |= (p_insn.operand_type[1][0]->indirect.ARnum << 8);
1093 	p_insn.opcode |= (p_insn.operand_type[1][0]->indirect.mod << 11);
1094 	p_insn.opcode |= (p_insn.operand_type[1][1]->reg.opcode << 19);
1095 	p_insn.opcode |= (p_insn.operand_type[0][1]->reg.opcode << 22);
1096 	if (p_insn.operand_type[1][1]->reg.opcode == p_insn.operand_type[0][1]->reg.opcode)
1097 	  as_warn ("loading the same register in parallel operation");
1098 	break;
1099       case OO_4op3:
1100 	p_insn.opcode |= (p_insn.operand_type[0][1]->indirect.ARnum);
1101 	p_insn.opcode |= (p_insn.operand_type[0][1]->indirect.mod << 3);
1102 	p_insn.opcode |= (p_insn.operand_type[1][1]->indirect.ARnum << 8);
1103 	p_insn.opcode |= (p_insn.operand_type[1][1]->indirect.mod << 11);
1104 	p_insn.opcode |= (p_insn.operand_type[1][0]->reg.opcode << 16);
1105 	p_insn.opcode |= (p_insn.operand_type[0][0]->reg.opcode << 22);
1106 	break;
1107       case OO_5op1:
1108 	p_insn.opcode |= (p_insn.operand_type[0][0]->indirect.ARnum);
1109 	p_insn.opcode |= (p_insn.operand_type[0][0]->indirect.mod << 3);
1110 	p_insn.opcode |= (p_insn.operand_type[1][1]->indirect.ARnum << 8);
1111 	p_insn.opcode |= (p_insn.operand_type[1][1]->indirect.mod << 11);
1112 	p_insn.opcode |= (p_insn.operand_type[1][0]->reg.opcode << 16);
1113 	p_insn.opcode |= (p_insn.operand_type[0][1]->reg.opcode << 19);
1114 	p_insn.opcode |= (p_insn.operand_type[0][2]->reg.opcode << 22);
1115 	break;
1116       case OO_5op2:
1117 	p_insn.opcode |= (p_insn.operand_type[0][1]->indirect.ARnum);
1118 	p_insn.opcode |= (p_insn.operand_type[0][1]->indirect.mod << 3);
1119 	p_insn.opcode |= (p_insn.operand_type[1][1]->indirect.ARnum << 8);
1120 	p_insn.opcode |= (p_insn.operand_type[1][1]->indirect.mod << 11);
1121 	p_insn.opcode |= (p_insn.operand_type[1][0]->reg.opcode << 16);
1122 	p_insn.opcode |= (p_insn.operand_type[0][0]->reg.opcode << 19);
1123 	p_insn.opcode |= (p_insn.operand_type[0][2]->reg.opcode << 22);
1124 	break;
1125       case OO_PField:
1126 	p_insn.opcode |= p_insn.p_field;
1127 	if (p_insn.operand_type[0][2]->reg.opcode == 0x01)
1128 	  p_insn.opcode |= 0x00800000;
1129 	if (p_insn.operand_type[1][2]->reg.opcode == 0x03)
1130 	  p_insn.opcode |= 0x00400000;
1131 	switch (p_insn.p_field)
1132 	  {
1133 	  case 0x00000000:
1134 	    p_insn.opcode |= (p_insn.operand_type[0][1]->indirect.ARnum);
1135 	    p_insn.opcode |= (p_insn.operand_type[0][1]->indirect.mod << 3);
1136 	    p_insn.opcode |= (p_insn.operand_type[0][0]->indirect.ARnum << 8);
1137 	    p_insn.opcode |= (p_insn.operand_type[0][0]->indirect.mod << 11);
1138 	    p_insn.opcode |= (p_insn.operand_type[1][1]->reg.opcode << 16);
1139 	    p_insn.opcode |= (p_insn.operand_type[1][0]->reg.opcode << 19);
1140 	    break;
1141 	  case 0x01000000:
1142 	    p_insn.opcode |= (p_insn.operand_type[1][0]->indirect.ARnum);
1143 	    p_insn.opcode |= (p_insn.operand_type[1][0]->indirect.mod << 3);
1144 	    p_insn.opcode |= (p_insn.operand_type[0][0]->indirect.ARnum << 8);
1145 	    p_insn.opcode |= (p_insn.operand_type[0][0]->indirect.mod << 11);
1146 	    p_insn.opcode |= (p_insn.operand_type[1][1]->reg.opcode << 16);
1147 	    p_insn.opcode |= (p_insn.operand_type[0][1]->reg.opcode << 19);
1148 	    break;
1149 	  case 0x02000000:
1150 	    p_insn.opcode |= (p_insn.operand_type[1][1]->indirect.ARnum);
1151 	    p_insn.opcode |= (p_insn.operand_type[1][1]->indirect.mod << 3);
1152 	    p_insn.opcode |= (p_insn.operand_type[1][0]->indirect.ARnum << 8);
1153 	    p_insn.opcode |= (p_insn.operand_type[1][0]->indirect.mod << 11);
1154 	    p_insn.opcode |= (p_insn.operand_type[0][1]->reg.opcode << 16);
1155 	    p_insn.opcode |= (p_insn.operand_type[0][0]->reg.opcode << 19);
1156 	    break;
1157 	  case 0x03000000:
1158 	    p_insn.opcode |= (p_insn.operand_type[1][1]->indirect.ARnum);
1159 	    p_insn.opcode |= (p_insn.operand_type[1][1]->indirect.mod << 3);
1160 	    p_insn.opcode |= (p_insn.operand_type[0][0]->indirect.ARnum << 8);
1161 	    p_insn.opcode |= (p_insn.operand_type[0][0]->indirect.mod << 11);
1162 	    p_insn.opcode |= (p_insn.operand_type[1][0]->reg.opcode << 16);
1163 	    p_insn.opcode |= (p_insn.operand_type[0][1]->reg.opcode << 19);
1164 	    break;
1165 	  }
1166 	break;
1167       }
1168   }				/* Opcode is finalised at this point for all parallel instructions.  */
1169   {				/* Output opcode */
1170     char *p;
1171     p = frag_more (INSN_SIZE);
1172     md_number_to_chars (p, (valueT) p_insn.opcode, INSN_SIZE);
1173   }
1174   {
1175     unsigned int i, j;
1176     for (i = 0; i < 2; i++)
1177       for (j = 0; j < p_insn.operands[i]; j++)
1178 	free (p_insn.operand_type[i][j]);
1179   }
1180   debug ("Final opcode: %08X\n", p_insn.opcode);
1181   debug ("\n");
1182   return 1;
1183 }
1184 
1185 operand *
tic30_operand(token)1186 tic30_operand (token)
1187      char *token;
1188 {
1189   unsigned int count;
1190   char ind_buffer[strlen (token)];
1191   operand *current_op;
1192 
1193   debug ("In tic30_operand with %s\n", token);
1194   current_op = (operand *) malloc (sizeof (operand));
1195   memset (current_op, '\0', sizeof (operand));
1196   if (*token == DIRECT_REFERENCE)
1197     {
1198       char *token_posn = token + 1;
1199       int direct_label = 0;
1200       debug ("Found direct reference\n");
1201       while (*token_posn)
1202 	{
1203 	  if (!is_digit_char (*token_posn))
1204 	    direct_label = 1;
1205 	  token_posn++;
1206 	}
1207       if (direct_label)
1208 	{
1209 	  char *save_input_line_pointer;
1210 	  segT retval;
1211 	  debug ("Direct reference is a label\n");
1212 	  current_op->direct.label = token + 1;
1213 	  save_input_line_pointer = input_line_pointer;
1214 	  input_line_pointer = token + 1;
1215 	  debug ("Current input_line_pointer: %s\n", input_line_pointer);
1216 	  retval = expression (&current_op->direct.direct_expr);
1217 	  debug ("Expression type: %d\n", current_op->direct.direct_expr.X_op);
1218 	  debug ("Expression addnum: %d\n", current_op->direct.direct_expr.X_add_number);
1219 	  debug ("Segment: %d\n", retval);
1220 	  input_line_pointer = save_input_line_pointer;
1221 	  if (current_op->direct.direct_expr.X_op == O_constant)
1222 	    {
1223 	      current_op->direct.address = current_op->direct.direct_expr.X_add_number;
1224 	      current_op->direct.resolved = 1;
1225 	    }
1226 	}
1227       else
1228 	{
1229 	  debug ("Direct reference is a number\n");
1230 	  current_op->direct.address = atoi (token + 1);
1231 	  current_op->direct.resolved = 1;
1232 	}
1233       current_op->op_type = Direct;
1234     }
1235   else if (*token == INDIRECT_REFERENCE)
1236     {				/* Indirect reference operand */
1237       int found_ar = 0;
1238       int found_disp = 0;
1239       int ar_number = -1;
1240       int disp_number = 0;
1241       int buffer_posn = 1;
1242       ind_addr_type *ind_addr_op;
1243       debug ("Found indirect reference\n");
1244       ind_buffer[0] = *token;
1245       for (count = 1; count < strlen (token); count++)
1246 	{			/* Strip operand */
1247 	  ind_buffer[buffer_posn] = TOLOWER (*(token + count));
1248 	  if ((*(token + count - 1) == 'a' || *(token + count - 1) == 'A') &&
1249 	      (*(token + count) == 'r' || *(token + count) == 'R'))
1250 	    {
1251 	      /* AR reference is found, so get its number and remove it from the buffer
1252 	         so it can pass through hash_find() */
1253 	      if (found_ar)
1254 		{
1255 		  as_bad ("More than one AR register found in indirect reference");
1256 		  return NULL;
1257 		}
1258 	      if (*(token + count + 1) < '0' || *(token + count + 1) > '7')
1259 		{
1260 		  as_bad ("Illegal AR register in indirect reference");
1261 		  return NULL;
1262 		}
1263 	      ar_number = *(token + count + 1) - '0';
1264 	      found_ar = 1;
1265 	      count++;
1266 	    }
1267 	  if (*(token + count) == '(')
1268 	    {
1269 	      /* Parenthesis found, so check if a displacement value is inside.  If so, get
1270 	         the value and remove it from the buffer.  */
1271 	      if (is_digit_char (*(token + count + 1)))
1272 		{
1273 		  char disp[10];
1274 		  int disp_posn = 0;
1275 
1276 		  if (found_disp)
1277 		    {
1278 		      as_bad ("More than one displacement found in indirect reference");
1279 		      return NULL;
1280 		    }
1281 		  count++;
1282 		  while (*(token + count) != ')')
1283 		    {
1284 		      if (!is_digit_char (*(token + count)))
1285 			{
1286 			  as_bad ("Invalid displacement in indirect reference");
1287 			  return NULL;
1288 			}
1289 		      disp[disp_posn++] = *(token + (count++));
1290 		    }
1291 		  disp[disp_posn] = '\0';
1292 		  disp_number = atoi (disp);
1293 		  count--;
1294 		  found_disp = 1;
1295 		}
1296 	    }
1297 	  buffer_posn++;
1298 	}
1299       ind_buffer[buffer_posn] = '\0';
1300       if (!found_ar)
1301 	{
1302 	  as_bad ("AR register not found in indirect reference");
1303 	  return NULL;
1304 	}
1305       ind_addr_op = (ind_addr_type *) hash_find (ind_hash, ind_buffer);
1306       if (ind_addr_op)
1307 	{
1308 	  debug ("Found indirect reference: %s\n", ind_addr_op->syntax);
1309 	  if (ind_addr_op->displacement == IMPLIED_DISP)
1310 	    {
1311 	      found_disp = 1;
1312 	      disp_number = 1;
1313 	    }
1314 	  else if ((ind_addr_op->displacement == DISP_REQUIRED) && !found_disp)
1315 	    {
1316 	      /* Maybe an implied displacement of 1 again */
1317 	      as_bad ("required displacement wasn't given in indirect reference");
1318 	      return 0;
1319 	    }
1320 	}
1321       else
1322 	{
1323 	  as_bad ("illegal indirect reference");
1324 	  return NULL;
1325 	}
1326       if (found_disp && (disp_number < 0 || disp_number > 255))
1327 	{
1328 	  as_bad ("displacement must be an unsigned 8-bit number");
1329 	  return NULL;
1330 	}
1331       current_op->indirect.mod = ind_addr_op->modfield;
1332       current_op->indirect.disp = disp_number;
1333       current_op->indirect.ARnum = ar_number;
1334       current_op->op_type = Indirect;
1335     }
1336   else
1337     {
1338       reg *regop = (reg *) hash_find (reg_hash, token);
1339       if (regop)
1340 	{
1341 	  debug ("Found register operand: %s\n", regop->name);
1342 	  if (regop->regtype == REG_ARn)
1343 	    current_op->op_type = ARn;
1344 	  else if (regop->regtype == REG_Rn)
1345 	    current_op->op_type = Rn;
1346 	  else if (regop->regtype == REG_DP)
1347 	    current_op->op_type = DPReg;
1348 	  else
1349 	    current_op->op_type = OtherReg;
1350 	  current_op->reg.opcode = regop->opcode;
1351 	}
1352       else
1353 	{
1354 	  if (!is_digit_char (*token) || *(token + 1) == 'x' || strchr (token, 'h'))
1355 	    {
1356 	      char *save_input_line_pointer;
1357 	      segT retval;
1358 	      debug ("Probably a label: %s\n", token);
1359 	      current_op->immediate.label = (char *) malloc (strlen (token) + 1);
1360 	      strcpy (current_op->immediate.label, token);
1361 	      current_op->immediate.label[strlen (token)] = '\0';
1362 	      save_input_line_pointer = input_line_pointer;
1363 	      input_line_pointer = token;
1364 	      debug ("Current input_line_pointer: %s\n", input_line_pointer);
1365 	      retval = expression (&current_op->immediate.imm_expr);
1366 	      debug ("Expression type: %d\n", current_op->immediate.imm_expr.X_op);
1367 	      debug ("Expression addnum: %d\n", current_op->immediate.imm_expr.X_add_number);
1368 	      debug ("Segment: %d\n", retval);
1369 	      input_line_pointer = save_input_line_pointer;
1370 	      if (current_op->immediate.imm_expr.X_op == O_constant)
1371 		{
1372 		  current_op->immediate.s_number = current_op->immediate.imm_expr.X_add_number;
1373 		  current_op->immediate.u_number = (unsigned int) current_op->immediate.imm_expr.X_add_number;
1374 		  current_op->immediate.resolved = 1;
1375 		}
1376 	    }
1377 	  else
1378 	    {
1379 	      unsigned count;
1380 	      debug ("Found a number or displacement\n");
1381 	      for (count = 0; count < strlen (token); count++)
1382 		if (*(token + count) == '.')
1383 		  current_op->immediate.decimal_found = 1;
1384 	      current_op->immediate.label = (char *) malloc (strlen (token) + 1);
1385 	      strcpy (current_op->immediate.label, token);
1386 	      current_op->immediate.label[strlen (token)] = '\0';
1387 	      current_op->immediate.f_number = (float) atof (token);
1388 	      current_op->immediate.s_number = (int) atoi (token);
1389 	      current_op->immediate.u_number = (unsigned int) atoi (token);
1390 	      current_op->immediate.resolved = 1;
1391 	    }
1392 	  current_op->op_type = Disp | Abs24 | Imm16 | Imm24;
1393 	  if (current_op->immediate.u_number <= 31)
1394 	    current_op->op_type |= IVector;
1395 	}
1396     }
1397   return current_op;
1398 }
1399 
1400 /* next_line points to the next line after the current instruction (current_line).
1401    Search for the parallel bars, and if found, merge two lines into internal syntax
1402    for a parallel instruction:
1403    q_[INSN1]_[INSN2] [OPERANDS1] | [OPERANDS2]
1404    By this stage, all comments are scrubbed, and only the bare lines are given.
1405  */
1406 
1407 #define NONE           0
1408 #define START_OPCODE   1
1409 #define END_OPCODE     2
1410 #define START_OPERANDS 3
1411 #define END_OPERANDS   4
1412 
1413 char *
tic30_find_parallel_insn(current_line,next_line)1414 tic30_find_parallel_insn (current_line, next_line)
1415      char *current_line;
1416      char *next_line;
1417 {
1418   int found_parallel = 0;
1419   char first_opcode[256];
1420   char second_opcode[256];
1421   char first_operands[256];
1422   char second_operands[256];
1423   char *parallel_insn;
1424 
1425   debug ("In tic30_find_parallel_insn()\n");
1426   while (!is_end_of_line[(unsigned char) *next_line])
1427     {
1428       if (*next_line == PARALLEL_SEPARATOR && *(next_line + 1) == PARALLEL_SEPARATOR)
1429 	{
1430 	  found_parallel = 1;
1431 	  next_line++;
1432 	  break;
1433 	}
1434       next_line++;
1435     }
1436   if (!found_parallel)
1437     return NULL;
1438   debug ("Found a parallel instruction\n");
1439   {
1440     int i;
1441     char *opcode, *operands, *line;
1442 
1443     for (i = 0; i < 2; i++)
1444       {
1445 	if (i == 0)
1446 	  {
1447 	    opcode = &first_opcode[0];
1448 	    operands = &first_operands[0];
1449 	    line = current_line;
1450 	  }
1451 	else
1452 	  {
1453 	    opcode = &second_opcode[0];
1454 	    operands = &second_operands[0];
1455 	    line = next_line;
1456 	  }
1457 	{
1458 	  int search_status = NONE;
1459 	  int char_ptr = 0;
1460 	  char c;
1461 
1462 	  while (!is_end_of_line[(unsigned char) (c = *line)])
1463 	    {
1464 	      if (is_opcode_char (c) && search_status == NONE)
1465 		{
1466 		  opcode[char_ptr++] = TOLOWER (c);
1467 		  search_status = START_OPCODE;
1468 		}
1469 	      else if (is_opcode_char (c) && search_status == START_OPCODE)
1470 		{
1471 		  opcode[char_ptr++] = TOLOWER (c);
1472 		}
1473 	      else if (!is_opcode_char (c) && search_status == START_OPCODE)
1474 		{
1475 		  opcode[char_ptr] = '\0';
1476 		  char_ptr = 0;
1477 		  search_status = END_OPCODE;
1478 		}
1479 	      else if (is_operand_char (c) && search_status == START_OPERANDS)
1480 		{
1481 		  operands[char_ptr++] = c;
1482 		}
1483 	      if (is_operand_char (c) && search_status == END_OPCODE)
1484 		{
1485 		  operands[char_ptr++] = c;
1486 		  search_status = START_OPERANDS;
1487 		}
1488 	      line++;
1489 	    }
1490 	  if (search_status != START_OPERANDS)
1491 	    return NULL;
1492 	  operands[char_ptr] = '\0';
1493 	}
1494       }
1495   }
1496   parallel_insn = (char *) malloc (strlen (first_opcode) + strlen (first_operands) +
1497 		     strlen (second_opcode) + strlen (second_operands) + 8);
1498   sprintf (parallel_insn, "q_%s_%s %s | %s", first_opcode, second_opcode, first_operands, second_operands);
1499   debug ("parallel insn = %s\n", parallel_insn);
1500   return parallel_insn;
1501 }
1502 
1503 #undef NONE
1504 #undef START_OPCODE
1505 #undef END_OPCODE
1506 #undef START_OPERANDS
1507 #undef END_OPERANDS
1508 
1509 /* In order to get gas to ignore any | chars at the start of a line,
1510    this function returns true if a | is found in a line.  */
1511 
1512 int
tic30_unrecognized_line(c)1513 tic30_unrecognized_line (c)
1514      int c;
1515 {
1516   debug ("In tc_unrecognized_line\n");
1517   return (c == PARALLEL_SEPARATOR);
1518 }
1519 
1520 int
md_estimate_size_before_relax(fragP,segment)1521 md_estimate_size_before_relax (fragP, segment)
1522      fragS *fragP ATTRIBUTE_UNUSED;
1523      segT segment ATTRIBUTE_UNUSED;
1524 {
1525   debug ("In md_estimate_size_before_relax()\n");
1526   return 0;
1527 }
1528 
1529 void
md_convert_frag(abfd,sec,fragP)1530 md_convert_frag (abfd, sec, fragP)
1531      bfd *abfd ATTRIBUTE_UNUSED;
1532      segT sec ATTRIBUTE_UNUSED;
1533      register fragS *fragP ATTRIBUTE_UNUSED;
1534 {
1535   debug ("In md_convert_frag()\n");
1536 }
1537 
1538 void
md_apply_fix3(fixP,valP,seg)1539 md_apply_fix3 (fixP, valP, seg)
1540      fixS *fixP;
1541      valueT *valP;
1542      segT seg ATTRIBUTE_UNUSED;
1543 {
1544   valueT value = *valP;
1545 
1546   debug ("In md_apply_fix() with value = %ld\n", (long) value);
1547   debug ("Values in fixP\n");
1548   debug ("fx_size = %d\n", fixP->fx_size);
1549   debug ("fx_pcrel = %d\n", fixP->fx_pcrel);
1550   debug ("fx_where = %d\n", fixP->fx_where);
1551   debug ("fx_offset = %d\n", (int) fixP->fx_offset);
1552   {
1553     char *buf = fixP->fx_frag->fr_literal + fixP->fx_where;
1554 
1555     value /= INSN_SIZE;
1556     if (fixP->fx_size == 1)
1557       /* Special fix for LDP instruction.  */
1558       value = (value & 0x00FF0000) >> 16;
1559 
1560     debug ("new value = %ld\n", (long) value);
1561     md_number_to_chars (buf, value, fixP->fx_size);
1562   }
1563 
1564   if (fixP->fx_addsy == NULL && fixP->fx_pcrel == 0)
1565     fixP->fx_done = 1;
1566 }
1567 
1568 int
md_parse_option(c,arg)1569 md_parse_option (c, arg)
1570      int c ATTRIBUTE_UNUSED;
1571      char *arg ATTRIBUTE_UNUSED;
1572 {
1573   debug ("In md_parse_option()\n");
1574   return 0;
1575 }
1576 
1577 void
md_show_usage(stream)1578 md_show_usage (stream)
1579      FILE *stream ATTRIBUTE_UNUSED;
1580 {
1581   debug ("In md_show_usage()\n");
1582 }
1583 
1584 symbolS *
md_undefined_symbol(name)1585 md_undefined_symbol (name)
1586      char *name ATTRIBUTE_UNUSED;
1587 {
1588   debug ("In md_undefined_symbol()\n");
1589   return (symbolS *) 0;
1590 }
1591 
1592 valueT
md_section_align(segment,size)1593 md_section_align (segment, size)
1594      segT segment;
1595      valueT size;
1596 {
1597   debug ("In md_section_align() segment = %d and size = %d\n", segment, size);
1598   size = (size + 3) / 4;
1599   size *= 4;
1600   debug ("New size value = %d\n", size);
1601   return size;
1602 }
1603 
1604 long
md_pcrel_from(fixP)1605 md_pcrel_from (fixP)
1606      fixS *fixP;
1607 {
1608   int offset;
1609 
1610   debug ("In md_pcrel_from()\n");
1611   debug ("fx_where = %d\n", fixP->fx_where);
1612   debug ("fx_size = %d\n", fixP->fx_size);
1613   /* Find the opcode that represents the current instruction in the fr_literal
1614      storage area, and check bit 21.  Bit 21 contains whether the current instruction
1615      is a delayed one or not, and then set the offset value appropriately.  */
1616   if (fixP->fx_frag->fr_literal[fixP->fx_where - fixP->fx_size + 1] & 0x20)
1617     offset = 3;
1618   else
1619     offset = 1;
1620   debug ("offset = %d\n", offset);
1621   /* PC Relative instructions have a format:
1622      displacement = Label - (PC + offset)
1623      This function returns PC + offset where:
1624      fx_where - fx_size = PC
1625      INSN_SIZE * offset = offset number of instructions
1626    */
1627   return fixP->fx_where - fixP->fx_size + (INSN_SIZE * offset);
1628 }
1629 
1630 char *
md_atof(what_statement_type,literalP,sizeP)1631 md_atof (what_statement_type, literalP, sizeP)
1632      int what_statement_type;
1633      char *literalP;
1634      int *sizeP;
1635 {
1636   int prec;
1637   char *token;
1638   char keepval;
1639   unsigned long value;
1640   float float_value;
1641   debug ("In md_atof()\n");
1642   debug ("precision = %c\n", what_statement_type);
1643   debug ("literal = %s\n", literalP);
1644   debug ("line = ");
1645   token = input_line_pointer;
1646   while (!is_end_of_line[(unsigned char) *input_line_pointer]
1647 	 && (*input_line_pointer != ','))
1648     {
1649       debug ("%c", *input_line_pointer);
1650       input_line_pointer++;
1651     }
1652   keepval = *input_line_pointer;
1653   *input_line_pointer = '\0';
1654   debug ("\n");
1655   float_value = (float) atof (token);
1656   *input_line_pointer = keepval;
1657   debug ("float_value = %f\n", float_value);
1658   switch (what_statement_type)
1659     {
1660     case 'f':
1661     case 'F':
1662     case 's':
1663     case 'S':
1664       prec = 2;
1665       break;
1666 
1667     case 'd':
1668     case 'D':
1669     case 'r':
1670     case 'R':
1671       prec = 4;
1672       break;
1673 
1674     default:
1675       *sizeP = 0;
1676       return "Bad call to MD_ATOF()";
1677     }
1678   if (float_value == 0.0)
1679     {
1680       value = (prec == 2) ? 0x00008000L : 0x80000000L;
1681     }
1682   else
1683     {
1684       unsigned long exp, sign, mant, tmsfloat;
1685       tmsfloat = *((long *) &float_value);
1686       sign = tmsfloat & 0x80000000;
1687       mant = tmsfloat & 0x007FFFFF;
1688       exp = tmsfloat & 0x7F800000;
1689       exp <<= 1;
1690       if (exp == 0xFF000000)
1691 	{
1692 	  if (mant == 0)
1693 	    value = 0x7F7FFFFF;
1694 	  else if (sign == 0)
1695 	    value = 0x7F7FFFFF;
1696 	  else
1697 	    value = 0x7F800000;
1698 	}
1699       else
1700 	{
1701 	  exp -= 0x7F000000;
1702 	  if (sign)
1703 	    {
1704 	      mant = mant & 0x007FFFFF;
1705 	      mant = -mant;
1706 	      mant = mant & 0x00FFFFFF;
1707 	      if (mant == 0)
1708 		{
1709 		  mant |= 0x00800000;
1710 		  exp = (long) exp - 0x01000000;
1711 		}
1712 	    }
1713 	  tmsfloat = exp | mant;
1714 	  value = tmsfloat;
1715 	}
1716       if (prec == 2)
1717 	{
1718 	  long exp, mant;
1719 
1720 	  if (tmsfloat == 0x80000000)
1721 	    {
1722 	      value = 0x8000;
1723 	    }
1724 	  else
1725 	    {
1726 	      value = 0;
1727 	      exp = (tmsfloat & 0xFF000000);
1728 	      exp >>= 24;
1729 	      mant = tmsfloat & 0x007FFFFF;
1730 	      if (tmsfloat & 0x00800000)
1731 		{
1732 		  mant |= 0xFF000000;
1733 		  mant += 0x00000800;
1734 		  mant >>= 12;
1735 		  mant |= 0x00000800;
1736 		  mant &= 0x0FFF;
1737 		  if (exp > 7)
1738 		    value = 0x7800;
1739 		}
1740 	      else
1741 		{
1742 		  mant |= 0x00800000;
1743 		  mant += 0x00000800;
1744 		  exp += (mant >> 24);
1745 		  mant >>= 12;
1746 		  mant &= 0x07FF;
1747 		  if (exp > 7)
1748 		    value = 0x77FF;
1749 		}
1750 	      if (exp < -8)
1751 		value = 0x8000;
1752 	      if (value == 0)
1753 		{
1754 		  mant = (exp << 12) | mant;
1755 		  value = mant & 0xFFFF;
1756 		}
1757 	    }
1758 	}
1759     }
1760   md_number_to_chars (literalP, value, prec);
1761   *sizeP = prec;
1762   return 0;
1763 }
1764 
1765 void
md_number_to_chars(buf,val,n)1766 md_number_to_chars (buf, val, n)
1767      char *buf;
1768      valueT val;
1769      int n;
1770 {
1771   debug ("In md_number_to_chars()\n");
1772   number_to_chars_bigendian (buf, val, n);
1773   /*  number_to_chars_littleendian(buf,val,n); */
1774 }
1775 
1776 #define F(SZ,PCREL)		(((SZ) << 1) + (PCREL))
1777 #define MAP(SZ,PCREL,TYPE)	case F(SZ,PCREL): code = (TYPE); break
1778 
1779 arelent *
tc_gen_reloc(section,fixP)1780 tc_gen_reloc (section, fixP)
1781      asection *section ATTRIBUTE_UNUSED;
1782      fixS *fixP;
1783 {
1784   arelent *rel;
1785   bfd_reloc_code_real_type code = 0;
1786 
1787   debug ("In tc_gen_reloc()\n");
1788   debug ("fixP.size = %d\n", fixP->fx_size);
1789   debug ("fixP.pcrel = %d\n", fixP->fx_pcrel);
1790   debug ("addsy.name = %s\n", S_GET_NAME (fixP->fx_addsy));
1791   switch (F (fixP->fx_size, fixP->fx_pcrel))
1792     {
1793       MAP (1, 0, BFD_RELOC_TIC30_LDP);
1794       MAP (2, 0, BFD_RELOC_16);
1795       MAP (3, 0, BFD_RELOC_24);
1796       MAP (2, 1, BFD_RELOC_16_PCREL);
1797       MAP (4, 0, BFD_RELOC_32);
1798     default:
1799       as_bad ("Can not do %d byte %srelocation", fixP->fx_size,
1800 	      fixP->fx_pcrel ? "pc-relative " : "");
1801     }
1802 #undef MAP
1803 #undef F
1804 
1805   rel = (arelent *) xmalloc (sizeof (arelent));
1806   assert (rel != 0);
1807   rel->sym_ptr_ptr = (asymbol **) xmalloc (sizeof (asymbol *));
1808   *rel->sym_ptr_ptr = symbol_get_bfdsym (fixP->fx_addsy);
1809   rel->address = fixP->fx_frag->fr_address + fixP->fx_where;
1810   rel->addend = 0;
1811   rel->howto = bfd_reloc_type_lookup (stdoutput, code);
1812   if (!rel->howto)
1813     {
1814       const char *name;
1815       name = S_GET_NAME (fixP->fx_addsy);
1816       if (name == NULL)
1817 	name = "<unknown>";
1818       as_fatal ("Cannot generate relocation type for symbol %s, code %s", name, bfd_get_reloc_code_name (code));
1819     }
1820   return rel;
1821 }
1822 
1823 void
md_operand(expressionP)1824 md_operand (expressionP)
1825      expressionS *expressionP ATTRIBUTE_UNUSED;
1826 {
1827   debug ("In md_operand()\n");
1828 }
1829 
1830 char output_invalid_buf[8];
1831 
1832 char *
output_invalid(c)1833 output_invalid (c)
1834      char c;
1835 {
1836   if (ISPRINT (c))
1837     sprintf (output_invalid_buf, "'%c'", c);
1838   else
1839     sprintf (output_invalid_buf, "(0x%x)", (unsigned) c);
1840   return output_invalid_buf;
1841 }
1842