1 /* tc-msp430.c -- Assembler code for the Texas Instruments MSP430
3 Copyright (C) 2002-2013 Free Software Foundation, Inc.
4 Contributed by Dmitry Diky <diwil@mail.ru>
6 This file is part of GAS, the GNU Assembler.
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 3, or (at your option)
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.
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, 51 Franklin Street - Fifth Floor,
21 Boston, MA 02110-1301, USA. */
25 #define PUSH_1X_WORKAROUND
27 #include "opcode/msp430.h"
28 #include "safe-ctype.h"
29 #include "dwarf2dbg.h"
30 #include "elf/msp430.h"
32 /* We will disable polymorphs by default because it is dangerous.
33 The potential problem here is the following: assume we got the
38 jump subroutine ; external symbol
43 In case of assembly time relaxation we'll get:
44 0: jmp .l1 <.text +0x08> (reloc deleted)
51 If the 'subroutine' is within +-1024 bytes range then linker
58 8: ret ; 'jmp .text +0x08' will land here. WRONG!!!
60 The workaround is the following:
61 1. Declare global var enable_polymorphs which set to 1 via option -mp.
62 2. Declare global var enable_relax which set to 1 via option -mQ.
64 If polymorphs are enabled, and relax isn't, treat all jumps as long jumps,
65 do not delete any relocs and leave them for linker.
67 If relax is enabled, relax at assembly time and kill relocs as necessary. */
69 int msp430_enable_relax
;
70 int msp430_enable_polys
;
72 /* Set linkrelax here to avoid fixups in most sections. */
75 /* GCC uses the some condition codes which we'll
76 implement as new polymorph instructions.
78 COND EXPL SHORT JUMP LONG JUMP
79 ===============================================
80 eq == jeq jne +4; br lab
81 ne != jne jeq +4; br lab
83 ltn honours no-overflow flag
84 ltn < jn jn +2; jmp +4; br lab
86 lt < jl jge +4; br lab
87 ltu < jlo lhs +4; br lab
93 ge >= jge jl +4; br lab
94 geu >= jhs jlo +4; br lab
95 ===============================================
97 Therefore, new opcodes are (BranchEQ -> beq; and so on...)
98 beq,bne,blt,bltn,bltu,bge,bgeu
99 'u' means unsigned compares
101 Also, we add 'jump' instruction:
102 jump UNCOND -> jmp br lab
104 They will have fmt == 4, and insn_opnumb == number of instruction. */
109 int index
; /* Corresponding insn_opnumb. */
110 int sop
; /* Opcode if jump length is short. */
111 long lpos
; /* Label position. */
112 long lop0
; /* Opcode 1 _word_ (16 bits). */
113 long lop1
; /* Opcode second word. */
114 long lop2
; /* Opcode third word. */
117 #define MSP430_RLC(n,i,sop,o1) \
118 {#n, i, sop, 2, (o1 + 2), 0x4010, 0}
120 static struct rcodes_s msp430_rcodes
[] =
122 MSP430_RLC (beq
, 0, 0x2400, 0x2000),
123 MSP430_RLC (bne
, 1, 0x2000, 0x2400),
124 MSP430_RLC (blt
, 2, 0x3800, 0x3400),
125 MSP430_RLC (bltu
, 3, 0x2800, 0x2c00),
126 MSP430_RLC (bge
, 4, 0x3400, 0x3800),
127 MSP430_RLC (bgeu
, 5, 0x2c00, 0x2800),
128 {"bltn", 6, 0x3000, 3, 0x3000 + 1, 0x3c00 + 2,0x4010},
129 {"jump", 7, 0x3c00, 1, 0x4010, 0, 0},
134 #define MSP430_RLC(n,i,sop,o1) \
135 {#n, i, sop, 2, (o1 + 2), 0x0030, 0}
137 static struct rcodes_s msp430x_rcodes
[] =
139 MSP430_RLC (beq
, 0, 0x2400, 0x2000),
140 MSP430_RLC (bne
, 1, 0x2000, 0x2400),
141 MSP430_RLC (blt
, 2, 0x3800, 0x3400),
142 MSP430_RLC (bltu
, 3, 0x2800, 0x2c00),
143 MSP430_RLC (bge
, 4, 0x3400, 0x3800),
144 MSP430_RLC (bgeu
, 5, 0x2c00, 0x2800),
145 {"bltn", 6, 0x3000, 3, 0x0030 + 1, 0x3c00 + 2, 0x3000},
146 {"jump", 7, 0x3c00, 1, 0x0030, 0, 0},
151 /* More difficult than above and they have format 5.
154 =================================================================
155 gt > jeq +2; jge label jeq +6; jl +4; br label
156 gtu > jeq +2; jhs label jeq +6; jlo +4; br label
157 leu <= jeq label; jlo label jeq +2; jhs +4; br label
158 le <= jeq label; jl label jeq +2; jge +4; br label
159 ================================================================= */
164 int index
; /* Corresponding insn_opnumb. */
165 int tlab
; /* Number of labels in short mode. */
166 int op0
; /* Opcode for first word of short jump. */
167 int op1
; /* Opcode for second word of short jump. */
168 int lop0
; /* Opcodes for long jump mode. */
173 static struct hcodes_s msp430_hcodes
[] =
175 {"bgt", 0, 1, 0x2401, 0x3400, 0x2403, 0x3802, 0x4010 },
176 {"bgtu", 1, 1, 0x2401, 0x2c00, 0x2403, 0x2802, 0x4010 },
177 {"bleu", 2, 2, 0x2400, 0x2800, 0x2401, 0x2c02, 0x4010 },
178 {"ble", 3, 2, 0x2400, 0x3800, 0x2401, 0x3402, 0x4010 },
182 static struct hcodes_s msp430x_hcodes
[] =
184 {"bgt", 0, 1, 0x2401, 0x3400, 0x2403, 0x3802, 0x0030 },
185 {"bgtu", 1, 1, 0x2401, 0x2c00, 0x2403, 0x2802, 0x0030 },
186 {"bleu", 2, 2, 0x2400, 0x2800, 0x2401, 0x2c02, 0x0030 },
187 {"ble", 3, 2, 0x2400, 0x3800, 0x2401, 0x3402, 0x0030 },
191 const char comment_chars
[] = ";";
192 const char line_comment_chars
[] = "#";
193 const char line_separator_chars
[] = "{";
194 const char EXP_CHARS
[] = "eE";
195 const char FLT_CHARS
[] = "dD";
197 /* Handle long expressions. */
198 extern LITTLENUM_TYPE generic_bignum
[];
200 static struct hash_control
*msp430_hash
;
203 #define STATE_UNCOND_BRANCH 1 /* jump */
204 #define STATE_NOOV_BRANCH 3 /* bltn */
205 #define STATE_SIMPLE_BRANCH 2 /* bne, beq, etc... */
206 #define STATE_EMUL_BRANCH 4
215 #define STATE_BITS10 1 /* wild guess. short jump */
216 #define STATE_WORD 2 /* 2 bytes pc rel. addr. more */
217 #define STATE_UNDEF 3 /* cannot handle this yet. convert to word mode */
219 #define ENCODE_RELAX(what,length) (((what) << 2) + (length))
220 #define RELAX_STATE(s) ((s) & 3)
221 #define RELAX_LEN(s) ((s) >> 2)
222 #define RELAX_NEXT(a,b) ENCODE_RELAX (a, b + 1)
224 relax_typeS md_relax_table
[] =
232 /* Unconditional jump. */
234 {1024, -1024, CNRL
, RELAX_NEXT (STATE_UNCOND_BRANCH
, STATE_BITS10
)}, /* state 10 bits displ */
235 {0, 0, CUBL
, RELAX_NEXT (STATE_UNCOND_BRANCH
, STATE_WORD
)}, /* state word */
236 {1, 1, CUBL
, 0}, /* state undef */
238 /* Simple branches. */
240 {1024, -1024, CNRL
, RELAX_NEXT (STATE_SIMPLE_BRANCH
, STATE_BITS10
)}, /* state 10 bits displ */
241 {0, 0, CSBL
, RELAX_NEXT (STATE_SIMPLE_BRANCH
, STATE_WORD
)}, /* state word */
244 /* blt no overflow branch. */
246 {1024, -1024, CNRL
, RELAX_NEXT (STATE_NOOV_BRANCH
, STATE_BITS10
)}, /* state 10 bits displ */
247 {0, 0, CNOL
, RELAX_NEXT (STATE_NOOV_BRANCH
, STATE_WORD
)}, /* state word */
250 /* Emulated branches. */
252 {1020, -1020, CEBL
, RELAX_NEXT (STATE_EMUL_BRANCH
, STATE_BITS10
)}, /* state 10 bits displ */
253 {0, 0, CNOL
, RELAX_NEXT (STATE_EMUL_BRANCH
, STATE_WORD
)}, /* state word */
258 #define MAX_OP_LEN 256
273 static struct mcu_type_s mcu_types
[] =
275 {"msp430afe221", MSP_ISA_430
},
276 {"msp430afe222", MSP_ISA_430
},
277 {"msp430afe223", MSP_ISA_430
},
278 {"msp430afe231", MSP_ISA_430
},
279 {"msp430afe232", MSP_ISA_430
},
280 {"msp430afe233", MSP_ISA_430
},
281 {"msp430afe251", MSP_ISA_430
},
282 {"msp430afe252", MSP_ISA_430
},
283 {"msp430afe253", MSP_ISA_430
},
284 {"msp430c091", MSP_ISA_430
},
285 {"msp430c092", MSP_ISA_430
},
286 {"msp430c111", MSP_ISA_430
},
287 {"msp430c1111", MSP_ISA_430
},
288 {"msp430c112", MSP_ISA_430
},
289 {"msp430c1121", MSP_ISA_430
},
290 {"msp430e112", MSP_ISA_430
},
291 {"msp430c1331", MSP_ISA_430
},
292 {"msp430c1351", MSP_ISA_430
},
293 {"msp430c311s", MSP_ISA_430
},
294 {"msp430c312", MSP_ISA_430
},
295 {"msp430c313", MSP_ISA_430
},
296 {"msp430c314", MSP_ISA_430
},
297 {"msp430c315", MSP_ISA_430
},
298 {"msp430c323", MSP_ISA_430
},
299 {"msp430c325", MSP_ISA_430
},
300 {"msp430c336", MSP_ISA_430
},
301 {"msp430c337", MSP_ISA_430
},
302 {"msp430c412", MSP_ISA_430
},
303 {"msp430c413", MSP_ISA_430
},
304 {"msp430e313", MSP_ISA_430
},
305 {"msp430e315", MSP_ISA_430
},
306 {"msp430e325", MSP_ISA_430
},
307 {"msp430e337", MSP_ISA_430
},
308 {"msp430f110", MSP_ISA_430
},
309 {"msp430f1101", MSP_ISA_430
},
310 {"msp430f1101a", MSP_ISA_430
},
311 {"msp430f1111", MSP_ISA_430
},
312 {"msp430f1111a", MSP_ISA_430
},
313 {"msp430f112", MSP_ISA_430
},
314 {"msp430f1121", MSP_ISA_430
},
315 {"msp430f1121a", MSP_ISA_430
},
316 {"msp430f1122", MSP_ISA_430
},
317 {"msp430f1132", MSP_ISA_430
},
318 {"msp430f122", MSP_ISA_430
},
319 {"msp430f1222", MSP_ISA_430
},
320 {"msp430f123", MSP_ISA_430
},
321 {"msp430f1232", MSP_ISA_430
},
322 {"msp430f133", MSP_ISA_430
},
323 {"msp430f135", MSP_ISA_430
},
324 {"msp430f147", MSP_ISA_430
},
325 {"msp430f1471", MSP_ISA_430
},
326 {"msp430f148", MSP_ISA_430
},
327 {"msp430f1481", MSP_ISA_430
},
328 {"msp430f149", MSP_ISA_430
},
329 {"msp430f1491", MSP_ISA_430
},
330 {"msp430f155", MSP_ISA_430
},
331 {"msp430f156", MSP_ISA_430
},
332 {"msp430f157", MSP_ISA_430
},
333 {"msp430f1610", MSP_ISA_430
},
334 {"msp430f1611", MSP_ISA_430
},
335 {"msp430f1612", MSP_ISA_430
},
336 {"msp430f167", MSP_ISA_430
},
337 {"msp430f168", MSP_ISA_430
},
338 {"msp430f169", MSP_ISA_430
},
339 {"msp430f2001", MSP_ISA_430
},
340 {"msp430f2002", MSP_ISA_430
},
341 {"msp430f2003", MSP_ISA_430
},
342 {"msp430f2011", MSP_ISA_430
},
343 {"msp430f2012", MSP_ISA_430
},
344 {"msp430f2013", MSP_ISA_430
},
345 {"msp430f2101", MSP_ISA_430
},
346 {"msp430f2111", MSP_ISA_430
},
347 {"msp430f2112", MSP_ISA_430
},
348 {"msp430f2121", MSP_ISA_430
},
349 {"msp430f2122", MSP_ISA_430
},
350 {"msp430f2131", MSP_ISA_430
},
351 {"msp430f2132", MSP_ISA_430
},
352 {"msp430f2232", MSP_ISA_430
},
353 {"msp430f2234", MSP_ISA_430
},
354 {"msp430f2252", MSP_ISA_430
},
355 {"msp430f2254", MSP_ISA_430
},
356 {"msp430f2272", MSP_ISA_430
},
357 {"msp430f2274", MSP_ISA_430
},
358 {"msp430f233", MSP_ISA_430
},
359 {"msp430f2330", MSP_ISA_430
},
360 {"msp430f235", MSP_ISA_430
},
361 {"msp430f2350", MSP_ISA_430
},
362 {"msp430f2370", MSP_ISA_430
},
363 {"msp430f2410", MSP_ISA_430
},
364 {"msp430f247", MSP_ISA_430
},
365 {"msp430f2471", MSP_ISA_430
},
366 {"msp430f248", MSP_ISA_430
},
367 {"msp430f2481", MSP_ISA_430
},
368 {"msp430f249", MSP_ISA_430
},
369 {"msp430f2491", MSP_ISA_430
},
370 {"msp430f412", MSP_ISA_430
},
371 {"msp430f413", MSP_ISA_430
},
372 {"msp430f4132", MSP_ISA_430
},
373 {"msp430f415", MSP_ISA_430
},
374 {"msp430f4152", MSP_ISA_430
},
375 {"msp430f417", MSP_ISA_430
},
376 {"msp430f423", MSP_ISA_430
},
377 {"msp430f423a", MSP_ISA_430
},
378 {"msp430f425", MSP_ISA_430
},
379 {"msp430f4250", MSP_ISA_430
},
380 {"msp430f425a", MSP_ISA_430
},
381 {"msp430f4260", MSP_ISA_430
},
382 {"msp430f427", MSP_ISA_430
},
383 {"msp430f4270", MSP_ISA_430
},
384 {"msp430f427a", MSP_ISA_430
},
385 {"msp430f435", MSP_ISA_430
},
386 {"msp430f4351", MSP_ISA_430
},
387 {"msp430f436", MSP_ISA_430
},
388 {"msp430f4361", MSP_ISA_430
},
389 {"msp430f437", MSP_ISA_430
},
390 {"msp430f4371", MSP_ISA_430
},
391 {"msp430f438", MSP_ISA_430
},
392 {"msp430f439", MSP_ISA_430
},
393 {"msp430f447", MSP_ISA_430
},
394 {"msp430f448", MSP_ISA_430
},
395 {"msp430f4481", MSP_ISA_430
},
396 {"msp430f449", MSP_ISA_430
},
397 {"msp430f4491", MSP_ISA_430
},
398 {"msp430f477", MSP_ISA_430
},
399 {"msp430f478", MSP_ISA_430
},
400 {"msp430f4783", MSP_ISA_430
},
401 {"msp430f4784", MSP_ISA_430
},
402 {"msp430f479", MSP_ISA_430
},
403 {"msp430f4793", MSP_ISA_430
},
404 {"msp430f4794", MSP_ISA_430
},
405 {"msp430fe423", MSP_ISA_430
},
406 {"msp430fe4232", MSP_ISA_430
},
407 {"msp430fe423a", MSP_ISA_430
},
408 {"msp430fe4242", MSP_ISA_430
},
409 {"msp430fe425", MSP_ISA_430
},
410 {"msp430fe4252", MSP_ISA_430
},
411 {"msp430fe425a", MSP_ISA_430
},
412 {"msp430fe427", MSP_ISA_430
},
413 {"msp430fe4272", MSP_ISA_430
},
414 {"msp430fe427a", MSP_ISA_430
},
415 {"msp430fg4250", MSP_ISA_430
},
416 {"msp430fg4260", MSP_ISA_430
},
417 {"msp430fg4270", MSP_ISA_430
},
418 {"msp430fg437", MSP_ISA_430
},
419 {"msp430fg438", MSP_ISA_430
},
420 {"msp430fg439", MSP_ISA_430
},
421 {"msp430fg477", MSP_ISA_430
},
422 {"msp430fg478", MSP_ISA_430
},
423 {"msp430fg479", MSP_ISA_430
},
424 {"msp430fw423", MSP_ISA_430
},
425 {"msp430fw425", MSP_ISA_430
},
426 {"msp430fw427", MSP_ISA_430
},
427 {"msp430fw428", MSP_ISA_430
},
428 {"msp430fw429", MSP_ISA_430
},
429 {"msp430g2001", MSP_ISA_430
},
430 {"msp430g2101", MSP_ISA_430
},
431 {"msp430g2102", MSP_ISA_430
},
432 {"msp430g2111", MSP_ISA_430
},
433 {"msp430g2112", MSP_ISA_430
},
434 {"msp430g2113", MSP_ISA_430
},
435 {"msp430g2121", MSP_ISA_430
},
436 {"msp430g2131", MSP_ISA_430
},
437 {"msp430g2132", MSP_ISA_430
},
438 {"msp430g2152", MSP_ISA_430
},
439 {"msp430g2153", MSP_ISA_430
},
440 {"msp430g2201", MSP_ISA_430
},
441 {"msp430g2202", MSP_ISA_430
},
442 {"msp430g2203", MSP_ISA_430
},
443 {"msp430g2210", MSP_ISA_430
},
444 {"msp430g2211", MSP_ISA_430
},
445 {"msp430g2212", MSP_ISA_430
},
446 {"msp430g2213", MSP_ISA_430
},
447 {"msp430g2221", MSP_ISA_430
},
448 {"msp430g2230", MSP_ISA_430
},
449 {"msp430g2231", MSP_ISA_430
},
450 {"msp430g2232", MSP_ISA_430
},
451 {"msp430g2233", MSP_ISA_430
},
452 {"msp430g2252", MSP_ISA_430
},
453 {"msp430g2253", MSP_ISA_430
},
454 {"msp430g2302", MSP_ISA_430
},
455 {"msp430g2303", MSP_ISA_430
},
456 {"msp430g2312", MSP_ISA_430
},
457 {"msp430g2313", MSP_ISA_430
},
458 {"msp430g2332", MSP_ISA_430
},
459 {"msp430g2333", MSP_ISA_430
},
460 {"msp430g2352", MSP_ISA_430
},
461 {"msp430g2353", MSP_ISA_430
},
462 {"msp430g2402", MSP_ISA_430
},
463 {"msp430g2403", MSP_ISA_430
},
464 {"msp430g2412", MSP_ISA_430
},
465 {"msp430g2413", MSP_ISA_430
},
466 {"msp430g2432", MSP_ISA_430
},
467 {"msp430g2433", MSP_ISA_430
},
468 {"msp430g2444", MSP_ISA_430
},
469 {"msp430g2452", MSP_ISA_430
},
470 {"msp430g2453", MSP_ISA_430
},
471 {"msp430g2513", MSP_ISA_430
},
472 {"msp430g2533", MSP_ISA_430
},
473 {"msp430g2544", MSP_ISA_430
},
474 {"msp430g2553", MSP_ISA_430
},
475 {"msp430g2744", MSP_ISA_430
},
476 {"msp430g2755", MSP_ISA_430
},
477 {"msp430g2855", MSP_ISA_430
},
478 {"msp430g2955", MSP_ISA_430
},
479 {"msp430l092", MSP_ISA_430
},
480 {"msp430p112", MSP_ISA_430
},
481 {"msp430p313", MSP_ISA_430
},
482 {"msp430p315", MSP_ISA_430
},
483 {"msp430p315s", MSP_ISA_430
},
484 {"msp430p325", MSP_ISA_430
},
485 {"msp430p337", MSP_ISA_430
},
486 {"msp430tch5e", MSP_ISA_430
},
488 {"msp430cg4616", MSP_ISA_430X
},
489 {"msp430cg4617", MSP_ISA_430X
},
490 {"msp430cg4618", MSP_ISA_430X
},
491 {"msp430cg4619", MSP_ISA_430X
},
492 {"msp430f2416", MSP_ISA_430X
},
493 {"msp430f2417", MSP_ISA_430X
},
494 {"msp430f2418", MSP_ISA_430X
},
495 {"msp430f2419", MSP_ISA_430X
},
496 {"msp430f2616", MSP_ISA_430X
},
497 {"msp430f2617", MSP_ISA_430X
},
498 {"msp430f2618", MSP_ISA_430X
},
499 {"msp430f2619", MSP_ISA_430X
},
500 {"msp430f47126", MSP_ISA_430X
},
501 {"msp430f47127", MSP_ISA_430X
},
502 {"msp430f47163", MSP_ISA_430X
},
503 {"msp430f47173", MSP_ISA_430X
},
504 {"msp430f47183", MSP_ISA_430X
},
505 {"msp430f47193", MSP_ISA_430X
},
506 {"msp430f47166", MSP_ISA_430X
},
507 {"msp430f47176", MSP_ISA_430X
},
508 {"msp430f47186", MSP_ISA_430X
},
509 {"msp430f47196", MSP_ISA_430X
},
510 {"msp430f47167", MSP_ISA_430X
},
511 {"msp430f47177", MSP_ISA_430X
},
512 {"msp430f47187", MSP_ISA_430X
},
513 {"msp430f47197", MSP_ISA_430X
},
514 {"msp430f46161", MSP_ISA_430X
},
515 {"msp430f46171", MSP_ISA_430X
},
516 {"msp430f46181", MSP_ISA_430X
},
517 {"msp430f46191", MSP_ISA_430X
},
518 {"msp430f4616", MSP_ISA_430X
},
519 {"msp430f4617", MSP_ISA_430X
},
520 {"msp430f4618", MSP_ISA_430X
},
521 {"msp430f4619", MSP_ISA_430X
},
522 {"msp430fg4616", MSP_ISA_430X
},
523 {"msp430fg4617", MSP_ISA_430X
},
524 {"msp430fg4618", MSP_ISA_430X
},
525 {"msp430fg4619", MSP_ISA_430X
},
527 {"msp430f5418", MSP_ISA_430Xv2
},
528 {"msp430f5419", MSP_ISA_430Xv2
},
529 {"msp430f5435", MSP_ISA_430Xv2
},
530 {"msp430f5436", MSP_ISA_430Xv2
},
531 {"msp430f5437", MSP_ISA_430Xv2
},
532 {"msp430f5438", MSP_ISA_430Xv2
},
533 {"msp430f5418a", MSP_ISA_430Xv2
},
534 {"msp430f5419a", MSP_ISA_430Xv2
},
535 {"msp430f5435a", MSP_ISA_430Xv2
},
536 {"msp430f5436a", MSP_ISA_430Xv2
},
537 {"msp430f5437a", MSP_ISA_430Xv2
},
538 {"msp430f5438a", MSP_ISA_430Xv2
},
539 {"msp430f5212", MSP_ISA_430Xv2
},
540 {"msp430f5213", MSP_ISA_430Xv2
},
541 {"msp430f5214", MSP_ISA_430Xv2
},
542 {"msp430f5217", MSP_ISA_430Xv2
},
543 {"msp430f5218", MSP_ISA_430Xv2
},
544 {"msp430f5219", MSP_ISA_430Xv2
},
545 {"msp430f5222", MSP_ISA_430Xv2
},
546 {"msp430f5223", MSP_ISA_430Xv2
},
547 {"msp430f5224", MSP_ISA_430Xv2
},
548 {"msp430f5227", MSP_ISA_430Xv2
},
549 {"msp430f5228", MSP_ISA_430Xv2
},
550 {"msp430f5229", MSP_ISA_430Xv2
},
551 {"msp430f5304", MSP_ISA_430Xv2
},
552 {"msp430f5308", MSP_ISA_430Xv2
},
553 {"msp430f5309", MSP_ISA_430Xv2
},
554 {"msp430f5310", MSP_ISA_430Xv2
},
555 {"msp430f5340", MSP_ISA_430Xv2
},
556 {"msp430f5341", MSP_ISA_430Xv2
},
557 {"msp430f5342", MSP_ISA_430Xv2
},
558 {"msp430f5324", MSP_ISA_430Xv2
},
559 {"msp430f5325", MSP_ISA_430Xv2
},
560 {"msp430f5326", MSP_ISA_430Xv2
},
561 {"msp430f5327", MSP_ISA_430Xv2
},
562 {"msp430f5328", MSP_ISA_430Xv2
},
563 {"msp430f5329", MSP_ISA_430Xv2
},
564 {"msp430f5500", MSP_ISA_430Xv2
},
565 {"msp430f5501", MSP_ISA_430Xv2
},
566 {"msp430f5502", MSP_ISA_430Xv2
},
567 {"msp430f5503", MSP_ISA_430Xv2
},
568 {"msp430f5504", MSP_ISA_430Xv2
},
569 {"msp430f5505", MSP_ISA_430Xv2
},
570 {"msp430f5506", MSP_ISA_430Xv2
},
571 {"msp430f5507", MSP_ISA_430Xv2
},
572 {"msp430f5508", MSP_ISA_430Xv2
},
573 {"msp430f5509", MSP_ISA_430Xv2
},
574 {"msp430f5510", MSP_ISA_430Xv2
},
575 {"msp430f5513", MSP_ISA_430Xv2
},
576 {"msp430f5514", MSP_ISA_430Xv2
},
577 {"msp430f5515", MSP_ISA_430Xv2
},
578 {"msp430f5517", MSP_ISA_430Xv2
},
579 {"msp430f5519", MSP_ISA_430Xv2
},
580 {"msp430f5521", MSP_ISA_430Xv2
},
581 {"msp430f5522", MSP_ISA_430Xv2
},
582 {"msp430f5524", MSP_ISA_430Xv2
},
583 {"msp430f5525", MSP_ISA_430Xv2
},
584 {"msp430f5526", MSP_ISA_430Xv2
},
585 {"msp430f5527", MSP_ISA_430Xv2
},
586 {"msp430f5528", MSP_ISA_430Xv2
},
587 {"msp430f5529", MSP_ISA_430Xv2
},
588 {"cc430f5133", MSP_ISA_430Xv2
},
589 {"cc430f5135", MSP_ISA_430Xv2
},
590 {"cc430f5137", MSP_ISA_430Xv2
},
591 {"cc430f6125", MSP_ISA_430Xv2
},
592 {"cc430f6126", MSP_ISA_430Xv2
},
593 {"cc430f6127", MSP_ISA_430Xv2
},
594 {"cc430f6135", MSP_ISA_430Xv2
},
595 {"cc430f6137", MSP_ISA_430Xv2
},
596 {"cc430f5123", MSP_ISA_430Xv2
},
597 {"cc430f5125", MSP_ISA_430Xv2
},
598 {"cc430f5143", MSP_ISA_430Xv2
},
599 {"cc430f5145", MSP_ISA_430Xv2
},
600 {"cc430f5147", MSP_ISA_430Xv2
},
601 {"cc430f6143", MSP_ISA_430Xv2
},
602 {"cc430f6145", MSP_ISA_430Xv2
},
603 {"cc430f6147", MSP_ISA_430Xv2
},
604 {"msp430f5333", MSP_ISA_430Xv2
},
605 {"msp430f5335", MSP_ISA_430Xv2
},
606 {"msp430f5336", MSP_ISA_430Xv2
},
607 {"msp430f5338", MSP_ISA_430Xv2
},
608 {"msp430f5630", MSP_ISA_430Xv2
},
609 {"msp430f5631", MSP_ISA_430Xv2
},
610 {"msp430f5632", MSP_ISA_430Xv2
},
611 {"msp430f5633", MSP_ISA_430Xv2
},
612 {"msp430f5634", MSP_ISA_430Xv2
},
613 {"msp430f5635", MSP_ISA_430Xv2
},
614 {"msp430f5636", MSP_ISA_430Xv2
},
615 {"msp430f5637", MSP_ISA_430Xv2
},
616 {"msp430f5638", MSP_ISA_430Xv2
},
617 {"msp430f6433", MSP_ISA_430Xv2
},
618 {"msp430f6435", MSP_ISA_430Xv2
},
619 {"msp430f6436", MSP_ISA_430Xv2
},
620 {"msp430f6438", MSP_ISA_430Xv2
},
621 {"msp430f6630", MSP_ISA_430Xv2
},
622 {"msp430f6631", MSP_ISA_430Xv2
},
623 {"msp430f6632", MSP_ISA_430Xv2
},
624 {"msp430f6633", MSP_ISA_430Xv2
},
625 {"msp430f6634", MSP_ISA_430Xv2
},
626 {"msp430f6635", MSP_ISA_430Xv2
},
627 {"msp430f6636", MSP_ISA_430Xv2
},
628 {"msp430f6637", MSP_ISA_430Xv2
},
629 {"msp430f6638", MSP_ISA_430Xv2
},
630 {"msp430f5358", MSP_ISA_430Xv2
},
631 {"msp430f5359", MSP_ISA_430Xv2
},
632 {"msp430f5658", MSP_ISA_430Xv2
},
633 {"msp430f5659", MSP_ISA_430Xv2
},
634 {"msp430f6458", MSP_ISA_430Xv2
},
635 {"msp430f6459", MSP_ISA_430Xv2
},
636 {"msp430f6658", MSP_ISA_430Xv2
},
637 {"msp430f6659", MSP_ISA_430Xv2
},
638 {"msp430f5131", MSP_ISA_430Xv2
},
639 {"msp430f5151", MSP_ISA_430Xv2
},
640 {"msp430f5171", MSP_ISA_430Xv2
},
641 {"msp430f5132", MSP_ISA_430Xv2
},
642 {"msp430f5152", MSP_ISA_430Xv2
},
643 {"msp430f5172", MSP_ISA_430Xv2
},
644 {"msp430f6720", MSP_ISA_430Xv2
},
645 {"msp430f6721", MSP_ISA_430Xv2
},
646 {"msp430f6723", MSP_ISA_430Xv2
},
647 {"msp430f6724", MSP_ISA_430Xv2
},
648 {"msp430f6725", MSP_ISA_430Xv2
},
649 {"msp430f6726", MSP_ISA_430Xv2
},
650 {"msp430f6730", MSP_ISA_430Xv2
},
651 {"msp430f6731", MSP_ISA_430Xv2
},
652 {"msp430f6733", MSP_ISA_430Xv2
},
653 {"msp430f6734", MSP_ISA_430Xv2
},
654 {"msp430f6735", MSP_ISA_430Xv2
},
655 {"msp430f6736", MSP_ISA_430Xv2
},
656 {"msp430f67451", MSP_ISA_430Xv2
},
657 {"msp430f67651", MSP_ISA_430Xv2
},
658 {"msp430f67751", MSP_ISA_430Xv2
},
659 {"msp430f67461", MSP_ISA_430Xv2
},
660 {"msp430f67661", MSP_ISA_430Xv2
},
661 {"msp430f67761", MSP_ISA_430Xv2
},
662 {"msp430f67471", MSP_ISA_430Xv2
},
663 {"msp430f67671", MSP_ISA_430Xv2
},
664 {"msp430f67771", MSP_ISA_430Xv2
},
665 {"msp430f67481", MSP_ISA_430Xv2
},
666 {"msp430f67681", MSP_ISA_430Xv2
},
667 {"msp430f67781", MSP_ISA_430Xv2
},
668 {"msp430f67491", MSP_ISA_430Xv2
},
669 {"msp430f67691", MSP_ISA_430Xv2
},
670 {"msp430f67791", MSP_ISA_430Xv2
},
671 {"msp430f6745", MSP_ISA_430Xv2
},
672 {"msp430f6765", MSP_ISA_430Xv2
},
673 {"msp430f6775", MSP_ISA_430Xv2
},
674 {"msp430f6746", MSP_ISA_430Xv2
},
675 {"msp430f6766", MSP_ISA_430Xv2
},
676 {"msp430f6776", MSP_ISA_430Xv2
},
677 {"msp430f6747", MSP_ISA_430Xv2
},
678 {"msp430f6767", MSP_ISA_430Xv2
},
679 {"msp430f6777", MSP_ISA_430Xv2
},
680 {"msp430f6748", MSP_ISA_430Xv2
},
681 {"msp430f6768", MSP_ISA_430Xv2
},
682 {"msp430f6778", MSP_ISA_430Xv2
},
683 {"msp430f6749", MSP_ISA_430Xv2
},
684 {"msp430f6769", MSP_ISA_430Xv2
},
685 {"msp430f6779", MSP_ISA_430Xv2
},
686 {"msp430fr5720", MSP_ISA_430Xv2
},
687 {"msp430fr5721", MSP_ISA_430Xv2
},
688 {"msp430fr5722", MSP_ISA_430Xv2
},
689 {"msp430fr5723", MSP_ISA_430Xv2
},
690 {"msp430fr5724", MSP_ISA_430Xv2
},
691 {"msp430fr5725", MSP_ISA_430Xv2
},
692 {"msp430fr5726", MSP_ISA_430Xv2
},
693 {"msp430fr5727", MSP_ISA_430Xv2
},
694 {"msp430fr5728", MSP_ISA_430Xv2
},
695 {"msp430fr5729", MSP_ISA_430Xv2
},
696 {"msp430fr5730", MSP_ISA_430Xv2
},
697 {"msp430fr5731", MSP_ISA_430Xv2
},
698 {"msp430fr5732", MSP_ISA_430Xv2
},
699 {"msp430fr5733", MSP_ISA_430Xv2
},
700 {"msp430fr5734", MSP_ISA_430Xv2
},
701 {"msp430fr5735", MSP_ISA_430Xv2
},
702 {"msp430fr5736", MSP_ISA_430Xv2
},
703 {"msp430fr5737", MSP_ISA_430Xv2
},
704 {"msp430fr5738", MSP_ISA_430Xv2
},
705 {"msp430fr5739", MSP_ISA_430Xv2
},
706 {"msp430bt5190", MSP_ISA_430Xv2
},
707 {"msp430fr5949", MSP_ISA_430Xv2
},
708 {"msp430fr5969", MSP_ISA_430Xv2
},
709 {"msp430sl5438a", MSP_ISA_430Xv2
},
712 {"msp430", MSP_ISA_430
},
713 {"msp430X", MSP_ISA_430X
},
714 {"msp430Xv2", MSP_ISA_430Xv2
},
719 static struct mcu_type_s default_mcu
= { "msp430x11", MSP_ISA_430
};
720 static struct mcu_type_s msp430x_mcu
= { "msp430x", MSP_ISA_430X
};
721 static struct mcu_type_s msp430xv2_mcu
= { "msp430xv2", MSP_ISA_430Xv2
};
723 static struct mcu_type_s
* msp430_mcu
= & default_mcu
;
725 static inline bfd_boolean
726 target_is_430x (void)
728 return msp430_mcu
->isa
>= MSP_ISA_430X
;
731 static inline bfd_boolean
732 target_is_430xv2 (void)
734 return msp430_mcu
->isa
== MSP_ISA_430Xv2
;
737 /* Generate a 16-bit relocation.
738 For the 430X we generate a relocation without linkwer range checking
739 if the value is being used in an extended (ie 20-bit) instruction.
740 For the 430 we generate a relocation without assembler range checking
741 if we are handling an immediate value or a byte-width instruction. */
742 #undef CHECK_RELOC_MSP430
743 #define CHECK_RELOC_MSP430 \
745 ? (extended_op ? BFD_RELOC_16 : BFD_RELOC_MSP430X_ABS16) \
746 : ((imm_op || byte_op) \
747 ? BFD_RELOC_MSP430_16_BYTE : BFD_RELOC_MSP430_16))
749 /* Generate a 16-bit pc-relative relocation.
750 For the 430X we generate a relocation without linkwer range checking.
751 For the 430 we generate a relocation without assembler range checking
752 if we are handling an immediate value or a byte-width instruction. */
753 #undef CHECK_RELOC_MSP430_PCREL
754 #define CHECK_RELOC_MSP430_PCREL \
756 ? BFD_RELOC_MSP430X_PCR16 \
757 : (imm_op || byte_op) \
758 ? BFD_RELOC_MSP430_16_PCREL_BYTE : BFD_RELOC_MSP430_16_PCREL)
760 /* Profiling capability:
761 It is a performance hit to use gcc's profiling approach for this tiny target.
762 Even more -- jtag hardware facility does not perform any profiling functions.
763 However we've got gdb's built-in simulator where we can do anything.
764 Therefore my suggestion is:
766 We define new section ".profiler" which holds all profiling information.
767 We define new pseudo operation .profiler which will instruct assembler to
768 add new profile entry to the object file. Profile should take place at the
773 .profiler flags,function_to_profile [, cycle_corrector, extra]
775 where 'flags' is a combination of the following chars:
778 i - function is in Init section
779 f - function is in Fini section
781 c - libC standard call
782 d - stack value Demand (saved at run-time in simulator)
783 I - Interrupt service routine
788 j - long Jump/ sjlj unwind
789 a - an Arbitrary code fragment
790 t - exTra parameter saved (constant value like frame size)
791 '""' optional: "sil" == sil
793 function_to_profile - function's address
794 cycle_corrector - a value which should be added to the cycle
795 counter, zero if omitted
796 extra - some extra parameter, zero if omitted.
799 ------------------------------
803 .LFrameOffset_fxx=0x08
804 .profiler "scdP", fxx ; function entry.
805 ; we also demand stack value to be displayed
810 .profiler "cdp",fxx,0, .LFrameOffset_fxx ; check stack value at this point
811 ; (this is a prologue end)
812 ; note, that spare var filled with the frame size
815 .profiler cdE,fxx ; check stack
820 .profiler xcde,fxx,3 ; exit adds 3 to the cycle counter
821 ret ; cause 'ret' insn takes 3 cycles
822 -------------------------------
824 This profiling approach does not produce any overhead and
826 So, even profiled code can be uploaded to the MCU. */
827 #define MSP430_PROFILER_FLAG_ENTRY 1 /* s */
828 #define MSP430_PROFILER_FLAG_EXIT 2 /* x */
829 #define MSP430_PROFILER_FLAG_INITSECT 4 /* i */
830 #define MSP430_PROFILER_FLAG_FINISECT 8 /* f */
831 #define MSP430_PROFILER_FLAG_LIBCALL 0x10 /* l */
832 #define MSP430_PROFILER_FLAG_STDCALL 0x20 /* c */
833 #define MSP430_PROFILER_FLAG_STACKDMD 0x40 /* d */
834 #define MSP430_PROFILER_FLAG_ISR 0x80 /* I */
835 #define MSP430_PROFILER_FLAG_PROLSTART 0x100 /* P */
836 #define MSP430_PROFILER_FLAG_PROLEND 0x200 /* p */
837 #define MSP430_PROFILER_FLAG_EPISTART 0x400 /* E */
838 #define MSP430_PROFILER_FLAG_EPIEND 0x800 /* e */
839 #define MSP430_PROFILER_FLAG_JUMP 0x1000 /* j */
840 #define MSP430_PROFILER_FLAG_FRAGMENT 0x2000 /* a */
841 #define MSP430_PROFILER_FLAG_EXTRA 0x4000 /* t */
842 #define MSP430_PROFILER_FLAG_notyet 0x8000 /* ? */
855 for (; x
; x
= x
>> 1)
862 /* Parse ordinary expression. */
865 parse_exp (char * s
, expressionS
* op
)
867 input_line_pointer
= s
;
869 if (op
->X_op
== O_absent
)
870 as_bad (_("missing operand"));
871 return input_line_pointer
;
875 /* Delete spaces from s: X ( r 1 2) => X(r12). */
878 del_spaces (char * s
)
886 while (ISSPACE (*m
) && *m
)
888 memmove (s
, m
, strlen (m
) + 1);
896 skip_space (char * s
)
903 /* Extract one word from FROM and copy it to TO. Delimiters are ",;\n" */
906 extract_operand (char * from
, char * to
, int limit
)
910 /* Drop leading whitespace. */
911 from
= skip_space (from
);
913 while (size
< limit
&& *from
)
915 *(to
+ size
) = *from
;
916 if (*from
== ',' || *from
== ';' || *from
== '\n')
931 msp430_profiler (int dummy ATTRIBUTE_UNUSED
)
948 s
= input_line_pointer
;
949 end
= input_line_pointer
;
951 while (*end
&& *end
!= '\n')
954 while (*s
&& *s
!= '\n')
965 as_bad (_(".profiler pseudo requires at least two operands."));
966 input_line_pointer
= end
;
970 input_line_pointer
= extract_operand (input_line_pointer
, flags
, 32);
979 p_flags
|= MSP430_PROFILER_FLAG_FRAGMENT
;
982 p_flags
|= MSP430_PROFILER_FLAG_JUMP
;
985 p_flags
|= MSP430_PROFILER_FLAG_PROLSTART
;
988 p_flags
|= MSP430_PROFILER_FLAG_PROLEND
;
991 p_flags
|= MSP430_PROFILER_FLAG_EPISTART
;
994 p_flags
|= MSP430_PROFILER_FLAG_EPIEND
;
997 p_flags
|= MSP430_PROFILER_FLAG_ENTRY
;
1000 p_flags
|= MSP430_PROFILER_FLAG_EXIT
;
1003 p_flags
|= MSP430_PROFILER_FLAG_INITSECT
;
1006 p_flags
|= MSP430_PROFILER_FLAG_FINISECT
;
1009 p_flags
|= MSP430_PROFILER_FLAG_LIBCALL
;
1012 p_flags
|= MSP430_PROFILER_FLAG_STDCALL
;
1015 p_flags
|= MSP430_PROFILER_FLAG_STACKDMD
;
1018 p_flags
|= MSP430_PROFILER_FLAG_ISR
;
1021 p_flags
|= MSP430_PROFILER_FLAG_EXTRA
;
1024 as_warn (_("unknown profiling flag - ignored."));
1031 && ( ! pow2value (p_flags
& ( MSP430_PROFILER_FLAG_ENTRY
1032 | MSP430_PROFILER_FLAG_EXIT
))
1033 || ! pow2value (p_flags
& ( MSP430_PROFILER_FLAG_PROLSTART
1034 | MSP430_PROFILER_FLAG_PROLEND
1035 | MSP430_PROFILER_FLAG_EPISTART
1036 | MSP430_PROFILER_FLAG_EPIEND
))
1037 || ! pow2value (p_flags
& ( MSP430_PROFILER_FLAG_INITSECT
1038 | MSP430_PROFILER_FLAG_FINISECT
))))
1040 as_bad (_("ambiguous flags combination - '.profiler' directive ignored."));
1041 input_line_pointer
= end
;
1045 /* Generate temp symbol which denotes current location. */
1046 if (now_seg
== absolute_section
) /* Paranoia ? */
1048 exp1
.X_op
= O_constant
;
1049 exp1
.X_add_number
= abs_section_offset
;
1050 as_warn (_("profiling in absolute section?"));
1054 exp1
.X_op
= O_symbol
;
1055 exp1
.X_add_symbol
= symbol_temp_new_now ();
1056 exp1
.X_add_number
= 0;
1059 /* Generate a symbol which holds flags value. */
1060 exp
.X_op
= O_constant
;
1061 exp
.X_add_number
= p_flags
;
1063 /* Save current section. */
1065 subseg
= now_subseg
;
1067 /* Now go to .profiler section. */
1068 obj_elf_change_section (".profiler", SHT_PROGBITS
, 0, 0, 0, 0, 0);
1071 emit_expr (& exp
, 2);
1073 /* Save label value. */
1074 emit_expr (& exp1
, 2);
1078 /* Now get profiling info. */
1079 halt
= extract_operand (input_line_pointer
, str
, 1024);
1080 /* Process like ".word xxx" directive. */
1081 parse_exp (str
, & exp
);
1082 emit_expr (& exp
, 2);
1083 input_line_pointer
= halt
;
1086 /* Fill the rest with zeros. */
1087 exp
.X_op
= O_constant
;
1088 exp
.X_add_number
= 0;
1090 emit_expr (& exp
, 2);
1092 /* Return to current section. */
1093 subseg_set (seg
, subseg
);
1097 extract_word (char * from
, char * to
, int limit
)
1102 /* Drop leading whitespace. */
1103 from
= skip_space (from
);
1106 /* Find the op code end. */
1107 for (op_end
= from
; *op_end
!= 0 && is_part_of_name (*op_end
);)
1109 to
[size
++] = *op_end
++;
1110 if (size
+ 1 >= limit
)
1118 #define OPTION_MMCU 'm'
1119 #define OPTION_RELAX 'Q'
1120 #define OPTION_POLYMORPHS 'P'
1121 #define OPTION_LARGE 'l'
1122 static bfd_boolean large_model
= FALSE
;
1123 #define OPTION_NO_INTR_NOPS 'N'
1124 static bfd_boolean gen_interrupt_nops
= TRUE
;
1125 #define OPTION_MCPU 'c'
1128 msp430_set_arch (int option
)
1130 char *str
= (char *) alloca (32); /* 32 for good measure. */
1132 input_line_pointer
= extract_word (input_line_pointer
, str
, 32);
1134 md_parse_option (option
, str
);
1135 bfd_set_arch_mach (stdoutput
, TARGET_ARCH
,
1136 target_is_430x () ? bfd_mach_msp430x
: bfd_mach_msp11
);
1140 show_mcu_list (FILE * stream
)
1144 fprintf (stream
, _("Known MCU names:\n"));
1146 for (i
= 0; mcu_types
[i
].name
; i
++)
1148 fprintf (stream
, "%14.14s", mcu_types
[i
].name
);
1150 fprintf (stream
, "\n");
1153 fprintf (stream
, "\n");
1157 md_parse_option (int c
, char * arg
)
1165 as_fatal (_("MCU option requires a name\n"));
1167 for (i
= 0; mcu_types
[i
].name
; ++i
)
1168 if (strcasecmp (mcu_types
[i
].name
, arg
) == 0)
1171 if (mcu_types
[i
].name
== NULL
)
1173 show_mcu_list (stderr
);
1174 as_fatal (_("unknown MCU: %s\n"), arg
);
1177 /* Allow switching to the same or a lesser architecture. */
1178 if (msp430_mcu
== &default_mcu
|| msp430_mcu
->isa
>= mcu_types
[i
].isa
)
1179 msp430_mcu
= mcu_types
+ i
;
1181 as_fatal (_("redefinition of mcu type '%s' to '%s'"),
1182 msp430_mcu
->name
, mcu_types
[i
].name
);
1186 if (strcmp (arg
, "430") == 0)
1187 msp430_mcu
= & default_mcu
;
1188 else if (strcmp (arg
, "430x") == 0
1189 || strcmp (arg
, "430X") == 0)
1190 msp430_mcu
= & msp430x_mcu
;
1191 else if (strcasecmp (arg
, "430xv2") == 0)
1192 msp430_mcu
= & msp430xv2_mcu
;
1194 as_fatal (_("unrecognised argument to -mcpu option '%s'"), arg
);
1199 msp430_enable_relax
= 1;
1202 case OPTION_POLYMORPHS
:
1203 msp430_enable_polys
= 1;
1210 case OPTION_NO_INTR_NOPS
:
1211 gen_interrupt_nops
= FALSE
;
1218 const pseudo_typeS md_pseudo_table
[] =
1220 {"arch", msp430_set_arch
, OPTION_MMCU
},
1221 {"cpu", msp430_set_arch
, OPTION_MCPU
},
1222 {"profiler", msp430_profiler
, 0},
1226 const char *md_shortopts
= "mm:,mP,mQ,ml,mN";
1228 struct option md_longopts
[] =
1230 {"mmcu", required_argument
, NULL
, OPTION_MMCU
},
1231 {"mcpu", required_argument
, NULL
, OPTION_MCPU
},
1232 {"mP", no_argument
, NULL
, OPTION_POLYMORPHS
},
1233 {"mQ", no_argument
, NULL
, OPTION_RELAX
},
1234 {"ml", no_argument
, NULL
, OPTION_LARGE
},
1235 {"mN", no_argument
, NULL
, OPTION_NO_INTR_NOPS
},
1236 {NULL
, no_argument
, NULL
, 0}
1239 size_t md_longopts_size
= sizeof (md_longopts
);
1242 md_show_usage (FILE * stream
)
1245 _("MSP430 options:\n"
1246 " -mmcu=<msp430-name> - select microcontroller type\n"
1247 " -mcpu={430|430x|430xv2} - select microcontroller architecture\n"));
1249 _(" -mQ - enable relaxation at assembly time. DANGEROUS!\n"
1250 " -mP - enable polymorph instructions\n"));
1252 _(" -ml - enable large code model\n"));
1254 _(" -mN - disable generation of NOP after changing interrupts\n"));
1256 show_mcu_list (stream
);
1260 md_undefined_symbol (char * name ATTRIBUTE_UNUSED
)
1266 extract_cmd (char * from
, char * to
, int limit
)
1270 while (*from
&& ! ISSPACE (*from
) && *from
!= '.' && limit
> size
)
1272 *(to
+ size
) = *from
;
1283 md_atof (int type
, char * litP
, int * sizeP
)
1285 return ieee_md_atof (type
, litP
, sizeP
, FALSE
);
1291 struct msp430_opcode_s
* opcode
;
1292 msp430_hash
= hash_new ();
1294 for (opcode
= msp430_opcodes
; opcode
->name
; opcode
++)
1295 hash_insert (msp430_hash
, opcode
->name
, (char *) opcode
);
1297 bfd_set_arch_mach (stdoutput
, TARGET_ARCH
,
1298 target_is_430x () ? bfd_mach_msp430x
: bfd_mach_msp11
);
1301 /* Returns the register number equivalent to the string T.
1302 Returns -1 if there is no such register.
1303 Skips a leading 'r' or 'R' character if there is one.
1304 Handles the register aliases PC and SP. */
1307 check_reg (char * t
)
1314 if (*t
== 'r' || *t
== 'R')
1317 if (strncasecmp (t
, "pc", 2) == 0)
1320 if (strncasecmp (t
, "sp", 2) == 0)
1323 if (strncasecmp (t
, "sr", 2) == 0)
1331 if (val
< 1 || val
> 15)
1338 msp430_srcoperand (struct msp430_operand_s
* op
,
1342 bfd_boolean allow_20bit_values
,
1343 bfd_boolean constants_allowed
)
1347 /* Check if an immediate #VALUE. The hash sign should be only at the beginning! */
1354 /* Check if there is:
1355 llo(x) - least significant 16 bits, x &= 0xffff
1356 lhi(x) - x = (x >> 16) & 0xffff,
1357 hlo(x) - x = (x >> 32) & 0xffff,
1358 hhi(x) - x = (x >> 48) & 0xffff
1359 The value _MUST_ be constant expression: #hlo(1231231231). */
1363 if (strncasecmp (h
, "#llo(", 5) == 0)
1368 else if (strncasecmp (h
, "#lhi(", 5) == 0)
1373 else if (strncasecmp (h
, "#hlo(", 5) == 0)
1378 else if (strncasecmp (h
, "#hhi(", 5) == 0)
1383 else if (strncasecmp (h
, "#lo(", 4) == 0)
1388 else if (strncasecmp (h
, "#hi(", 4) == 0)
1394 op
->reg
= 0; /* Reg PC. */
1396 op
->ol
= 1; /* Immediate will follow an instruction. */
1397 __tl
= h
+ 1 + rval
;
1400 parse_exp (__tl
, &(op
->exp
));
1401 if (op
->exp
.X_op
== O_constant
)
1403 int x
= op
->exp
.X_add_number
;
1408 op
->exp
.X_add_number
= x
;
1410 else if (vshift
== 1)
1412 x
= (x
>> 16) & 0xffff;
1413 op
->exp
.X_add_number
= x
;
1415 else if (vshift
> 1)
1418 op
->exp
.X_add_number
= -1;
1420 op
->exp
.X_add_number
= 0; /* Nothing left. */
1421 x
= op
->exp
.X_add_number
;
1424 if (allow_20bit_values
)
1426 if (op
->exp
.X_add_number
> 0xfffff || op
->exp
.X_add_number
< - (0x7ffff))
1428 as_bad (_("value 0x%x out of extended range."), x
);
1432 else if (op
->exp
.X_add_number
> 65535 || op
->exp
.X_add_number
< -32768)
1434 as_bad (_("value %d out of range. Use #lo() or #hi()"), x
);
1438 /* Now check constants. */
1439 /* Substitute register mode with a constant generator if applicable. */
1441 if (!allow_20bit_values
)
1442 x
= (short) x
; /* Extend sign. */
1444 if (! constants_allowed
)
1476 #ifdef PUSH_1X_WORKAROUND
1479 /* Remove warning as confusing.
1480 as_warn (_("Hardware push bug workaround")); */
1493 #ifdef PUSH_1X_WORKAROUND
1496 /* Remove warning as confusing.
1497 as_warn (_("Hardware push bug workaround")); */
1509 else if (op
->exp
.X_op
== O_symbol
)
1513 else if (op
->exp
.X_op
== O_big
)
1518 op
->exp
.X_op
= O_constant
;
1519 op
->exp
.X_add_number
= 0xffff & generic_bignum
[vshift
];
1520 x
= op
->exp
.X_add_number
;
1525 ("unknown expression in operand %s. use #llo() #lhi() #hlo() #hhi() "),
1573 /* Redundant (yet) check. */
1574 else if (op
->exp
.X_op
== O_register
)
1576 (_("Registers cannot be used within immediate expression [%s]"), l
);
1578 as_bad (_("unknown operand %s"), l
);
1583 /* Check if absolute &VALUE (assume that we can construct something like ((a&b)<<7 + 25). */
1588 op
->reg
= 2; /* reg 2 in absolute addr mode. */
1589 op
->am
= 1; /* mode As == 01 bin. */
1590 op
->ol
= 1; /* Immediate value followed by instruction. */
1592 parse_exp (__tl
, &(op
->exp
));
1594 if (op
->exp
.X_op
== O_constant
)
1596 int x
= op
->exp
.X_add_number
;
1598 if (allow_20bit_values
)
1600 if (x
> 0xfffff || x
< -(0x7ffff))
1602 as_bad (_("value 0x%x out of extended range."), x
);
1606 else if (x
> 65535 || x
< -32768)
1608 as_bad (_("value out of range: 0x%x"), x
);
1612 else if (op
->exp
.X_op
== O_symbol
)
1616 /* Redundant (yet) check. */
1617 if (op
->exp
.X_op
== O_register
)
1619 (_("Registers cannot be used within absolute expression [%s]"), l
);
1621 as_bad (_("unknown expression in operand %s"), l
);
1627 /* Check if indirect register mode @Rn / postincrement @Rn+. */
1631 char *m
= strchr (l
, '+');
1635 as_bad (_("unknown addressing mode %s"), l
);
1641 if ((op
->reg
= check_reg (t
)) == -1)
1643 as_bad (_("Bad register name %s"), t
);
1651 /* PC cannot be used in indirect addressing. */
1652 if (target_is_430xv2 () && op
->reg
== 0)
1654 as_bad (_("cannot use indirect addressing with the PC"));
1660 /* Check if register indexed X(Rn). */
1663 char *h
= strrchr (l
, '(');
1664 char *m
= strrchr (l
, ')');
1673 as_bad (_("')' required"));
1681 /* Extract a register. */
1682 if ((op
->reg
= check_reg (t
+ 1)) == -1)
1685 ("unknown operator %s. Did you mean X(Rn) or #[hl][hl][oi](CONST) ?"),
1692 as_bad (_("r2 should not be used in indexed addressing mode"));
1696 /* Extract constant. */
1700 parse_exp (__tl
, &(op
->exp
));
1701 if (op
->exp
.X_op
== O_constant
)
1703 int x
= op
->exp
.X_add_number
;
1705 if (allow_20bit_values
)
1707 if (x
> 0xfffff || x
< - (0x7ffff))
1709 as_bad (_("value 0x%x out of extended range."), x
);
1713 else if (x
> 65535 || x
< -32768)
1715 as_bad (_("value out of range: 0x%x"), x
);
1727 else if (op
->exp
.X_op
== O_symbol
)
1731 /* Redundant (yet) check. */
1732 if (op
->exp
.X_op
== O_register
)
1734 (_("Registers cannot be used as a prefix of indexed expression [%s]"), l
);
1736 as_bad (_("unknown expression in operand %s"), l
);
1744 /* Possibly register mode 'mov r1,r2'. */
1745 if ((op
->reg
= check_reg (l
)) != -1)
1753 /* Symbolic mode 'mov a, b' == 'mov x(pc), y(pc)'. */
1757 op
->reg
= 0; /* PC relative... be careful. */
1758 /* An expression starting with a minus sign is a constant, not an address. */
1759 op
->am
= (*l
== '-' ? 3 : 1);
1762 parse_exp (__tl
, &(op
->exp
));
1768 as_bad (_("unknown addressing mode for operand %s"), l
);
1774 msp430_dstoperand (struct msp430_operand_s
* op
,
1777 bfd_boolean allow_20bit_values
,
1778 bfd_boolean constants_allowed
)
1781 int ret
= msp430_srcoperand (op
, l
, bin
, & dummy
,
1795 parse_exp (__tl
, &(op
->exp
));
1797 if (op
->exp
.X_op
!= O_constant
|| op
->exp
.X_add_number
!= 0)
1799 as_bad (_("Internal bug. Try to use 0(r%d) instead of @r%d"),
1809 ("this addressing mode is not applicable for destination operand"));
1816 /* Attempt to encode a MOVA instruction with the given operands.
1817 Returns the length of the encoded instruction if successful
1818 or 0 upon failure. If the encoding fails, an error message
1819 will be returned if a pointer is provided. */
1822 try_encode_mova (bfd_boolean imm_op
,
1824 struct msp430_operand_s
* op1
,
1825 struct msp430_operand_s
* op2
,
1826 const char ** error_message_return
)
1832 /* Only a restricted subset of the normal MSP430 addressing modes
1833 are supported here, so check for the ones that are allowed. */
1836 if (op1
->mode
== OP_EXP
)
1838 if (op2
->mode
!= OP_REG
)
1840 if (error_message_return
!= NULL
)
1841 * error_message_return
= _("expected register as second argument of %s");
1847 /* MOVA #imm20, Rdst. */
1848 bin
|= 0x80 | op2
->reg
;
1849 frag
= frag_more (4);
1850 where
= frag
- frag_now
->fr_literal
;
1851 if (op1
->exp
.X_op
== O_constant
)
1853 bin
|= ((op1
->exp
.X_add_number
>> 16) & 0xf) << 8;
1854 bfd_putl16 ((bfd_vma
) bin
, frag
);
1855 bfd_putl16 (op1
->exp
.X_add_number
& 0xffff, frag
+ 2);
1859 bfd_putl16 ((bfd_vma
) bin
, frag
);
1860 fix_new_exp (frag_now
, where
, 4, &(op1
->exp
), FALSE
,
1861 BFD_RELOC_MSP430X_ABS20_ADR_SRC
);
1862 bfd_putl16 ((bfd_vma
) ZEROS
, frag
+ 2);
1867 else if (op1
->am
== 1)
1869 /* MOVA z16(Rsrc), Rdst. */
1870 bin
|= 0x30 | (op1
->reg
<< 8) | op2
->reg
;
1871 frag
= frag_more (4);
1872 where
= frag
- frag_now
->fr_literal
;
1873 bfd_putl16 ((bfd_vma
) bin
, frag
);
1874 if (op1
->exp
.X_op
== O_constant
)
1876 if (op1
->exp
.X_add_number
> 0xffff
1877 || op1
->exp
.X_add_number
< -(0x7fff))
1879 if (error_message_return
!= NULL
)
1880 * error_message_return
= _("index value too big for %s");
1883 bfd_putl16 (op1
->exp
.X_add_number
& 0xffff, frag
+ 2);
1887 bfd_putl16 ((bfd_vma
) ZEROS
, frag
+ 2);
1888 fix_new_exp (frag_now
, where
+ 2, 2, &(op1
->exp
), FALSE
,
1890 BFD_RELOC_MSP430X_PCR16
:
1891 BFD_RELOC_MSP430X_ABS16
);
1896 if (error_message_return
!= NULL
)
1897 * error_message_return
= _("unexpected addressing mode for %s");
1900 else if (op1
->am
== 0)
1902 /* MOVA Rsrc, ... */
1903 if (op2
->mode
== OP_REG
)
1905 bin
|= 0xc0 | (op1
->reg
<< 8) | op2
->reg
;
1906 frag
= frag_more (2);
1907 where
= frag
- frag_now
->fr_literal
;
1908 bfd_putl16 ((bfd_vma
) bin
, frag
);
1911 else if (op2
->am
== 1)
1915 /* MOVA Rsrc, &abs20. */
1916 bin
|= 0x60 | (op1
->reg
<< 8);
1917 frag
= frag_more (4);
1918 where
= frag
- frag_now
->fr_literal
;
1919 if (op2
->exp
.X_op
== O_constant
)
1921 bin
|= (op2
->exp
.X_add_number
>> 16) & 0xf;
1922 bfd_putl16 ((bfd_vma
) bin
, frag
);
1923 bfd_putl16 (op2
->exp
.X_add_number
& 0xffff, frag
+ 2);
1927 bfd_putl16 ((bfd_vma
) bin
, frag
);
1928 bfd_putl16 ((bfd_vma
) ZEROS
, frag
+ 2);
1929 fix_new_exp (frag_now
, where
, 4, &(op2
->exp
), FALSE
,
1930 BFD_RELOC_MSP430X_ABS20_ADR_DST
);
1935 /* MOVA Rsrc, z16(Rdst). */
1936 bin
|= 0x70 | (op1
->reg
<< 8) | op2
->reg
;
1937 frag
= frag_more (4);
1938 where
= frag
- frag_now
->fr_literal
;
1939 bfd_putl16 ((bfd_vma
) bin
, frag
);
1940 if (op2
->exp
.X_op
== O_constant
)
1942 if (op2
->exp
.X_add_number
> 0xffff
1943 || op2
->exp
.X_add_number
< -(0x7fff))
1945 if (error_message_return
!= NULL
)
1946 * error_message_return
= _("index value too big for %s");
1949 bfd_putl16 (op2
->exp
.X_add_number
& 0xffff, frag
+ 2);
1953 bfd_putl16 ((bfd_vma
) ZEROS
, frag
+ 2);
1954 fix_new_exp (frag_now
, where
+ 2, 2, &(op2
->exp
), FALSE
,
1956 BFD_RELOC_MSP430X_PCR16
:
1957 BFD_RELOC_MSP430X_ABS16
);
1962 if (error_message_return
!= NULL
)
1963 * error_message_return
= _("unexpected addressing mode for %s");
1968 /* imm_op == FALSE. */
1970 if (op1
->reg
== 2 && op1
->am
== 1 && op1
->mode
== OP_EXP
)
1972 /* MOVA &abs20, Rdst. */
1973 if (op2
->mode
!= OP_REG
)
1975 if (error_message_return
!= NULL
)
1976 * error_message_return
= _("expected register as second argument of %s");
1980 if (op2
->reg
== 2 || op2
->reg
== 3)
1982 if (error_message_return
!= NULL
)
1983 * error_message_return
= _("constant generator destination register found in %s");
1987 bin
|= 0x20 | op2
->reg
;
1988 frag
= frag_more (4);
1989 where
= frag
- frag_now
->fr_literal
;
1990 if (op1
->exp
.X_op
== O_constant
)
1992 bin
|= ((op1
->exp
.X_add_number
>> 16) & 0xf) << 8;
1993 bfd_putl16 ((bfd_vma
) bin
, frag
);
1994 bfd_putl16 (op1
->exp
.X_add_number
& 0xffff, frag
+ 2);
1998 bfd_putl16 ((bfd_vma
) bin
, frag
);
1999 bfd_putl16 ((bfd_vma
) ZEROS
, frag
+ 2);
2000 fix_new_exp (frag_now
, where
, 4, &(op1
->exp
), FALSE
,
2001 BFD_RELOC_MSP430X_ABS20_ADR_SRC
);
2005 else if (op1
->mode
== OP_REG
)
2009 /* MOVA @Rsrc+, Rdst. */
2010 if (op2
->mode
!= OP_REG
)
2012 if (error_message_return
!= NULL
)
2013 * error_message_return
= _("expected register as second argument of %s");
2017 if (op2
->reg
== 2 || op2
->reg
== 3)
2019 if (error_message_return
!= NULL
)
2020 * error_message_return
= _("constant generator destination register found in %s");
2024 if (op1
->reg
== 2 || op1
->reg
== 3)
2026 if (error_message_return
!= NULL
)
2027 * error_message_return
= _("constant generator source register found in %s");
2031 bin
|= 0x10 | (op1
->reg
<< 8) | op2
->reg
;
2032 frag
= frag_more (2);
2033 where
= frag
- frag_now
->fr_literal
;
2034 bfd_putl16 ((bfd_vma
) bin
, frag
);
2037 else if (op1
->am
== 2)
2039 /* MOVA @Rsrc,Rdst */
2040 if (op2
->mode
!= OP_REG
)
2042 if (error_message_return
!= NULL
)
2043 * error_message_return
= _("expected register as second argument of %s");
2047 if (op2
->reg
== 2 || op2
->reg
== 3)
2049 if (error_message_return
!= NULL
)
2050 * error_message_return
= _("constant generator destination register found in %s");
2054 if (op1
->reg
== 2 || op1
->reg
== 3)
2056 if (error_message_return
!= NULL
)
2057 * error_message_return
= _("constant generator source register found in %s");
2061 bin
|= (op1
->reg
<< 8) | op2
->reg
;
2062 frag
= frag_more (2);
2063 where
= frag
- frag_now
->fr_literal
;
2064 bfd_putl16 ((bfd_vma
) bin
, frag
);
2069 if (error_message_return
!= NULL
)
2070 * error_message_return
= _("unexpected addressing mode for %s");
2075 #define is_opcode(NAME) (strcmp (opcode->name, NAME) == 0)
2077 /* Parse instruction operands.
2078 Return binary opcode. */
2081 msp430_operands (struct msp430_opcode_s
* opcode
, char * line
)
2083 int bin
= opcode
->bin_opcode
; /* Opcode mask. */
2084 int insn_length
= 0;
2085 char l1
[MAX_OP_LEN
], l2
[MAX_OP_LEN
];
2088 struct msp430_operand_s op1
, op2
;
2090 static short ZEROS
= 0;
2091 int byte_op
, imm_op
;
2094 int extended
= 0x1800;
2095 bfd_boolean extended_op
= FALSE
;
2096 bfd_boolean addr_op
;
2097 const char * error_message
;
2098 static signed int repeat_count
= 0;
2099 bfd_boolean fix_emitted
;
2101 /* Opcode is the one from opcodes table
2102 line contains something like
2107 /* Check if byte or word operation. */
2108 if (*line
== '.' && TOLOWER (*(line
+ 1)) == 'b')
2110 bin
|= BYTE_OPERATION
;
2116 /* "Address" ops work on 20-bit values. */
2117 if (*line
== '.' && TOLOWER (*(line
+ 1)) == 'a')
2120 bin
|= BYTE_OPERATION
;
2125 /* skip .[aAbwBW]. */
2126 while (! ISSPACE (*line
) && *line
)
2129 if (opcode
->fmt
!= -1
2130 && opcode
->insn_opnumb
2131 && (!*line
|| *line
== '\n'))
2133 as_bad (_("instruction %s requires %d operand(s)"),
2134 opcode
->name
, opcode
->insn_opnumb
);
2138 memset (l1
, 0, sizeof (l1
));
2139 memset (l2
, 0, sizeof (l2
));
2140 memset (&op1
, 0, sizeof (op1
));
2141 memset (&op2
, 0, sizeof (op2
));
2145 if ((fmt
= opcode
->fmt
) < 0)
2147 if (! target_is_430x ())
2149 as_bad (_("instruction %s requires MSP430X mcu"),
2160 /* If requested set the extended instruction repeat count. */
2163 if (repeat_count
> 0)
2164 extended
|= (repeat_count
- 1);
2166 extended
|= (1 << 7) | (- repeat_count
);
2169 as_bad (_("unable to repeat %s insn"), opcode
->name
);
2176 case 0: /* Emulated. */
2177 switch (opcode
->insn_opnumb
)
2180 /* Set/clear bits instructions. */
2184 extended
|= BYTE_OPERATION
;
2186 /* Emit the extension word. */
2188 frag
= frag_more (insn_length
);
2189 bfd_putl16 (extended
, frag
);
2193 frag
= frag_more (insn_length
);
2194 bfd_putl16 ((bfd_vma
) bin
, frag
);
2196 if (gen_interrupt_nops
2197 && target_is_430xv2 ()
2198 && (is_opcode ("eint") || is_opcode ("dint")))
2200 /* Emit a NOP following interrupt enable/disable.
2201 See 1.3.4.1 of the MSP430x5xx User Guide. */
2203 frag
= frag_more (2);
2204 bfd_putl16 ((bfd_vma
) 0x4303 /* NOP */, frag
);
2206 dwarf2_emit_insn (insn_length
);
2210 /* Something which works with destination operand. */
2211 line
= extract_operand (line
, l1
, sizeof (l1
));
2212 res
= msp430_dstoperand (&op1
, l1
, opcode
->bin_opcode
, extended_op
, TRUE
);
2216 /* Compute the entire instruction length, in bytes. */
2217 insn_length
= (extended_op
? 2 : 0) + 2 + (op1
.ol
* 2);
2218 frag
= frag_more (insn_length
);
2219 where
= frag
- frag_now
->fr_literal
;
2224 extended
|= BYTE_OPERATION
;
2226 if (op1
.ol
!= 0 && ((extended
& 0xf) != 0))
2228 as_bad (_("repeat instruction used with non-register mode instruction"));
2232 if (op1
.mode
== OP_EXP
)
2234 if (op1
.exp
.X_op
== O_constant
)
2235 extended
|= ((op1
.exp
.X_add_number
>> 16) & 0xf) << 7;
2237 else if (op1
.reg
|| (op1
.reg
== 0 && op1
.am
== 3)) /* Not PC relative. */
2238 fix_new_exp (frag_now
, where
, 6, &(op1
.exp
), FALSE
,
2239 BFD_RELOC_MSP430X_ABS20_EXT_SRC
);
2241 fix_new_exp (frag_now
, where
, 6, &(op1
.exp
), FALSE
,
2242 BFD_RELOC_MSP430X_PCR20_EXT_SRC
);
2245 /* Emit the extension word. */
2246 bfd_putl16 (extended
, frag
);
2251 bin
|= (op1
.reg
| (op1
.am
<< 7));
2252 bfd_putl16 ((bfd_vma
) bin
, frag
);
2256 if (op1
.mode
== OP_EXP
)
2258 if (op1
.exp
.X_op
== O_constant
)
2260 bfd_putl16 (op1
.exp
.X_add_number
& 0xffff, frag
);
2264 bfd_putl16 ((bfd_vma
) ZEROS
, frag
);
2269 fix_new_exp (frag_now
, where
, 2,
2270 &(op1
.exp
), FALSE
, CHECK_RELOC_MSP430
);
2272 fix_new_exp (frag_now
, where
, 2,
2273 &(op1
.exp
), TRUE
, CHECK_RELOC_MSP430_PCREL
);
2278 if (gen_interrupt_nops
2279 && target_is_430xv2 ()
2280 && is_opcode ("clr")
2281 && bin
== 0x4302 /* CLR R2*/)
2283 /* Emit a NOP following interrupt enable/disable.
2284 See 1.3.4.1 of the MSP430x5xx User Guide. */
2286 frag
= frag_more (2);
2287 bfd_putl16 ((bfd_vma
) 0x4303 /* NOP */, frag
);
2290 dwarf2_emit_insn (insn_length
);
2294 /* Shift instruction. */
2295 line
= extract_operand (line
, l1
, sizeof (l1
));
2296 strncpy (l2
, l1
, sizeof (l2
));
2297 l2
[sizeof (l2
) - 1] = '\0';
2298 res
= msp430_srcoperand (&op1
, l1
, opcode
->bin_opcode
, &imm_op
, extended_op
, TRUE
);
2299 res
+= msp430_dstoperand (&op2
, l2
, opcode
->bin_opcode
, extended_op
, TRUE
);
2302 break; /* An error occurred. All warnings were done before. */
2304 insn_length
= (extended_op
? 2 : 0) + 2 + (op1
.ol
* 2) + (op2
.ol
* 2);
2305 frag
= frag_more (insn_length
);
2306 where
= frag
- frag_now
->fr_literal
;
2308 if (target_is_430xv2 ()
2309 && op1
.mode
== OP_REG
2311 && (is_opcode ("rlax")
2312 || is_opcode ("rlcx")
2313 || is_opcode ("rla")
2314 || is_opcode ("rlc")))
2316 as_bad (_("%s: attempt to rotate the PC register"), opcode
->name
);
2323 extended
|= BYTE_OPERATION
;
2325 if ((op1
.ol
!= 0 || op2
.ol
!= 0) && ((extended
& 0xf) != 0))
2327 as_bad (_("repeat instruction used with non-register mode instruction"));
2331 if (op1
.mode
== OP_EXP
)
2333 if (op1
.exp
.X_op
== O_constant
)
2334 extended
|= ((op1
.exp
.X_add_number
>> 16) & 0xf) << 7;
2336 else if (op1
.reg
|| (op1
.reg
== 0 && op1
.am
== 3)) /* Not PC relative. */
2337 fix_new_exp (frag_now
, where
, 6, &(op1
.exp
), FALSE
,
2338 BFD_RELOC_MSP430X_ABS20_EXT_SRC
);
2340 fix_new_exp (frag_now
, where
, 6, &(op1
.exp
), FALSE
,
2341 BFD_RELOC_MSP430X_PCR20_EXT_SRC
);
2344 if (op2
.mode
== OP_EXP
)
2346 if (op2
.exp
.X_op
== O_constant
)
2347 extended
|= (op2
.exp
.X_add_number
>> 16) & 0xf;
2349 else if (op1
.mode
== OP_EXP
)
2350 fix_new_exp (frag_now
, where
, 8, &(op2
.exp
), FALSE
,
2351 op2
.reg
? BFD_RELOC_MSP430X_ABS20_EXT_ODST
2352 : BFD_RELOC_MSP430X_PCR20_EXT_ODST
);
2354 fix_new_exp (frag_now
, where
, 6, &(op2
.exp
), FALSE
,
2355 op2
.reg
? BFD_RELOC_MSP430X_ABS20_EXT_DST
2356 : BFD_RELOC_MSP430X_PCR20_EXT_DST
);
2359 /* Emit the extension word. */
2360 bfd_putl16 (extended
, frag
);
2365 bin
|= (op2
.reg
| (op1
.reg
<< 8) | (op1
.am
<< 4) | (op2
.am
<< 7));
2366 bfd_putl16 ((bfd_vma
) bin
, frag
);
2370 if (op1
.mode
== OP_EXP
)
2372 if (op1
.exp
.X_op
== O_constant
)
2374 bfd_putl16 (op1
.exp
.X_add_number
& 0xffff, frag
);
2378 bfd_putl16 ((bfd_vma
) ZEROS
, frag
);
2382 if (op1
.reg
|| (op1
.reg
== 0 && op1
.am
== 3)) /* Not PC relative. */
2383 fix_new_exp (frag_now
, where
, 2,
2384 &(op1
.exp
), FALSE
, CHECK_RELOC_MSP430
);
2386 fix_new_exp (frag_now
, where
, 2,
2387 &(op1
.exp
), TRUE
, CHECK_RELOC_MSP430_PCREL
);
2394 if (op2
.mode
== OP_EXP
)
2396 if (op2
.exp
.X_op
== O_constant
)
2398 bfd_putl16 (op2
.exp
.X_add_number
& 0xffff, frag
);
2402 bfd_putl16 ((bfd_vma
) ZEROS
, frag
);
2406 if (op2
.reg
) /* Not PC relative. */
2407 fix_new_exp (frag_now
, where
, 2,
2408 &(op2
.exp
), FALSE
, CHECK_RELOC_MSP430
);
2410 fix_new_exp (frag_now
, where
, 2,
2411 &(op2
.exp
), TRUE
, CHECK_RELOC_MSP430_PCREL
);
2416 dwarf2_emit_insn (insn_length
);
2420 /* Branch instruction => mov dst, r0. */
2423 as_bad ("Internal error: state 0/3 not coded for extended instructions");
2427 line
= extract_operand (line
, l1
, sizeof (l1
));
2428 res
= msp430_srcoperand (&op1
, l1
, opcode
->bin_opcode
, &imm_op
, extended_op
, FALSE
);
2434 bin
|= ((op1
.reg
<< 8) | (op1
.am
<< 4));
2435 op_length
= 2 + 2 * op1
.ol
;
2436 frag
= frag_more (op_length
);
2437 where
= frag
- frag_now
->fr_literal
;
2438 bfd_putl16 ((bfd_vma
) bin
, frag
);
2440 if (op1
.mode
== OP_EXP
)
2442 if (op1
.exp
.X_op
== O_constant
)
2444 bfd_putl16 (op1
.exp
.X_add_number
& 0xffff, frag
+ 2);
2450 bfd_putl16 ((bfd_vma
) ZEROS
, frag
+ 2);
2452 if (op1
.reg
|| (op1
.reg
== 0 && op1
.am
== 3))
2453 fix_new_exp (frag_now
, where
, 2,
2454 &(op1
.exp
), FALSE
, CHECK_RELOC_MSP430
);
2456 fix_new_exp (frag_now
, where
, 2,
2457 &(op1
.exp
), TRUE
, CHECK_RELOC_MSP430_PCREL
);
2461 dwarf2_emit_insn (insn_length
+ op_length
);
2465 /* CALLA instructions. */
2466 fix_emitted
= FALSE
;
2468 line
= extract_operand (line
, l1
, sizeof (l1
));
2471 res
= msp430_srcoperand (&op1
, l1
, opcode
->bin_opcode
, &imm_op
,
2472 extended_op
, FALSE
);
2478 op_length
= 2 + 2 * op1
.ol
;
2479 frag
= frag_more (op_length
);
2480 where
= frag
- frag_now
->fr_literal
;
2488 fix_new_exp (frag_now
, where
, 4, &(op1
.exp
), FALSE
,
2489 BFD_RELOC_MSP430X_ABS20_ADR_DST
);
2492 else if (op1
.am
== 1)
2498 fix_new_exp (frag_now
, where
, 4, &(op1
.exp
), FALSE
,
2499 BFD_RELOC_MSP430X_PCR20_CALL
);
2503 bin
|= 0x50 | op1
.reg
;
2505 else if (op1
.am
== 0)
2506 bin
|= 0x40 | op1
.reg
;
2508 else if (op1
.am
== 1)
2512 fix_new_exp (frag_now
, where
, 4, &(op1
.exp
), FALSE
,
2513 BFD_RELOC_MSP430X_ABS20_ADR_DST
);
2516 else if (op1
.am
== 2)
2517 bin
|= 0x60 | op1
.reg
;
2518 else if (op1
.am
== 3)
2519 bin
|= 0x70 | op1
.reg
;
2521 bfd_putl16 ((bfd_vma
) bin
, frag
);
2523 if (op1
.mode
== OP_EXP
)
2527 as_bad ("Internal error: unexpected CALLA instruction length: %d\n", op1
.ol
);
2531 bfd_putl16 ((bfd_vma
) ZEROS
, frag
+ 2);
2534 fix_new_exp (frag_now
, where
+ 2, 2,
2535 &(op1
.exp
), FALSE
, BFD_RELOC_16
);
2538 dwarf2_emit_insn (insn_length
+ op_length
);
2546 /* [POP|PUSH]M[.A] #N, Rd */
2547 line
= extract_operand (line
, l1
, sizeof (l1
));
2548 line
= extract_operand (line
, l2
, sizeof (l2
));
2552 as_bad (_("expected #n as first argument of %s"), opcode
->name
);
2555 parse_exp (l1
+ 1, &(op1
.exp
));
2556 if (op1
.exp
.X_op
!= O_constant
)
2558 as_bad (_("expected constant expression for first argument of %s"),
2563 if ((reg
= check_reg (l2
)) == -1)
2565 as_bad (_("expected register as second argument of %s"),
2571 frag
= frag_more (op_length
);
2572 where
= frag
- frag_now
->fr_literal
;
2573 bin
= opcode
->bin_opcode
;
2576 n
= op1
.exp
.X_add_number
;
2577 bin
|= (n
- 1) << 4;
2578 if (is_opcode ("pushm"))
2582 if (reg
- n
+ 1 < 0)
2584 as_bad (_("Too many registers popped"));
2588 /* CPU21 parts cannot use POPM to restore the SR register. */
2589 if (target_is_430xv2 ()
2590 && (reg
- n
+ 1 < 3)
2592 && is_opcode ("popm"))
2594 as_bad (_("Cannot use POPM to restore the SR register"));
2598 bin
|= (reg
- n
+ 1);
2601 bfd_putl16 ((bfd_vma
) bin
, frag
);
2602 dwarf2_emit_insn (op_length
);
2611 /* Bit rotation instructions. RRCM, RRAM, RRUM, RLAM. */
2612 if (extended
& 0xff)
2614 as_bad (_("repeat count cannot be used with %s"), opcode
->name
);
2618 line
= extract_operand (line
, l1
, sizeof (l1
));
2619 line
= extract_operand (line
, l2
, sizeof (l2
));
2623 as_bad (_("expected #n as first argument of %s"), opcode
->name
);
2626 parse_exp (l1
+ 1, &(op1
.exp
));
2627 if (op1
.exp
.X_op
!= O_constant
)
2629 as_bad (_("expected constant expression for first argument of %s"),
2633 n
= op1
.exp
.X_add_number
;
2636 as_bad (_("expected first argument of %s to be in the range 1-4"),
2641 if ((reg
= check_reg (l2
)) == -1)
2643 as_bad (_("expected register as second argument of %s"),
2648 if (target_is_430xv2 () && reg
== 0)
2650 as_bad (_("%s: attempt to rotate the PC register"), opcode
->name
);
2655 frag
= frag_more (op_length
);
2656 where
= frag
- frag_now
->fr_literal
;
2658 bin
= opcode
->bin_opcode
;
2661 bin
|= (n
- 1) << 10;
2664 bfd_putl16 ((bfd_vma
) bin
, frag
);
2665 dwarf2_emit_insn (op_length
);
2673 /* RRUX: Synthetic unsigned right shift of a register by one bit. */
2674 if (extended
& 0xff)
2676 as_bad (_("repeat count cannot be used with %s"), opcode
->name
);
2680 line
= extract_operand (line
, l1
, sizeof (l1
));
2681 if ((reg
= check_reg (l1
)) == -1)
2683 as_bad (_("expected register as argument of %s"),
2688 if (target_is_430xv2 () && reg
== 0)
2690 as_bad (_("%s: attempt to rotate the PC register"), opcode
->name
);
2696 /* Tricky - there is no single instruction that will do this.
2697 Encode as: RRA.B rN { BIC.B #0x80, rN */
2699 frag
= frag_more (op_length
);
2700 where
= frag
- frag_now
->fr_literal
;
2702 bfd_putl16 ((bfd_vma
) bin
, frag
);
2703 dwarf2_emit_insn (2);
2705 bfd_putl16 ((bfd_vma
) bin
, frag
+ 2);
2707 bfd_putl16 ((bfd_vma
) bin
, frag
+ 4);
2708 dwarf2_emit_insn (4);
2712 /* Encode as RRUM[.A] rN. */
2713 bin
= opcode
->bin_opcode
;
2718 frag
= frag_more (op_length
);
2719 where
= frag
- frag_now
->fr_literal
;
2720 bfd_putl16 ((bfd_vma
) bin
, frag
);
2721 dwarf2_emit_insn (op_length
);
2728 bfd_boolean need_reloc
= FALSE
;
2732 /* ADDA, CMPA and SUBA address instructions. */
2733 if (extended
& 0xff)
2735 as_bad (_("repeat count cannot be used with %s"), opcode
->name
);
2739 line
= extract_operand (line
, l1
, sizeof (l1
));
2740 line
= extract_operand (line
, l2
, sizeof (l2
));
2742 bin
= opcode
->bin_opcode
;
2746 parse_exp (l1
+ 1, &(op1
.exp
));
2748 if (op1
.exp
.X_op
== O_constant
)
2750 n
= op1
.exp
.X_add_number
;
2751 if (n
> 0xfffff || n
< - (0x7ffff))
2753 as_bad (_("expected value of first argument of %s to fit into 20-bits"),
2758 bin
|= ((n
>> 16) & 0xf) << 8;
2770 if ((n
= check_reg (l1
)) == -1)
2772 as_bad (_("expected register name or constant as first argument of %s"),
2777 bin
|= (n
<< 8) | (1 << 6);
2781 if ((reg
= check_reg (l2
)) == -1)
2783 as_bad (_("expected register as second argument of %s"),
2788 frag
= frag_more (op_length
);
2789 where
= frag
- frag_now
->fr_literal
;
2792 fix_new_exp (frag_now
, where
, 4, &(op1
.exp
), FALSE
,
2793 BFD_RELOC_MSP430X_ABS20_ADR_SRC
);
2795 bfd_putl16 ((bfd_vma
) bin
, frag
);
2797 bfd_putl16 ((bfd_vma
) (n
& 0xffff), frag
+ 2);
2798 dwarf2_emit_insn (op_length
);
2802 case 9: /* MOVA, BRA, RETA. */
2804 bin
= opcode
->bin_opcode
;
2806 if (is_opcode ("reta"))
2808 /* The RETA instruction does not take any arguments.
2809 The implicit first argument is @SP+.
2810 The implicit second argument is PC. */
2820 line
= extract_operand (line
, l1
, sizeof (l1
));
2821 res
= msp430_srcoperand (&op1
, l1
, opcode
->bin_opcode
,
2822 &imm_op
, extended_op
, FALSE
);
2824 if (is_opcode ("bra"))
2826 /* This is the BRA synthetic instruction.
2827 The second argument is always PC. */
2833 line
= extract_operand (line
, l2
, sizeof (l2
));
2834 res
+= msp430_dstoperand (&op2
, l2
, opcode
->bin_opcode
,
2839 break; /* Error occurred. All warnings were done before. */
2842 /* Only a restricted subset of the normal MSP430 addressing modes
2843 are supported here, so check for the ones that are allowed. */
2844 if ((op_length
= try_encode_mova (imm_op
, bin
, & op1
, & op2
,
2845 & error_message
)) == 0)
2847 as_bad (error_message
, opcode
->name
);
2850 dwarf2_emit_insn (op_length
);
2854 line
= extract_operand (line
, l1
, sizeof l1
);
2855 /* The RPT instruction only accepted immediates and registers. */
2858 parse_exp (l1
+ 1, &(op1
.exp
));
2859 if (op1
.exp
.X_op
!= O_constant
)
2861 as_bad (_("expected constant value as argument to RPT"));
2864 if (op1
.exp
.X_add_number
< 1
2865 || op1
.exp
.X_add_number
> (1 << 4))
2867 as_bad (_("expected constant in the range 2..16"));
2871 /* We silently accept and ignore a repeat count of 1. */
2872 if (op1
.exp
.X_add_number
> 1)
2873 repeat_count
= op1
.exp
.X_add_number
;
2879 if ((reg
= check_reg (l1
)) != -1)
2882 as_warn (_("PC used as an argument to RPT"));
2884 repeat_count
= - reg
;
2888 as_bad (_("expected constant or register name as argument to RPT insn"));
2895 as_bad (_("Illegal emulated instruction "));
2900 case 1: /* Format 1, double operand. */
2901 line
= extract_operand (line
, l1
, sizeof (l1
));
2902 line
= extract_operand (line
, l2
, sizeof (l2
));
2903 res
= msp430_srcoperand (&op1
, l1
, opcode
->bin_opcode
, &imm_op
, extended_op
, TRUE
);
2904 res
+= msp430_dstoperand (&op2
, l2
, opcode
->bin_opcode
, extended_op
, TRUE
);
2907 break; /* Error occurred. All warnings were done before. */
2910 && is_opcode ("movx")
2912 && msp430_enable_relax
)
2914 /* This is the MOVX.A instruction. See if we can convert
2915 it into the MOVA instruction instead. This saves 2 bytes. */
2916 if ((op_length
= try_encode_mova (imm_op
, 0x0000, & op1
, & op2
,
2919 dwarf2_emit_insn (op_length
);
2924 /* Compute the entire length of the instruction in bytes. */
2926 (extended_op
? 2 : 0) /* The extension word. */
2927 + 2 /* The opcode */
2928 + (2 * op1
.ol
) /* The first operand. */
2929 + (2 * op2
.ol
); /* The second operand. */
2931 frag
= frag_more (insn_length
);
2932 where
= frag
- frag_now
->fr_literal
;
2937 extended
|= BYTE_OPERATION
;
2939 if ((op1
.ol
!= 0 || op2
.ol
!= 0) && ((extended
& 0xf) != 0))
2941 as_bad (_("repeat instruction used with non-register mode instruction"));
2945 /* If necessary, emit a reloc to update the extension word. */
2946 if (op1
.mode
== OP_EXP
)
2948 if (op1
.exp
.X_op
== O_constant
)
2949 extended
|= ((op1
.exp
.X_add_number
>> 16) & 0xf) << 7;
2951 else if (op1
.reg
|| (op1
.reg
== 0 && op1
.am
== 3)) /* Not PC relative. */
2952 fix_new_exp (frag_now
, where
, 6, &(op1
.exp
), FALSE
,
2953 BFD_RELOC_MSP430X_ABS20_EXT_SRC
);
2955 fix_new_exp (frag_now
, where
, 6, &(op1
.exp
), FALSE
,
2956 BFD_RELOC_MSP430X_PCR20_EXT_SRC
);
2959 if (op2
.mode
== OP_EXP
)
2961 if (op2
.exp
.X_op
== O_constant
)
2962 extended
|= (op2
.exp
.X_add_number
>> 16) & 0xf;
2964 else if (op1
.mode
== OP_EXP
)
2965 fix_new_exp (frag_now
, where
, 8, &(op2
.exp
), FALSE
,
2966 op2
.reg
? BFD_RELOC_MSP430X_ABS20_EXT_ODST
2967 : BFD_RELOC_MSP430X_PCR20_EXT_ODST
);
2970 fix_new_exp (frag_now
, where
, 6, &(op2
.exp
), FALSE
,
2971 op2
.reg
? BFD_RELOC_MSP430X_ABS20_EXT_DST
2972 : BFD_RELOC_MSP430X_PCR20_EXT_DST
);
2975 /* Emit the extension word. */
2976 bfd_putl16 (extended
, frag
);
2981 bin
|= (op2
.reg
| (op1
.reg
<< 8) | (op1
.am
<< 4) | (op2
.am
<< 7));
2982 bfd_putl16 ((bfd_vma
) bin
, frag
);
2986 if (op1
.mode
== OP_EXP
)
2988 if (op1
.exp
.X_op
== O_constant
)
2990 bfd_putl16 (op1
.exp
.X_add_number
& 0xffff, frag
);
2994 bfd_putl16 ((bfd_vma
) ZEROS
, frag
);
2998 if (op1
.reg
|| (op1
.reg
== 0 && op1
.am
== 3)) /* Not PC relative. */
2999 fix_new_exp (frag_now
, where
, 2,
3000 &(op1
.exp
), FALSE
, CHECK_RELOC_MSP430
);
3002 fix_new_exp (frag_now
, where
, 2,
3003 &(op1
.exp
), TRUE
, CHECK_RELOC_MSP430_PCREL
);
3011 if (op2
.mode
== OP_EXP
)
3013 if (op2
.exp
.X_op
== O_constant
)
3015 bfd_putl16 (op2
.exp
.X_add_number
& 0xffff, frag
);
3019 bfd_putl16 ((bfd_vma
) ZEROS
, frag
);
3023 if (op2
.reg
) /* Not PC relative. */
3024 fix_new_exp (frag_now
, where
, 2,
3025 &(op2
.exp
), FALSE
, CHECK_RELOC_MSP430
);
3027 fix_new_exp (frag_now
, where
, 2,
3028 &(op2
.exp
), TRUE
, CHECK_RELOC_MSP430_PCREL
);
3033 if (gen_interrupt_nops
3034 && target_is_430xv2 ()
3035 && ( (is_opcode ("bic") && bin
== 0xc232)
3036 || (is_opcode ("bis") && bin
== 0xd232)
3037 || (is_opcode ("mov") && op2
.mode
== OP_REG
&& op2
.reg
== 2)))
3039 /* Emit a NOP following interrupt enable/disable.
3040 See 1.3.4.1 of the MSP430x5xx User Guide. */
3042 frag
= frag_more (2);
3043 bfd_putl16 ((bfd_vma
) 0x4303 /* NOP */, frag
);
3046 dwarf2_emit_insn (insn_length
);
3049 case 2: /* Single-operand mostly instr. */
3050 if (opcode
->insn_opnumb
== 0)
3052 /* reti instruction. */
3054 frag
= frag_more (2);
3055 bfd_putl16 ((bfd_vma
) bin
, frag
);
3056 dwarf2_emit_insn (insn_length
);
3060 line
= extract_operand (line
, l1
, sizeof (l1
));
3061 res
= msp430_srcoperand (&op1
, l1
, opcode
->bin_opcode
,
3062 &imm_op
, extended_op
, TRUE
);
3064 break; /* Error in operand. */
3066 if (target_is_430xv2 ()
3067 && op1
.mode
== OP_REG
3069 && (is_opcode ("rrax")
3070 || is_opcode ("rrcx")
3071 || is_opcode ("rra")
3072 || is_opcode ("rrc")))
3074 as_bad (_("%s: attempt to rotate the PC register"), opcode
->name
);
3078 insn_length
= (extended_op
? 2 : 0) + 2 + (op1
.ol
* 2);
3079 frag
= frag_more (insn_length
);
3080 where
= frag
- frag_now
->fr_literal
;
3084 if (is_opcode ("swpbx") || is_opcode ("sxtx"))
3086 /* These two instructions use a special
3087 encoding of the A/L and B/W bits. */
3088 bin
&= ~ BYTE_OPERATION
;
3092 as_bad (_("%s instruction does not accept a .b suffix"),
3097 extended
|= BYTE_OPERATION
;
3100 extended
|= BYTE_OPERATION
;
3102 if (op1
.ol
!= 0 && ((extended
& 0xf) != 0))
3104 as_bad (_("repeat instruction used with non-register mode instruction"));
3108 if (op1
.mode
== OP_EXP
)
3110 if (op1
.exp
.X_op
== O_constant
)
3111 extended
|= ((op1
.exp
.X_add_number
>> 16) & 0xf) << 7;
3113 else if (op1
.reg
|| (op1
.reg
== 0 && op1
.am
== 3)) /* Not PC relative. */
3114 fix_new_exp (frag_now
, where
, 6, &(op1
.exp
), FALSE
,
3115 BFD_RELOC_MSP430X_ABS20_EXT_SRC
);
3117 fix_new_exp (frag_now
, where
, 6, &(op1
.exp
), FALSE
,
3118 BFD_RELOC_MSP430X_PCR20_EXT_SRC
);
3121 /* Emit the extension word. */
3122 bfd_putl16 (extended
, frag
);
3127 bin
|= op1
.reg
| (op1
.am
<< 4);
3128 bfd_putl16 ((bfd_vma
) bin
, frag
);
3132 if (op1
.mode
== OP_EXP
)
3134 if (op1
.exp
.X_op
== O_constant
)
3136 bfd_putl16 (op1
.exp
.X_add_number
& 0xffff, frag
);
3140 bfd_putl16 ((bfd_vma
) ZEROS
, frag
);
3144 if (op1
.reg
|| (op1
.reg
== 0 && op1
.am
== 3)) /* Not PC relative. */
3145 fix_new_exp (frag_now
, where
, 2,
3146 &(op1
.exp
), FALSE
, CHECK_RELOC_MSP430
);
3148 fix_new_exp (frag_now
, where
, 2,
3149 &(op1
.exp
), TRUE
, CHECK_RELOC_MSP430_PCREL
);
3154 dwarf2_emit_insn (insn_length
);
3157 case 3: /* Conditional jumps instructions. */
3158 line
= extract_operand (line
, l1
, sizeof (l1
));
3159 /* l1 is a label. */
3168 parse_exp (m
, &exp
);
3170 /* In order to handle something like:
3174 jz 4 ; skip next 4 bytes
3177 nop ; will jump here if r5 positive or zero
3179 jCOND -n ;assumes jump n bytes backward:
3189 jCOND $n ; jump from PC in either direction. */
3191 if (exp
.X_op
== O_constant
)
3193 int x
= exp
.X_add_number
;
3197 as_warn (_("Even number required. Rounded to %d"), x
+ 1);
3201 if ((*l1
== '$' && x
> 0) || x
< 0)
3206 if (x
> 512 || x
< -511)
3208 as_bad (_("Wrong displacement %d"), x
<< 1);
3213 frag
= frag_more (2); /* Instr size is 1 word. */
3216 bfd_putl16 ((bfd_vma
) bin
, frag
);
3218 else if (exp
.X_op
== O_symbol
&& *l1
!= '$')
3221 frag
= frag_more (2); /* Instr size is 1 word. */
3222 where
= frag
- frag_now
->fr_literal
;
3223 fix_new_exp (frag_now
, where
, 2,
3224 &exp
, TRUE
, BFD_RELOC_MSP430_10_PCREL
);
3226 bfd_putl16 ((bfd_vma
) bin
, frag
);
3228 else if (*l1
== '$')
3230 as_bad (_("instruction requires label sans '$'"));
3234 ("instruction requires label or value in range -511:512"));
3235 dwarf2_emit_insn (insn_length
);
3240 as_bad (_("instruction requires label"));
3245 case 4: /* Extended jumps. */
3246 if (!msp430_enable_polys
)
3248 as_bad (_("polymorphs are not enabled. Use -mP option to enable."));
3252 line
= extract_operand (line
, l1
, sizeof (l1
));
3258 /* Ignore absolute addressing. make it PC relative anyway. */
3259 if (*m
== '#' || *m
== '$')
3262 parse_exp (m
, & exp
);
3263 if (exp
.X_op
== O_symbol
)
3265 /* Relaxation required. */
3266 struct rcodes_s rc
= msp430_rcodes
[opcode
->insn_opnumb
];
3268 if (target_is_430x ())
3269 rc
= msp430x_rcodes
[opcode
->insn_opnumb
];
3271 /* The parameter to dwarf2_emit_insn is actually the offset to
3272 the start of the insn from the fix piece of instruction that
3273 was emitted. Since next fragments may have variable size we
3274 tie debug info to the beginning of the instruction. */
3276 frag
= frag_more (8);
3277 dwarf2_emit_insn (0);
3278 bfd_putl16 ((bfd_vma
) rc
.sop
, frag
);
3279 frag
= frag_variant (rs_machine_dependent
, 8, 2,
3281 ENCODE_RELAX (rc
.lpos
, STATE_BITS10
),
3283 0, /* Offset is zero if jump dist less than 1K. */
3289 as_bad (_("instruction requires label"));
3292 case 5: /* Emulated extended branches. */
3293 if (!msp430_enable_polys
)
3295 as_bad (_("polymorphs are not enabled. Use -mP option to enable."));
3298 line
= extract_operand (line
, l1
, sizeof (l1
));
3304 /* Ignore absolute addressing. make it PC relative anyway. */
3305 if (*m
== '#' || *m
== '$')
3308 parse_exp (m
, & exp
);
3309 if (exp
.X_op
== O_symbol
)
3311 /* Relaxation required. */
3312 struct hcodes_s hc
= msp430_hcodes
[opcode
->insn_opnumb
];
3314 if (target_is_430x ())
3315 hc
= msp430x_hcodes
[opcode
->insn_opnumb
];
3318 frag
= frag_more (8);
3319 dwarf2_emit_insn (0);
3320 bfd_putl16 ((bfd_vma
) hc
.op0
, frag
);
3321 bfd_putl16 ((bfd_vma
) hc
.op1
, frag
+2);
3323 frag
= frag_variant (rs_machine_dependent
, 8, 2,
3324 ENCODE_RELAX (STATE_EMUL_BRANCH
, STATE_BITS10
), /* Wild guess. */
3326 0, /* Offset is zero if jump dist less than 1K. */
3332 as_bad (_("instruction requires label"));
3336 as_bad (_("Illegal instruction or not implemented opcode."));
3339 input_line_pointer
= line
;
3344 md_assemble (char * str
)
3346 struct msp430_opcode_s
* opcode
;
3350 str
= skip_space (str
); /* Skip leading spaces. */
3351 str
= extract_cmd (str
, cmd
, sizeof (cmd
));
3353 while (cmd
[i
] && i
< sizeof (cmd
))
3355 char a
= TOLOWER (cmd
[i
]);
3362 as_bad (_("can't find opcode "));
3366 opcode
= (struct msp430_opcode_s
*) hash_find (msp430_hash
, cmd
);
3370 as_bad (_("unknown opcode `%s'"), cmd
);
3375 char *__t
= input_line_pointer
;
3377 msp430_operands (opcode
, str
);
3378 input_line_pointer
= __t
;
3382 /* GAS will call this function for each section at the end of the assembly,
3383 to permit the CPU backend to adjust the alignment of a section. */
3386 md_section_align (asection
* seg
, valueT addr
)
3388 int align
= bfd_get_section_alignment (stdoutput
, seg
);
3390 return ((addr
+ (1 << align
) - 1) & (-1 << align
));
3393 /* If you define this macro, it should return the offset between the
3394 address of a PC relative fixup and the position from which the PC
3395 relative adjustment should be made. On many processors, the base
3396 of a PC relative instruction is the next instruction, so this
3397 macro would return the length of an instruction. */
3400 md_pcrel_from_section (fixS
* fixp
, segT sec
)
3402 if (fixp
->fx_addsy
!= (symbolS
*) NULL
3403 && (!S_IS_DEFINED (fixp
->fx_addsy
)
3404 || (S_GET_SEGMENT (fixp
->fx_addsy
) != sec
)))
3407 return fixp
->fx_frag
->fr_address
+ fixp
->fx_where
;
3410 /* Replaces standard TC_FORCE_RELOCATION_LOCAL.
3411 Now it handles the situation when relocations
3412 have to be passed to linker. */
3414 msp430_force_relocation_local (fixS
*fixp
)
3416 if (fixp
->fx_r_type
== BFD_RELOC_MSP430_10_PCREL
)
3420 if (msp430_enable_polys
3421 && !msp430_enable_relax
)
3424 return (!fixp
->fx_pcrel
3425 || generic_force_reloc (fixp
));
3429 /* GAS will call this for each fixup. It should store the correct
3430 value in the object file. */
3432 md_apply_fix (fixS
* fixp
, valueT
* valuep
, segT seg
)
3434 unsigned char * where
;
3438 if (fixp
->fx_addsy
== (symbolS
*) NULL
)
3443 else if (fixp
->fx_pcrel
)
3445 segT s
= S_GET_SEGMENT (fixp
->fx_addsy
);
3447 if (fixp
->fx_addsy
&& (s
== seg
|| s
== absolute_section
))
3449 /* FIXME: We can appear here only in case if we perform a pc
3450 relative jump to the label which is i) global, ii) locally
3451 defined or this is a jump to an absolute symbol.
3452 If this is an absolute symbol -- everything is OK.
3453 If this is a global label, we've got a symbol value defined
3455 1. S_GET_VALUE (fixp->fx_addsy) will contain a symbol offset
3456 from this section start
3457 2. *valuep will contain the real offset from jump insn to the
3459 So, the result of S_GET_VALUE (fixp->fx_addsy) + (* valuep);
3460 will be incorrect. Therefore remove s_get_value. */
3461 value
= /* S_GET_VALUE (fixp->fx_addsy) + */ * valuep
;
3469 value
= fixp
->fx_offset
;
3471 if (fixp
->fx_subsy
!= (symbolS
*) NULL
)
3473 if (S_GET_SEGMENT (fixp
->fx_subsy
) == absolute_section
)
3475 value
-= S_GET_VALUE (fixp
->fx_subsy
);
3481 fixp
->fx_no_overflow
= 1;
3483 /* If polymorphs are enabled and relax disabled.
3484 do not kill any relocs and pass them to linker. */
3485 if (msp430_enable_polys
3486 && !msp430_enable_relax
)
3488 if (!fixp
->fx_addsy
|| (fixp
->fx_addsy
3489 && S_GET_SEGMENT (fixp
->fx_addsy
) == absolute_section
))
3490 fixp
->fx_done
= 1; /* It is ok to kill 'abs' reloc. */
3497 /* Fetch the instruction, insert the fully resolved operand
3498 value, and stuff the instruction back again. */
3499 where
= (unsigned char *) fixp
->fx_frag
->fr_literal
+ fixp
->fx_where
;
3501 insn
= bfd_getl16 (where
);
3503 switch (fixp
->fx_r_type
)
3505 case BFD_RELOC_MSP430_10_PCREL
:
3507 as_bad_where (fixp
->fx_file
, fixp
->fx_line
,
3508 _("odd address operand: %ld"), value
);
3510 /* Jumps are in words. */
3512 --value
; /* Correct PC. */
3514 if (value
< -512 || value
> 511)
3515 as_bad_where (fixp
->fx_file
, fixp
->fx_line
,
3516 _("operand out of range: %ld"), value
);
3518 value
&= 0x3ff; /* get rid of extended sign */
3519 bfd_putl16 ((bfd_vma
) (value
| insn
), where
);
3522 case BFD_RELOC_MSP430X_PCR16
:
3523 case BFD_RELOC_MSP430_RL_PCREL
:
3524 case BFD_RELOC_MSP430_16_PCREL
:
3526 as_bad_where (fixp
->fx_file
, fixp
->fx_line
,
3527 _("odd address operand: %ld"), value
);
3530 case BFD_RELOC_MSP430_16_PCREL_BYTE
:
3531 /* Nothing to be corrected here. */
3532 if (value
< -32768 || value
> 65536)
3533 as_bad_where (fixp
->fx_file
, fixp
->fx_line
,
3534 _("operand out of range: %ld"), value
);
3537 case BFD_RELOC_MSP430X_ABS16
:
3538 case BFD_RELOC_MSP430_16
:
3540 case BFD_RELOC_MSP430_16_BYTE
:
3541 value
&= 0xffff; /* Get rid of extended sign. */
3542 bfd_putl16 ((bfd_vma
) value
, where
);
3546 bfd_putl16 ((bfd_vma
) value
, where
);
3549 case BFD_RELOC_MSP430_ABS8
:
3551 bfd_put_8 (NULL
, (bfd_vma
) value
, where
);
3554 case BFD_RELOC_MSP430X_ABS20_EXT_SRC
:
3555 case BFD_RELOC_MSP430X_PCR20_EXT_SRC
:
3556 bfd_putl16 ((bfd_vma
) (value
& 0xffff), where
+ 4);
3558 bfd_putl16 ((bfd_vma
) (((value
& 0xf) << 7) | insn
), where
);
3561 case BFD_RELOC_MSP430X_ABS20_ADR_SRC
:
3562 bfd_putl16 ((bfd_vma
) (value
& 0xffff), where
+ 2);
3564 bfd_putl16 ((bfd_vma
) (((value
& 0xf) << 8) | insn
), where
);
3567 case BFD_RELOC_MSP430X_ABS20_EXT_ODST
:
3568 bfd_putl16 ((bfd_vma
) (value
& 0xffff), where
+ 6);
3570 bfd_putl16 ((bfd_vma
) ((value
& 0xf) | insn
), where
);
3573 case BFD_RELOC_MSP430X_PCR20_CALL
:
3574 bfd_putl16 ((bfd_vma
) (value
& 0xffff), where
+ 2);
3576 bfd_putl16 ((bfd_vma
) ((value
& 0xf) | insn
), where
);
3579 case BFD_RELOC_MSP430X_ABS20_EXT_DST
:
3580 case BFD_RELOC_MSP430X_PCR20_EXT_DST
:
3581 bfd_putl16 ((bfd_vma
) (value
& 0xffff), where
+ 4);
3583 bfd_putl16 ((bfd_vma
) ((value
& 0xf) | insn
), where
);
3586 case BFD_RELOC_MSP430X_PCR20_EXT_ODST
:
3587 bfd_putl16 ((bfd_vma
) (value
& 0xffff), where
+ 6);
3589 bfd_putl16 ((bfd_vma
) ((value
& 0xf) | insn
), where
);
3592 case BFD_RELOC_MSP430X_ABS20_ADR_DST
:
3593 bfd_putl16 ((bfd_vma
) (value
& 0xffff), where
+ 2);
3595 bfd_putl16 ((bfd_vma
) ((value
& 0xf) | insn
), where
);
3599 as_fatal (_("line %d: unknown relocation type: 0x%x"),
3600 fixp
->fx_line
, fixp
->fx_r_type
);
3606 fixp
->fx_addnumber
= value
;
3611 S_IS_GAS_LOCAL (symbolS
* s
)
3618 name
= S_GET_NAME (s
);
3619 len
= strlen (name
) - 1;
3621 return name
[len
] == 1 || name
[len
] == 2;
3624 /* GAS will call this to generate a reloc, passing the resulting reloc
3625 to `bfd_install_relocation'. This currently works poorly, as
3626 `bfd_install_relocation' often does the wrong thing, and instances of
3627 `tc_gen_reloc' have been written to work around the problems, which
3628 in turns makes it difficult to fix `bfd_install_relocation'. */
3630 /* If while processing a fixup, a reloc really needs to be created
3631 then it is done here. */
3634 tc_gen_reloc (asection
* seg ATTRIBUTE_UNUSED
, fixS
* fixp
)
3636 static arelent
* no_relocs
= NULL
;
3637 static arelent
* relocs
[MAX_RELOC_EXPANSION
+ 1];
3640 reloc
= xmalloc (sizeof (arelent
));
3641 reloc
->address
= fixp
->fx_frag
->fr_address
+ fixp
->fx_where
;
3642 reloc
->howto
= bfd_reloc_type_lookup (stdoutput
, fixp
->fx_r_type
);
3644 if (reloc
->howto
== (reloc_howto_type
*) NULL
)
3646 as_bad_where (fixp
->fx_file
, fixp
->fx_line
,
3647 _("reloc %d not supported by object file format"),
3648 (int) fixp
->fx_r_type
);
3657 && S_GET_SEGMENT (fixp
->fx_subsy
) == absolute_section
)
3659 fixp
->fx_offset
-= S_GET_VALUE (fixp
->fx_subsy
);
3660 fixp
->fx_subsy
= NULL
;
3663 if (fixp
->fx_addsy
&& fixp
->fx_subsy
)
3665 asection
*asec
, *ssec
;
3667 asec
= S_GET_SEGMENT (fixp
->fx_addsy
);
3668 ssec
= S_GET_SEGMENT (fixp
->fx_subsy
);
3670 /* If we have a difference between two different, non-absolute symbols
3671 we must generate two relocs (one for each symbol) and allow the
3672 linker to resolve them - relaxation may change the distances between
3673 symbols, even local symbols defined in the same section.
3675 Unfortunately we cannot do this with assembler generated local labels
3676 because there can be multiple incarnations of the same label, with
3677 exactly the same name, in any given section and the linker will have
3678 no way to identify the correct one. Instead we just have to hope
3679 that no relaxtion will occur between the local label and the other
3680 symbol in the expression.
3682 Similarly we have to compute differences between symbols in the .eh_frame
3683 section as the linker is not smart enough to apply relocations there
3684 before attempting to process it. */
3685 if ((ssec
!= absolute_section
|| asec
!= absolute_section
)
3686 && (fixp
->fx_addsy
!= fixp
->fx_subsy
)
3687 && strcmp (ssec
->name
, ".eh_frame") != 0
3688 && ! S_IS_GAS_LOCAL (fixp
->fx_addsy
)
3689 && ! S_IS_GAS_LOCAL (fixp
->fx_subsy
))
3691 arelent
* reloc2
= xmalloc (sizeof * reloc
);
3696 reloc2
->address
= reloc
->address
;
3697 reloc2
->howto
= bfd_reloc_type_lookup (stdoutput
,
3698 BFD_RELOC_MSP430_SYM_DIFF
);
3699 reloc2
->addend
= - S_GET_VALUE (fixp
->fx_subsy
);
3701 if (ssec
== absolute_section
)
3702 reloc2
->sym_ptr_ptr
= bfd_abs_section_ptr
->symbol_ptr_ptr
;
3705 reloc2
->sym_ptr_ptr
= xmalloc (sizeof (asymbol
*));
3706 *reloc2
->sym_ptr_ptr
= symbol_get_bfdsym (fixp
->fx_subsy
);
3709 reloc
->addend
= fixp
->fx_offset
;
3710 if (asec
== absolute_section
)
3712 reloc
->addend
+= S_GET_VALUE (fixp
->fx_addsy
);
3713 reloc
->sym_ptr_ptr
= bfd_abs_section_ptr
->symbol_ptr_ptr
;
3717 reloc
->sym_ptr_ptr
= xmalloc (sizeof (asymbol
*));
3718 *reloc
->sym_ptr_ptr
= symbol_get_bfdsym (fixp
->fx_addsy
);
3727 char *fixpos
= fixp
->fx_where
+ fixp
->fx_frag
->fr_literal
;
3729 reloc
->addend
= (S_GET_VALUE (fixp
->fx_addsy
)
3730 - S_GET_VALUE (fixp
->fx_subsy
) + fixp
->fx_offset
);
3732 switch (fixp
->fx_r_type
)
3735 md_number_to_chars (fixpos
, reloc
->addend
, 1);
3739 md_number_to_chars (fixpos
, reloc
->addend
, 2);
3743 md_number_to_chars (fixpos
, reloc
->addend
, 3);
3747 md_number_to_chars (fixpos
, reloc
->addend
, 4);
3752 = (asymbol
**) bfd_abs_section_ptr
->symbol_ptr_ptr
;
3763 if (fixp
->fx_r_type
== BFD_RELOC_MSP430X_ABS16
3764 && S_GET_SEGMENT (fixp
->fx_addsy
) == absolute_section
)
3766 bfd_vma amount
= S_GET_VALUE (fixp
->fx_addsy
);
3767 char *fixpos
= fixp
->fx_where
+ fixp
->fx_frag
->fr_literal
;
3769 md_number_to_chars (fixpos
, amount
, 2);
3774 reloc
->sym_ptr_ptr
= xmalloc (sizeof (asymbol
*));
3775 *reloc
->sym_ptr_ptr
= symbol_get_bfdsym (fixp
->fx_addsy
);
3776 reloc
->addend
= fixp
->fx_offset
;
3778 if (fixp
->fx_r_type
== BFD_RELOC_VTABLE_INHERIT
3779 || fixp
->fx_r_type
== BFD_RELOC_VTABLE_ENTRY
)
3780 reloc
->address
= fixp
->fx_offset
;
3787 md_estimate_size_before_relax (fragS
* fragP ATTRIBUTE_UNUSED
,
3788 asection
* segment_type ATTRIBUTE_UNUSED
)
3790 if (fragP
->fr_symbol
&& S_GET_SEGMENT (fragP
->fr_symbol
) == segment_type
)
3792 /* This is a jump -> pcrel mode. Nothing to do much here.
3793 Return value == 2. */
3795 ENCODE_RELAX (RELAX_LEN (fragP
->fr_subtype
), STATE_BITS10
);
3797 else if (fragP
->fr_symbol
)
3799 /* Its got a segment, but its not ours. Even if fr_symbol is in
3800 an absolute segment, we don't know a displacement until we link
3801 object files. So it will always be long. This also applies to
3802 labels in a subsegment of current. Liker may relax it to short
3803 jump later. Return value == 8. */
3805 ENCODE_RELAX (RELAX_LEN (fragP
->fr_subtype
), STATE_WORD
);
3809 /* We know the abs value. may be it is a jump to fixed address.
3810 Impossible in our case, cause all constants already handled. */
3812 ENCODE_RELAX (RELAX_LEN (fragP
->fr_subtype
), STATE_UNDEF
);
3815 return md_relax_table
[fragP
->fr_subtype
].rlx_length
;
3819 md_convert_frag (bfd
* abfd ATTRIBUTE_UNUSED
,
3820 asection
* sec ATTRIBUTE_UNUSED
,
3826 struct rcodes_s
* cc
= NULL
;
3827 struct hcodes_s
* hc
= NULL
;
3829 switch (fragP
->fr_subtype
)
3831 case ENCODE_RELAX (STATE_UNCOND_BRANCH
, STATE_BITS10
):
3832 case ENCODE_RELAX (STATE_SIMPLE_BRANCH
, STATE_BITS10
):
3833 case ENCODE_RELAX (STATE_NOOV_BRANCH
, STATE_BITS10
):
3834 /* We do not have to convert anything here.
3835 Just apply a fix. */
3836 rela
= BFD_RELOC_MSP430_10_PCREL
;
3839 case ENCODE_RELAX (STATE_UNCOND_BRANCH
, STATE_WORD
):
3840 case ENCODE_RELAX (STATE_UNCOND_BRANCH
, STATE_UNDEF
):
3841 /* Convert uncond branch jmp lab -> br lab. */
3842 if (target_is_430x ())
3843 cc
= msp430x_rcodes
+ 7;
3845 cc
= msp430_rcodes
+ 7;
3846 where
= fragP
->fr_literal
+ fragP
->fr_fix
;
3847 bfd_putl16 (cc
->lop0
, where
);
3848 rela
= BFD_RELOC_MSP430_RL_PCREL
;
3852 case ENCODE_RELAX (STATE_SIMPLE_BRANCH
, STATE_WORD
):
3853 case ENCODE_RELAX (STATE_SIMPLE_BRANCH
, STATE_UNDEF
):
3855 /* Other simple branches. */
3856 int insn
= bfd_getl16 (fragP
->fr_opcode
);
3859 /* Find actual instruction. */
3860 if (target_is_430x ())
3862 for (i
= 0; i
< 7 && !cc
; i
++)
3863 if (msp430x_rcodes
[i
].sop
== insn
)
3864 cc
= msp430x_rcodes
+ i
;
3868 for (i
= 0; i
< 7 && !cc
; i
++)
3869 if (msp430_rcodes
[i
].sop
== insn
)
3870 cc
= & msp430_rcodes
[i
];
3873 if (!cc
|| !cc
->name
)
3874 as_fatal (_("internal inconsistency problem in %s: insn %04lx"),
3875 __FUNCTION__
, (long) insn
);
3876 where
= fragP
->fr_literal
+ fragP
->fr_fix
;
3877 bfd_putl16 (cc
->lop0
, where
);
3878 bfd_putl16 (cc
->lop1
, where
+ 2);
3879 rela
= BFD_RELOC_MSP430_RL_PCREL
;
3884 case ENCODE_RELAX (STATE_NOOV_BRANCH
, STATE_WORD
):
3885 case ENCODE_RELAX (STATE_NOOV_BRANCH
, STATE_UNDEF
):
3886 if (target_is_430x ())
3887 cc
= msp430x_rcodes
+ 6;
3889 cc
= msp430_rcodes
+ 6;
3890 where
= fragP
->fr_literal
+ fragP
->fr_fix
;
3891 bfd_putl16 (cc
->lop0
, where
);
3892 bfd_putl16 (cc
->lop1
, where
+ 2);
3893 bfd_putl16 (cc
->lop2
, where
+ 4);
3894 rela
= BFD_RELOC_MSP430_RL_PCREL
;
3898 case ENCODE_RELAX (STATE_EMUL_BRANCH
, STATE_BITS10
):
3900 int insn
= bfd_getl16 (fragP
->fr_opcode
+ 2);
3903 if (target_is_430x ())
3905 for (i
= 0; i
< 4 && !hc
; i
++)
3906 if (msp430x_hcodes
[i
].op1
== insn
)
3907 hc
= msp430x_hcodes
+ i
;
3911 for (i
= 0; i
< 4 && !hc
; i
++)
3912 if (msp430_hcodes
[i
].op1
== insn
)
3913 hc
= &msp430_hcodes
[i
];
3915 if (!hc
|| !hc
->name
)
3916 as_fatal (_("internal inconsistency problem in %s: ext. insn %04lx"),
3917 __FUNCTION__
, (long) insn
);
3918 rela
= BFD_RELOC_MSP430_10_PCREL
;
3919 /* Apply a fix for a first label if necessary.
3920 another fix will be applied to the next word of insn anyway. */
3922 fix_new (fragP
, fragP
->fr_fix
, 2, fragP
->fr_symbol
,
3923 fragP
->fr_offset
, TRUE
, rela
);
3929 case ENCODE_RELAX (STATE_EMUL_BRANCH
, STATE_WORD
):
3930 case ENCODE_RELAX (STATE_EMUL_BRANCH
, STATE_UNDEF
):
3932 int insn
= bfd_getl16 (fragP
->fr_opcode
+ 2);
3935 if (target_is_430x ())
3937 for (i
= 0; i
< 4 && !hc
; i
++)
3938 if (msp430x_hcodes
[i
].op1
== insn
)
3939 hc
= msp430x_hcodes
+ i
;
3943 for (i
= 0; i
< 4 && !hc
; i
++)
3944 if (msp430_hcodes
[i
].op1
== insn
)
3945 hc
= & msp430_hcodes
[i
];
3947 if (!hc
|| !hc
->name
)
3948 as_fatal (_("internal inconsistency problem in %s: ext. insn %04lx"),
3949 __FUNCTION__
, (long) insn
);
3950 rela
= BFD_RELOC_MSP430_RL_PCREL
;
3951 where
= fragP
->fr_literal
+ fragP
->fr_fix
;
3952 bfd_putl16 (hc
->lop0
, where
);
3953 bfd_putl16 (hc
->lop1
, where
+ 2);
3954 bfd_putl16 (hc
->lop2
, where
+ 4);
3960 as_fatal (_("internal inconsistency problem in %s: %lx"),
3961 __FUNCTION__
, (long) fragP
->fr_subtype
);
3965 /* Now apply fix. */
3966 fix_new (fragP
, fragP
->fr_fix
, 2, fragP
->fr_symbol
,
3967 fragP
->fr_offset
, TRUE
, rela
);
3968 /* Just fixed 2 bytes. */
3972 /* Relax fragment. Mostly stolen from hc11 and mcore
3973 which arches I think I know. */
3976 msp430_relax_frag (segT seg ATTRIBUTE_UNUSED
, fragS
* fragP
,
3977 long stretch ATTRIBUTE_UNUSED
)
3982 const relax_typeS
*this_type
;
3983 const relax_typeS
*start_type
;
3984 relax_substateT next_state
;
3985 relax_substateT this_state
;
3986 const relax_typeS
*table
= md_relax_table
;
3988 /* Nothing to be done if the frag has already max size. */
3989 if (RELAX_STATE (fragP
->fr_subtype
) == STATE_UNDEF
3990 || RELAX_STATE (fragP
->fr_subtype
) == STATE_WORD
)
3993 if (RELAX_STATE (fragP
->fr_subtype
) == STATE_BITS10
)
3995 symbolP
= fragP
->fr_symbol
;
3996 if (symbol_resolved_p (symbolP
))
3997 as_fatal (_("internal inconsistency problem in %s: resolved symbol"),
3999 /* We know the offset. calculate a distance. */
4000 aim
= S_GET_VALUE (symbolP
) - fragP
->fr_address
- fragP
->fr_fix
;
4003 if (!msp430_enable_relax
)
4005 /* Relaxation is not enabled. So, make all jump as long ones
4006 by setting 'aim' to quite high value. */
4010 this_state
= fragP
->fr_subtype
;
4011 start_type
= this_type
= table
+ this_state
;
4015 /* Look backwards. */
4016 for (next_state
= this_type
->rlx_more
; next_state
;)
4017 if (aim
>= this_type
->rlx_backward
|| !this_type
->rlx_backward
)
4021 /* Grow to next state. */
4022 this_state
= next_state
;
4023 this_type
= table
+ this_state
;
4024 next_state
= this_type
->rlx_more
;
4029 /* Look forwards. */
4030 for (next_state
= this_type
->rlx_more
; next_state
;)
4031 if (aim
<= this_type
->rlx_forward
|| !this_type
->rlx_forward
)
4035 /* Grow to next state. */
4036 this_state
= next_state
;
4037 this_type
= table
+ this_state
;
4038 next_state
= this_type
->rlx_more
;
4042 growth
= this_type
->rlx_length
- start_type
->rlx_length
;
4044 fragP
->fr_subtype
= this_state
;
4048 /* Return FALSE if the fixup in fixp should be left alone and not
4049 adjusted. We return FALSE here so that linker relaxation will
4053 msp430_fix_adjustable (struct fix
*fixp ATTRIBUTE_UNUSED
)
4055 /* If the symbol is in a non-code section then it should be OK. */
4057 && ((S_GET_SEGMENT (fixp
->fx_addsy
)->flags
& SEC_CODE
) == 0))
4063 /* Set the contents of the .MSP430.attributes section. */
4066 msp430_md_end (void)
4068 bfd_elf_add_proc_attr_int (stdoutput
, OFBA_MSPABI_Tag_ISA
,
4069 target_is_430x () ? 2 : 1);
4071 bfd_elf_add_proc_attr_int (stdoutput
, OFBA_MSPABI_Tag_Code_Model
,
4072 large_model
? 2 : 1);
4074 bfd_elf_add_proc_attr_int (stdoutput
, OFBA_MSPABI_Tag_Data_Model
,
4075 large_model
? 2 : 1);
4078 /* Returns FALSE if there is a msp430 specific reason why the
4079 subtraction of two same-section symbols cannot be computed by
4083 msp430_allow_local_subtract (expressionS
* left
,
4084 expressionS
* right
,
4087 /* If the symbols are not in a code section then they are OK. */
4088 if ((section
->flags
& SEC_CODE
) == 0)
4091 if (S_IS_GAS_LOCAL (left
->X_add_symbol
) || S_IS_GAS_LOCAL (right
->X_add_symbol
))
4094 if (left
->X_add_symbol
== right
->X_add_symbol
)
4097 /* We have to assume that there may be instructions between the
4098 two symbols and that relaxation may increase the distance between