xref: /dragonfly/contrib/binutils-2.27/gas/expr.c (revision a9fa9459)
1*a9fa9459Szrj /* expr.c -operands, expressions-
2*a9fa9459Szrj    Copyright (C) 1987-2016 Free Software Foundation, Inc.
3*a9fa9459Szrj 
4*a9fa9459Szrj    This file is part of GAS, the GNU Assembler.
5*a9fa9459Szrj 
6*a9fa9459Szrj    GAS is free software; you can redistribute it and/or modify
7*a9fa9459Szrj    it under the terms of the GNU General Public License as published by
8*a9fa9459Szrj    the Free Software Foundation; either version 3, or (at your option)
9*a9fa9459Szrj    any later version.
10*a9fa9459Szrj 
11*a9fa9459Szrj    GAS is distributed in the hope that it will be useful,
12*a9fa9459Szrj    but WITHOUT ANY WARRANTY; without even the implied warranty of
13*a9fa9459Szrj    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14*a9fa9459Szrj    GNU General Public License for more details.
15*a9fa9459Szrj 
16*a9fa9459Szrj    You should have received a copy of the GNU General Public License
17*a9fa9459Szrj    along with GAS; see the file COPYING.  If not, write to the Free
18*a9fa9459Szrj    Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA
19*a9fa9459Szrj    02110-1301, USA.  */
20*a9fa9459Szrj 
21*a9fa9459Szrj /* This is really a branch office of as-read.c. I split it out to clearly
22*a9fa9459Szrj    distinguish the world of expressions from the world of statements.
23*a9fa9459Szrj    (It also gives smaller files to re-compile.)
24*a9fa9459Szrj    Here, "operand"s are of expressions, not instructions.  */
25*a9fa9459Szrj 
26*a9fa9459Szrj #define min(a, b)       ((a) < (b) ? (a) : (b))
27*a9fa9459Szrj 
28*a9fa9459Szrj #include "as.h"
29*a9fa9459Szrj #include "safe-ctype.h"
30*a9fa9459Szrj 
31*a9fa9459Szrj #ifdef HAVE_LIMITS_H
32*a9fa9459Szrj #include <limits.h>
33*a9fa9459Szrj #endif
34*a9fa9459Szrj #ifndef CHAR_BIT
35*a9fa9459Szrj #define CHAR_BIT 8
36*a9fa9459Szrj #endif
37*a9fa9459Szrj 
38*a9fa9459Szrj static void floating_constant (expressionS * expressionP);
39*a9fa9459Szrj static valueT generic_bignum_to_int32 (void);
40*a9fa9459Szrj #ifdef BFD64
41*a9fa9459Szrj static valueT generic_bignum_to_int64 (void);
42*a9fa9459Szrj #endif
43*a9fa9459Szrj static void integer_constant (int radix, expressionS * expressionP);
44*a9fa9459Szrj static void mri_char_constant (expressionS *);
45*a9fa9459Szrj static void clean_up_expression (expressionS * expressionP);
46*a9fa9459Szrj static segT operand (expressionS *, enum expr_mode);
47*a9fa9459Szrj static operatorT operatorf (int *);
48*a9fa9459Szrj 
49*a9fa9459Szrj /* We keep a mapping of expression symbols to file positions, so that
50*a9fa9459Szrj    we can provide better error messages.  */
51*a9fa9459Szrj 
52*a9fa9459Szrj struct expr_symbol_line {
53*a9fa9459Szrj   struct expr_symbol_line *next;
54*a9fa9459Szrj   symbolS *sym;
55*a9fa9459Szrj   const char *file;
56*a9fa9459Szrj   unsigned int line;
57*a9fa9459Szrj };
58*a9fa9459Szrj 
59*a9fa9459Szrj static struct expr_symbol_line *expr_symbol_lines;
60*a9fa9459Szrj 
61*a9fa9459Szrj /* Build a dummy symbol to hold a complex expression.  This is how we
62*a9fa9459Szrj    build expressions up out of other expressions.  The symbol is put
63*a9fa9459Szrj    into the fake section expr_section.  */
64*a9fa9459Szrj 
65*a9fa9459Szrj symbolS *
make_expr_symbol(expressionS * expressionP)66*a9fa9459Szrj make_expr_symbol (expressionS *expressionP)
67*a9fa9459Szrj {
68*a9fa9459Szrj   expressionS zero;
69*a9fa9459Szrj   symbolS *symbolP;
70*a9fa9459Szrj   struct expr_symbol_line *n;
71*a9fa9459Szrj 
72*a9fa9459Szrj   if (expressionP->X_op == O_symbol
73*a9fa9459Szrj       && expressionP->X_add_number == 0)
74*a9fa9459Szrj     return expressionP->X_add_symbol;
75*a9fa9459Szrj 
76*a9fa9459Szrj   if (expressionP->X_op == O_big)
77*a9fa9459Szrj     {
78*a9fa9459Szrj       /* This won't work, because the actual value is stored in
79*a9fa9459Szrj 	 generic_floating_point_number or generic_bignum, and we are
80*a9fa9459Szrj 	 going to lose it if we haven't already.  */
81*a9fa9459Szrj       if (expressionP->X_add_number > 0)
82*a9fa9459Szrj 	as_bad (_("bignum invalid"));
83*a9fa9459Szrj       else
84*a9fa9459Szrj 	as_bad (_("floating point number invalid"));
85*a9fa9459Szrj       zero.X_op = O_constant;
86*a9fa9459Szrj       zero.X_add_number = 0;
87*a9fa9459Szrj       zero.X_unsigned = 0;
88*a9fa9459Szrj       zero.X_extrabit = 0;
89*a9fa9459Szrj       clean_up_expression (&zero);
90*a9fa9459Szrj       expressionP = &zero;
91*a9fa9459Szrj     }
92*a9fa9459Szrj 
93*a9fa9459Szrj   /* Putting constant symbols in absolute_section rather than
94*a9fa9459Szrj      expr_section is convenient for the old a.out code, for which
95*a9fa9459Szrj      S_GET_SEGMENT does not always retrieve the value put in by
96*a9fa9459Szrj      S_SET_SEGMENT.  */
97*a9fa9459Szrj   symbolP = symbol_create (FAKE_LABEL_NAME,
98*a9fa9459Szrj 			   (expressionP->X_op == O_constant
99*a9fa9459Szrj 			    ? absolute_section
100*a9fa9459Szrj 			    : expressionP->X_op == O_register
101*a9fa9459Szrj 			      ? reg_section
102*a9fa9459Szrj 			      : expr_section),
103*a9fa9459Szrj 			   0, &zero_address_frag);
104*a9fa9459Szrj   symbol_set_value_expression (symbolP, expressionP);
105*a9fa9459Szrj 
106*a9fa9459Szrj   if (expressionP->X_op == O_constant)
107*a9fa9459Szrj     resolve_symbol_value (symbolP);
108*a9fa9459Szrj 
109*a9fa9459Szrj   n = XNEW (struct expr_symbol_line);
110*a9fa9459Szrj   n->sym = symbolP;
111*a9fa9459Szrj   n->file = as_where (&n->line);
112*a9fa9459Szrj   n->next = expr_symbol_lines;
113*a9fa9459Szrj   expr_symbol_lines = n;
114*a9fa9459Szrj 
115*a9fa9459Szrj   return symbolP;
116*a9fa9459Szrj }
117*a9fa9459Szrj 
118*a9fa9459Szrj /* Return the file and line number for an expr symbol.  Return
119*a9fa9459Szrj    non-zero if something was found, 0 if no information is known for
120*a9fa9459Szrj    the symbol.  */
121*a9fa9459Szrj 
122*a9fa9459Szrj int
expr_symbol_where(symbolS * sym,const char ** pfile,unsigned int * pline)123*a9fa9459Szrj expr_symbol_where (symbolS *sym, const char **pfile, unsigned int *pline)
124*a9fa9459Szrj {
125*a9fa9459Szrj   struct expr_symbol_line *l;
126*a9fa9459Szrj 
127*a9fa9459Szrj   for (l = expr_symbol_lines; l != NULL; l = l->next)
128*a9fa9459Szrj     {
129*a9fa9459Szrj       if (l->sym == sym)
130*a9fa9459Szrj 	{
131*a9fa9459Szrj 	  *pfile = l->file;
132*a9fa9459Szrj 	  *pline = l->line;
133*a9fa9459Szrj 	  return 1;
134*a9fa9459Szrj 	}
135*a9fa9459Szrj     }
136*a9fa9459Szrj 
137*a9fa9459Szrj   return 0;
138*a9fa9459Szrj }
139*a9fa9459Szrj 
140*a9fa9459Szrj /* Utilities for building expressions.
141*a9fa9459Szrj    Since complex expressions are recorded as symbols for use in other
142*a9fa9459Szrj    expressions these return a symbolS * and not an expressionS *.
143*a9fa9459Szrj    These explicitly do not take an "add_number" argument.  */
144*a9fa9459Szrj /* ??? For completeness' sake one might want expr_build_symbol.
145*a9fa9459Szrj    It would just return its argument.  */
146*a9fa9459Szrj 
147*a9fa9459Szrj /* Build an expression for an unsigned constant.
148*a9fa9459Szrj    The corresponding one for signed constants is missing because
149*a9fa9459Szrj    there's currently no need for it.  One could add an unsigned_p flag
150*a9fa9459Szrj    but that seems more clumsy.  */
151*a9fa9459Szrj 
152*a9fa9459Szrj symbolS *
expr_build_uconstant(offsetT value)153*a9fa9459Szrj expr_build_uconstant (offsetT value)
154*a9fa9459Szrj {
155*a9fa9459Szrj   expressionS e;
156*a9fa9459Szrj 
157*a9fa9459Szrj   e.X_op = O_constant;
158*a9fa9459Szrj   e.X_add_number = value;
159*a9fa9459Szrj   e.X_unsigned = 1;
160*a9fa9459Szrj   e.X_extrabit = 0;
161*a9fa9459Szrj   return make_expr_symbol (&e);
162*a9fa9459Szrj }
163*a9fa9459Szrj 
164*a9fa9459Szrj /* Build an expression for the current location ('.').  */
165*a9fa9459Szrj 
166*a9fa9459Szrj symbolS *
expr_build_dot(void)167*a9fa9459Szrj expr_build_dot (void)
168*a9fa9459Szrj {
169*a9fa9459Szrj   expressionS e;
170*a9fa9459Szrj 
171*a9fa9459Szrj   current_location (&e);
172*a9fa9459Szrj   return symbol_clone_if_forward_ref (make_expr_symbol (&e));
173*a9fa9459Szrj }
174*a9fa9459Szrj 
175*a9fa9459Szrj /* Build any floating-point literal here.
176*a9fa9459Szrj    Also build any bignum literal here.  */
177*a9fa9459Szrj 
178*a9fa9459Szrj /* Seems atof_machine can backscan through generic_bignum and hit whatever
179*a9fa9459Szrj    happens to be loaded before it in memory.  And its way too complicated
180*a9fa9459Szrj    for me to fix right.  Thus a hack.  JF:  Just make generic_bignum bigger,
181*a9fa9459Szrj    and never write into the early words, thus they'll always be zero.
182*a9fa9459Szrj    I hate Dean's floating-point code.  Bleh.  */
183*a9fa9459Szrj LITTLENUM_TYPE generic_bignum[SIZE_OF_LARGE_NUMBER + 6];
184*a9fa9459Szrj 
185*a9fa9459Szrj FLONUM_TYPE generic_floating_point_number = {
186*a9fa9459Szrj   &generic_bignum[6],		/* low.  (JF: Was 0)  */
187*a9fa9459Szrj   &generic_bignum[SIZE_OF_LARGE_NUMBER + 6 - 1], /* high.  JF: (added +6)  */
188*a9fa9459Szrj   0,				/* leader.  */
189*a9fa9459Szrj   0,				/* exponent.  */
190*a9fa9459Szrj   0				/* sign.  */
191*a9fa9459Szrj };
192*a9fa9459Szrj 
193*a9fa9459Szrj 
194*a9fa9459Szrj static void
floating_constant(expressionS * expressionP)195*a9fa9459Szrj floating_constant (expressionS *expressionP)
196*a9fa9459Szrj {
197*a9fa9459Szrj   /* input_line_pointer -> floating-point constant.  */
198*a9fa9459Szrj   int error_code;
199*a9fa9459Szrj 
200*a9fa9459Szrj   error_code = atof_generic (&input_line_pointer, ".", EXP_CHARS,
201*a9fa9459Szrj 			     &generic_floating_point_number);
202*a9fa9459Szrj 
203*a9fa9459Szrj   if (error_code)
204*a9fa9459Szrj     {
205*a9fa9459Szrj       if (error_code == ERROR_EXPONENT_OVERFLOW)
206*a9fa9459Szrj 	{
207*a9fa9459Szrj 	  as_bad (_("bad floating-point constant: exponent overflow"));
208*a9fa9459Szrj 	}
209*a9fa9459Szrj       else
210*a9fa9459Szrj 	{
211*a9fa9459Szrj 	  as_bad (_("bad floating-point constant: unknown error code=%d"),
212*a9fa9459Szrj 		  error_code);
213*a9fa9459Szrj 	}
214*a9fa9459Szrj     }
215*a9fa9459Szrj   expressionP->X_op = O_big;
216*a9fa9459Szrj   /* input_line_pointer -> just after constant, which may point to
217*a9fa9459Szrj      whitespace.  */
218*a9fa9459Szrj   expressionP->X_add_number = -1;
219*a9fa9459Szrj }
220*a9fa9459Szrj 
221*a9fa9459Szrj static valueT
generic_bignum_to_int32(void)222*a9fa9459Szrj generic_bignum_to_int32 (void)
223*a9fa9459Szrj {
224*a9fa9459Szrj   valueT number =
225*a9fa9459Szrj 	   ((generic_bignum[1] & LITTLENUM_MASK) << LITTLENUM_NUMBER_OF_BITS)
226*a9fa9459Szrj 	   | (generic_bignum[0] & LITTLENUM_MASK);
227*a9fa9459Szrj   number &= 0xffffffff;
228*a9fa9459Szrj   return number;
229*a9fa9459Szrj }
230*a9fa9459Szrj 
231*a9fa9459Szrj #ifdef BFD64
232*a9fa9459Szrj static valueT
generic_bignum_to_int64(void)233*a9fa9459Szrj generic_bignum_to_int64 (void)
234*a9fa9459Szrj {
235*a9fa9459Szrj   valueT number =
236*a9fa9459Szrj     ((((((((valueT) generic_bignum[3] & LITTLENUM_MASK)
237*a9fa9459Szrj 	  << LITTLENUM_NUMBER_OF_BITS)
238*a9fa9459Szrj 	 | ((valueT) generic_bignum[2] & LITTLENUM_MASK))
239*a9fa9459Szrj 	<< LITTLENUM_NUMBER_OF_BITS)
240*a9fa9459Szrj        | ((valueT) generic_bignum[1] & LITTLENUM_MASK))
241*a9fa9459Szrj       << LITTLENUM_NUMBER_OF_BITS)
242*a9fa9459Szrj      | ((valueT) generic_bignum[0] & LITTLENUM_MASK));
243*a9fa9459Szrj   return number;
244*a9fa9459Szrj }
245*a9fa9459Szrj #endif
246*a9fa9459Szrj 
247*a9fa9459Szrj static void
integer_constant(int radix,expressionS * expressionP)248*a9fa9459Szrj integer_constant (int radix, expressionS *expressionP)
249*a9fa9459Szrj {
250*a9fa9459Szrj   char *start;		/* Start of number.  */
251*a9fa9459Szrj   char *suffix = NULL;
252*a9fa9459Szrj   char c;
253*a9fa9459Szrj   valueT number;	/* Offset or (absolute) value.  */
254*a9fa9459Szrj   short int digit;	/* Value of next digit in current radix.  */
255*a9fa9459Szrj   short int maxdig = 0;	/* Highest permitted digit value.  */
256*a9fa9459Szrj   int too_many_digits = 0;	/* If we see >= this number of.  */
257*a9fa9459Szrj   char *name;		/* Points to name of symbol.  */
258*a9fa9459Szrj   symbolS *symbolP;	/* Points to symbol.  */
259*a9fa9459Szrj 
260*a9fa9459Szrj   int small;			/* True if fits in 32 bits.  */
261*a9fa9459Szrj 
262*a9fa9459Szrj   /* May be bignum, or may fit in 32 bits.  */
263*a9fa9459Szrj   /* Most numbers fit into 32 bits, and we want this case to be fast.
264*a9fa9459Szrj      so we pretend it will fit into 32 bits.  If, after making up a 32
265*a9fa9459Szrj      bit number, we realise that we have scanned more digits than
266*a9fa9459Szrj      comfortably fit into 32 bits, we re-scan the digits coding them
267*a9fa9459Szrj      into a bignum.  For decimal and octal numbers we are
268*a9fa9459Szrj      conservative: Some numbers may be assumed bignums when in fact
269*a9fa9459Szrj      they do fit into 32 bits.  Numbers of any radix can have excess
270*a9fa9459Szrj      leading zeros: We strive to recognise this and cast them back
271*a9fa9459Szrj      into 32 bits.  We must check that the bignum really is more than
272*a9fa9459Szrj      32 bits, and change it back to a 32-bit number if it fits.  The
273*a9fa9459Szrj      number we are looking for is expected to be positive, but if it
274*a9fa9459Szrj      fits into 32 bits as an unsigned number, we let it be a 32-bit
275*a9fa9459Szrj      number.  The cavalier approach is for speed in ordinary cases.  */
276*a9fa9459Szrj   /* This has been extended for 64 bits.  We blindly assume that if
277*a9fa9459Szrj      you're compiling in 64-bit mode, the target is a 64-bit machine.
278*a9fa9459Szrj      This should be cleaned up.  */
279*a9fa9459Szrj 
280*a9fa9459Szrj #ifdef BFD64
281*a9fa9459Szrj #define valuesize 64
282*a9fa9459Szrj #else /* includes non-bfd case, mostly */
283*a9fa9459Szrj #define valuesize 32
284*a9fa9459Szrj #endif
285*a9fa9459Szrj 
286*a9fa9459Szrj   if (is_end_of_line[(unsigned char) *input_line_pointer])
287*a9fa9459Szrj     {
288*a9fa9459Szrj       expressionP->X_op = O_absent;
289*a9fa9459Szrj       return;
290*a9fa9459Szrj     }
291*a9fa9459Szrj 
292*a9fa9459Szrj   if ((NUMBERS_WITH_SUFFIX || flag_m68k_mri) && radix == 0)
293*a9fa9459Szrj     {
294*a9fa9459Szrj       int flt = 0;
295*a9fa9459Szrj 
296*a9fa9459Szrj       /* In MRI mode, the number may have a suffix indicating the
297*a9fa9459Szrj 	 radix.  For that matter, it might actually be a floating
298*a9fa9459Szrj 	 point constant.  */
299*a9fa9459Szrj       for (suffix = input_line_pointer; ISALNUM (*suffix); suffix++)
300*a9fa9459Szrj 	{
301*a9fa9459Szrj 	  if (*suffix == 'e' || *suffix == 'E')
302*a9fa9459Szrj 	    flt = 1;
303*a9fa9459Szrj 	}
304*a9fa9459Szrj 
305*a9fa9459Szrj       if (suffix == input_line_pointer)
306*a9fa9459Szrj 	{
307*a9fa9459Szrj 	  radix = 10;
308*a9fa9459Szrj 	  suffix = NULL;
309*a9fa9459Szrj 	}
310*a9fa9459Szrj       else
311*a9fa9459Szrj 	{
312*a9fa9459Szrj 	  c = *--suffix;
313*a9fa9459Szrj 	  c = TOUPPER (c);
314*a9fa9459Szrj 	  /* If we have both NUMBERS_WITH_SUFFIX and LOCAL_LABELS_FB,
315*a9fa9459Szrj 	     we distinguish between 'B' and 'b'.  This is the case for
316*a9fa9459Szrj 	     Z80.  */
317*a9fa9459Szrj 	  if ((NUMBERS_WITH_SUFFIX && LOCAL_LABELS_FB ? *suffix : c) == 'B')
318*a9fa9459Szrj 	    radix = 2;
319*a9fa9459Szrj 	  else if (c == 'D')
320*a9fa9459Szrj 	    radix = 10;
321*a9fa9459Szrj 	  else if (c == 'O' || c == 'Q')
322*a9fa9459Szrj 	    radix = 8;
323*a9fa9459Szrj 	  else if (c == 'H')
324*a9fa9459Szrj 	    radix = 16;
325*a9fa9459Szrj 	  else if (suffix[1] == '.' || c == 'E' || flt)
326*a9fa9459Szrj 	    {
327*a9fa9459Szrj 	      floating_constant (expressionP);
328*a9fa9459Szrj 	      return;
329*a9fa9459Szrj 	    }
330*a9fa9459Szrj 	  else
331*a9fa9459Szrj 	    {
332*a9fa9459Szrj 	      radix = 10;
333*a9fa9459Szrj 	      suffix = NULL;
334*a9fa9459Szrj 	    }
335*a9fa9459Szrj 	}
336*a9fa9459Szrj     }
337*a9fa9459Szrj 
338*a9fa9459Szrj   switch (radix)
339*a9fa9459Szrj     {
340*a9fa9459Szrj     case 2:
341*a9fa9459Szrj       maxdig = 2;
342*a9fa9459Szrj       too_many_digits = valuesize + 1;
343*a9fa9459Szrj       break;
344*a9fa9459Szrj     case 8:
345*a9fa9459Szrj       maxdig = radix = 8;
346*a9fa9459Szrj       too_many_digits = (valuesize + 2) / 3 + 1;
347*a9fa9459Szrj       break;
348*a9fa9459Szrj     case 16:
349*a9fa9459Szrj       maxdig = radix = 16;
350*a9fa9459Szrj       too_many_digits = (valuesize + 3) / 4 + 1;
351*a9fa9459Szrj       break;
352*a9fa9459Szrj     case 10:
353*a9fa9459Szrj       maxdig = radix = 10;
354*a9fa9459Szrj       too_many_digits = (valuesize + 11) / 4; /* Very rough.  */
355*a9fa9459Szrj     }
356*a9fa9459Szrj #undef valuesize
357*a9fa9459Szrj   start = input_line_pointer;
358*a9fa9459Szrj   c = *input_line_pointer++;
359*a9fa9459Szrj   for (number = 0;
360*a9fa9459Szrj        (digit = hex_value (c)) < maxdig;
361*a9fa9459Szrj        c = *input_line_pointer++)
362*a9fa9459Szrj     {
363*a9fa9459Szrj       number = number * radix + digit;
364*a9fa9459Szrj     }
365*a9fa9459Szrj   /* c contains character after number.  */
366*a9fa9459Szrj   /* input_line_pointer->char after c.  */
367*a9fa9459Szrj   small = (input_line_pointer - start - 1) < too_many_digits;
368*a9fa9459Szrj 
369*a9fa9459Szrj   if (radix == 16 && c == '_')
370*a9fa9459Szrj     {
371*a9fa9459Szrj       /* This is literal of the form 0x333_0_12345678_1.
372*a9fa9459Szrj 	 This example is equivalent to 0x00000333000000001234567800000001.  */
373*a9fa9459Szrj 
374*a9fa9459Szrj       int num_little_digits = 0;
375*a9fa9459Szrj       int i;
376*a9fa9459Szrj       input_line_pointer = start;	/* -> 1st digit.  */
377*a9fa9459Szrj 
378*a9fa9459Szrj       know (LITTLENUM_NUMBER_OF_BITS == 16);
379*a9fa9459Szrj 
380*a9fa9459Szrj       for (c = '_'; c == '_'; num_little_digits += 2)
381*a9fa9459Szrj 	{
382*a9fa9459Szrj 
383*a9fa9459Szrj 	  /* Convert one 64-bit word.  */
384*a9fa9459Szrj 	  int ndigit = 0;
385*a9fa9459Szrj 	  number = 0;
386*a9fa9459Szrj 	  for (c = *input_line_pointer++;
387*a9fa9459Szrj 	       (digit = hex_value (c)) < maxdig;
388*a9fa9459Szrj 	       c = *(input_line_pointer++))
389*a9fa9459Szrj 	    {
390*a9fa9459Szrj 	      number = number * radix + digit;
391*a9fa9459Szrj 	      ndigit++;
392*a9fa9459Szrj 	    }
393*a9fa9459Szrj 
394*a9fa9459Szrj 	  /* Check for 8 digit per word max.  */
395*a9fa9459Szrj 	  if (ndigit > 8)
396*a9fa9459Szrj 	    as_bad (_("a bignum with underscores may not have more than 8 hex digits in any word"));
397*a9fa9459Szrj 
398*a9fa9459Szrj 	  /* Add this chunk to the bignum.
399*a9fa9459Szrj 	     Shift things down 2 little digits.  */
400*a9fa9459Szrj 	  know (LITTLENUM_NUMBER_OF_BITS == 16);
401*a9fa9459Szrj 	  for (i = min (num_little_digits + 1, SIZE_OF_LARGE_NUMBER - 1);
402*a9fa9459Szrj 	       i >= 2;
403*a9fa9459Szrj 	       i--)
404*a9fa9459Szrj 	    generic_bignum[i] = generic_bignum[i - 2];
405*a9fa9459Szrj 
406*a9fa9459Szrj 	  /* Add the new digits as the least significant new ones.  */
407*a9fa9459Szrj 	  generic_bignum[0] = number & 0xffffffff;
408*a9fa9459Szrj 	  generic_bignum[1] = number >> 16;
409*a9fa9459Szrj 	}
410*a9fa9459Szrj 
411*a9fa9459Szrj       /* Again, c is char after number, input_line_pointer->after c.  */
412*a9fa9459Szrj 
413*a9fa9459Szrj       if (num_little_digits > SIZE_OF_LARGE_NUMBER - 1)
414*a9fa9459Szrj 	num_little_digits = SIZE_OF_LARGE_NUMBER - 1;
415*a9fa9459Szrj 
416*a9fa9459Szrj       gas_assert (num_little_digits >= 4);
417*a9fa9459Szrj 
418*a9fa9459Szrj       if (num_little_digits != 8)
419*a9fa9459Szrj 	as_bad (_("a bignum with underscores must have exactly 4 words"));
420*a9fa9459Szrj 
421*a9fa9459Szrj       /* We might have some leading zeros.  These can be trimmed to give
422*a9fa9459Szrj 	 us a change to fit this constant into a small number.  */
423*a9fa9459Szrj       while (generic_bignum[num_little_digits - 1] == 0
424*a9fa9459Szrj 	     && num_little_digits > 1)
425*a9fa9459Szrj 	num_little_digits--;
426*a9fa9459Szrj 
427*a9fa9459Szrj       if (num_little_digits <= 2)
428*a9fa9459Szrj 	{
429*a9fa9459Szrj 	  /* will fit into 32 bits.  */
430*a9fa9459Szrj 	  number = generic_bignum_to_int32 ();
431*a9fa9459Szrj 	  small = 1;
432*a9fa9459Szrj 	}
433*a9fa9459Szrj #ifdef BFD64
434*a9fa9459Szrj       else if (num_little_digits <= 4)
435*a9fa9459Szrj 	{
436*a9fa9459Szrj 	  /* Will fit into 64 bits.  */
437*a9fa9459Szrj 	  number = generic_bignum_to_int64 ();
438*a9fa9459Szrj 	  small = 1;
439*a9fa9459Szrj 	}
440*a9fa9459Szrj #endif
441*a9fa9459Szrj       else
442*a9fa9459Szrj 	{
443*a9fa9459Szrj 	  small = 0;
444*a9fa9459Szrj 
445*a9fa9459Szrj 	  /* Number of littlenums in the bignum.  */
446*a9fa9459Szrj 	  number = num_little_digits;
447*a9fa9459Szrj 	}
448*a9fa9459Szrj     }
449*a9fa9459Szrj   else if (!small)
450*a9fa9459Szrj     {
451*a9fa9459Szrj       /* We saw a lot of digits. manufacture a bignum the hard way.  */
452*a9fa9459Szrj       LITTLENUM_TYPE *leader;	/* -> high order littlenum of the bignum.  */
453*a9fa9459Szrj       LITTLENUM_TYPE *pointer;	/* -> littlenum we are frobbing now.  */
454*a9fa9459Szrj       long carry;
455*a9fa9459Szrj 
456*a9fa9459Szrj       leader = generic_bignum;
457*a9fa9459Szrj       generic_bignum[0] = 0;
458*a9fa9459Szrj       generic_bignum[1] = 0;
459*a9fa9459Szrj       generic_bignum[2] = 0;
460*a9fa9459Szrj       generic_bignum[3] = 0;
461*a9fa9459Szrj       input_line_pointer = start;	/* -> 1st digit.  */
462*a9fa9459Szrj       c = *input_line_pointer++;
463*a9fa9459Szrj       for (; (carry = hex_value (c)) < maxdig; c = *input_line_pointer++)
464*a9fa9459Szrj 	{
465*a9fa9459Szrj 	  for (pointer = generic_bignum; pointer <= leader; pointer++)
466*a9fa9459Szrj 	    {
467*a9fa9459Szrj 	      long work;
468*a9fa9459Szrj 
469*a9fa9459Szrj 	      work = carry + radix * *pointer;
470*a9fa9459Szrj 	      *pointer = work & LITTLENUM_MASK;
471*a9fa9459Szrj 	      carry = work >> LITTLENUM_NUMBER_OF_BITS;
472*a9fa9459Szrj 	    }
473*a9fa9459Szrj 	  if (carry)
474*a9fa9459Szrj 	    {
475*a9fa9459Szrj 	      if (leader < generic_bignum + SIZE_OF_LARGE_NUMBER - 1)
476*a9fa9459Szrj 		{
477*a9fa9459Szrj 		  /* Room to grow a longer bignum.  */
478*a9fa9459Szrj 		  *++leader = carry;
479*a9fa9459Szrj 		}
480*a9fa9459Szrj 	    }
481*a9fa9459Szrj 	}
482*a9fa9459Szrj       /* Again, c is char after number.  */
483*a9fa9459Szrj       /* input_line_pointer -> after c.  */
484*a9fa9459Szrj       know (LITTLENUM_NUMBER_OF_BITS == 16);
485*a9fa9459Szrj       if (leader < generic_bignum + 2)
486*a9fa9459Szrj 	{
487*a9fa9459Szrj 	  /* Will fit into 32 bits.  */
488*a9fa9459Szrj 	  number = generic_bignum_to_int32 ();
489*a9fa9459Szrj 	  small = 1;
490*a9fa9459Szrj 	}
491*a9fa9459Szrj #ifdef BFD64
492*a9fa9459Szrj       else if (leader < generic_bignum + 4)
493*a9fa9459Szrj 	{
494*a9fa9459Szrj 	  /* Will fit into 64 bits.  */
495*a9fa9459Szrj 	  number = generic_bignum_to_int64 ();
496*a9fa9459Szrj 	  small = 1;
497*a9fa9459Szrj 	}
498*a9fa9459Szrj #endif
499*a9fa9459Szrj       else
500*a9fa9459Szrj 	{
501*a9fa9459Szrj 	  /* Number of littlenums in the bignum.  */
502*a9fa9459Szrj 	  number = leader - generic_bignum + 1;
503*a9fa9459Szrj 	}
504*a9fa9459Szrj     }
505*a9fa9459Szrj 
506*a9fa9459Szrj   if ((NUMBERS_WITH_SUFFIX || flag_m68k_mri)
507*a9fa9459Szrj       && suffix != NULL
508*a9fa9459Szrj       && input_line_pointer - 1 == suffix)
509*a9fa9459Szrj     c = *input_line_pointer++;
510*a9fa9459Szrj 
511*a9fa9459Szrj #ifndef tc_allow_U_suffix
512*a9fa9459Szrj #define tc_allow_U_suffix 1
513*a9fa9459Szrj #endif
514*a9fa9459Szrj   /* PR 19910: Look for, and ignore, a U suffix to the number.  */
515*a9fa9459Szrj   if (tc_allow_U_suffix && (c == 'U' || c == 'u'))
516*a9fa9459Szrj     c = * input_line_pointer++;
517*a9fa9459Szrj 
518*a9fa9459Szrj   if (small)
519*a9fa9459Szrj     {
520*a9fa9459Szrj       /* Here with number, in correct radix. c is the next char.
521*a9fa9459Szrj 	 Note that unlike un*x, we allow "011f" "0x9f" to both mean
522*a9fa9459Szrj 	 the same as the (conventional) "9f".
523*a9fa9459Szrj 	 This is simply easier than checking for strict canonical
524*a9fa9459Szrj 	 form.  Syntax sux!  */
525*a9fa9459Szrj 
526*a9fa9459Szrj       if (LOCAL_LABELS_FB && c == 'b')
527*a9fa9459Szrj 	{
528*a9fa9459Szrj 	  /* Backward ref to local label.
529*a9fa9459Szrj 	     Because it is backward, expect it to be defined.  */
530*a9fa9459Szrj 	  /* Construct a local label.  */
531*a9fa9459Szrj 	  name = fb_label_name ((int) number, 0);
532*a9fa9459Szrj 
533*a9fa9459Szrj 	  /* Seen before, or symbol is defined: OK.  */
534*a9fa9459Szrj 	  symbolP = symbol_find (name);
535*a9fa9459Szrj 	  if ((symbolP != NULL) && (S_IS_DEFINED (symbolP)))
536*a9fa9459Szrj 	    {
537*a9fa9459Szrj 	      /* Local labels are never absolute.  Don't waste time
538*a9fa9459Szrj 		 checking absoluteness.  */
539*a9fa9459Szrj 	      know (SEG_NORMAL (S_GET_SEGMENT (symbolP)));
540*a9fa9459Szrj 
541*a9fa9459Szrj 	      expressionP->X_op = O_symbol;
542*a9fa9459Szrj 	      expressionP->X_add_symbol = symbolP;
543*a9fa9459Szrj 	    }
544*a9fa9459Szrj 	  else
545*a9fa9459Szrj 	    {
546*a9fa9459Szrj 	      /* Either not seen or not defined.  */
547*a9fa9459Szrj 	      /* @@ Should print out the original string instead of
548*a9fa9459Szrj 		 the parsed number.  */
549*a9fa9459Szrj 	      as_bad (_("backward ref to unknown label \"%d:\""),
550*a9fa9459Szrj 		      (int) number);
551*a9fa9459Szrj 	      expressionP->X_op = O_constant;
552*a9fa9459Szrj 	    }
553*a9fa9459Szrj 
554*a9fa9459Szrj 	  expressionP->X_add_number = 0;
555*a9fa9459Szrj 	}			/* case 'b' */
556*a9fa9459Szrj       else if (LOCAL_LABELS_FB && c == 'f')
557*a9fa9459Szrj 	{
558*a9fa9459Szrj 	  /* Forward reference.  Expect symbol to be undefined or
559*a9fa9459Szrj 	     unknown.  undefined: seen it before.  unknown: never seen
560*a9fa9459Szrj 	     it before.
561*a9fa9459Szrj 
562*a9fa9459Szrj 	     Construct a local label name, then an undefined symbol.
563*a9fa9459Szrj 	     Don't create a xseg frag for it: caller may do that.
564*a9fa9459Szrj 	     Just return it as never seen before.  */
565*a9fa9459Szrj 	  name = fb_label_name ((int) number, 1);
566*a9fa9459Szrj 	  symbolP = symbol_find_or_make (name);
567*a9fa9459Szrj 	  /* We have no need to check symbol properties.  */
568*a9fa9459Szrj #ifndef many_segments
569*a9fa9459Szrj 	  /* Since "know" puts its arg into a "string", we
570*a9fa9459Szrj 	     can't have newlines in the argument.  */
571*a9fa9459Szrj 	  know (S_GET_SEGMENT (symbolP) == undefined_section || S_GET_SEGMENT (symbolP) == text_section || S_GET_SEGMENT (symbolP) == data_section);
572*a9fa9459Szrj #endif
573*a9fa9459Szrj 	  expressionP->X_op = O_symbol;
574*a9fa9459Szrj 	  expressionP->X_add_symbol = symbolP;
575*a9fa9459Szrj 	  expressionP->X_add_number = 0;
576*a9fa9459Szrj 	}			/* case 'f' */
577*a9fa9459Szrj       else if (LOCAL_LABELS_DOLLAR && c == '$')
578*a9fa9459Szrj 	{
579*a9fa9459Szrj 	  /* If the dollar label is *currently* defined, then this is just
580*a9fa9459Szrj 	     another reference to it.  If it is not *currently* defined,
581*a9fa9459Szrj 	     then this is a fresh instantiation of that number, so create
582*a9fa9459Szrj 	     it.  */
583*a9fa9459Szrj 
584*a9fa9459Szrj 	  if (dollar_label_defined ((long) number))
585*a9fa9459Szrj 	    {
586*a9fa9459Szrj 	      name = dollar_label_name ((long) number, 0);
587*a9fa9459Szrj 	      symbolP = symbol_find (name);
588*a9fa9459Szrj 	      know (symbolP != NULL);
589*a9fa9459Szrj 	    }
590*a9fa9459Szrj 	  else
591*a9fa9459Szrj 	    {
592*a9fa9459Szrj 	      name = dollar_label_name ((long) number, 1);
593*a9fa9459Szrj 	      symbolP = symbol_find_or_make (name);
594*a9fa9459Szrj 	    }
595*a9fa9459Szrj 
596*a9fa9459Szrj 	  expressionP->X_op = O_symbol;
597*a9fa9459Szrj 	  expressionP->X_add_symbol = symbolP;
598*a9fa9459Szrj 	  expressionP->X_add_number = 0;
599*a9fa9459Szrj 	}			/* case '$' */
600*a9fa9459Szrj       else
601*a9fa9459Szrj 	{
602*a9fa9459Szrj 	  expressionP->X_op = O_constant;
603*a9fa9459Szrj 	  expressionP->X_add_number = number;
604*a9fa9459Szrj 	  input_line_pointer--;	/* Restore following character.  */
605*a9fa9459Szrj 	}			/* Really just a number.  */
606*a9fa9459Szrj     }
607*a9fa9459Szrj   else
608*a9fa9459Szrj     {
609*a9fa9459Szrj       /* Not a small number.  */
610*a9fa9459Szrj       expressionP->X_op = O_big;
611*a9fa9459Szrj       expressionP->X_add_number = number;	/* Number of littlenums.  */
612*a9fa9459Szrj       input_line_pointer--;	/* -> char following number.  */
613*a9fa9459Szrj     }
614*a9fa9459Szrj }
615*a9fa9459Szrj 
616*a9fa9459Szrj /* Parse an MRI multi character constant.  */
617*a9fa9459Szrj 
618*a9fa9459Szrj static void
mri_char_constant(expressionS * expressionP)619*a9fa9459Szrj mri_char_constant (expressionS *expressionP)
620*a9fa9459Szrj {
621*a9fa9459Szrj   int i;
622*a9fa9459Szrj 
623*a9fa9459Szrj   if (*input_line_pointer == '\''
624*a9fa9459Szrj       && input_line_pointer[1] != '\'')
625*a9fa9459Szrj     {
626*a9fa9459Szrj       expressionP->X_op = O_constant;
627*a9fa9459Szrj       expressionP->X_add_number = 0;
628*a9fa9459Szrj       return;
629*a9fa9459Szrj     }
630*a9fa9459Szrj 
631*a9fa9459Szrj   /* In order to get the correct byte ordering, we must build the
632*a9fa9459Szrj      number in reverse.  */
633*a9fa9459Szrj   for (i = SIZE_OF_LARGE_NUMBER - 1; i >= 0; i--)
634*a9fa9459Szrj     {
635*a9fa9459Szrj       int j;
636*a9fa9459Szrj 
637*a9fa9459Szrj       generic_bignum[i] = 0;
638*a9fa9459Szrj       for (j = 0; j < CHARS_PER_LITTLENUM; j++)
639*a9fa9459Szrj 	{
640*a9fa9459Szrj 	  if (*input_line_pointer == '\'')
641*a9fa9459Szrj 	    {
642*a9fa9459Szrj 	      if (input_line_pointer[1] != '\'')
643*a9fa9459Szrj 		break;
644*a9fa9459Szrj 	      ++input_line_pointer;
645*a9fa9459Szrj 	    }
646*a9fa9459Szrj 	  generic_bignum[i] <<= 8;
647*a9fa9459Szrj 	  generic_bignum[i] += *input_line_pointer;
648*a9fa9459Szrj 	  ++input_line_pointer;
649*a9fa9459Szrj 	}
650*a9fa9459Szrj 
651*a9fa9459Szrj       if (i < SIZE_OF_LARGE_NUMBER - 1)
652*a9fa9459Szrj 	{
653*a9fa9459Szrj 	  /* If there is more than one littlenum, left justify the
654*a9fa9459Szrj 	     last one to make it match the earlier ones.  If there is
655*a9fa9459Szrj 	     only one, we can just use the value directly.  */
656*a9fa9459Szrj 	  for (; j < CHARS_PER_LITTLENUM; j++)
657*a9fa9459Szrj 	    generic_bignum[i] <<= 8;
658*a9fa9459Szrj 	}
659*a9fa9459Szrj 
660*a9fa9459Szrj       if (*input_line_pointer == '\''
661*a9fa9459Szrj 	  && input_line_pointer[1] != '\'')
662*a9fa9459Szrj 	break;
663*a9fa9459Szrj     }
664*a9fa9459Szrj 
665*a9fa9459Szrj   if (i < 0)
666*a9fa9459Szrj     {
667*a9fa9459Szrj       as_bad (_("character constant too large"));
668*a9fa9459Szrj       i = 0;
669*a9fa9459Szrj     }
670*a9fa9459Szrj 
671*a9fa9459Szrj   if (i > 0)
672*a9fa9459Szrj     {
673*a9fa9459Szrj       int c;
674*a9fa9459Szrj       int j;
675*a9fa9459Szrj 
676*a9fa9459Szrj       c = SIZE_OF_LARGE_NUMBER - i;
677*a9fa9459Szrj       for (j = 0; j < c; j++)
678*a9fa9459Szrj 	generic_bignum[j] = generic_bignum[i + j];
679*a9fa9459Szrj       i = c;
680*a9fa9459Szrj     }
681*a9fa9459Szrj 
682*a9fa9459Szrj   know (LITTLENUM_NUMBER_OF_BITS == 16);
683*a9fa9459Szrj   if (i > 2)
684*a9fa9459Szrj     {
685*a9fa9459Szrj       expressionP->X_op = O_big;
686*a9fa9459Szrj       expressionP->X_add_number = i;
687*a9fa9459Szrj     }
688*a9fa9459Szrj   else
689*a9fa9459Szrj     {
690*a9fa9459Szrj       expressionP->X_op = O_constant;
691*a9fa9459Szrj       if (i < 2)
692*a9fa9459Szrj 	expressionP->X_add_number = generic_bignum[0] & LITTLENUM_MASK;
693*a9fa9459Szrj       else
694*a9fa9459Szrj 	expressionP->X_add_number =
695*a9fa9459Szrj 	  (((generic_bignum[1] & LITTLENUM_MASK)
696*a9fa9459Szrj 	    << LITTLENUM_NUMBER_OF_BITS)
697*a9fa9459Szrj 	   | (generic_bignum[0] & LITTLENUM_MASK));
698*a9fa9459Szrj     }
699*a9fa9459Szrj 
700*a9fa9459Szrj   /* Skip the final closing quote.  */
701*a9fa9459Szrj   ++input_line_pointer;
702*a9fa9459Szrj }
703*a9fa9459Szrj 
704*a9fa9459Szrj /* Return an expression representing the current location.  This
705*a9fa9459Szrj    handles the magic symbol `.'.  */
706*a9fa9459Szrj 
707*a9fa9459Szrj void
current_location(expressionS * expressionp)708*a9fa9459Szrj current_location (expressionS *expressionp)
709*a9fa9459Szrj {
710*a9fa9459Szrj   if (now_seg == absolute_section)
711*a9fa9459Szrj     {
712*a9fa9459Szrj       expressionp->X_op = O_constant;
713*a9fa9459Szrj       expressionp->X_add_number = abs_section_offset;
714*a9fa9459Szrj     }
715*a9fa9459Szrj   else
716*a9fa9459Szrj     {
717*a9fa9459Szrj       expressionp->X_op = O_symbol;
718*a9fa9459Szrj       expressionp->X_add_symbol = &dot_symbol;
719*a9fa9459Szrj       expressionp->X_add_number = 0;
720*a9fa9459Szrj     }
721*a9fa9459Szrj }
722*a9fa9459Szrj 
723*a9fa9459Szrj /* In:	Input_line_pointer points to 1st char of operand, which may
724*a9fa9459Szrj 	be a space.
725*a9fa9459Szrj 
726*a9fa9459Szrj    Out:	An expressionS.
727*a9fa9459Szrj 	The operand may have been empty: in this case X_op == O_absent.
728*a9fa9459Szrj 	Input_line_pointer->(next non-blank) char after operand.  */
729*a9fa9459Szrj 
730*a9fa9459Szrj static segT
operand(expressionS * expressionP,enum expr_mode mode)731*a9fa9459Szrj operand (expressionS *expressionP, enum expr_mode mode)
732*a9fa9459Szrj {
733*a9fa9459Szrj   char c;
734*a9fa9459Szrj   symbolS *symbolP;	/* Points to symbol.  */
735*a9fa9459Szrj   char *name;		/* Points to name of symbol.  */
736*a9fa9459Szrj   segT segment;
737*a9fa9459Szrj 
738*a9fa9459Szrj   /* All integers are regarded as unsigned unless they are negated.
739*a9fa9459Szrj      This is because the only thing which cares whether a number is
740*a9fa9459Szrj      unsigned is the code in emit_expr which extends constants into
741*a9fa9459Szrj      bignums.  It should only sign extend negative numbers, so that
742*a9fa9459Szrj      something like ``.quad 0x80000000'' is not sign extended even
743*a9fa9459Szrj      though it appears negative if valueT is 32 bits.  */
744*a9fa9459Szrj   expressionP->X_unsigned = 1;
745*a9fa9459Szrj   expressionP->X_extrabit = 0;
746*a9fa9459Szrj 
747*a9fa9459Szrj   /* Digits, assume it is a bignum.  */
748*a9fa9459Szrj 
749*a9fa9459Szrj   SKIP_WHITESPACE ();		/* Leading whitespace is part of operand.  */
750*a9fa9459Szrj   c = *input_line_pointer++;	/* input_line_pointer -> past char in c.  */
751*a9fa9459Szrj 
752*a9fa9459Szrj   if (is_end_of_line[(unsigned char) c])
753*a9fa9459Szrj     goto eol;
754*a9fa9459Szrj 
755*a9fa9459Szrj   switch (c)
756*a9fa9459Szrj     {
757*a9fa9459Szrj     case '1':
758*a9fa9459Szrj     case '2':
759*a9fa9459Szrj     case '3':
760*a9fa9459Szrj     case '4':
761*a9fa9459Szrj     case '5':
762*a9fa9459Szrj     case '6':
763*a9fa9459Szrj     case '7':
764*a9fa9459Szrj     case '8':
765*a9fa9459Szrj     case '9':
766*a9fa9459Szrj       input_line_pointer--;
767*a9fa9459Szrj 
768*a9fa9459Szrj       integer_constant ((NUMBERS_WITH_SUFFIX || flag_m68k_mri)
769*a9fa9459Szrj 			? 0 : 10,
770*a9fa9459Szrj 			expressionP);
771*a9fa9459Szrj       break;
772*a9fa9459Szrj 
773*a9fa9459Szrj #ifdef LITERAL_PREFIXDOLLAR_HEX
774*a9fa9459Szrj     case '$':
775*a9fa9459Szrj       /* $L is the start of a local label, not a hex constant.  */
776*a9fa9459Szrj       if (* input_line_pointer == 'L')
777*a9fa9459Szrj       goto isname;
778*a9fa9459Szrj       integer_constant (16, expressionP);
779*a9fa9459Szrj       break;
780*a9fa9459Szrj #endif
781*a9fa9459Szrj 
782*a9fa9459Szrj #ifdef LITERAL_PREFIXPERCENT_BIN
783*a9fa9459Szrj     case '%':
784*a9fa9459Szrj       integer_constant (2, expressionP);
785*a9fa9459Szrj       break;
786*a9fa9459Szrj #endif
787*a9fa9459Szrj 
788*a9fa9459Szrj     case '0':
789*a9fa9459Szrj       /* Non-decimal radix.  */
790*a9fa9459Szrj 
791*a9fa9459Szrj       if (NUMBERS_WITH_SUFFIX || flag_m68k_mri)
792*a9fa9459Szrj 	{
793*a9fa9459Szrj 	  char *s;
794*a9fa9459Szrj 
795*a9fa9459Szrj 	  /* Check for a hex or float constant.  */
796*a9fa9459Szrj 	  for (s = input_line_pointer; hex_p (*s); s++)
797*a9fa9459Szrj 	    ;
798*a9fa9459Szrj 	  if (*s == 'h' || *s == 'H' || *input_line_pointer == '.')
799*a9fa9459Szrj 	    {
800*a9fa9459Szrj 	      --input_line_pointer;
801*a9fa9459Szrj 	      integer_constant (0, expressionP);
802*a9fa9459Szrj 	      break;
803*a9fa9459Szrj 	    }
804*a9fa9459Szrj 	}
805*a9fa9459Szrj       c = *input_line_pointer;
806*a9fa9459Szrj       switch (c)
807*a9fa9459Szrj 	{
808*a9fa9459Szrj 	case 'o':
809*a9fa9459Szrj 	case 'O':
810*a9fa9459Szrj 	case 'q':
811*a9fa9459Szrj 	case 'Q':
812*a9fa9459Szrj 	case '8':
813*a9fa9459Szrj 	case '9':
814*a9fa9459Szrj 	  if (NUMBERS_WITH_SUFFIX || flag_m68k_mri)
815*a9fa9459Szrj 	    {
816*a9fa9459Szrj 	      integer_constant (0, expressionP);
817*a9fa9459Szrj 	      break;
818*a9fa9459Szrj 	    }
819*a9fa9459Szrj 	  /* Fall through.  */
820*a9fa9459Szrj 	default:
821*a9fa9459Szrj 	default_case:
822*a9fa9459Szrj 	  if (c && strchr (FLT_CHARS, c))
823*a9fa9459Szrj 	    {
824*a9fa9459Szrj 	      input_line_pointer++;
825*a9fa9459Szrj 	      floating_constant (expressionP);
826*a9fa9459Szrj 	      expressionP->X_add_number = - TOLOWER (c);
827*a9fa9459Szrj 	    }
828*a9fa9459Szrj 	  else
829*a9fa9459Szrj 	    {
830*a9fa9459Szrj 	      /* The string was only zero.  */
831*a9fa9459Szrj 	      expressionP->X_op = O_constant;
832*a9fa9459Szrj 	      expressionP->X_add_number = 0;
833*a9fa9459Szrj 	    }
834*a9fa9459Szrj 
835*a9fa9459Szrj 	  break;
836*a9fa9459Szrj 
837*a9fa9459Szrj 	case 'x':
838*a9fa9459Szrj 	case 'X':
839*a9fa9459Szrj 	  if (flag_m68k_mri)
840*a9fa9459Szrj 	    goto default_case;
841*a9fa9459Szrj 	  input_line_pointer++;
842*a9fa9459Szrj 	  integer_constant (16, expressionP);
843*a9fa9459Szrj 	  break;
844*a9fa9459Szrj 
845*a9fa9459Szrj 	case 'b':
846*a9fa9459Szrj 	  if (LOCAL_LABELS_FB && !flag_m68k_mri
847*a9fa9459Szrj 	      && input_line_pointer[1] != '0'
848*a9fa9459Szrj 	      && input_line_pointer[1] != '1')
849*a9fa9459Szrj 	    {
850*a9fa9459Szrj 	      /* Parse this as a back reference to label 0.  */
851*a9fa9459Szrj 	      input_line_pointer--;
852*a9fa9459Szrj 	      integer_constant (10, expressionP);
853*a9fa9459Szrj 	      break;
854*a9fa9459Szrj 	    }
855*a9fa9459Szrj 	  /* Otherwise, parse this as a binary number.  */
856*a9fa9459Szrj 	  /* Fall through.  */
857*a9fa9459Szrj 	case 'B':
858*a9fa9459Szrj 	  if (input_line_pointer[1] == '0'
859*a9fa9459Szrj 	      || input_line_pointer[1] == '1')
860*a9fa9459Szrj 	    {
861*a9fa9459Szrj 	      input_line_pointer++;
862*a9fa9459Szrj 	      integer_constant (2, expressionP);
863*a9fa9459Szrj 	      break;
864*a9fa9459Szrj 	    }
865*a9fa9459Szrj 	  if (flag_m68k_mri || NUMBERS_WITH_SUFFIX)
866*a9fa9459Szrj 	    input_line_pointer++;
867*a9fa9459Szrj 	  goto default_case;
868*a9fa9459Szrj 
869*a9fa9459Szrj 	case '0':
870*a9fa9459Szrj 	case '1':
871*a9fa9459Szrj 	case '2':
872*a9fa9459Szrj 	case '3':
873*a9fa9459Szrj 	case '4':
874*a9fa9459Szrj 	case '5':
875*a9fa9459Szrj 	case '6':
876*a9fa9459Szrj 	case '7':
877*a9fa9459Szrj 	  integer_constant ((flag_m68k_mri || NUMBERS_WITH_SUFFIX)
878*a9fa9459Szrj 			    ? 0 : 8,
879*a9fa9459Szrj 			    expressionP);
880*a9fa9459Szrj 	  break;
881*a9fa9459Szrj 
882*a9fa9459Szrj 	case 'f':
883*a9fa9459Szrj 	  if (LOCAL_LABELS_FB)
884*a9fa9459Szrj 	    {
885*a9fa9459Szrj 	      int is_label = 1;
886*a9fa9459Szrj 
887*a9fa9459Szrj 	      /* If it says "0f" and it could possibly be a floating point
888*a9fa9459Szrj 		 number, make it one.  Otherwise, make it a local label,
889*a9fa9459Szrj 		 and try to deal with parsing the rest later.  */
890*a9fa9459Szrj 	      if (!is_end_of_line[(unsigned char) input_line_pointer[1]]
891*a9fa9459Szrj 		  && strchr (FLT_CHARS, 'f') != NULL)
892*a9fa9459Szrj 		{
893*a9fa9459Szrj 		  char *cp = input_line_pointer + 1;
894*a9fa9459Szrj 
895*a9fa9459Szrj 		  atof_generic (&cp, ".", EXP_CHARS,
896*a9fa9459Szrj 				&generic_floating_point_number);
897*a9fa9459Szrj 
898*a9fa9459Szrj 		  /* Was nothing parsed, or does it look like an
899*a9fa9459Szrj 		     expression?  */
900*a9fa9459Szrj 		  is_label = (cp == input_line_pointer + 1
901*a9fa9459Szrj 			      || (cp == input_line_pointer + 2
902*a9fa9459Szrj 				  && (cp[-1] == '-' || cp[-1] == '+'))
903*a9fa9459Szrj 			      || *cp == 'f'
904*a9fa9459Szrj 			      || *cp == 'b');
905*a9fa9459Szrj 		}
906*a9fa9459Szrj 	      if (is_label)
907*a9fa9459Szrj 		{
908*a9fa9459Szrj 		  input_line_pointer--;
909*a9fa9459Szrj 		  integer_constant (10, expressionP);
910*a9fa9459Szrj 		  break;
911*a9fa9459Szrj 		}
912*a9fa9459Szrj 	    }
913*a9fa9459Szrj 	  /* Fall through.  */
914*a9fa9459Szrj 
915*a9fa9459Szrj 	case 'd':
916*a9fa9459Szrj 	case 'D':
917*a9fa9459Szrj 	  if (flag_m68k_mri || NUMBERS_WITH_SUFFIX)
918*a9fa9459Szrj 	    {
919*a9fa9459Szrj 	      integer_constant (0, expressionP);
920*a9fa9459Szrj 	      break;
921*a9fa9459Szrj 	    }
922*a9fa9459Szrj 	  /* Fall through.  */
923*a9fa9459Szrj 	case 'F':
924*a9fa9459Szrj 	case 'r':
925*a9fa9459Szrj 	case 'e':
926*a9fa9459Szrj 	case 'E':
927*a9fa9459Szrj 	case 'g':
928*a9fa9459Szrj 	case 'G':
929*a9fa9459Szrj 	  input_line_pointer++;
930*a9fa9459Szrj 	  floating_constant (expressionP);
931*a9fa9459Szrj 	  expressionP->X_add_number = - TOLOWER (c);
932*a9fa9459Szrj 	  break;
933*a9fa9459Szrj 
934*a9fa9459Szrj 	case '$':
935*a9fa9459Szrj 	  if (LOCAL_LABELS_DOLLAR)
936*a9fa9459Szrj 	    {
937*a9fa9459Szrj 	      integer_constant (10, expressionP);
938*a9fa9459Szrj 	      break;
939*a9fa9459Szrj 	    }
940*a9fa9459Szrj 	  else
941*a9fa9459Szrj 	    goto default_case;
942*a9fa9459Szrj 	}
943*a9fa9459Szrj 
944*a9fa9459Szrj       break;
945*a9fa9459Szrj 
946*a9fa9459Szrj #ifndef NEED_INDEX_OPERATOR
947*a9fa9459Szrj     case '[':
948*a9fa9459Szrj # ifdef md_need_index_operator
949*a9fa9459Szrj       if (md_need_index_operator())
950*a9fa9459Szrj 	goto de_fault;
951*a9fa9459Szrj # endif
952*a9fa9459Szrj       /* FALLTHROUGH */
953*a9fa9459Szrj #endif
954*a9fa9459Szrj     case '(':
955*a9fa9459Szrj       /* Didn't begin with digit & not a name.  */
956*a9fa9459Szrj       segment = expr (0, expressionP, mode);
957*a9fa9459Szrj       /* expression () will pass trailing whitespace.  */
958*a9fa9459Szrj       if ((c == '(' && *input_line_pointer != ')')
959*a9fa9459Szrj 	  || (c == '[' && *input_line_pointer != ']'))
960*a9fa9459Szrj 	{
961*a9fa9459Szrj 	  if (* input_line_pointer)
962*a9fa9459Szrj 	    as_bad (_("found '%c', expected: '%c'"),
963*a9fa9459Szrj 		    * input_line_pointer, c == '(' ? ')' : ']');
964*a9fa9459Szrj 	  else
965*a9fa9459Szrj 	    as_bad (_("missing '%c'"), c == '(' ? ')' : ']');
966*a9fa9459Szrj 	}
967*a9fa9459Szrj       else
968*a9fa9459Szrj 	input_line_pointer++;
969*a9fa9459Szrj       SKIP_WHITESPACE ();
970*a9fa9459Szrj       /* Here with input_line_pointer -> char after "(...)".  */
971*a9fa9459Szrj       return segment;
972*a9fa9459Szrj 
973*a9fa9459Szrj #ifdef TC_M68K
974*a9fa9459Szrj     case 'E':
975*a9fa9459Szrj       if (! flag_m68k_mri || *input_line_pointer != '\'')
976*a9fa9459Szrj 	goto de_fault;
977*a9fa9459Szrj       as_bad (_("EBCDIC constants are not supported"));
978*a9fa9459Szrj       /* Fall through.  */
979*a9fa9459Szrj     case 'A':
980*a9fa9459Szrj       if (! flag_m68k_mri || *input_line_pointer != '\'')
981*a9fa9459Szrj 	goto de_fault;
982*a9fa9459Szrj       ++input_line_pointer;
983*a9fa9459Szrj       /* Fall through.  */
984*a9fa9459Szrj #endif
985*a9fa9459Szrj     case '\'':
986*a9fa9459Szrj       if (! flag_m68k_mri)
987*a9fa9459Szrj 	{
988*a9fa9459Szrj 	  /* Warning: to conform to other people's assemblers NO
989*a9fa9459Szrj 	     ESCAPEMENT is permitted for a single quote.  The next
990*a9fa9459Szrj 	     character, parity errors and all, is taken as the value
991*a9fa9459Szrj 	     of the operand.  VERY KINKY.  */
992*a9fa9459Szrj 	  expressionP->X_op = O_constant;
993*a9fa9459Szrj 	  expressionP->X_add_number = *input_line_pointer++;
994*a9fa9459Szrj 	  break;
995*a9fa9459Szrj 	}
996*a9fa9459Szrj 
997*a9fa9459Szrj       mri_char_constant (expressionP);
998*a9fa9459Szrj       break;
999*a9fa9459Szrj 
1000*a9fa9459Szrj #ifdef TC_M68K
1001*a9fa9459Szrj     case '"':
1002*a9fa9459Szrj       /* Double quote is the bitwise not operator in MRI mode.  */
1003*a9fa9459Szrj       if (! flag_m68k_mri)
1004*a9fa9459Szrj 	goto de_fault;
1005*a9fa9459Szrj       /* Fall through.  */
1006*a9fa9459Szrj #endif
1007*a9fa9459Szrj     case '~':
1008*a9fa9459Szrj       /* '~' is permitted to start a label on the Delta.  */
1009*a9fa9459Szrj       if (is_name_beginner (c))
1010*a9fa9459Szrj 	goto isname;
1011*a9fa9459Szrj     case '!':
1012*a9fa9459Szrj     case '-':
1013*a9fa9459Szrj     case '+':
1014*a9fa9459Szrj       {
1015*a9fa9459Szrj #ifdef md_operator
1016*a9fa9459Szrj       unary:
1017*a9fa9459Szrj #endif
1018*a9fa9459Szrj 	operand (expressionP, mode);
1019*a9fa9459Szrj 	if (expressionP->X_op == O_constant)
1020*a9fa9459Szrj 	  {
1021*a9fa9459Szrj 	    /* input_line_pointer -> char after operand.  */
1022*a9fa9459Szrj 	    if (c == '-')
1023*a9fa9459Szrj 	      {
1024*a9fa9459Szrj 		expressionP->X_add_number
1025*a9fa9459Szrj 		  = - (addressT) expressionP->X_add_number;
1026*a9fa9459Szrj 		/* Notice: '-' may overflow: no warning is given.
1027*a9fa9459Szrj 		   This is compatible with other people's
1028*a9fa9459Szrj 		   assemblers.  Sigh.  */
1029*a9fa9459Szrj 		expressionP->X_unsigned = 0;
1030*a9fa9459Szrj 		if (expressionP->X_add_number)
1031*a9fa9459Szrj 		  expressionP->X_extrabit ^= 1;
1032*a9fa9459Szrj 	      }
1033*a9fa9459Szrj 	    else if (c == '~' || c == '"')
1034*a9fa9459Szrj 	      expressionP->X_add_number = ~ expressionP->X_add_number;
1035*a9fa9459Szrj 	    else if (c == '!')
1036*a9fa9459Szrj 	      expressionP->X_add_number = ! expressionP->X_add_number;
1037*a9fa9459Szrj 	  }
1038*a9fa9459Szrj 	else if (expressionP->X_op == O_big
1039*a9fa9459Szrj 		 && expressionP->X_add_number <= 0
1040*a9fa9459Szrj 		 && c == '-'
1041*a9fa9459Szrj 		 && (generic_floating_point_number.sign == '+'
1042*a9fa9459Szrj 		     || generic_floating_point_number.sign == 'P'))
1043*a9fa9459Szrj 	  {
1044*a9fa9459Szrj 	    /* Negative flonum (eg, -1.000e0).  */
1045*a9fa9459Szrj 	    if (generic_floating_point_number.sign == '+')
1046*a9fa9459Szrj 	      generic_floating_point_number.sign = '-';
1047*a9fa9459Szrj 	    else
1048*a9fa9459Szrj 	      generic_floating_point_number.sign = 'N';
1049*a9fa9459Szrj 	  }
1050*a9fa9459Szrj 	else if (expressionP->X_op == O_big
1051*a9fa9459Szrj 		 && expressionP->X_add_number > 0)
1052*a9fa9459Szrj 	  {
1053*a9fa9459Szrj 	    int i;
1054*a9fa9459Szrj 
1055*a9fa9459Szrj 	    if (c == '~' || c == '-')
1056*a9fa9459Szrj 	      {
1057*a9fa9459Szrj 		for (i = 0; i < expressionP->X_add_number; ++i)
1058*a9fa9459Szrj 		  generic_bignum[i] = ~generic_bignum[i];
1059*a9fa9459Szrj 
1060*a9fa9459Szrj 		/* Extend the bignum to at least the size of .octa.  */
1061*a9fa9459Szrj 		if (expressionP->X_add_number < SIZE_OF_LARGE_NUMBER)
1062*a9fa9459Szrj 		  {
1063*a9fa9459Szrj 		    expressionP->X_add_number = SIZE_OF_LARGE_NUMBER;
1064*a9fa9459Szrj 		    for (; i < expressionP->X_add_number; ++i)
1065*a9fa9459Szrj 		      generic_bignum[i] = ~(LITTLENUM_TYPE) 0;
1066*a9fa9459Szrj 		  }
1067*a9fa9459Szrj 
1068*a9fa9459Szrj 		if (c == '-')
1069*a9fa9459Szrj 		  for (i = 0; i < expressionP->X_add_number; ++i)
1070*a9fa9459Szrj 		    {
1071*a9fa9459Szrj 		      generic_bignum[i] += 1;
1072*a9fa9459Szrj 		      if (generic_bignum[i])
1073*a9fa9459Szrj 			break;
1074*a9fa9459Szrj 		    }
1075*a9fa9459Szrj 	      }
1076*a9fa9459Szrj 	    else if (c == '!')
1077*a9fa9459Szrj 	      {
1078*a9fa9459Szrj 		for (i = 0; i < expressionP->X_add_number; ++i)
1079*a9fa9459Szrj 		  if (generic_bignum[i] != 0)
1080*a9fa9459Szrj 		    break;
1081*a9fa9459Szrj 		expressionP->X_add_number = i >= expressionP->X_add_number;
1082*a9fa9459Szrj 		expressionP->X_op = O_constant;
1083*a9fa9459Szrj 		expressionP->X_unsigned = 1;
1084*a9fa9459Szrj 		expressionP->X_extrabit = 0;
1085*a9fa9459Szrj 	      }
1086*a9fa9459Szrj 	  }
1087*a9fa9459Szrj 	else if (expressionP->X_op != O_illegal
1088*a9fa9459Szrj 		 && expressionP->X_op != O_absent)
1089*a9fa9459Szrj 	  {
1090*a9fa9459Szrj 	    if (c != '+')
1091*a9fa9459Szrj 	      {
1092*a9fa9459Szrj 		expressionP->X_add_symbol = make_expr_symbol (expressionP);
1093*a9fa9459Szrj 		if (c == '-')
1094*a9fa9459Szrj 		  expressionP->X_op = O_uminus;
1095*a9fa9459Szrj 		else if (c == '~' || c == '"')
1096*a9fa9459Szrj 		  expressionP->X_op = O_bit_not;
1097*a9fa9459Szrj 		else
1098*a9fa9459Szrj 		  expressionP->X_op = O_logical_not;
1099*a9fa9459Szrj 		expressionP->X_add_number = 0;
1100*a9fa9459Szrj 	      }
1101*a9fa9459Szrj 	  }
1102*a9fa9459Szrj 	else
1103*a9fa9459Szrj 	  as_warn (_("Unary operator %c ignored because bad operand follows"),
1104*a9fa9459Szrj 		   c);
1105*a9fa9459Szrj       }
1106*a9fa9459Szrj       break;
1107*a9fa9459Szrj 
1108*a9fa9459Szrj #if defined (DOLLAR_DOT) || defined (TC_M68K)
1109*a9fa9459Szrj     case '$':
1110*a9fa9459Szrj       /* '$' is the program counter when in MRI mode, or when
1111*a9fa9459Szrj 	 DOLLAR_DOT is defined.  */
1112*a9fa9459Szrj #ifndef DOLLAR_DOT
1113*a9fa9459Szrj       if (! flag_m68k_mri)
1114*a9fa9459Szrj 	goto de_fault;
1115*a9fa9459Szrj #endif
1116*a9fa9459Szrj       if (DOLLAR_AMBIGU && hex_p (*input_line_pointer))
1117*a9fa9459Szrj 	{
1118*a9fa9459Szrj 	  /* In MRI mode and on Z80, '$' is also used as the prefix
1119*a9fa9459Szrj 	     for a hexadecimal constant.  */
1120*a9fa9459Szrj 	  integer_constant (16, expressionP);
1121*a9fa9459Szrj 	  break;
1122*a9fa9459Szrj 	}
1123*a9fa9459Szrj 
1124*a9fa9459Szrj       if (is_part_of_name (*input_line_pointer))
1125*a9fa9459Szrj 	goto isname;
1126*a9fa9459Szrj 
1127*a9fa9459Szrj       current_location (expressionP);
1128*a9fa9459Szrj       break;
1129*a9fa9459Szrj #endif
1130*a9fa9459Szrj 
1131*a9fa9459Szrj     case '.':
1132*a9fa9459Szrj       if (!is_part_of_name (*input_line_pointer))
1133*a9fa9459Szrj 	{
1134*a9fa9459Szrj 	  current_location (expressionP);
1135*a9fa9459Szrj 	  break;
1136*a9fa9459Szrj 	}
1137*a9fa9459Szrj       else if ((strncasecmp (input_line_pointer, "startof.", 8) == 0
1138*a9fa9459Szrj 		&& ! is_part_of_name (input_line_pointer[8]))
1139*a9fa9459Szrj 	       || (strncasecmp (input_line_pointer, "sizeof.", 7) == 0
1140*a9fa9459Szrj 		   && ! is_part_of_name (input_line_pointer[7])))
1141*a9fa9459Szrj 	{
1142*a9fa9459Szrj 	  int start;
1143*a9fa9459Szrj 
1144*a9fa9459Szrj 	  start = (input_line_pointer[1] == 't'
1145*a9fa9459Szrj 		   || input_line_pointer[1] == 'T');
1146*a9fa9459Szrj 	  input_line_pointer += start ? 8 : 7;
1147*a9fa9459Szrj 	  SKIP_WHITESPACE ();
1148*a9fa9459Szrj 	  if (*input_line_pointer != '(')
1149*a9fa9459Szrj 	    as_bad (_("syntax error in .startof. or .sizeof."));
1150*a9fa9459Szrj 	  else
1151*a9fa9459Szrj 	    {
1152*a9fa9459Szrj 	      char *buf;
1153*a9fa9459Szrj 
1154*a9fa9459Szrj 	      ++input_line_pointer;
1155*a9fa9459Szrj 	      SKIP_WHITESPACE ();
1156*a9fa9459Szrj 	      c = get_symbol_name (& name);
1157*a9fa9459Szrj 
1158*a9fa9459Szrj 	      buf = concat (start ? ".startof." : ".sizeof.", name,
1159*a9fa9459Szrj 			    (char *) NULL);
1160*a9fa9459Szrj 	      symbolP = symbol_make (buf);
1161*a9fa9459Szrj 	      free (buf);
1162*a9fa9459Szrj 
1163*a9fa9459Szrj 	      expressionP->X_op = O_symbol;
1164*a9fa9459Szrj 	      expressionP->X_add_symbol = symbolP;
1165*a9fa9459Szrj 	      expressionP->X_add_number = 0;
1166*a9fa9459Szrj 
1167*a9fa9459Szrj 	      *input_line_pointer = c;
1168*a9fa9459Szrj 	      SKIP_WHITESPACE_AFTER_NAME ();
1169*a9fa9459Szrj 	      if (*input_line_pointer != ')')
1170*a9fa9459Szrj 		as_bad (_("syntax error in .startof. or .sizeof."));
1171*a9fa9459Szrj 	      else
1172*a9fa9459Szrj 		++input_line_pointer;
1173*a9fa9459Szrj 	    }
1174*a9fa9459Szrj 	  break;
1175*a9fa9459Szrj 	}
1176*a9fa9459Szrj       else
1177*a9fa9459Szrj 	{
1178*a9fa9459Szrj 	  goto isname;
1179*a9fa9459Szrj 	}
1180*a9fa9459Szrj 
1181*a9fa9459Szrj     case ',':
1182*a9fa9459Szrj     eol:
1183*a9fa9459Szrj       /* Can't imagine any other kind of operand.  */
1184*a9fa9459Szrj       expressionP->X_op = O_absent;
1185*a9fa9459Szrj       input_line_pointer--;
1186*a9fa9459Szrj       break;
1187*a9fa9459Szrj 
1188*a9fa9459Szrj #ifdef TC_M68K
1189*a9fa9459Szrj     case '%':
1190*a9fa9459Szrj       if (! flag_m68k_mri)
1191*a9fa9459Szrj 	goto de_fault;
1192*a9fa9459Szrj       integer_constant (2, expressionP);
1193*a9fa9459Szrj       break;
1194*a9fa9459Szrj 
1195*a9fa9459Szrj     case '@':
1196*a9fa9459Szrj       if (! flag_m68k_mri)
1197*a9fa9459Szrj 	goto de_fault;
1198*a9fa9459Szrj       integer_constant (8, expressionP);
1199*a9fa9459Szrj       break;
1200*a9fa9459Szrj 
1201*a9fa9459Szrj     case ':':
1202*a9fa9459Szrj       if (! flag_m68k_mri)
1203*a9fa9459Szrj 	goto de_fault;
1204*a9fa9459Szrj 
1205*a9fa9459Szrj       /* In MRI mode, this is a floating point constant represented
1206*a9fa9459Szrj 	 using hexadecimal digits.  */
1207*a9fa9459Szrj 
1208*a9fa9459Szrj       ++input_line_pointer;
1209*a9fa9459Szrj       integer_constant (16, expressionP);
1210*a9fa9459Szrj       break;
1211*a9fa9459Szrj 
1212*a9fa9459Szrj     case '*':
1213*a9fa9459Szrj       if (! flag_m68k_mri || is_part_of_name (*input_line_pointer))
1214*a9fa9459Szrj 	goto de_fault;
1215*a9fa9459Szrj 
1216*a9fa9459Szrj       current_location (expressionP);
1217*a9fa9459Szrj       break;
1218*a9fa9459Szrj #endif
1219*a9fa9459Szrj 
1220*a9fa9459Szrj     default:
1221*a9fa9459Szrj #if defined(md_need_index_operator) || defined(TC_M68K)
1222*a9fa9459Szrj     de_fault:
1223*a9fa9459Szrj #endif
1224*a9fa9459Szrj       if (is_name_beginner (c) || c == '"')	/* Here if did not begin with a digit.  */
1225*a9fa9459Szrj 	{
1226*a9fa9459Szrj 	  /* Identifier begins here.
1227*a9fa9459Szrj 	     This is kludged for speed, so code is repeated.  */
1228*a9fa9459Szrj 	isname:
1229*a9fa9459Szrj 	  -- input_line_pointer;
1230*a9fa9459Szrj 	  c = get_symbol_name (&name);
1231*a9fa9459Szrj 
1232*a9fa9459Szrj #ifdef md_operator
1233*a9fa9459Szrj 	  {
1234*a9fa9459Szrj 	    operatorT op = md_operator (name, 1, &c);
1235*a9fa9459Szrj 
1236*a9fa9459Szrj 	    switch (op)
1237*a9fa9459Szrj 	      {
1238*a9fa9459Szrj 	      case O_uminus:
1239*a9fa9459Szrj 		restore_line_pointer (c);
1240*a9fa9459Szrj 		c = '-';
1241*a9fa9459Szrj 		goto unary;
1242*a9fa9459Szrj 	      case O_bit_not:
1243*a9fa9459Szrj 		restore_line_pointer (c);
1244*a9fa9459Szrj 		c = '~';
1245*a9fa9459Szrj 		goto unary;
1246*a9fa9459Szrj 	      case O_logical_not:
1247*a9fa9459Szrj 		restore_line_pointer (c);
1248*a9fa9459Szrj 		c = '!';
1249*a9fa9459Szrj 		goto unary;
1250*a9fa9459Szrj 	      case O_illegal:
1251*a9fa9459Szrj 		as_bad (_("invalid use of operator \"%s\""), name);
1252*a9fa9459Szrj 		break;
1253*a9fa9459Szrj 	      default:
1254*a9fa9459Szrj 		break;
1255*a9fa9459Szrj 	      }
1256*a9fa9459Szrj 
1257*a9fa9459Szrj 	    if (op != O_absent && op != O_illegal)
1258*a9fa9459Szrj 	      {
1259*a9fa9459Szrj 		restore_line_pointer (c);
1260*a9fa9459Szrj 		expr (9, expressionP, mode);
1261*a9fa9459Szrj 		expressionP->X_add_symbol = make_expr_symbol (expressionP);
1262*a9fa9459Szrj 		expressionP->X_op_symbol = NULL;
1263*a9fa9459Szrj 		expressionP->X_add_number = 0;
1264*a9fa9459Szrj 		expressionP->X_op = op;
1265*a9fa9459Szrj 		break;
1266*a9fa9459Szrj 	      }
1267*a9fa9459Szrj 	  }
1268*a9fa9459Szrj #endif
1269*a9fa9459Szrj 
1270*a9fa9459Szrj #ifdef md_parse_name
1271*a9fa9459Szrj 	  /* This is a hook for the backend to parse certain names
1272*a9fa9459Szrj 	     specially in certain contexts.  If a name always has a
1273*a9fa9459Szrj 	     specific value, it can often be handled by simply
1274*a9fa9459Szrj 	     entering it in the symbol table.  */
1275*a9fa9459Szrj 	  if (md_parse_name (name, expressionP, mode, &c))
1276*a9fa9459Szrj 	    {
1277*a9fa9459Szrj 	      restore_line_pointer (c);
1278*a9fa9459Szrj 	      break;
1279*a9fa9459Szrj 	    }
1280*a9fa9459Szrj #endif
1281*a9fa9459Szrj 
1282*a9fa9459Szrj #ifdef TC_I960
1283*a9fa9459Szrj 	  /* The MRI i960 assembler permits
1284*a9fa9459Szrj 	         lda sizeof code,g13
1285*a9fa9459Szrj 	     FIXME: This should use md_parse_name.  */
1286*a9fa9459Szrj 	  if (flag_mri
1287*a9fa9459Szrj 	      && (strcasecmp (name, "sizeof") == 0
1288*a9fa9459Szrj 		  || strcasecmp (name, "startof") == 0))
1289*a9fa9459Szrj 	    {
1290*a9fa9459Szrj 	      int start;
1291*a9fa9459Szrj 	      char *buf;
1292*a9fa9459Szrj 
1293*a9fa9459Szrj 	      start = (name[1] == 't'
1294*a9fa9459Szrj 		       || name[1] == 'T');
1295*a9fa9459Szrj 
1296*a9fa9459Szrj 	      *input_line_pointer = c;
1297*a9fa9459Szrj 	      SKIP_WHITESPACE_AFTER_NAME ();
1298*a9fa9459Szrj 
1299*a9fa9459Szrj 	      c = get_symbol_name (& name);
1300*a9fa9459Szrj 
1301*a9fa9459Szrj 	      buf = concat (start ? ".startof." : ".sizeof.", name,
1302*a9fa9459Szrj 			    (char *) NULL);
1303*a9fa9459Szrj 	      symbolP = symbol_make (buf);
1304*a9fa9459Szrj 	      free (buf);
1305*a9fa9459Szrj 
1306*a9fa9459Szrj 	      expressionP->X_op = O_symbol;
1307*a9fa9459Szrj 	      expressionP->X_add_symbol = symbolP;
1308*a9fa9459Szrj 	      expressionP->X_add_number = 0;
1309*a9fa9459Szrj 
1310*a9fa9459Szrj 	      *input_line_pointer = c;
1311*a9fa9459Szrj 	      SKIP_WHITESPACE_AFTER_NAME ();
1312*a9fa9459Szrj 	      break;
1313*a9fa9459Szrj 	    }
1314*a9fa9459Szrj #endif
1315*a9fa9459Szrj 
1316*a9fa9459Szrj 	  symbolP = symbol_find_or_make (name);
1317*a9fa9459Szrj 
1318*a9fa9459Szrj 	  /* If we have an absolute symbol or a reg, then we know its
1319*a9fa9459Szrj 	     value now.  */
1320*a9fa9459Szrj 	  segment = S_GET_SEGMENT (symbolP);
1321*a9fa9459Szrj 	  if (mode != expr_defer
1322*a9fa9459Szrj 	      && segment == absolute_section
1323*a9fa9459Szrj 	      && !S_FORCE_RELOC (symbolP, 0))
1324*a9fa9459Szrj 	    {
1325*a9fa9459Szrj 	      expressionP->X_op = O_constant;
1326*a9fa9459Szrj 	      expressionP->X_add_number = S_GET_VALUE (symbolP);
1327*a9fa9459Szrj 	    }
1328*a9fa9459Szrj 	  else if (mode != expr_defer && segment == reg_section)
1329*a9fa9459Szrj 	    {
1330*a9fa9459Szrj 	      expressionP->X_op = O_register;
1331*a9fa9459Szrj 	      expressionP->X_add_number = S_GET_VALUE (symbolP);
1332*a9fa9459Szrj 	    }
1333*a9fa9459Szrj 	  else
1334*a9fa9459Szrj 	    {
1335*a9fa9459Szrj 	      expressionP->X_op = O_symbol;
1336*a9fa9459Szrj 	      expressionP->X_add_symbol = symbolP;
1337*a9fa9459Szrj 	      expressionP->X_add_number = 0;
1338*a9fa9459Szrj 	    }
1339*a9fa9459Szrj 
1340*a9fa9459Szrj 	  restore_line_pointer (c);
1341*a9fa9459Szrj 	}
1342*a9fa9459Szrj       else
1343*a9fa9459Szrj 	{
1344*a9fa9459Szrj 	  /* Let the target try to parse it.  Success is indicated by changing
1345*a9fa9459Szrj 	     the X_op field to something other than O_absent and pointing
1346*a9fa9459Szrj 	     input_line_pointer past the expression.  If it can't parse the
1347*a9fa9459Szrj 	     expression, X_op and input_line_pointer should be unchanged.  */
1348*a9fa9459Szrj 	  expressionP->X_op = O_absent;
1349*a9fa9459Szrj 	  --input_line_pointer;
1350*a9fa9459Szrj 	  md_operand (expressionP);
1351*a9fa9459Szrj 	  if (expressionP->X_op == O_absent)
1352*a9fa9459Szrj 	    {
1353*a9fa9459Szrj 	      ++input_line_pointer;
1354*a9fa9459Szrj 	      as_bad (_("bad expression"));
1355*a9fa9459Szrj 	      expressionP->X_op = O_constant;
1356*a9fa9459Szrj 	      expressionP->X_add_number = 0;
1357*a9fa9459Szrj 	    }
1358*a9fa9459Szrj 	}
1359*a9fa9459Szrj       break;
1360*a9fa9459Szrj     }
1361*a9fa9459Szrj 
1362*a9fa9459Szrj   /* It is more 'efficient' to clean up the expressionS when they are
1363*a9fa9459Szrj      created.  Doing it here saves lines of code.  */
1364*a9fa9459Szrj   clean_up_expression (expressionP);
1365*a9fa9459Szrj   SKIP_WHITESPACE ();		/* -> 1st char after operand.  */
1366*a9fa9459Szrj   know (*input_line_pointer != ' ');
1367*a9fa9459Szrj 
1368*a9fa9459Szrj   /* The PA port needs this information.  */
1369*a9fa9459Szrj   if (expressionP->X_add_symbol)
1370*a9fa9459Szrj     symbol_mark_used (expressionP->X_add_symbol);
1371*a9fa9459Szrj 
1372*a9fa9459Szrj   if (mode != expr_defer)
1373*a9fa9459Szrj     {
1374*a9fa9459Szrj       expressionP->X_add_symbol
1375*a9fa9459Szrj 	= symbol_clone_if_forward_ref (expressionP->X_add_symbol);
1376*a9fa9459Szrj       expressionP->X_op_symbol
1377*a9fa9459Szrj 	= symbol_clone_if_forward_ref (expressionP->X_op_symbol);
1378*a9fa9459Szrj     }
1379*a9fa9459Szrj 
1380*a9fa9459Szrj   switch (expressionP->X_op)
1381*a9fa9459Szrj     {
1382*a9fa9459Szrj     default:
1383*a9fa9459Szrj       return absolute_section;
1384*a9fa9459Szrj     case O_symbol:
1385*a9fa9459Szrj       return S_GET_SEGMENT (expressionP->X_add_symbol);
1386*a9fa9459Szrj     case O_register:
1387*a9fa9459Szrj       return reg_section;
1388*a9fa9459Szrj     }
1389*a9fa9459Szrj }
1390*a9fa9459Szrj 
1391*a9fa9459Szrj /* Internal.  Simplify a struct expression for use by expr ().  */
1392*a9fa9459Szrj 
1393*a9fa9459Szrj /* In:	address of an expressionS.
1394*a9fa9459Szrj 	The X_op field of the expressionS may only take certain values.
1395*a9fa9459Szrj 	Elsewise we waste time special-case testing. Sigh. Ditto SEG_ABSENT.
1396*a9fa9459Szrj 
1397*a9fa9459Szrj    Out:	expressionS may have been modified:
1398*a9fa9459Szrj 	Unused fields zeroed to help expr ().  */
1399*a9fa9459Szrj 
1400*a9fa9459Szrj static void
clean_up_expression(expressionS * expressionP)1401*a9fa9459Szrj clean_up_expression (expressionS *expressionP)
1402*a9fa9459Szrj {
1403*a9fa9459Szrj   switch (expressionP->X_op)
1404*a9fa9459Szrj     {
1405*a9fa9459Szrj     case O_illegal:
1406*a9fa9459Szrj     case O_absent:
1407*a9fa9459Szrj       expressionP->X_add_number = 0;
1408*a9fa9459Szrj       /* Fall through.  */
1409*a9fa9459Szrj     case O_big:
1410*a9fa9459Szrj     case O_constant:
1411*a9fa9459Szrj     case O_register:
1412*a9fa9459Szrj       expressionP->X_add_symbol = NULL;
1413*a9fa9459Szrj       /* Fall through.  */
1414*a9fa9459Szrj     case O_symbol:
1415*a9fa9459Szrj     case O_uminus:
1416*a9fa9459Szrj     case O_bit_not:
1417*a9fa9459Szrj       expressionP->X_op_symbol = NULL;
1418*a9fa9459Szrj       break;
1419*a9fa9459Szrj     default:
1420*a9fa9459Szrj       break;
1421*a9fa9459Szrj     }
1422*a9fa9459Szrj }
1423*a9fa9459Szrj 
1424*a9fa9459Szrj /* Expression parser.  */
1425*a9fa9459Szrj 
1426*a9fa9459Szrj /* We allow an empty expression, and just assume (absolute,0) silently.
1427*a9fa9459Szrj    Unary operators and parenthetical expressions are treated as operands.
1428*a9fa9459Szrj    As usual, Q==quantity==operand, O==operator, X==expression mnemonics.
1429*a9fa9459Szrj 
1430*a9fa9459Szrj    We used to do an aho/ullman shift-reduce parser, but the logic got so
1431*a9fa9459Szrj    warped that I flushed it and wrote a recursive-descent parser instead.
1432*a9fa9459Szrj    Now things are stable, would anybody like to write a fast parser?
1433*a9fa9459Szrj    Most expressions are either register (which does not even reach here)
1434*a9fa9459Szrj    or 1 symbol. Then "symbol+constant" and "symbol-symbol" are common.
1435*a9fa9459Szrj    So I guess it doesn't really matter how inefficient more complex expressions
1436*a9fa9459Szrj    are parsed.
1437*a9fa9459Szrj 
1438*a9fa9459Szrj    After expr(RANK,resultP) input_line_pointer->operator of rank <= RANK.
1439*a9fa9459Szrj    Also, we have consumed any leading or trailing spaces (operand does that)
1440*a9fa9459Szrj    and done all intervening operators.
1441*a9fa9459Szrj 
1442*a9fa9459Szrj    This returns the segment of the result, which will be
1443*a9fa9459Szrj    absolute_section or the segment of a symbol.  */
1444*a9fa9459Szrj 
1445*a9fa9459Szrj #undef __
1446*a9fa9459Szrj #define __ O_illegal
1447*a9fa9459Szrj #ifndef O_SINGLE_EQ
1448*a9fa9459Szrj #define O_SINGLE_EQ O_illegal
1449*a9fa9459Szrj #endif
1450*a9fa9459Szrj 
1451*a9fa9459Szrj /* Maps ASCII -> operators.  */
1452*a9fa9459Szrj static const operatorT op_encoding[256] = {
1453*a9fa9459Szrj   __, __, __, __, __, __, __, __, __, __, __, __, __, __, __, __,
1454*a9fa9459Szrj   __, __, __, __, __, __, __, __, __, __, __, __, __, __, __, __,
1455*a9fa9459Szrj 
1456*a9fa9459Szrj   __, O_bit_or_not, __, __, __, O_modulus, O_bit_and, __,
1457*a9fa9459Szrj   __, __, O_multiply, O_add, __, O_subtract, __, O_divide,
1458*a9fa9459Szrj   __, __, __, __, __, __, __, __,
1459*a9fa9459Szrj   __, __, __, __, O_lt, O_SINGLE_EQ, O_gt, __,
1460*a9fa9459Szrj   __, __, __, __, __, __, __, __,
1461*a9fa9459Szrj   __, __, __, __, __, __, __, __,
1462*a9fa9459Szrj   __, __, __, __, __, __, __, __,
1463*a9fa9459Szrj   __, __, __,
1464*a9fa9459Szrj #ifdef NEED_INDEX_OPERATOR
1465*a9fa9459Szrj   O_index,
1466*a9fa9459Szrj #else
1467*a9fa9459Szrj   __,
1468*a9fa9459Szrj #endif
1469*a9fa9459Szrj   __, __, O_bit_exclusive_or, __,
1470*a9fa9459Szrj   __, __, __, __, __, __, __, __,
1471*a9fa9459Szrj   __, __, __, __, __, __, __, __,
1472*a9fa9459Szrj   __, __, __, __, __, __, __, __,
1473*a9fa9459Szrj   __, __, __, __, O_bit_inclusive_or, __, __, __,
1474*a9fa9459Szrj 
1475*a9fa9459Szrj   __, __, __, __, __, __, __, __, __, __, __, __, __, __, __, __,
1476*a9fa9459Szrj   __, __, __, __, __, __, __, __, __, __, __, __, __, __, __, __,
1477*a9fa9459Szrj   __, __, __, __, __, __, __, __, __, __, __, __, __, __, __, __,
1478*a9fa9459Szrj   __, __, __, __, __, __, __, __, __, __, __, __, __, __, __, __,
1479*a9fa9459Szrj   __, __, __, __, __, __, __, __, __, __, __, __, __, __, __, __,
1480*a9fa9459Szrj   __, __, __, __, __, __, __, __, __, __, __, __, __, __, __, __,
1481*a9fa9459Szrj   __, __, __, __, __, __, __, __, __, __, __, __, __, __, __, __,
1482*a9fa9459Szrj   __, __, __, __, __, __, __, __, __, __, __, __, __, __, __, __
1483*a9fa9459Szrj };
1484*a9fa9459Szrj 
1485*a9fa9459Szrj /* Rank	Examples
1486*a9fa9459Szrj    0	operand, (expression)
1487*a9fa9459Szrj    1	||
1488*a9fa9459Szrj    2	&&
1489*a9fa9459Szrj    3	== <> < <= >= >
1490*a9fa9459Szrj    4	+ -
1491*a9fa9459Szrj    5	used for * / % in MRI mode
1492*a9fa9459Szrj    6	& ^ ! |
1493*a9fa9459Szrj    7	* / % << >>
1494*a9fa9459Szrj    8	unary - unary ~
1495*a9fa9459Szrj */
1496*a9fa9459Szrj static operator_rankT op_rank[O_max] = {
1497*a9fa9459Szrj   0,	/* O_illegal */
1498*a9fa9459Szrj   0,	/* O_absent */
1499*a9fa9459Szrj   0,	/* O_constant */
1500*a9fa9459Szrj   0,	/* O_symbol */
1501*a9fa9459Szrj   0,	/* O_symbol_rva */
1502*a9fa9459Szrj   0,	/* O_register */
1503*a9fa9459Szrj   0,	/* O_big */
1504*a9fa9459Szrj   9,	/* O_uminus */
1505*a9fa9459Szrj   9,	/* O_bit_not */
1506*a9fa9459Szrj   9,	/* O_logical_not */
1507*a9fa9459Szrj   8,	/* O_multiply */
1508*a9fa9459Szrj   8,	/* O_divide */
1509*a9fa9459Szrj   8,	/* O_modulus */
1510*a9fa9459Szrj   8,	/* O_left_shift */
1511*a9fa9459Szrj   8,	/* O_right_shift */
1512*a9fa9459Szrj   7,	/* O_bit_inclusive_or */
1513*a9fa9459Szrj   7,	/* O_bit_or_not */
1514*a9fa9459Szrj   7,	/* O_bit_exclusive_or */
1515*a9fa9459Szrj   7,	/* O_bit_and */
1516*a9fa9459Szrj   5,	/* O_add */
1517*a9fa9459Szrj   5,	/* O_subtract */
1518*a9fa9459Szrj   4,	/* O_eq */
1519*a9fa9459Szrj   4,	/* O_ne */
1520*a9fa9459Szrj   4,	/* O_lt */
1521*a9fa9459Szrj   4,	/* O_le */
1522*a9fa9459Szrj   4,	/* O_ge */
1523*a9fa9459Szrj   4,	/* O_gt */
1524*a9fa9459Szrj   3,	/* O_logical_and */
1525*a9fa9459Szrj   2,	/* O_logical_or */
1526*a9fa9459Szrj   1,	/* O_index */
1527*a9fa9459Szrj };
1528*a9fa9459Szrj 
1529*a9fa9459Szrj /* Unfortunately, in MRI mode for the m68k, multiplication and
1530*a9fa9459Szrj    division have lower precedence than the bit wise operators.  This
1531*a9fa9459Szrj    function sets the operator precedences correctly for the current
1532*a9fa9459Szrj    mode.  Also, MRI uses a different bit_not operator, and this fixes
1533*a9fa9459Szrj    that as well.  */
1534*a9fa9459Szrj 
1535*a9fa9459Szrj #define STANDARD_MUL_PRECEDENCE 8
1536*a9fa9459Szrj #define MRI_MUL_PRECEDENCE 6
1537*a9fa9459Szrj 
1538*a9fa9459Szrj void
expr_set_precedence(void)1539*a9fa9459Szrj expr_set_precedence (void)
1540*a9fa9459Szrj {
1541*a9fa9459Szrj   if (flag_m68k_mri)
1542*a9fa9459Szrj     {
1543*a9fa9459Szrj       op_rank[O_multiply] = MRI_MUL_PRECEDENCE;
1544*a9fa9459Szrj       op_rank[O_divide] = MRI_MUL_PRECEDENCE;
1545*a9fa9459Szrj       op_rank[O_modulus] = MRI_MUL_PRECEDENCE;
1546*a9fa9459Szrj     }
1547*a9fa9459Szrj   else
1548*a9fa9459Szrj     {
1549*a9fa9459Szrj       op_rank[O_multiply] = STANDARD_MUL_PRECEDENCE;
1550*a9fa9459Szrj       op_rank[O_divide] = STANDARD_MUL_PRECEDENCE;
1551*a9fa9459Szrj       op_rank[O_modulus] = STANDARD_MUL_PRECEDENCE;
1552*a9fa9459Szrj     }
1553*a9fa9459Szrj }
1554*a9fa9459Szrj 
1555*a9fa9459Szrj void
expr_set_rank(operatorT op,operator_rankT rank)1556*a9fa9459Szrj expr_set_rank (operatorT op, operator_rankT rank)
1557*a9fa9459Szrj {
1558*a9fa9459Szrj   gas_assert (op >= O_md1 && op < ARRAY_SIZE (op_rank));
1559*a9fa9459Szrj   op_rank[op] = rank;
1560*a9fa9459Szrj }
1561*a9fa9459Szrj 
1562*a9fa9459Szrj /* Initialize the expression parser.  */
1563*a9fa9459Szrj 
1564*a9fa9459Szrj void
expr_begin(void)1565*a9fa9459Szrj expr_begin (void)
1566*a9fa9459Szrj {
1567*a9fa9459Szrj   expr_set_precedence ();
1568*a9fa9459Szrj 
1569*a9fa9459Szrj   /* Verify that X_op field is wide enough.  */
1570*a9fa9459Szrj   {
1571*a9fa9459Szrj     expressionS e;
1572*a9fa9459Szrj     e.X_op = O_max;
1573*a9fa9459Szrj     gas_assert (e.X_op == O_max);
1574*a9fa9459Szrj   }
1575*a9fa9459Szrj }
1576*a9fa9459Szrj 
1577*a9fa9459Szrj /* Return the encoding for the operator at INPUT_LINE_POINTER, and
1578*a9fa9459Szrj    sets NUM_CHARS to the number of characters in the operator.
1579*a9fa9459Szrj    Does not advance INPUT_LINE_POINTER.  */
1580*a9fa9459Szrj 
1581*a9fa9459Szrj static inline operatorT
operatorf(int * num_chars)1582*a9fa9459Szrj operatorf (int *num_chars)
1583*a9fa9459Szrj {
1584*a9fa9459Szrj   int c;
1585*a9fa9459Szrj   operatorT ret;
1586*a9fa9459Szrj 
1587*a9fa9459Szrj   c = *input_line_pointer & 0xff;
1588*a9fa9459Szrj   *num_chars = 1;
1589*a9fa9459Szrj 
1590*a9fa9459Szrj   if (is_end_of_line[c])
1591*a9fa9459Szrj     return O_illegal;
1592*a9fa9459Szrj 
1593*a9fa9459Szrj #ifdef md_operator
1594*a9fa9459Szrj   if (is_name_beginner (c))
1595*a9fa9459Szrj     {
1596*a9fa9459Szrj       char *name;
1597*a9fa9459Szrj       char ec = get_symbol_name (& name);
1598*a9fa9459Szrj 
1599*a9fa9459Szrj       ret = md_operator (name, 2, &ec);
1600*a9fa9459Szrj       switch (ret)
1601*a9fa9459Szrj 	{
1602*a9fa9459Szrj 	case O_absent:
1603*a9fa9459Szrj 	  *input_line_pointer = ec;
1604*a9fa9459Szrj 	  input_line_pointer = name;
1605*a9fa9459Szrj 	  break;
1606*a9fa9459Szrj 	case O_uminus:
1607*a9fa9459Szrj 	case O_bit_not:
1608*a9fa9459Szrj 	case O_logical_not:
1609*a9fa9459Szrj 	  as_bad (_("invalid use of operator \"%s\""), name);
1610*a9fa9459Szrj 	  ret = O_illegal;
1611*a9fa9459Szrj 	  /* FALLTHROUGH */
1612*a9fa9459Szrj 	default:
1613*a9fa9459Szrj 	  *input_line_pointer = ec;
1614*a9fa9459Szrj 	  *num_chars = input_line_pointer - name;
1615*a9fa9459Szrj 	  input_line_pointer = name;
1616*a9fa9459Szrj 	  return ret;
1617*a9fa9459Szrj 	}
1618*a9fa9459Szrj     }
1619*a9fa9459Szrj #endif
1620*a9fa9459Szrj 
1621*a9fa9459Szrj   switch (c)
1622*a9fa9459Szrj     {
1623*a9fa9459Szrj     default:
1624*a9fa9459Szrj       ret = op_encoding[c];
1625*a9fa9459Szrj #ifdef md_operator
1626*a9fa9459Szrj       if (ret == O_illegal)
1627*a9fa9459Szrj 	{
1628*a9fa9459Szrj 	  char *start = input_line_pointer;
1629*a9fa9459Szrj 
1630*a9fa9459Szrj 	  ret = md_operator (NULL, 2, NULL);
1631*a9fa9459Szrj 	  if (ret != O_illegal)
1632*a9fa9459Szrj 	    *num_chars = input_line_pointer - start;
1633*a9fa9459Szrj 	  input_line_pointer = start;
1634*a9fa9459Szrj 	}
1635*a9fa9459Szrj #endif
1636*a9fa9459Szrj       return ret;
1637*a9fa9459Szrj 
1638*a9fa9459Szrj     case '+':
1639*a9fa9459Szrj     case '-':
1640*a9fa9459Szrj       return op_encoding[c];
1641*a9fa9459Szrj 
1642*a9fa9459Szrj     case '<':
1643*a9fa9459Szrj       switch (input_line_pointer[1])
1644*a9fa9459Szrj 	{
1645*a9fa9459Szrj 	default:
1646*a9fa9459Szrj 	  return op_encoding[c];
1647*a9fa9459Szrj 	case '<':
1648*a9fa9459Szrj 	  ret = O_left_shift;
1649*a9fa9459Szrj 	  break;
1650*a9fa9459Szrj 	case '>':
1651*a9fa9459Szrj 	  ret = O_ne;
1652*a9fa9459Szrj 	  break;
1653*a9fa9459Szrj 	case '=':
1654*a9fa9459Szrj 	  ret = O_le;
1655*a9fa9459Szrj 	  break;
1656*a9fa9459Szrj 	}
1657*a9fa9459Szrj       *num_chars = 2;
1658*a9fa9459Szrj       return ret;
1659*a9fa9459Szrj 
1660*a9fa9459Szrj     case '=':
1661*a9fa9459Szrj       if (input_line_pointer[1] != '=')
1662*a9fa9459Szrj 	return op_encoding[c];
1663*a9fa9459Szrj 
1664*a9fa9459Szrj       *num_chars = 2;
1665*a9fa9459Szrj       return O_eq;
1666*a9fa9459Szrj 
1667*a9fa9459Szrj     case '>':
1668*a9fa9459Szrj       switch (input_line_pointer[1])
1669*a9fa9459Szrj 	{
1670*a9fa9459Szrj 	default:
1671*a9fa9459Szrj 	  return op_encoding[c];
1672*a9fa9459Szrj 	case '>':
1673*a9fa9459Szrj 	  ret = O_right_shift;
1674*a9fa9459Szrj 	  break;
1675*a9fa9459Szrj 	case '=':
1676*a9fa9459Szrj 	  ret = O_ge;
1677*a9fa9459Szrj 	  break;
1678*a9fa9459Szrj 	}
1679*a9fa9459Szrj       *num_chars = 2;
1680*a9fa9459Szrj       return ret;
1681*a9fa9459Szrj 
1682*a9fa9459Szrj     case '!':
1683*a9fa9459Szrj       switch (input_line_pointer[1])
1684*a9fa9459Szrj 	{
1685*a9fa9459Szrj 	case '!':
1686*a9fa9459Szrj 	  /* We accept !! as equivalent to ^ for MRI compatibility. */
1687*a9fa9459Szrj 	  *num_chars = 2;
1688*a9fa9459Szrj 	  return O_bit_exclusive_or;
1689*a9fa9459Szrj 	case '=':
1690*a9fa9459Szrj 	  /* We accept != as equivalent to <>.  */
1691*a9fa9459Szrj 	  *num_chars = 2;
1692*a9fa9459Szrj 	  return O_ne;
1693*a9fa9459Szrj 	default:
1694*a9fa9459Szrj 	  if (flag_m68k_mri)
1695*a9fa9459Szrj 	    return O_bit_inclusive_or;
1696*a9fa9459Szrj 	  return op_encoding[c];
1697*a9fa9459Szrj 	}
1698*a9fa9459Szrj 
1699*a9fa9459Szrj     case '|':
1700*a9fa9459Szrj       if (input_line_pointer[1] != '|')
1701*a9fa9459Szrj 	return op_encoding[c];
1702*a9fa9459Szrj 
1703*a9fa9459Szrj       *num_chars = 2;
1704*a9fa9459Szrj       return O_logical_or;
1705*a9fa9459Szrj 
1706*a9fa9459Szrj     case '&':
1707*a9fa9459Szrj       if (input_line_pointer[1] != '&')
1708*a9fa9459Szrj 	return op_encoding[c];
1709*a9fa9459Szrj 
1710*a9fa9459Szrj       *num_chars = 2;
1711*a9fa9459Szrj       return O_logical_and;
1712*a9fa9459Szrj     }
1713*a9fa9459Szrj 
1714*a9fa9459Szrj   /* NOTREACHED  */
1715*a9fa9459Szrj }
1716*a9fa9459Szrj 
1717*a9fa9459Szrj /* Implement "word-size + 1 bit" addition for
1718*a9fa9459Szrj    {resultP->X_extrabit:resultP->X_add_number} + {rhs_highbit:amount}.  This
1719*a9fa9459Szrj    is used so that the full range of unsigned word values and the full range of
1720*a9fa9459Szrj    signed word values can be represented in an O_constant expression, which is
1721*a9fa9459Szrj    useful e.g. for .sleb128 directives.  */
1722*a9fa9459Szrj 
1723*a9fa9459Szrj void
add_to_result(expressionS * resultP,offsetT amount,int rhs_highbit)1724*a9fa9459Szrj add_to_result (expressionS *resultP, offsetT amount, int rhs_highbit)
1725*a9fa9459Szrj {
1726*a9fa9459Szrj   valueT ures = resultP->X_add_number;
1727*a9fa9459Szrj   valueT uamount = amount;
1728*a9fa9459Szrj 
1729*a9fa9459Szrj   resultP->X_add_number += amount;
1730*a9fa9459Szrj 
1731*a9fa9459Szrj   resultP->X_extrabit ^= rhs_highbit;
1732*a9fa9459Szrj 
1733*a9fa9459Szrj   if (ures + uamount < ures)
1734*a9fa9459Szrj     resultP->X_extrabit ^= 1;
1735*a9fa9459Szrj }
1736*a9fa9459Szrj 
1737*a9fa9459Szrj /* Similarly, for subtraction.  */
1738*a9fa9459Szrj 
1739*a9fa9459Szrj void
subtract_from_result(expressionS * resultP,offsetT amount,int rhs_highbit)1740*a9fa9459Szrj subtract_from_result (expressionS *resultP, offsetT amount, int rhs_highbit)
1741*a9fa9459Szrj {
1742*a9fa9459Szrj   valueT ures = resultP->X_add_number;
1743*a9fa9459Szrj   valueT uamount = amount;
1744*a9fa9459Szrj 
1745*a9fa9459Szrj   resultP->X_add_number -= amount;
1746*a9fa9459Szrj 
1747*a9fa9459Szrj   resultP->X_extrabit ^= rhs_highbit;
1748*a9fa9459Szrj 
1749*a9fa9459Szrj   if (ures < uamount)
1750*a9fa9459Szrj     resultP->X_extrabit ^= 1;
1751*a9fa9459Szrj }
1752*a9fa9459Szrj 
1753*a9fa9459Szrj /* Parse an expression.  */
1754*a9fa9459Szrj 
1755*a9fa9459Szrj segT
expr(int rankarg,expressionS * resultP,enum expr_mode mode)1756*a9fa9459Szrj expr (int rankarg,		/* Larger # is higher rank.  */
1757*a9fa9459Szrj       expressionS *resultP,	/* Deliver result here.  */
1758*a9fa9459Szrj       enum expr_mode mode	/* Controls behavior.  */)
1759*a9fa9459Szrj {
1760*a9fa9459Szrj   operator_rankT rank = (operator_rankT) rankarg;
1761*a9fa9459Szrj   segT retval;
1762*a9fa9459Szrj   expressionS right;
1763*a9fa9459Szrj   operatorT op_left;
1764*a9fa9459Szrj   operatorT op_right;
1765*a9fa9459Szrj   int op_chars;
1766*a9fa9459Szrj 
1767*a9fa9459Szrj   know (rankarg >= 0);
1768*a9fa9459Szrj 
1769*a9fa9459Szrj   /* Save the value of dot for the fixup code.  */
1770*a9fa9459Szrj   if (rank == 0)
1771*a9fa9459Szrj     {
1772*a9fa9459Szrj       dot_value = frag_now_fix ();
1773*a9fa9459Szrj       dot_frag = frag_now;
1774*a9fa9459Szrj     }
1775*a9fa9459Szrj 
1776*a9fa9459Szrj   retval = operand (resultP, mode);
1777*a9fa9459Szrj 
1778*a9fa9459Szrj   /* operand () gobbles spaces.  */
1779*a9fa9459Szrj   know (*input_line_pointer != ' ');
1780*a9fa9459Szrj 
1781*a9fa9459Szrj   op_left = operatorf (&op_chars);
1782*a9fa9459Szrj   while (op_left != O_illegal && op_rank[(int) op_left] > rank)
1783*a9fa9459Szrj     {
1784*a9fa9459Szrj       segT rightseg;
1785*a9fa9459Szrj       offsetT frag_off;
1786*a9fa9459Szrj 
1787*a9fa9459Szrj       input_line_pointer += op_chars;	/* -> after operator.  */
1788*a9fa9459Szrj 
1789*a9fa9459Szrj       right.X_md = 0;
1790*a9fa9459Szrj       rightseg = expr (op_rank[(int) op_left], &right, mode);
1791*a9fa9459Szrj       if (right.X_op == O_absent)
1792*a9fa9459Szrj 	{
1793*a9fa9459Szrj 	  as_warn (_("missing operand; zero assumed"));
1794*a9fa9459Szrj 	  right.X_op = O_constant;
1795*a9fa9459Szrj 	  right.X_add_number = 0;
1796*a9fa9459Szrj 	  right.X_add_symbol = NULL;
1797*a9fa9459Szrj 	  right.X_op_symbol = NULL;
1798*a9fa9459Szrj 	}
1799*a9fa9459Szrj 
1800*a9fa9459Szrj       know (*input_line_pointer != ' ');
1801*a9fa9459Szrj 
1802*a9fa9459Szrj       if (op_left == O_index)
1803*a9fa9459Szrj 	{
1804*a9fa9459Szrj 	  if (*input_line_pointer != ']')
1805*a9fa9459Szrj 	    as_bad ("missing right bracket");
1806*a9fa9459Szrj 	  else
1807*a9fa9459Szrj 	    {
1808*a9fa9459Szrj 	      ++input_line_pointer;
1809*a9fa9459Szrj 	      SKIP_WHITESPACE ();
1810*a9fa9459Szrj 	    }
1811*a9fa9459Szrj 	}
1812*a9fa9459Szrj 
1813*a9fa9459Szrj       op_right = operatorf (&op_chars);
1814*a9fa9459Szrj 
1815*a9fa9459Szrj       know (op_right == O_illegal || op_left == O_index
1816*a9fa9459Szrj 	    || op_rank[(int) op_right] <= op_rank[(int) op_left]);
1817*a9fa9459Szrj       know ((int) op_left >= (int) O_multiply);
1818*a9fa9459Szrj #ifndef md_operator
1819*a9fa9459Szrj       know ((int) op_left <= (int) O_index);
1820*a9fa9459Szrj #else
1821*a9fa9459Szrj       know ((int) op_left < (int) O_max);
1822*a9fa9459Szrj #endif
1823*a9fa9459Szrj 
1824*a9fa9459Szrj       /* input_line_pointer->after right-hand quantity.  */
1825*a9fa9459Szrj       /* left-hand quantity in resultP.  */
1826*a9fa9459Szrj       /* right-hand quantity in right.  */
1827*a9fa9459Szrj       /* operator in op_left.  */
1828*a9fa9459Szrj 
1829*a9fa9459Szrj       if (resultP->X_op == O_big)
1830*a9fa9459Szrj 	{
1831*a9fa9459Szrj 	  if (resultP->X_add_number > 0)
1832*a9fa9459Szrj 	    as_warn (_("left operand is a bignum; integer 0 assumed"));
1833*a9fa9459Szrj 	  else
1834*a9fa9459Szrj 	    as_warn (_("left operand is a float; integer 0 assumed"));
1835*a9fa9459Szrj 	  resultP->X_op = O_constant;
1836*a9fa9459Szrj 	  resultP->X_add_number = 0;
1837*a9fa9459Szrj 	  resultP->X_add_symbol = NULL;
1838*a9fa9459Szrj 	  resultP->X_op_symbol = NULL;
1839*a9fa9459Szrj 	}
1840*a9fa9459Szrj       if (right.X_op == O_big)
1841*a9fa9459Szrj 	{
1842*a9fa9459Szrj 	  if (right.X_add_number > 0)
1843*a9fa9459Szrj 	    as_warn (_("right operand is a bignum; integer 0 assumed"));
1844*a9fa9459Szrj 	  else
1845*a9fa9459Szrj 	    as_warn (_("right operand is a float; integer 0 assumed"));
1846*a9fa9459Szrj 	  right.X_op = O_constant;
1847*a9fa9459Szrj 	  right.X_add_number = 0;
1848*a9fa9459Szrj 	  right.X_add_symbol = NULL;
1849*a9fa9459Szrj 	  right.X_op_symbol = NULL;
1850*a9fa9459Szrj 	}
1851*a9fa9459Szrj 
1852*a9fa9459Szrj       /* Optimize common cases.  */
1853*a9fa9459Szrj #ifdef md_optimize_expr
1854*a9fa9459Szrj       if (md_optimize_expr (resultP, op_left, &right))
1855*a9fa9459Szrj 	{
1856*a9fa9459Szrj 	  /* Skip.  */
1857*a9fa9459Szrj 	  ;
1858*a9fa9459Szrj 	}
1859*a9fa9459Szrj       else
1860*a9fa9459Szrj #endif
1861*a9fa9459Szrj #ifndef md_register_arithmetic
1862*a9fa9459Szrj # define md_register_arithmetic 1
1863*a9fa9459Szrj #endif
1864*a9fa9459Szrj       if (op_left == O_add && right.X_op == O_constant
1865*a9fa9459Szrj 	  && (md_register_arithmetic || resultP->X_op != O_register))
1866*a9fa9459Szrj 	{
1867*a9fa9459Szrj 	  /* X + constant.  */
1868*a9fa9459Szrj 	  add_to_result (resultP, right.X_add_number, right.X_extrabit);
1869*a9fa9459Szrj 	}
1870*a9fa9459Szrj       /* This case comes up in PIC code.  */
1871*a9fa9459Szrj       else if (op_left == O_subtract
1872*a9fa9459Szrj 	       && right.X_op == O_symbol
1873*a9fa9459Szrj 	       && resultP->X_op == O_symbol
1874*a9fa9459Szrj 	       && retval == rightseg
1875*a9fa9459Szrj #ifdef md_allow_local_subtract
1876*a9fa9459Szrj 	       && md_allow_local_subtract (resultP, & right, rightseg)
1877*a9fa9459Szrj #endif
1878*a9fa9459Szrj 	       && ((SEG_NORMAL (rightseg)
1879*a9fa9459Szrj 		    && !S_FORCE_RELOC (resultP->X_add_symbol, 0)
1880*a9fa9459Szrj 		    && !S_FORCE_RELOC (right.X_add_symbol, 0))
1881*a9fa9459Szrj 		   || right.X_add_symbol == resultP->X_add_symbol)
1882*a9fa9459Szrj 	       && frag_offset_fixed_p (symbol_get_frag (resultP->X_add_symbol),
1883*a9fa9459Szrj 				       symbol_get_frag (right.X_add_symbol),
1884*a9fa9459Szrj 				       &frag_off))
1885*a9fa9459Szrj 	{
1886*a9fa9459Szrj 	  offsetT symval_diff = S_GET_VALUE (resultP->X_add_symbol)
1887*a9fa9459Szrj 				- S_GET_VALUE (right.X_add_symbol);
1888*a9fa9459Szrj 	  subtract_from_result (resultP, right.X_add_number, right.X_extrabit);
1889*a9fa9459Szrj 	  subtract_from_result (resultP, frag_off / OCTETS_PER_BYTE, 0);
1890*a9fa9459Szrj 	  add_to_result (resultP, symval_diff, symval_diff < 0);
1891*a9fa9459Szrj 	  resultP->X_op = O_constant;
1892*a9fa9459Szrj 	  resultP->X_add_symbol = 0;
1893*a9fa9459Szrj 	}
1894*a9fa9459Szrj       else if (op_left == O_subtract && right.X_op == O_constant
1895*a9fa9459Szrj 	       && (md_register_arithmetic || resultP->X_op != O_register))
1896*a9fa9459Szrj 	{
1897*a9fa9459Szrj 	  /* X - constant.  */
1898*a9fa9459Szrj 	  subtract_from_result (resultP, right.X_add_number, right.X_extrabit);
1899*a9fa9459Szrj 	}
1900*a9fa9459Szrj       else if (op_left == O_add && resultP->X_op == O_constant
1901*a9fa9459Szrj 	       && (md_register_arithmetic || right.X_op != O_register))
1902*a9fa9459Szrj 	{
1903*a9fa9459Szrj 	  /* Constant + X.  */
1904*a9fa9459Szrj 	  resultP->X_op = right.X_op;
1905*a9fa9459Szrj 	  resultP->X_add_symbol = right.X_add_symbol;
1906*a9fa9459Szrj 	  resultP->X_op_symbol = right.X_op_symbol;
1907*a9fa9459Szrj 	  add_to_result (resultP, right.X_add_number, right.X_extrabit);
1908*a9fa9459Szrj 	  retval = rightseg;
1909*a9fa9459Szrj 	}
1910*a9fa9459Szrj       else if (resultP->X_op == O_constant && right.X_op == O_constant)
1911*a9fa9459Szrj 	{
1912*a9fa9459Szrj 	  /* Constant OP constant.  */
1913*a9fa9459Szrj 	  offsetT v = right.X_add_number;
1914*a9fa9459Szrj 	  if (v == 0 && (op_left == O_divide || op_left == O_modulus))
1915*a9fa9459Szrj 	    {
1916*a9fa9459Szrj 	      as_warn (_("division by zero"));
1917*a9fa9459Szrj 	      v = 1;
1918*a9fa9459Szrj 	    }
1919*a9fa9459Szrj 	  if ((valueT) v >= sizeof(valueT) * CHAR_BIT
1920*a9fa9459Szrj 	      && (op_left == O_left_shift || op_left == O_right_shift))
1921*a9fa9459Szrj 	    {
1922*a9fa9459Szrj 	      as_warn_value_out_of_range (_("shift count"), v, 0,
1923*a9fa9459Szrj 					  sizeof(valueT) * CHAR_BIT - 1,
1924*a9fa9459Szrj 					  NULL, 0);
1925*a9fa9459Szrj 	      resultP->X_add_number = v = 0;
1926*a9fa9459Szrj 	    }
1927*a9fa9459Szrj 	  switch (op_left)
1928*a9fa9459Szrj 	    {
1929*a9fa9459Szrj 	    default:			goto general;
1930*a9fa9459Szrj 	    case O_multiply:		resultP->X_add_number *= v; break;
1931*a9fa9459Szrj 	    case O_divide:		resultP->X_add_number /= v; break;
1932*a9fa9459Szrj 	    case O_modulus:		resultP->X_add_number %= v; break;
1933*a9fa9459Szrj 	    case O_left_shift:		resultP->X_add_number <<= v; break;
1934*a9fa9459Szrj 	    case O_right_shift:
1935*a9fa9459Szrj 	      /* We always use unsigned shifts, to avoid relying on
1936*a9fa9459Szrj 		 characteristics of the compiler used to compile gas.  */
1937*a9fa9459Szrj 	      resultP->X_add_number =
1938*a9fa9459Szrj 		(offsetT) ((valueT) resultP->X_add_number >> (valueT) v);
1939*a9fa9459Szrj 	      break;
1940*a9fa9459Szrj 	    case O_bit_inclusive_or:	resultP->X_add_number |= v; break;
1941*a9fa9459Szrj 	    case O_bit_or_not:		resultP->X_add_number |= ~v; break;
1942*a9fa9459Szrj 	    case O_bit_exclusive_or:	resultP->X_add_number ^= v; break;
1943*a9fa9459Szrj 	    case O_bit_and:		resultP->X_add_number &= v; break;
1944*a9fa9459Szrj 	      /* Constant + constant (O_add) is handled by the
1945*a9fa9459Szrj 		 previous if statement for constant + X, so is omitted
1946*a9fa9459Szrj 		 here.  */
1947*a9fa9459Szrj 	    case O_subtract:
1948*a9fa9459Szrj 	      subtract_from_result (resultP, v, 0);
1949*a9fa9459Szrj 	      break;
1950*a9fa9459Szrj 	    case O_eq:
1951*a9fa9459Szrj 	      resultP->X_add_number =
1952*a9fa9459Szrj 		resultP->X_add_number == v ? ~ (offsetT) 0 : 0;
1953*a9fa9459Szrj 	      break;
1954*a9fa9459Szrj 	    case O_ne:
1955*a9fa9459Szrj 	      resultP->X_add_number =
1956*a9fa9459Szrj 		resultP->X_add_number != v ? ~ (offsetT) 0 : 0;
1957*a9fa9459Szrj 	      break;
1958*a9fa9459Szrj 	    case O_lt:
1959*a9fa9459Szrj 	      resultP->X_add_number =
1960*a9fa9459Szrj 		resultP->X_add_number <  v ? ~ (offsetT) 0 : 0;
1961*a9fa9459Szrj 	      break;
1962*a9fa9459Szrj 	    case O_le:
1963*a9fa9459Szrj 	      resultP->X_add_number =
1964*a9fa9459Szrj 		resultP->X_add_number <= v ? ~ (offsetT) 0 : 0;
1965*a9fa9459Szrj 	      break;
1966*a9fa9459Szrj 	    case O_ge:
1967*a9fa9459Szrj 	      resultP->X_add_number =
1968*a9fa9459Szrj 		resultP->X_add_number >= v ? ~ (offsetT) 0 : 0;
1969*a9fa9459Szrj 	      break;
1970*a9fa9459Szrj 	    case O_gt:
1971*a9fa9459Szrj 	      resultP->X_add_number =
1972*a9fa9459Szrj 		resultP->X_add_number >  v ? ~ (offsetT) 0 : 0;
1973*a9fa9459Szrj 	      break;
1974*a9fa9459Szrj 	    case O_logical_and:
1975*a9fa9459Szrj 	      resultP->X_add_number = resultP->X_add_number && v;
1976*a9fa9459Szrj 	      break;
1977*a9fa9459Szrj 	    case O_logical_or:
1978*a9fa9459Szrj 	      resultP->X_add_number = resultP->X_add_number || v;
1979*a9fa9459Szrj 	      break;
1980*a9fa9459Szrj 	    }
1981*a9fa9459Szrj 	}
1982*a9fa9459Szrj       else if (resultP->X_op == O_symbol
1983*a9fa9459Szrj 	       && right.X_op == O_symbol
1984*a9fa9459Szrj 	       && (op_left == O_add
1985*a9fa9459Szrj 		   || op_left == O_subtract
1986*a9fa9459Szrj 		   || (resultP->X_add_number == 0
1987*a9fa9459Szrj 		       && right.X_add_number == 0)))
1988*a9fa9459Szrj 	{
1989*a9fa9459Szrj 	  /* Symbol OP symbol.  */
1990*a9fa9459Szrj 	  resultP->X_op = op_left;
1991*a9fa9459Szrj 	  resultP->X_op_symbol = right.X_add_symbol;
1992*a9fa9459Szrj 	  if (op_left == O_add)
1993*a9fa9459Szrj 	    add_to_result (resultP, right.X_add_number, right.X_extrabit);
1994*a9fa9459Szrj 	  else if (op_left == O_subtract)
1995*a9fa9459Szrj 	    {
1996*a9fa9459Szrj 	      subtract_from_result (resultP, right.X_add_number,
1997*a9fa9459Szrj 				    right.X_extrabit);
1998*a9fa9459Szrj 	      if (retval == rightseg
1999*a9fa9459Szrj 		  && SEG_NORMAL (retval)
2000*a9fa9459Szrj 		  && !S_FORCE_RELOC (resultP->X_add_symbol, 0)
2001*a9fa9459Szrj 		  && !S_FORCE_RELOC (right.X_add_symbol, 0))
2002*a9fa9459Szrj 		{
2003*a9fa9459Szrj 		  retval = absolute_section;
2004*a9fa9459Szrj 		  rightseg = absolute_section;
2005*a9fa9459Szrj 		}
2006*a9fa9459Szrj 	    }
2007*a9fa9459Szrj 	}
2008*a9fa9459Szrj       else
2009*a9fa9459Szrj 	{
2010*a9fa9459Szrj         general:
2011*a9fa9459Szrj 	  /* The general case.  */
2012*a9fa9459Szrj 	  resultP->X_add_symbol = make_expr_symbol (resultP);
2013*a9fa9459Szrj 	  resultP->X_op_symbol = make_expr_symbol (&right);
2014*a9fa9459Szrj 	  resultP->X_op = op_left;
2015*a9fa9459Szrj 	  resultP->X_add_number = 0;
2016*a9fa9459Szrj 	  resultP->X_unsigned = 1;
2017*a9fa9459Szrj 	  resultP->X_extrabit = 0;
2018*a9fa9459Szrj 	}
2019*a9fa9459Szrj 
2020*a9fa9459Szrj       if (retval != rightseg)
2021*a9fa9459Szrj 	{
2022*a9fa9459Szrj 	  if (retval == undefined_section)
2023*a9fa9459Szrj 	    ;
2024*a9fa9459Szrj 	  else if (rightseg == undefined_section)
2025*a9fa9459Szrj 	    retval = rightseg;
2026*a9fa9459Szrj 	  else if (retval == expr_section)
2027*a9fa9459Szrj 	    ;
2028*a9fa9459Szrj 	  else if (rightseg == expr_section)
2029*a9fa9459Szrj 	    retval = rightseg;
2030*a9fa9459Szrj 	  else if (retval == reg_section)
2031*a9fa9459Szrj 	    ;
2032*a9fa9459Szrj 	  else if (rightseg == reg_section)
2033*a9fa9459Szrj 	    retval = rightseg;
2034*a9fa9459Szrj 	  else if (rightseg == absolute_section)
2035*a9fa9459Szrj 	    ;
2036*a9fa9459Szrj 	  else if (retval == absolute_section)
2037*a9fa9459Szrj 	    retval = rightseg;
2038*a9fa9459Szrj #ifdef DIFF_EXPR_OK
2039*a9fa9459Szrj 	  else if (op_left == O_subtract)
2040*a9fa9459Szrj 	    ;
2041*a9fa9459Szrj #endif
2042*a9fa9459Szrj 	  else
2043*a9fa9459Szrj 	    as_bad (_("operation combines symbols in different segments"));
2044*a9fa9459Szrj 	}
2045*a9fa9459Szrj 
2046*a9fa9459Szrj       op_left = op_right;
2047*a9fa9459Szrj     }				/* While next operator is >= this rank.  */
2048*a9fa9459Szrj 
2049*a9fa9459Szrj   /* The PA port needs this information.  */
2050*a9fa9459Szrj   if (resultP->X_add_symbol)
2051*a9fa9459Szrj     symbol_mark_used (resultP->X_add_symbol);
2052*a9fa9459Szrj 
2053*a9fa9459Szrj   if (rank == 0 && mode == expr_evaluate)
2054*a9fa9459Szrj     resolve_expression (resultP);
2055*a9fa9459Szrj 
2056*a9fa9459Szrj   return resultP->X_op == O_constant ? absolute_section : retval;
2057*a9fa9459Szrj }
2058*a9fa9459Szrj 
2059*a9fa9459Szrj /* Resolve an expression without changing any symbols/sub-expressions
2060*a9fa9459Szrj    used.  */
2061*a9fa9459Szrj 
2062*a9fa9459Szrj int
resolve_expression(expressionS * expressionP)2063*a9fa9459Szrj resolve_expression (expressionS *expressionP)
2064*a9fa9459Szrj {
2065*a9fa9459Szrj   /* Help out with CSE.  */
2066*a9fa9459Szrj   valueT final_val = expressionP->X_add_number;
2067*a9fa9459Szrj   symbolS *add_symbol = expressionP->X_add_symbol;
2068*a9fa9459Szrj   symbolS *orig_add_symbol = add_symbol;
2069*a9fa9459Szrj   symbolS *op_symbol = expressionP->X_op_symbol;
2070*a9fa9459Szrj   operatorT op = expressionP->X_op;
2071*a9fa9459Szrj   valueT left, right;
2072*a9fa9459Szrj   segT seg_left, seg_right;
2073*a9fa9459Szrj   fragS *frag_left, *frag_right;
2074*a9fa9459Szrj   offsetT frag_off;
2075*a9fa9459Szrj 
2076*a9fa9459Szrj   switch (op)
2077*a9fa9459Szrj     {
2078*a9fa9459Szrj     default:
2079*a9fa9459Szrj       return 0;
2080*a9fa9459Szrj 
2081*a9fa9459Szrj     case O_constant:
2082*a9fa9459Szrj     case O_register:
2083*a9fa9459Szrj       left = 0;
2084*a9fa9459Szrj       break;
2085*a9fa9459Szrj 
2086*a9fa9459Szrj     case O_symbol:
2087*a9fa9459Szrj     case O_symbol_rva:
2088*a9fa9459Szrj       if (!snapshot_symbol (&add_symbol, &left, &seg_left, &frag_left))
2089*a9fa9459Szrj 	return 0;
2090*a9fa9459Szrj 
2091*a9fa9459Szrj       break;
2092*a9fa9459Szrj 
2093*a9fa9459Szrj     case O_uminus:
2094*a9fa9459Szrj     case O_bit_not:
2095*a9fa9459Szrj     case O_logical_not:
2096*a9fa9459Szrj       if (!snapshot_symbol (&add_symbol, &left, &seg_left, &frag_left))
2097*a9fa9459Szrj 	return 0;
2098*a9fa9459Szrj 
2099*a9fa9459Szrj       if (seg_left != absolute_section)
2100*a9fa9459Szrj 	return 0;
2101*a9fa9459Szrj 
2102*a9fa9459Szrj       if (op == O_logical_not)
2103*a9fa9459Szrj 	left = !left;
2104*a9fa9459Szrj       else if (op == O_uminus)
2105*a9fa9459Szrj 	left = -left;
2106*a9fa9459Szrj       else
2107*a9fa9459Szrj 	left = ~left;
2108*a9fa9459Szrj       op = O_constant;
2109*a9fa9459Szrj       break;
2110*a9fa9459Szrj 
2111*a9fa9459Szrj     case O_multiply:
2112*a9fa9459Szrj     case O_divide:
2113*a9fa9459Szrj     case O_modulus:
2114*a9fa9459Szrj     case O_left_shift:
2115*a9fa9459Szrj     case O_right_shift:
2116*a9fa9459Szrj     case O_bit_inclusive_or:
2117*a9fa9459Szrj     case O_bit_or_not:
2118*a9fa9459Szrj     case O_bit_exclusive_or:
2119*a9fa9459Szrj     case O_bit_and:
2120*a9fa9459Szrj     case O_add:
2121*a9fa9459Szrj     case O_subtract:
2122*a9fa9459Szrj     case O_eq:
2123*a9fa9459Szrj     case O_ne:
2124*a9fa9459Szrj     case O_lt:
2125*a9fa9459Szrj     case O_le:
2126*a9fa9459Szrj     case O_ge:
2127*a9fa9459Szrj     case O_gt:
2128*a9fa9459Szrj     case O_logical_and:
2129*a9fa9459Szrj     case O_logical_or:
2130*a9fa9459Szrj       if (!snapshot_symbol (&add_symbol, &left, &seg_left, &frag_left)
2131*a9fa9459Szrj 	  || !snapshot_symbol (&op_symbol, &right, &seg_right, &frag_right))
2132*a9fa9459Szrj 	return 0;
2133*a9fa9459Szrj 
2134*a9fa9459Szrj       /* Simplify addition or subtraction of a constant by folding the
2135*a9fa9459Szrj 	 constant into X_add_number.  */
2136*a9fa9459Szrj       if (op == O_add)
2137*a9fa9459Szrj 	{
2138*a9fa9459Szrj 	  if (seg_right == absolute_section)
2139*a9fa9459Szrj 	    {
2140*a9fa9459Szrj 	      final_val += right;
2141*a9fa9459Szrj 	      op = O_symbol;
2142*a9fa9459Szrj 	      break;
2143*a9fa9459Szrj 	    }
2144*a9fa9459Szrj 	  else if (seg_left == absolute_section)
2145*a9fa9459Szrj 	    {
2146*a9fa9459Szrj 	      final_val += left;
2147*a9fa9459Szrj 	      left = right;
2148*a9fa9459Szrj 	      seg_left = seg_right;
2149*a9fa9459Szrj 	      add_symbol = op_symbol;
2150*a9fa9459Szrj 	      orig_add_symbol = expressionP->X_op_symbol;
2151*a9fa9459Szrj 	      op = O_symbol;
2152*a9fa9459Szrj 	      break;
2153*a9fa9459Szrj 	    }
2154*a9fa9459Szrj 	}
2155*a9fa9459Szrj       else if (op == O_subtract)
2156*a9fa9459Szrj 	{
2157*a9fa9459Szrj 	  if (seg_right == absolute_section)
2158*a9fa9459Szrj 	    {
2159*a9fa9459Szrj 	      final_val -= right;
2160*a9fa9459Szrj 	      op = O_symbol;
2161*a9fa9459Szrj 	      break;
2162*a9fa9459Szrj 	    }
2163*a9fa9459Szrj 	}
2164*a9fa9459Szrj 
2165*a9fa9459Szrj       /* Equality and non-equality tests are permitted on anything.
2166*a9fa9459Szrj 	 Subtraction, and other comparison operators are permitted if
2167*a9fa9459Szrj 	 both operands are in the same section.
2168*a9fa9459Szrj 	 Shifts by constant zero are permitted on anything.
2169*a9fa9459Szrj 	 Multiplies, bit-ors, and bit-ands with constant zero are
2170*a9fa9459Szrj 	 permitted on anything.
2171*a9fa9459Szrj 	 Multiplies and divides by constant one are permitted on
2172*a9fa9459Szrj 	 anything.
2173*a9fa9459Szrj 	 Binary operations with both operands being the same register
2174*a9fa9459Szrj 	 or undefined symbol are permitted if the result doesn't depend
2175*a9fa9459Szrj 	 on the input value.
2176*a9fa9459Szrj 	 Otherwise, both operands must be absolute.  We already handled
2177*a9fa9459Szrj 	 the case of addition or subtraction of a constant above.  */
2178*a9fa9459Szrj       frag_off = 0;
2179*a9fa9459Szrj       if (!(seg_left == absolute_section
2180*a9fa9459Szrj 	       && seg_right == absolute_section)
2181*a9fa9459Szrj 	  && !(op == O_eq || op == O_ne)
2182*a9fa9459Szrj 	  && !((op == O_subtract
2183*a9fa9459Szrj 		|| op == O_lt || op == O_le || op == O_ge || op == O_gt)
2184*a9fa9459Szrj 	       && seg_left == seg_right
2185*a9fa9459Szrj 	       && (finalize_syms
2186*a9fa9459Szrj 		   || frag_offset_fixed_p (frag_left, frag_right, &frag_off))
2187*a9fa9459Szrj 	       && (seg_left != reg_section || left == right)
2188*a9fa9459Szrj 	       && (seg_left != undefined_section || add_symbol == op_symbol)))
2189*a9fa9459Szrj 	{
2190*a9fa9459Szrj 	  if ((seg_left == absolute_section && left == 0)
2191*a9fa9459Szrj 	      || (seg_right == absolute_section && right == 0))
2192*a9fa9459Szrj 	    {
2193*a9fa9459Szrj 	      if (op == O_bit_exclusive_or || op == O_bit_inclusive_or)
2194*a9fa9459Szrj 		{
2195*a9fa9459Szrj 		  if (!(seg_right == absolute_section && right == 0))
2196*a9fa9459Szrj 		    {
2197*a9fa9459Szrj 		      seg_left = seg_right;
2198*a9fa9459Szrj 		      left = right;
2199*a9fa9459Szrj 		      add_symbol = op_symbol;
2200*a9fa9459Szrj 		      orig_add_symbol = expressionP->X_op_symbol;
2201*a9fa9459Szrj 		    }
2202*a9fa9459Szrj 		  op = O_symbol;
2203*a9fa9459Szrj 		  break;
2204*a9fa9459Szrj 		}
2205*a9fa9459Szrj 	      else if (op == O_left_shift || op == O_right_shift)
2206*a9fa9459Szrj 		{
2207*a9fa9459Szrj 		  if (!(seg_left == absolute_section && left == 0))
2208*a9fa9459Szrj 		    {
2209*a9fa9459Szrj 		      op = O_symbol;
2210*a9fa9459Szrj 		      break;
2211*a9fa9459Szrj 		    }
2212*a9fa9459Szrj 		}
2213*a9fa9459Szrj 	      else if (op != O_multiply
2214*a9fa9459Szrj 		       && op != O_bit_or_not && op != O_bit_and)
2215*a9fa9459Szrj 	        return 0;
2216*a9fa9459Szrj 	    }
2217*a9fa9459Szrj 	  else if (op == O_multiply
2218*a9fa9459Szrj 		   && seg_left == absolute_section && left == 1)
2219*a9fa9459Szrj 	    {
2220*a9fa9459Szrj 	      seg_left = seg_right;
2221*a9fa9459Szrj 	      left = right;
2222*a9fa9459Szrj 	      add_symbol = op_symbol;
2223*a9fa9459Szrj 	      orig_add_symbol = expressionP->X_op_symbol;
2224*a9fa9459Szrj 	      op = O_symbol;
2225*a9fa9459Szrj 	      break;
2226*a9fa9459Szrj 	    }
2227*a9fa9459Szrj 	  else if ((op == O_multiply || op == O_divide)
2228*a9fa9459Szrj 		   && seg_right == absolute_section && right == 1)
2229*a9fa9459Szrj 	    {
2230*a9fa9459Szrj 	      op = O_symbol;
2231*a9fa9459Szrj 	      break;
2232*a9fa9459Szrj 	    }
2233*a9fa9459Szrj 	  else if (!(left == right
2234*a9fa9459Szrj 		     && ((seg_left == reg_section && seg_right == reg_section)
2235*a9fa9459Szrj 			 || (seg_left == undefined_section
2236*a9fa9459Szrj 			     && seg_right == undefined_section
2237*a9fa9459Szrj 			     && add_symbol == op_symbol))))
2238*a9fa9459Szrj 	    return 0;
2239*a9fa9459Szrj 	  else if (op == O_bit_and || op == O_bit_inclusive_or)
2240*a9fa9459Szrj 	    {
2241*a9fa9459Szrj 	      op = O_symbol;
2242*a9fa9459Szrj 	      break;
2243*a9fa9459Szrj 	    }
2244*a9fa9459Szrj 	  else if (op != O_bit_exclusive_or && op != O_bit_or_not)
2245*a9fa9459Szrj 	    return 0;
2246*a9fa9459Szrj 	}
2247*a9fa9459Szrj 
2248*a9fa9459Szrj       right += frag_off / OCTETS_PER_BYTE;
2249*a9fa9459Szrj       switch (op)
2250*a9fa9459Szrj 	{
2251*a9fa9459Szrj 	case O_add:			left += right; break;
2252*a9fa9459Szrj 	case O_subtract:		left -= right; break;
2253*a9fa9459Szrj 	case O_multiply:		left *= right; break;
2254*a9fa9459Szrj 	case O_divide:
2255*a9fa9459Szrj 	  if (right == 0)
2256*a9fa9459Szrj 	    return 0;
2257*a9fa9459Szrj 	  left = (offsetT) left / (offsetT) right;
2258*a9fa9459Szrj 	  break;
2259*a9fa9459Szrj 	case O_modulus:
2260*a9fa9459Szrj 	  if (right == 0)
2261*a9fa9459Szrj 	    return 0;
2262*a9fa9459Szrj 	  left = (offsetT) left % (offsetT) right;
2263*a9fa9459Szrj 	  break;
2264*a9fa9459Szrj 	case O_left_shift:		left <<= right; break;
2265*a9fa9459Szrj 	case O_right_shift:		left >>= right; break;
2266*a9fa9459Szrj 	case O_bit_inclusive_or:	left |= right; break;
2267*a9fa9459Szrj 	case O_bit_or_not:		left |= ~right; break;
2268*a9fa9459Szrj 	case O_bit_exclusive_or:	left ^= right; break;
2269*a9fa9459Szrj 	case O_bit_and:			left &= right; break;
2270*a9fa9459Szrj 	case O_eq:
2271*a9fa9459Szrj 	case O_ne:
2272*a9fa9459Szrj 	  left = (left == right
2273*a9fa9459Szrj 		  && seg_left == seg_right
2274*a9fa9459Szrj 		  && (finalize_syms || frag_left == frag_right)
2275*a9fa9459Szrj 		  && (seg_left != undefined_section
2276*a9fa9459Szrj 		      || add_symbol == op_symbol)
2277*a9fa9459Szrj 		  ? ~ (valueT) 0 : 0);
2278*a9fa9459Szrj 	  if (op == O_ne)
2279*a9fa9459Szrj 	    left = ~left;
2280*a9fa9459Szrj 	  break;
2281*a9fa9459Szrj 	case O_lt:
2282*a9fa9459Szrj 	  left = (offsetT) left <  (offsetT) right ? ~ (valueT) 0 : 0;
2283*a9fa9459Szrj 	  break;
2284*a9fa9459Szrj 	case O_le:
2285*a9fa9459Szrj 	  left = (offsetT) left <= (offsetT) right ? ~ (valueT) 0 : 0;
2286*a9fa9459Szrj 	  break;
2287*a9fa9459Szrj 	case O_ge:
2288*a9fa9459Szrj 	  left = (offsetT) left >= (offsetT) right ? ~ (valueT) 0 : 0;
2289*a9fa9459Szrj 	  break;
2290*a9fa9459Szrj 	case O_gt:
2291*a9fa9459Szrj 	  left = (offsetT) left >  (offsetT) right ? ~ (valueT) 0 : 0;
2292*a9fa9459Szrj 	  break;
2293*a9fa9459Szrj 	case O_logical_and:	left = left && right; break;
2294*a9fa9459Szrj 	case O_logical_or:	left = left || right; break;
2295*a9fa9459Szrj 	default:		abort ();
2296*a9fa9459Szrj 	}
2297*a9fa9459Szrj 
2298*a9fa9459Szrj       op = O_constant;
2299*a9fa9459Szrj       break;
2300*a9fa9459Szrj     }
2301*a9fa9459Szrj 
2302*a9fa9459Szrj   if (op == O_symbol)
2303*a9fa9459Szrj     {
2304*a9fa9459Szrj       if (seg_left == absolute_section)
2305*a9fa9459Szrj 	op = O_constant;
2306*a9fa9459Szrj       else if (seg_left == reg_section && final_val == 0)
2307*a9fa9459Szrj 	op = O_register;
2308*a9fa9459Szrj       else if (!symbol_same_p (add_symbol, orig_add_symbol))
2309*a9fa9459Szrj 	final_val += left;
2310*a9fa9459Szrj       expressionP->X_add_symbol = add_symbol;
2311*a9fa9459Szrj     }
2312*a9fa9459Szrj   expressionP->X_op = op;
2313*a9fa9459Szrj 
2314*a9fa9459Szrj   if (op == O_constant || op == O_register)
2315*a9fa9459Szrj     final_val += left;
2316*a9fa9459Szrj   expressionP->X_add_number = final_val;
2317*a9fa9459Szrj 
2318*a9fa9459Szrj   return 1;
2319*a9fa9459Szrj }
2320*a9fa9459Szrj 
2321*a9fa9459Szrj /* This lives here because it belongs equally in expr.c & read.c.
2322*a9fa9459Szrj    expr.c is just a branch office read.c anyway, and putting it
2323*a9fa9459Szrj    here lessens the crowd at read.c.
2324*a9fa9459Szrj 
2325*a9fa9459Szrj    Assume input_line_pointer is at start of symbol name, or the
2326*a9fa9459Szrj     start of a double quote enclosed symbol name.
2327*a9fa9459Szrj    Advance input_line_pointer past symbol name.
2328*a9fa9459Szrj    Turn that character into a '\0', returning its former value,
2329*a9fa9459Szrj     which may be the closing double quote.
2330*a9fa9459Szrj    This allows a string compare (RMS wants symbol names to be strings)
2331*a9fa9459Szrj     of the symbol name.
2332*a9fa9459Szrj    There will always be a char following symbol name, because all good
2333*a9fa9459Szrj    lines end in end-of-line.  */
2334*a9fa9459Szrj 
2335*a9fa9459Szrj char
get_symbol_name(char ** ilp_return)2336*a9fa9459Szrj get_symbol_name (char ** ilp_return)
2337*a9fa9459Szrj {
2338*a9fa9459Szrj   char c;
2339*a9fa9459Szrj 
2340*a9fa9459Szrj   * ilp_return = input_line_pointer;
2341*a9fa9459Szrj   /* We accept \001 in a name in case this is being called with a
2342*a9fa9459Szrj      constructed string.  */
2343*a9fa9459Szrj   if (is_name_beginner (c = *input_line_pointer++) || c == '\001')
2344*a9fa9459Szrj     {
2345*a9fa9459Szrj       while (is_part_of_name (c = *input_line_pointer++)
2346*a9fa9459Szrj 	     || c == '\001')
2347*a9fa9459Szrj 	;
2348*a9fa9459Szrj       if (is_name_ender (c))
2349*a9fa9459Szrj 	c = *input_line_pointer++;
2350*a9fa9459Szrj     }
2351*a9fa9459Szrj   else if (c == '"')
2352*a9fa9459Szrj     {
2353*a9fa9459Szrj       bfd_boolean backslash_seen;
2354*a9fa9459Szrj 
2355*a9fa9459Szrj       * ilp_return = input_line_pointer;
2356*a9fa9459Szrj       do
2357*a9fa9459Szrj 	{
2358*a9fa9459Szrj 	  backslash_seen = c == '\\';
2359*a9fa9459Szrj 	  c = * input_line_pointer ++;
2360*a9fa9459Szrj 	}
2361*a9fa9459Szrj       while (c != 0 && (c != '"' || backslash_seen));
2362*a9fa9459Szrj 
2363*a9fa9459Szrj       if (c == 0)
2364*a9fa9459Szrj 	as_warn (_("missing closing '\"'"));
2365*a9fa9459Szrj     }
2366*a9fa9459Szrj   *--input_line_pointer = 0;
2367*a9fa9459Szrj   return c;
2368*a9fa9459Szrj }
2369*a9fa9459Szrj 
2370*a9fa9459Szrj /* Replace the NUL character pointed to by input_line_pointer
2371*a9fa9459Szrj    with C.  If C is \" then advance past it.  Return the character
2372*a9fa9459Szrj    now pointed to by input_line_pointer.  */
2373*a9fa9459Szrj 
2374*a9fa9459Szrj char
restore_line_pointer(char c)2375*a9fa9459Szrj restore_line_pointer (char c)
2376*a9fa9459Szrj {
2377*a9fa9459Szrj   * input_line_pointer = c;
2378*a9fa9459Szrj   if (c == '"')
2379*a9fa9459Szrj     c = * ++ input_line_pointer;
2380*a9fa9459Szrj   return c;
2381*a9fa9459Szrj }
2382*a9fa9459Szrj 
2383*a9fa9459Szrj unsigned int
get_single_number(void)2384*a9fa9459Szrj get_single_number (void)
2385*a9fa9459Szrj {
2386*a9fa9459Szrj   expressionS exp;
2387*a9fa9459Szrj   operand (&exp, expr_normal);
2388*a9fa9459Szrj   return exp.X_add_number;
2389*a9fa9459Szrj }
2390