ea8008c2a420d762ef79b94816ab141a8c520b4c
[binutils-gdb.git] / gas / config / tc-avr.c
1 /* tc-avr.c -- Assembler code for the ATMEL AVR
2
3 Copyright (C) 1999, 2000 Free Software Foundation, Inc.
4 Contributed by Denis Chertykov <denisc@overta.ru>
5
6 This file is part of GAS, the GNU Assembler.
7
8 GAS is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2, or (at your option)
11 any later version.
12
13 GAS is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with GAS; see the file COPYING. If not, write to
20 the Free Software Foundation, 59 Temple Place - Suite 330,
21 Boston, MA 02111-1307, USA. */
22
23 #include <stdio.h>
24 #include <ctype.h>
25 #include "as.h"
26 #include "subsegs.h"
27
28 const char comment_chars[] = ";";
29 const char line_comment_chars[] = "#";
30 const char line_separator_chars[] = "$";
31
32 #define AVR_ISA_1200 1
33 #define AVR_ISA_2xxx 3
34 #define AVR_ISA_MEGA_x03 0x17
35 #define AVR_ISA_MEGA 0x10
36 #define AVR_ISA_MEGA_161 0x1b
37
38 const char *md_shortopts = "m:";
39 struct mcu_type_s
40 {
41 char *name;
42 int isa;
43 int mach;
44 };
45
46 static struct mcu_type_s mcu_types[] =
47 {
48 {"avr1", AVR_ISA_1200, bfd_mach_avr1},
49 {"avr2", AVR_ISA_2xxx, bfd_mach_avr2},
50 {"avr3", AVR_ISA_MEGA_x03, bfd_mach_avr3},
51 {"avr4", AVR_ISA_MEGA_161, bfd_mach_avr4},
52 {"at90s1200", AVR_ISA_1200, bfd_mach_avr1},
53 {"at90s2313", AVR_ISA_2xxx, bfd_mach_avr2},
54 {"at90s2323", AVR_ISA_2xxx, bfd_mach_avr2},
55 {"at90s2333", AVR_ISA_2xxx, bfd_mach_avr2},
56 {"attiny22" , AVR_ISA_2xxx, bfd_mach_avr2},
57 {"at90s2343", AVR_ISA_2xxx, bfd_mach_avr2},
58 {"at90s4433", AVR_ISA_2xxx, bfd_mach_avr2},
59 {"at90s4414", AVR_ISA_2xxx, bfd_mach_avr2},
60 {"at90s4434", AVR_ISA_2xxx, bfd_mach_avr2},
61 {"at90s8515", AVR_ISA_2xxx, bfd_mach_avr2},
62 {"at90s8535", AVR_ISA_2xxx, bfd_mach_avr2},
63 {"atmega603", AVR_ISA_MEGA_x03, bfd_mach_avr3},
64 {"atmega103", AVR_ISA_MEGA_x03, bfd_mach_avr3},
65 {"atmega161", AVR_ISA_MEGA_161, bfd_mach_avr4},
66 {NULL, 0, 0}
67 };
68
69
70 /* Current MCU type. */
71 static struct mcu_type_s default_mcu = {"avr2", AVR_ISA_2xxx,bfd_mach_avr2};
72 static struct mcu_type_s *avr_mcu = &default_mcu;
73
74 const char EXP_CHARS[] = "eE";
75 const char FLT_CHARS[] = "dD";
76 static void avr_set_arch (int dummy);
77
78 /* The target specific pseudo-ops which we support. */
79 const pseudo_typeS md_pseudo_table[] =
80 {
81 {"arch", avr_set_arch, 0},
82 { NULL, NULL, 0}
83 };
84
85 #define LDI_IMMEDIATE(x) (((x) & 0xf) | (((x) << 4) & 0xf00))
86 #define REGISTER_P(x) ((x) == 'r' || (x) == 'd' || (x) == 'w')
87
88 struct avr_opcodes_s
89 {
90 char *name;
91 char *constraints;
92 char *opcode;
93 int insn_size; /* in words */
94 int isa;
95 unsigned int bin_opcode;
96 };
97
98 static char * skip_space (char * s);
99 static char * extract_word (char *from, char *to, int limit);
100 static unsigned int avr_operand (struct avr_opcodes_s *opcode,
101 int where, char *op, char **line);
102 static unsigned int avr_operands (struct avr_opcodes_s *opcode, char **line);
103 static unsigned int avr_get_constant (char * str, unsigned int max);
104 static char *parse_exp (char *s, expressionS * op);
105 static bfd_reloc_code_real_type avr_ldi_expression (expressionS *exp);
106 long md_pcrel_from_section PARAMS ((fixS *, segT));
107
108 /* constraint letters
109 r - any register
110 d - `ldi' register (r16-r31)
111 M - immediate value from 0 to 255
112 n - immediate value from 0 to 255 ( n = ~M ). Relocation impossible
113 w - `adiw' register (r24,r26,r28,r30)
114 s - immediate value from 0 to 7
115 P - Port address value from 0 to 64. (in, out)
116 p - Port address value from 0 to 32. (cbi, sbi, sbic, sbis)
117 K - immediate value from 0 to 64 (used in `adiw', `sbiw')
118 e - pointer regegisters (X,Y,Z)
119 b - base pointer register and displacement ([YZ]+disp)
120 i - immediate value
121 l - signed pc relative offset from -64 to 63
122 L - signed pc relative offset from -2048 to 2047
123 h - absolut code address (call, jmp)
124 S - immediate value from 0 to 7 (S = s << 4)
125 */
126 struct avr_opcodes_s avr_opcodes[] =
127 {
128 {"adc", "r,r", "000111rdddddrrrr", 1, AVR_ISA_1200, 0x1c00},
129 {"add", "r,r", "000011rdddddrrrr", 1, AVR_ISA_1200, 0x0c00},
130 {"and", "r,r", "001000rdddddrrrr", 1, AVR_ISA_1200, 0x2000},
131 {"cp", "r,r", "000101rdddddrrrr", 1, AVR_ISA_1200, 0x1400},
132 {"cpc", "r,r", "000001rdddddrrrr", 1, AVR_ISA_1200, 0x0400},
133 {"cpse", "r,r", "000100rdddddrrrr", 1, AVR_ISA_1200, 0x1000},
134 {"eor", "r,r", "001001rdddddrrrr", 1, AVR_ISA_1200, 0x2400},
135 {"mov", "r,r", "001011rdddddrrrr", 1, AVR_ISA_1200, 0x2c00},
136 {"mul", "r,r", "100111rdddddrrrr", 1, AVR_ISA_MEGA_161, 0x9c00},
137 {"or", "r,r", "001010rdddddrrrr", 1, AVR_ISA_1200, 0x2800},
138 {"sbc", "r,r", "000010rdddddrrrr", 1, AVR_ISA_1200, 0x0800},
139 {"sub", "r,r", "000110rdddddrrrr", 1, AVR_ISA_1200, 0x1800},
140
141 {"clr", "r=r", "001001rdddddrrrr", 1, AVR_ISA_1200, 0x2400},
142 {"lsl", "r=r", "000011rdddddrrrr", 1, AVR_ISA_1200, 0x0c00},
143 {"rol", "r=r", "000111rdddddrrrr", 1, AVR_ISA_1200, 0x1c00},
144 {"tst", "r=r", "001000rdddddrrrr", 1, AVR_ISA_1200, 0x2000},
145
146 {"andi", "d,M", "0111KKKKddddKKKK", 1, AVR_ISA_1200, 0x7000},
147 /*XXX special case*/
148 {"cbr", "d,n", "0111KKKKddddKKKK", 1, AVR_ISA_1200, 0x7000},
149 {"cpi", "d,M", "0011KKKKddddKKKK", 1, AVR_ISA_1200, 0x3000},
150 {"ldi", "d,M", "1110KKKKddddKKKK", 1, AVR_ISA_1200, 0xe000},
151 {"ori", "d,M", "0110KKKKddddKKKK", 1, AVR_ISA_1200, 0x6000},
152 {"sbci", "d,M", "0100KKKKddddKKKK", 1, AVR_ISA_1200, 0x4000},
153 {"sbr", "d,M", "0110KKKKddddKKKK", 1, AVR_ISA_1200, 0x6000},
154 {"subi", "d,M", "0101KKKKddddKKKK", 1, AVR_ISA_1200, 0x5000},
155
156 {"sbrc", "r,s", "1111110rrrrr0sss", 1, AVR_ISA_1200, 0xfc00},
157 {"sbrs", "r,s", "1111111rrrrr0sss", 1, AVR_ISA_1200, 0xfe00},
158 {"bld", "r,s", "1111100ddddd0sss", 1, AVR_ISA_1200, 0xf800},
159 {"bst", "r,s", "1111101ddddd0sss", 1, AVR_ISA_1200, 0xfa00},
160
161 {"in", "r,P", "10110PPdddddPPPP", 1, AVR_ISA_1200, 0xb000},
162 {"out", "P,r", "10111PPrrrrrPPPP", 1, AVR_ISA_1200, 0xb800},
163
164 {"adiw", "w,K", "10010110KKddKKKK", 1, AVR_ISA_2xxx, 0x9600},
165 {"sbiw", "w,K", "10010111KKddKKKK", 1, AVR_ISA_2xxx, 0x9700},
166
167 {"cbi", "p,s", "10011000pppppsss", 1, AVR_ISA_1200, 0x9800},
168 {"sbi", "p,s", "10011010pppppsss", 1, AVR_ISA_1200, 0x9a00},
169 {"sbic", "p,s", "10011001pppppsss", 1, AVR_ISA_1200, 0x9900},
170 {"sbis", "p,s", "10011011pppppsss", 1, AVR_ISA_1200, 0x9b00},
171
172 /* ee = {X=11,Y=10,Z=00, 0} */
173 {"ld", "r,e", "100!000dddddee-+", 1, AVR_ISA_2xxx, 0x8000},
174 {"st", "e,r", "100!001rrrrree-+", 1, AVR_ISA_2xxx, 0x8200},
175 {"ldd", "r,b", "10o0oo0dddddbooo", 1, AVR_ISA_2xxx, 0x8000},
176 {"std", "b,r", "10o0oo1rrrrrbooo", 1, AVR_ISA_2xxx, 0x8200},
177 {"sts", "i,r", "1001001ddddd0000", 2, AVR_ISA_2xxx, 0x9200},
178 {"lds", "r,i", "1001000ddddd0000", 2, AVR_ISA_2xxx, 0x9000},
179
180 {"brbc", "s,l", "111101lllllllsss", 1, AVR_ISA_1200, 0xf400},
181 {"brbs", "s,l", "111100lllllllsss", 1, AVR_ISA_1200, 0xf000},
182
183 {"brcc", "l", "111101lllllll000", 1, AVR_ISA_1200, 0xf400},
184 {"brcs", "l", "111100lllllll000", 1, AVR_ISA_1200, 0xf000},
185 {"breq", "l", "111100lllllll001", 1, AVR_ISA_1200, 0xf001},
186 {"brge", "l", "111101lllllll100", 1, AVR_ISA_1200, 0xf404},
187 {"brhc", "l", "111101lllllll101", 1, AVR_ISA_1200, 0xf405},
188 {"brhs", "l", "111100lllllll101", 1, AVR_ISA_1200, 0xf005},
189 {"brid", "l", "111101lllllll111", 1, AVR_ISA_1200, 0xf407},
190 {"brie", "l", "111100lllllll111", 1, AVR_ISA_1200, 0xf007},
191 {"brlo", "l", "111100lllllll000", 1, AVR_ISA_1200, 0xf000},
192 {"brlt", "l", "111100lllllll100", 1, AVR_ISA_1200, 0xf004},
193 {"brmi", "l", "111100lllllll010", 1, AVR_ISA_1200, 0xf002},
194 {"brne", "l", "111101lllllll001", 1, AVR_ISA_1200, 0xf401},
195 {"brpl", "l", "111101lllllll010", 1, AVR_ISA_1200, 0xf402},
196 {"brsh", "l", "111101lllllll000", 1, AVR_ISA_1200, 0xf400},
197 {"brtc", "l", "111101lllllll110", 1, AVR_ISA_1200, 0xf406},
198 {"brts", "l", "111100lllllll110", 1, AVR_ISA_1200, 0xf006},
199 {"brvc", "l", "111101lllllll011", 1, AVR_ISA_1200, 0xf403},
200 {"brvs", "l", "111100lllllll011", 1, AVR_ISA_1200, 0xf003},
201
202 {"rcall", "L", "1101LLLLLLLLLLLL", 1, AVR_ISA_1200, 0xd000},
203 {"rjmp", "L", "1100LLLLLLLLLLLL", 1, AVR_ISA_1200, 0xc000},
204
205 {"call", "h", "1001010hhhhh111h", 2, AVR_ISA_MEGA, 0x940e},
206 {"jmp", "h", "1001010hhhhh110h", 2, AVR_ISA_MEGA, 0x940c},
207
208 {"asr", "r", "1001010rrrrr0101", 1, AVR_ISA_1200, 0x9405},
209 {"com", "r", "1001010rrrrr0000", 1, AVR_ISA_1200, 0x9400},
210 {"dec", "r", "1001010rrrrr1010", 1, AVR_ISA_1200, 0x940a},
211 {"inc", "r", "1001010rrrrr0011", 1, AVR_ISA_1200, 0x9403},
212 {"lsr", "r", "1001010rrrrr0110", 1, AVR_ISA_1200, 0x9406},
213 {"neg", "r", "1001010rrrrr0001", 1, AVR_ISA_1200, 0x9401},
214 {"pop", "r", "1001000rrrrr1111", 1, AVR_ISA_2xxx, 0x900f},
215 {"push", "r", "1001001rrrrr1111", 1, AVR_ISA_2xxx, 0x920f},
216 {"ror", "r", "1001010rrrrr0111", 1, AVR_ISA_1200, 0x9407},
217 {"ser", "d", "11101111dddd1111", 1, AVR_ISA_1200, 0xef0f},
218 {"swap", "r", "1001010rrrrr0010", 1, AVR_ISA_1200, 0x9402},
219
220 {"bclr", "S", "100101001SSS1000", 1, AVR_ISA_1200, 0x9488},
221 {"bset", "S", "100101000SSS1000", 1, AVR_ISA_1200, 0x9408},
222
223 {"clc", "", "1001010010001000", 1, AVR_ISA_1200, 0x9488},
224 {"clh", "", "1001010011011000", 1, AVR_ISA_1200, 0x94d8},
225 {"cli", "", "1001010011111000", 1, AVR_ISA_1200, 0x94f8},
226 {"cln", "", "1001010010101000", 1, AVR_ISA_1200, 0x94a8},
227 {"cls", "", "1001010011001000", 1, AVR_ISA_1200, 0x94c8},
228 {"clt", "", "1001010011101000", 1, AVR_ISA_1200, 0x94e8},
229 {"clv", "", "1001010010111000", 1, AVR_ISA_1200, 0x94b8},
230 {"clz", "", "1001010010011000", 1, AVR_ISA_1200, 0x9498},
231 {"icall","", "1001010100001001", 1, AVR_ISA_2xxx, 0x9509},
232 {"ijmp", "", "1001010000001001", 1, AVR_ISA_2xxx, 0x9409},
233 {"lpm", "", "1001010111001000", 1, AVR_ISA_2xxx, 0x95c8},
234 {"nop", "", "0000000000000000", 1, AVR_ISA_1200, 0x0000},
235 {"ret", "", "1001010100001000", 1, AVR_ISA_1200, 0x9508},
236 {"reti", "", "1001010100011000", 1, AVR_ISA_1200, 0x9518},
237 {"sec", "", "1001010000001000", 1, AVR_ISA_1200, 0x9408},
238 {"seh", "", "1001010001011000", 1, AVR_ISA_1200, 0x9458},
239 {"sei", "", "1001010001111000", 1, AVR_ISA_1200, 0x9478},
240 {"sen", "", "1001010000101000", 1, AVR_ISA_1200, 0x9428},
241 {"ses", "", "1001010001001000", 1, AVR_ISA_1200, 0x9448},
242 {"set", "", "1001010001101000", 1, AVR_ISA_1200, 0x9468},
243 {"sev", "", "1001010000111000", 1, AVR_ISA_1200, 0x9438},
244 {"sez", "", "1001010000011000", 1, AVR_ISA_1200, 0x9418},
245 {"sleep","", "1001010110001000", 1, AVR_ISA_1200, 0x9588},
246 {"wdr", "", "1001010110101000", 1, AVR_ISA_1200, 0x95a8},
247 {"elpm", "", "1001010111011000", 1, AVR_ISA_MEGA_x03, 0x95d8},
248 {NULL, NULL, NULL, 0, 0, 0}
249 };
250
251
252
253 #define EXP_MOD_NAME(i) exp_mod[i].name
254 #define EXP_MOD_RELOC(i) exp_mod[i].reloc
255 #define EXP_MOD_NEG_RELOC(i) exp_mod[i].neg_reloc
256 #define HAVE_PM_P(i) exp_mod[i].have_pm
257
258 struct exp_mod_s
259 {
260 char * name;
261 bfd_reloc_code_real_type reloc;
262 bfd_reloc_code_real_type neg_reloc;
263 int have_pm;
264 };
265
266 static struct exp_mod_s exp_mod[] = {
267 {"hh8", BFD_RELOC_AVR_HH8_LDI, BFD_RELOC_AVR_HH8_LDI_NEG, 1},
268 {"pm_hh8", BFD_RELOC_AVR_HH8_LDI_PM, BFD_RELOC_AVR_HH8_LDI_PM_NEG, 0},
269 {"hi8", BFD_RELOC_AVR_HI8_LDI, BFD_RELOC_AVR_HI8_LDI_NEG, 1},
270 {"pm_hi8", BFD_RELOC_AVR_HI8_LDI_PM, BFD_RELOC_AVR_HI8_LDI_PM_NEG, 0},
271 {"lo8", BFD_RELOC_AVR_LO8_LDI, BFD_RELOC_AVR_LO8_LDI_NEG, 1},
272 {"pm_lo8", BFD_RELOC_AVR_LO8_LDI_PM, BFD_RELOC_AVR_LO8_LDI_PM_NEG, 0},
273 {"hlo8", -BFD_RELOC_AVR_LO8_LDI, -BFD_RELOC_AVR_LO8_LDI_NEG, 0},
274 {"hhi8", -BFD_RELOC_AVR_HI8_LDI, -BFD_RELOC_AVR_HI8_LDI_NEG, 0},
275 };
276
277 /* Opcode hash table. */
278 static struct hash_control *avr_hash;
279
280 /* Reloc modifiers hash control (hh8,hi8,lo8,pm_xx). */
281 static struct hash_control *avr_mod_hash;
282
283 #define OPTION_MMCU (OPTION_MD_BASE + 1)
284
285 struct option md_longopts[] = {
286 {"mmcu", required_argument, NULL, 'm'},
287 {NULL, no_argument, NULL, 0}
288 };
289 size_t md_longopts_size = sizeof(md_longopts);
290
291 static inline char *
292 skip_space (s)
293 char * s;
294 {
295 while (*s == ' ' || *s == '\t')
296 ++s;
297 return s;
298 }
299
300 /* Extract one word from FROM and copy it to TO. */
301 static char *
302 extract_word (char *from, char *to, int limit)
303 {
304 char *op_start;
305 char *op_end;
306 int size = 0;
307
308 /* Drop leading whitespace. */
309 from = skip_space (from);
310 *to = 0;
311 /* Find the op code end. */
312 for (op_start = op_end = from; *op_end != 0 && is_part_of_name(*op_end); )
313 {
314 to[size++] = *op_end++;
315 if (size + 1 >= limit)
316 break;
317 }
318 to[size] = 0;
319 return op_end;
320 }
321
322 int
323 md_estimate_size_before_relax (fragp, seg)
324 fragS *fragp;
325 asection *seg;
326 {
327 abort ();
328 return 0;
329 }
330
331 void
332 md_show_usage (stream)
333 FILE *stream;
334 {
335 fprintf
336 (stream,
337 _ ("AVR options:\n"
338 " -mmcu=[avr-name] select microcontroller variant\n"
339 " [avr-name] can be:\n"
340 " avr1 - AT90S1200\n"
341 " avr2 - AT90S2xxx, AT90S4xxx, AT90S85xx, ATtiny22\n"
342 " avr3 - ATmega103 or ATmega603\n"
343 " avr4 - ATmega161\n"
344 " or immediate microcontroller name.\n"));
345 }
346
347 static void
348 avr_set_arch (dummy)
349 int dummy;
350 {
351 char * str;
352 str = (char *)alloca (20);
353 input_line_pointer = extract_word (input_line_pointer, str, 20);
354 md_parse_option ('m', str);
355 bfd_set_arch_mach (stdoutput, TARGET_ARCH, avr_mcu->mach);
356 }
357
358 int
359 md_parse_option (c, arg)
360 int c;
361 char *arg;
362 {
363 char *t = alloca (strlen (arg) + 1);
364 char *s = t;
365 char *arg1 = arg;
366 do
367 *t = tolower (*arg1++);
368 while (*t++);
369
370 if (c == 'm')
371 {
372 int i;
373
374 for (i = 0; mcu_types[i].name; ++i)
375 if (strcmp (mcu_types[i].name, s) == 0)
376 break;
377
378 if (!mcu_types[i].name)
379 as_fatal (_ ("unknown MCU: %s\n"), arg);
380 if (avr_mcu == &default_mcu)
381 avr_mcu = &mcu_types[i];
382 else
383 as_fatal (_ ("redefinition of mcu type `%s'"), mcu_types[i].name);
384 return 1;
385 }
386 return 0;
387 }
388
389 symbolS *
390 md_undefined_symbol (name)
391 char *name;
392 {
393 return 0;
394 }
395
396 /* Convert a string pointed to by input_line_pointer into a floating point
397 constant of type `type', and store the appropriate bytes to `*litP'.
398 The number of LITTLENUMS emitted is stored in `*sizeP'. Returns NULL if
399 OK, or an error message otherwise. */
400 char *
401 md_atof (type, litP, sizeP)
402 int type;
403 char *litP;
404 int *sizeP;
405 {
406 int prec;
407 LITTLENUM_TYPE words[4];
408 LITTLENUM_TYPE *wordP;
409 char *t;
410
411 switch (type)
412 {
413 case 'f':
414 prec = 2;
415 break;
416 case 'd':
417 prec = 4;
418 break;
419 default:
420 *sizeP = 0;
421 return _("bad call to md_atof");
422 }
423
424 t = atof_ieee (input_line_pointer, type, words);
425 if (t)
426 input_line_pointer = t;
427
428 *sizeP = prec * sizeof (LITTLENUM_TYPE);
429 /* This loop outputs the LITTLENUMs in REVERSE order. */
430 for (wordP = words + prec - 1; prec--;)
431 {
432 md_number_to_chars (litP, (valueT) (*wordP--), sizeof (LITTLENUM_TYPE));
433 litP += sizeof (LITTLENUM_TYPE);
434 }
435 return NULL;
436 }
437
438 void
439 md_convert_frag (abfd, sec, fragP)
440 bfd *abfd;
441 asection *sec;
442 fragS *fragP;
443 {
444 abort ();
445 }
446
447
448 void
449 md_begin ()
450 {
451 int i;
452 struct avr_opcodes_s *opcode;
453 avr_hash = hash_new();
454
455 /* Insert unique names into hash table. This hash table then provides a
456 quick index to the first opcode with a particular name in the opcode
457 table. */
458
459 for (opcode = avr_opcodes; opcode->name; opcode++)
460 hash_insert (avr_hash, opcode->name, (char *) opcode);
461
462 avr_mod_hash = hash_new ();
463
464 for (i = 0; i < sizeof (exp_mod) / sizeof (exp_mod[0]); ++i)
465 hash_insert (avr_mod_hash, EXP_MOD_NAME(i), (void*)(i+10));
466
467 for (i = 0; i < 32; i++)
468 {
469 char buf[5];
470
471 sprintf (buf, "r%d", i);
472 symbol_table_insert (symbol_new (buf, reg_section, i,
473 &zero_address_frag));
474 sprintf (buf, "R%d", i);
475 symbol_table_insert (symbol_new (buf, reg_section, i,
476 &zero_address_frag));
477 }
478
479 bfd_set_arch_mach (stdoutput, TARGET_ARCH, avr_mcu->mach);
480 }
481
482
483 static unsigned int
484 avr_operands (opcode, line)
485 struct avr_opcodes_s *opcode;
486 char **line;
487 {
488 char *op = opcode->constraints;
489 unsigned int bin = opcode->bin_opcode;
490 char *frag = frag_more (opcode->insn_size * 2);
491 char *str = *line;
492 int where = frag - frag_now->fr_literal;
493
494 /* Opcode have operands. */
495 if (*op)
496 {
497 unsigned int reg1 = 0;
498 unsigned int reg2 = 0;
499 int reg1_present = 0;
500 int reg2_present = 0;
501
502 /* Parse first operand. */
503 if (REGISTER_P (*op))
504 reg1_present = 1;
505 reg1 = avr_operand (opcode, where, op, &str);
506 ++op;
507
508 /* Parse second operand. */
509 if (*op)
510 {
511 if (*op == ',')
512 ++op;
513 if (*op == '=')
514 {
515 reg2 = reg1;
516 reg2_present = 1;
517 }
518 else
519 {
520 if (REGISTER_P (*op))
521 reg2_present = 1;
522
523 str = skip_space (str);
524 if (*str++ != ',')
525 as_bad (_ ("`,' required"));
526 str = skip_space (str);
527
528 reg2 = avr_operand (opcode, where, op, &str);
529
530 }
531 if (reg1_present && reg2_present)
532 reg2 = (reg2 & 0xf) | ((reg2 << 5) & 0x200);
533 else if (reg2_present)
534 reg2 <<= 4;
535 }
536 if (reg1_present)
537 reg1 <<= 4;
538 bin |= reg1 | reg2;
539 }
540 if (opcode->insn_size == 2)
541 {
542 bfd_putl32 ((bfd_vma)bin, frag);
543 }
544 else
545 {
546 bfd_putl16 ((bfd_vma)bin, frag);
547 }
548 *line = str;
549 return bin;
550 }
551
552 static unsigned int
553 avr_get_constant (str, max)
554 char * str;
555 unsigned int max;
556 {
557 expressionS ex;
558 str = skip_space (str);
559 input_line_pointer = str;
560 expression (&ex);
561
562 if (ex.X_op != O_constant)
563 as_bad (_("constant value required"));
564
565 if (ex.X_add_number > max)
566 as_bad (_("number must be less than %d"), max+1);
567 return ex.X_add_number;
568 }
569
570 static unsigned int
571 avr_operand (opcode, where, op, line)
572 struct avr_opcodes_s *opcode;
573 int where;
574 char *op;
575 char **line;
576 {
577 unsigned int op_mask = 0;
578 char *str = *line;
579 expressionS op_expr;
580
581 str = skip_space (str);
582 switch (*op)
583 {
584 /* Any register operand. */
585 case 'w':
586 case 'd':
587 case 'r':
588 {
589 char r_name[256];
590 str = extract_word (str, r_name, sizeof (r_name));
591 parse_exp (r_name, &op_expr);
592 if (op_expr.X_op == O_register)
593 {
594 op_mask = op_expr.X_add_number;
595 if (op_mask <= 31)
596 {
597 if (*op == 'd')
598 {
599 if (op_mask < 16)
600 as_bad (_ ("register number above 15 required"));
601 op_mask -= 16;
602 }
603 if (*op == 'w')
604 {
605 op_mask -= 24;
606 if (op_mask & 1 || op_mask > 6)
607 as_bad (_ ("register r24,r26,r28 or r30 required"));
608 op_mask >>= 1;
609 }
610 break;
611 }
612 }
613 as_bad (_ ("register required"));
614 }
615 break;
616
617 case 'e':
618 {
619 char c;
620 if (*str == '-')
621 {
622 str = skip_space (str+1);
623 op_mask = 0x1002;
624 }
625 c = tolower (*str);
626 if (c == 'x')
627 op_mask |= 0x100c;
628 else if (c == 'y')
629 op_mask |= 0x8;
630 else if (c != 'z')
631 as_bad (_ ("pointer register (X,Y or Z) required"));
632
633 str = skip_space (str+1);
634 if (*str == '+')
635 {
636 ++str;
637 if (op_mask & 2)
638 as_bad (_ ("cannot both predecrement and postincrement"));
639 op_mask |= 0x1001;
640 }
641 }
642 break;
643
644 case 'b':
645 {
646 char c = tolower (*str++);
647 if (c == 'y')
648 op_mask |= 0x8;
649 else if (c != 'z')
650 as_bad (_ ("pointer register (Y or Z) required"));
651 str = skip_space (str);
652 if (*str++ == '+')
653 {
654 unsigned int x;
655 x = avr_get_constant (str, 63);
656 str = input_line_pointer;
657 op_mask |= (x & 7) | ((x & (3 << 3)) << 7) | ((x & (1 << 5)) << 8);
658 }
659 }
660 break;
661
662 case 'h':
663 {
664 str = parse_exp (str, &op_expr);
665 fix_new_exp (frag_now, where, opcode->insn_size * 2,
666 &op_expr, false, BFD_RELOC_AVR_CALL);
667
668 }
669 break;
670
671 case 'L':
672 {
673 str = parse_exp (str, &op_expr);
674 fix_new_exp (frag_now, where, opcode->insn_size * 2,
675 &op_expr, true, BFD_RELOC_AVR_13_PCREL);
676
677 }
678 break;
679
680 case 'l':
681 {
682 str = parse_exp (str, &op_expr);
683 fix_new_exp (frag_now, where, opcode->insn_size * 2,
684 &op_expr, true, BFD_RELOC_AVR_7_PCREL);
685
686 }
687 break;
688
689 case 'i':
690 {
691 str = parse_exp (str, &op_expr);
692 fix_new_exp (frag_now, where+2, opcode->insn_size * 2,
693 &op_expr, false, BFD_RELOC_16);
694
695 }
696 break;
697
698 case 'M':
699 {
700 bfd_reloc_code_real_type r_type;
701 input_line_pointer = str;
702 r_type = avr_ldi_expression (&op_expr);
703 str = input_line_pointer;
704 fix_new_exp (frag_now, where, 3,
705 &op_expr, false, r_type);
706 }
707 break;
708
709 case 'n':
710 {
711 unsigned int x;
712 x = ~avr_get_constant (str, 255);
713 str = input_line_pointer;
714 op_mask |= (x & 0xf) | ((x << 4) & 0xf00);
715 }
716 break;
717
718 case 'K':
719 {
720 unsigned int x;
721 x = avr_get_constant (str, 63);
722 str = input_line_pointer;
723 op_mask |= (x & 0xf) | ((x & 0x30) << 2);
724 }
725 break;
726
727 case 'S':
728 case 's':
729 {
730 unsigned int x;
731 x = avr_get_constant (str, 7);
732 str = input_line_pointer;
733 if (*op == 'S')
734 x <<= 4;
735 op_mask |= x;
736 }
737 break;
738
739 case 'P':
740 {
741 unsigned int x;
742 x = avr_get_constant (str, 63);
743 str = input_line_pointer;
744 op_mask |= (x & 0xf) | ((x & 0x30) << 5);
745 }
746 break;
747
748 case 'p':
749 {
750 unsigned int x;
751 x = avr_get_constant (str, 31);
752 str = input_line_pointer;
753 op_mask |= x << 3;
754 }
755 break;
756 default:
757 as_bad (_ ("unknown constraint `%c'"), *op);
758 }
759 *line = str;
760 return op_mask;
761 }
762
763 /* GAS will call this function for each section at the end of the assembly,
764 to permit the CPU backend to adjust the alignment of a section. */
765 valueT
766 md_section_align (seg, addr)
767 asection *seg;
768 valueT addr;
769 {
770 int align = bfd_get_section_alignment (stdoutput, seg);
771 return ((addr + (1 << align) - 1) & (-1 << align));
772 }
773
774 /* If you define this macro, it should return the offset between the
775 address of a PC relative fixup and the position from which the PC
776 relative adjustment should be made. On many processors, the base
777 of a PC relative instruction is the next instruction, so this
778 macro would return the length of an instruction. */
779 long
780 md_pcrel_from_section (fixp, sec)
781 fixS *fixp;
782 segT sec;
783 {
784 if (fixp->fx_addsy != (symbolS *)NULL
785 && (!S_IS_DEFINED (fixp->fx_addsy)
786 || (S_GET_SEGMENT (fixp->fx_addsy) != sec)))
787 return 0;
788 return fixp->fx_frag->fr_address + fixp->fx_where;
789 }
790
791 /* GAS will call this for each fixup. It should store the correct
792 value in the object file. */
793 int
794 md_apply_fix3 (fixp, valuep, seg)
795 fixS *fixp;
796 valueT *valuep;
797 segT seg;
798 {
799 unsigned char *where;
800 unsigned long insn;
801 long value;
802
803 if (fixp->fx_addsy == (symbolS *) NULL)
804 {
805 value = *valuep;
806 fixp->fx_done = 1;
807 }
808 else if (fixp->fx_pcrel)
809 {
810 segT s = S_GET_SEGMENT (fixp->fx_addsy);
811 if (fixp->fx_addsy && (s == seg || s == absolute_section))
812 {
813 value = S_GET_VALUE (fixp->fx_addsy) + *valuep;
814 fixp->fx_done = 1;
815 }
816 else
817 value = *valuep;
818 }
819 else
820 {
821 value = fixp->fx_offset;
822 if (fixp->fx_subsy != (symbolS *) NULL)
823 {
824 if (S_GET_SEGMENT (fixp->fx_subsy) == absolute_section)
825 {
826 value -= S_GET_VALUE (fixp->fx_subsy);
827 fixp->fx_done = 1;
828 }
829 else
830 {
831 /* We don't actually support subtracting a symbol. */
832 as_bad_where (fixp->fx_file, fixp->fx_line,
833 _ ("expression too complex"));
834 }
835 }
836 }
837 switch (fixp->fx_r_type)
838 {
839 default:
840 fixp->fx_no_overflow = 1;
841 break;
842 case BFD_RELOC_AVR_7_PCREL:
843 case BFD_RELOC_AVR_13_PCREL:
844 case BFD_RELOC_32:
845 case BFD_RELOC_16:
846 case BFD_RELOC_AVR_CALL:
847 break;
848 }
849
850 if (fixp->fx_done)
851 {
852 /* Fetch the instruction, insert the fully resolved operand
853 value, and stuff the instruction back again. */
854 where = fixp->fx_frag->fr_literal + fixp->fx_where;
855 insn = bfd_getl16 (where);
856
857 switch (fixp->fx_r_type)
858 {
859 case BFD_RELOC_AVR_7_PCREL:
860 if (value & 1)
861 as_bad_where (fixp->fx_file, fixp->fx_line,
862 _("odd address operand: %ld"), value);
863 /* Instruction addresses are always right-shifted by 1. */
864 value >>= 1;
865 --value; /* Correct PC. */
866 if (value < -64 || value > 63)
867 as_bad_where (fixp->fx_file, fixp->fx_line,
868 _("operand out of range: %ld"), value);
869 value = (value << 3) & 0x3f8;
870 bfd_putl16 ((bfd_vma) (value | insn), where);
871 break;
872
873 case BFD_RELOC_AVR_13_PCREL:
874 if (value & 1)
875 as_bad_where (fixp->fx_file, fixp->fx_line,
876 _("odd address operand: %ld"), value);
877 /* Instruction addresses are always right-shifted by 1. */
878 value >>= 1;
879 --value; /* Correct PC. */
880 /* XXX AT90S8515 must have WRAP here. */
881
882 if (value < -2048 || value > 2047)
883 {
884 if (avr_mcu->mach == bfd_mach_avr2)
885 {
886 if (value > 2047)
887 value -= 4096;
888 else
889 value += 4096;
890 }
891 else
892 as_bad_where (fixp->fx_file, fixp->fx_line,
893 _("operand out of range: %ld"), value);
894 }
895
896 value &= 0xfff;
897 bfd_putl16 ((bfd_vma) (value | insn), where);
898 break;
899
900 case BFD_RELOC_32:
901 bfd_putl16 ((bfd_vma) value, where);
902 break;
903
904 case BFD_RELOC_16:
905 bfd_putl16 ((bfd_vma) value, where);
906 break;
907
908 case BFD_RELOC_AVR_16_PM:
909 bfd_putl16 ((bfd_vma) (value>>1), where);
910 break;
911
912 case BFD_RELOC_AVR_LO8_LDI:
913 bfd_putl16 ((bfd_vma) insn | LDI_IMMEDIATE (value), where);
914 break;
915
916 case -BFD_RELOC_AVR_LO8_LDI:
917 bfd_putl16 ((bfd_vma) insn | LDI_IMMEDIATE (value >> 16), where);
918 break;
919
920 case BFD_RELOC_AVR_HI8_LDI:
921 bfd_putl16 ((bfd_vma) insn | LDI_IMMEDIATE (value >> 8), where);
922 break;
923
924 case -BFD_RELOC_AVR_HI8_LDI:
925 bfd_putl16 ((bfd_vma) insn | LDI_IMMEDIATE (value >> 24), where);
926 break;
927
928 case BFD_RELOC_AVR_HH8_LDI:
929 bfd_putl16 ((bfd_vma) insn | LDI_IMMEDIATE (value >> 16), where);
930 break;
931
932 case BFD_RELOC_AVR_LO8_LDI_NEG:
933 bfd_putl16 ((bfd_vma) insn | LDI_IMMEDIATE (-value), where);
934 break;
935
936 case -BFD_RELOC_AVR_LO8_LDI_NEG:
937 bfd_putl16 ((bfd_vma) insn | LDI_IMMEDIATE (-value >> 16), where);
938 break;
939
940 case BFD_RELOC_AVR_HI8_LDI_NEG:
941 bfd_putl16 ((bfd_vma) insn | LDI_IMMEDIATE (-value >> 8), where);
942 break;
943
944 case -BFD_RELOC_AVR_HI8_LDI_NEG:
945 bfd_putl16 ((bfd_vma) insn | LDI_IMMEDIATE (-value >> 24), where);
946 break;
947
948 case BFD_RELOC_AVR_HH8_LDI_NEG:
949 bfd_putl16 ((bfd_vma) insn | LDI_IMMEDIATE (-value >> 16), where);
950 break;
951
952 case BFD_RELOC_AVR_LO8_LDI_PM:
953 bfd_putl16 ((bfd_vma) insn | LDI_IMMEDIATE (value >> 1), where);
954 break;
955
956 case BFD_RELOC_AVR_HI8_LDI_PM:
957 bfd_putl16 ((bfd_vma) insn | LDI_IMMEDIATE (value >> 9), where);
958 break;
959
960 case BFD_RELOC_AVR_HH8_LDI_PM:
961 bfd_putl16 ((bfd_vma) insn | LDI_IMMEDIATE (value >> 17), where);
962 break;
963
964 case BFD_RELOC_AVR_LO8_LDI_PM_NEG:
965 bfd_putl16 ((bfd_vma) insn | LDI_IMMEDIATE (-value >> 1), where);
966 break;
967
968 case BFD_RELOC_AVR_HI8_LDI_PM_NEG:
969 bfd_putl16 ((bfd_vma) insn | LDI_IMMEDIATE (-value >> 9), where);
970 break;
971
972 case BFD_RELOC_AVR_HH8_LDI_PM_NEG:
973 bfd_putl16 ((bfd_vma) insn | LDI_IMMEDIATE (-value >> 17), where);
974 break;
975
976 case BFD_RELOC_AVR_CALL:
977 {
978 unsigned long x;
979 x = bfd_getl16 (where);
980 if (value & 1)
981 as_bad_where (fixp->fx_file, fixp->fx_line,
982 _("odd address operand: %ld"), value);
983 value >>= 1;
984 x |= ((value & 0x10000) | ((value << 3) & 0x1f00000)) >> 16;
985 bfd_putl16 ((bfd_vma) x, where);
986 bfd_putl16 ((bfd_vma) (value & 0xffff), where+2);
987 }
988 break;
989
990 default:
991 as_fatal ( _("line %d: unknown relocation type: 0x%x"),
992 fixp->fx_line, fixp->fx_r_type);
993 break;
994 }
995 }
996 else
997 {
998 switch (fixp->fx_r_type)
999 {
1000 case -BFD_RELOC_AVR_HI8_LDI_NEG:
1001 case -BFD_RELOC_AVR_HI8_LDI:
1002 case -BFD_RELOC_AVR_LO8_LDI_NEG:
1003 case -BFD_RELOC_AVR_LO8_LDI:
1004 as_bad_where (fixp->fx_file, fixp->fx_line,
1005 _("only constant expression allowed"));
1006 fixp->fx_done = 1;
1007 break;
1008 default:
1009 break;
1010 }
1011 fixp->fx_addnumber = value;
1012 }
1013 return 0;
1014 }
1015
1016
1017 /* A `BFD_ASSEMBLER' GAS will call this to generate a reloc. GAS
1018 will pass the resulting reloc to `bfd_install_relocation'. This
1019 currently works poorly, as `bfd_install_relocation' often does the
1020 wrong thing, and instances of `tc_gen_reloc' have been written to
1021 work around the problems, which in turns makes it difficult to fix
1022 `bfd_install_relocation'. */
1023
1024 /* If while processing a fixup, a reloc really needs to be created
1025 then it is done here. */
1026
1027 arelent *
1028 tc_gen_reloc (seg, fixp)
1029 asection *seg;
1030 fixS *fixp;
1031 {
1032 arelent *reloc;
1033
1034 reloc = (arelent *) xmalloc (sizeof (arelent));
1035
1036 reloc->sym_ptr_ptr = (asymbol **) xmalloc (sizeof (asymbol *));
1037 *reloc->sym_ptr_ptr = symbol_get_bfdsym (fixp->fx_addsy);
1038
1039 reloc->address = fixp->fx_frag->fr_address + fixp->fx_where;
1040 reloc->howto = bfd_reloc_type_lookup (stdoutput, fixp->fx_r_type);
1041 if (reloc->howto == (reloc_howto_type *) NULL)
1042 {
1043 as_bad_where (fixp->fx_file, fixp->fx_line,
1044 _("reloc %d not supported by object file format"),
1045 (int)fixp->fx_r_type);
1046 return NULL;
1047 }
1048
1049 if (fixp->fx_r_type == BFD_RELOC_VTABLE_INHERIT
1050 || fixp->fx_r_type == BFD_RELOC_VTABLE_ENTRY)
1051 reloc->address = fixp->fx_offset;
1052
1053 reloc->addend = fixp->fx_offset;
1054
1055 return reloc;
1056 }
1057
1058
1059 void
1060 md_assemble (str)
1061 char *str;
1062 {
1063 struct avr_opcodes_s * opcode;
1064 char op[11];
1065
1066 str = extract_word (str, op, sizeof(op));
1067
1068 if (!op[0])
1069 as_bad (_ ("can't find opcode "));
1070
1071 opcode = (struct avr_opcodes_s *) hash_find (avr_hash, op);
1072
1073 if (opcode == NULL)
1074 {
1075 as_bad (_ ("unknown opcode `%s'"), op);
1076 return;
1077 }
1078
1079 if ((opcode->isa & avr_mcu->isa) != opcode->isa)
1080 as_bad (_ ("illegal opcode %s for mcu %s"), opcode->name, avr_mcu->name);
1081
1082 /* We used to set input_line_pointer to the result of get_operands,
1083 but that is wrong. Our caller assumes we don't change it. */
1084 {
1085 char *t = input_line_pointer;
1086 avr_operands (opcode, &str);
1087 if (*str)
1088 as_bad (_ ("garbage at end of line"));
1089 input_line_pointer = t;
1090 }
1091 }
1092
1093 /* Parse ordinary expression. */
1094 static char *
1095 parse_exp (s, op)
1096 char *s;
1097 expressionS * op;
1098 {
1099 input_line_pointer = s;
1100 expression (op);
1101 if (op->X_op == O_absent)
1102 as_bad (_("missing operand"));
1103 return input_line_pointer;
1104 }
1105
1106
1107 /* Parse special expressions (needed for LDI command):
1108 xx8 (address)
1109 xx8 (-address)
1110 pm_xx8 (address)
1111 pm_xx8 (-address)
1112 where xx is: hh, hi, lo
1113 */
1114 static bfd_reloc_code_real_type
1115 avr_ldi_expression (exp)
1116 expressionS *exp;
1117 {
1118 char *str = input_line_pointer;
1119 char *tmp;
1120 char op[8];
1121 int mod;
1122 tmp = str;
1123
1124 str = extract_word (str, op, sizeof (op));
1125 if (op[0])
1126 {
1127 mod = (int) hash_find (avr_mod_hash, op);
1128 if (mod)
1129 {
1130 int closes = 0;
1131 mod -= 10;
1132 str = skip_space (str);
1133 if (*str == '(')
1134 {
1135 int neg_p = 0;
1136 ++str;
1137 if (strncmp ("pm(", str, 3) == 0
1138 || strncmp ("-(pm(", str, 5) == 0)
1139 {
1140 if (HAVE_PM_P(mod))
1141 {
1142 ++mod;
1143 ++closes;
1144 }
1145 else
1146 as_bad (_ ("illegal expression"));
1147 if (*str == '-')
1148 {
1149 neg_p = 1;
1150 ++closes;
1151 str += 5;
1152 }
1153 else
1154 str += 3;
1155 }
1156 if (*str == '-' && *(str + 1) == '(')
1157 {
1158 neg_p ^= 1;
1159 ++closes;
1160 str += 2;
1161 }
1162 input_line_pointer = str;
1163 expression (exp);
1164 do
1165 {
1166 if (*input_line_pointer != ')')
1167 {
1168 as_bad (_ ("`)' required"));
1169 break;
1170 }
1171 input_line_pointer++;
1172 }
1173 while (closes--);
1174 return neg_p ? EXP_MOD_NEG_RELOC (mod) : EXP_MOD_RELOC (mod);
1175 }
1176 }
1177 }
1178 input_line_pointer = tmp;
1179 expression (exp);
1180 return BFD_RELOC_AVR_LO8_LDI;
1181 }
1182
1183 /* Flag to pass `pm' mode between `avr_parse_cons_expression' and
1184 `avr_cons_fix_new' */
1185 static int exp_mod_pm = 0;
1186
1187 /* Parse special CONS expression: pm (expression)
1188 which is used for addressing to a program memory.
1189 Relocation: BFD_RELOC_AVR_16_PM */
1190 void
1191 avr_parse_cons_expression (exp, nbytes)
1192 expressionS *exp;
1193 int nbytes;
1194 {
1195 char * tmp;
1196
1197 exp_mod_pm = 0;
1198
1199 tmp = input_line_pointer = skip_space (input_line_pointer);
1200
1201 if (nbytes == 2)
1202 {
1203 char * pm_name = "pm";
1204 int len = strlen (pm_name);
1205 if (strncasecmp (input_line_pointer, pm_name, len) == 0)
1206 {
1207 input_line_pointer = skip_space (input_line_pointer + len);
1208 if (*input_line_pointer == '(')
1209 {
1210 input_line_pointer = skip_space (input_line_pointer + 1);
1211 exp_mod_pm = 1;
1212 expression (exp);
1213 if (*input_line_pointer == ')')
1214 ++input_line_pointer;
1215 else
1216 {
1217 as_bad (_ ("`)' required"));
1218 exp_mod_pm = 0;
1219 }
1220 return;
1221 }
1222 input_line_pointer = tmp;
1223 }
1224 }
1225 expression (exp);
1226 }
1227
1228 void
1229 avr_cons_fix_new(frag, where, nbytes, exp)
1230 fragS *frag;
1231 int where;
1232 int nbytes;
1233 expressionS *exp;
1234 {
1235 if (exp_mod_pm == 0)
1236 {
1237 if (nbytes == 2)
1238 fix_new_exp (frag, where, nbytes, exp, false, BFD_RELOC_16);
1239 else if (nbytes == 4)
1240 fix_new_exp (frag, where, nbytes, exp, false, BFD_RELOC_32);
1241 else
1242 as_bad (_ ("illegal %srelocation size: %d"), "", nbytes);
1243 }
1244 else
1245 {
1246 if (nbytes == 2)
1247 fix_new_exp (frag, where, nbytes, exp, false, BFD_RELOC_AVR_16_PM);
1248 else
1249 as_bad (_ ("illegal %srelocation size: %d"), "`pm' ", nbytes);
1250 exp_mod_pm = 0;
1251 }
1252 }