]> git.ipfire.org Git - thirdparty/gcc.git/blame - gcc/final.c
howto.html: Update commentary.
[thirdparty/gcc.git] / gcc / final.c
CommitLineData
3cf2715d 1/* Convert RTL to assembler code and output it, for GNU compiler.
3b708058 2 Copyright (C) 1987, 1988, 1989, 1992, 1993, 1994, 1995, 1996, 1997,
b660f82f 3 1998, 1999, 2000, 2001 Free Software Foundation, Inc.
3cf2715d 4
1322177d 5This file is part of GCC.
3cf2715d 6
1322177d
LB
7GCC is free software; you can redistribute it and/or modify it under
8the terms of the GNU General Public License as published by the Free
9Software Foundation; either version 2, or (at your option) any later
10version.
3cf2715d 11
1322177d
LB
12GCC is distributed in the hope that it will be useful, but WITHOUT ANY
13WARRANTY; without even the implied warranty of MERCHANTABILITY or
14FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
15for more details.
3cf2715d
DE
16
17You should have received a copy of the GNU General Public License
1322177d
LB
18along with GCC; see the file COPYING. If not, write to the Free
19Software Foundation, 59 Temple Place - Suite 330, Boston, MA
2002111-1307, USA. */
3cf2715d 21
3cf2715d
DE
22/* This is the final pass of the compiler.
23 It looks at the rtl code for a function and outputs assembler code.
24
25 Call `final_start_function' to output the assembler code for function entry,
26 `final' to output assembler code for some RTL code,
27 `final_end_function' to output assembler code for function exit.
28 If a function is compiled in several pieces, each piece is
29 output separately with `final'.
30
31 Some optimizations are also done at this level.
32 Move instructions that were made unnecessary by good register allocation
33 are detected and omitted from the output. (Though most of these
34 are removed by the last jump pass.)
35
36 Instructions to set the condition codes are omitted when it can be
37 seen that the condition codes already had the desired values.
38
39 In some cases it is sufficient if the inherited condition codes
40 have related values, but this may require the following insn
41 (the one that tests the condition codes) to be modified.
42
43 The code for the function prologue and epilogue are generated
08c148a8
NB
44 directly in assembler by the target functions function_prologue and
45 function_epilogue. Those instructions never exist as rtl. */
3cf2715d
DE
46
47#include "config.h"
670ee920 48#include "system.h"
3cf2715d
DE
49
50#include "tree.h"
51#include "rtl.h"
6baf1cc8 52#include "tm_p.h"
3cf2715d
DE
53#include "regs.h"
54#include "insn-config.h"
3cf2715d 55#include "insn-attr.h"
3cf2715d
DE
56#include "recog.h"
57#include "conditions.h"
58#include "flags.h"
59#include "real.h"
60#include "hard-reg-set.h"
3cf2715d 61#include "output.h"
3d195391 62#include "except.h"
49ad7cfa 63#include "function.h"
10f0ad3d 64#include "toplev.h"
d6f4ec51 65#include "reload.h"
ab87f8c8 66#include "intl.h"
be1bb652 67#include "basic-block.h"
08c148a8 68#include "target.h"
a5a42b92 69#include "debug.h"
49d801d3 70#include "expr.h"
3cf2715d 71
440aabf8
NB
72#ifdef XCOFF_DEBUGGING_INFO
73#include "xcoffout.h" /* Needed for external data
74 declarations for e.g. AIX 4.x. */
75#endif
76
76ead72b
RL
77#if defined (DWARF2_UNWIND_INFO) || defined (DWARF2_DEBUGGING_INFO)
78#include "dwarf2out.h"
79#endif
80
3cf2715d
DE
81/* If we aren't using cc0, CC_STATUS_INIT shouldn't exist. So define a
82 null default for it to save conditionalization later. */
83#ifndef CC_STATUS_INIT
84#define CC_STATUS_INIT
85#endif
86
87/* How to start an assembler comment. */
88#ifndef ASM_COMMENT_START
89#define ASM_COMMENT_START ";#"
90#endif
91
92/* Is the given character a logical line separator for the assembler? */
93#ifndef IS_ASM_LOGICAL_LINE_SEPARATOR
94#define IS_ASM_LOGICAL_LINE_SEPARATOR(C) ((C) == ';')
95#endif
96
75197b37
BS
97#ifndef JUMP_TABLES_IN_TEXT_SECTION
98#define JUMP_TABLES_IN_TEXT_SECTION 0
99#endif
100
3cf2715d 101/* Last insn processed by final_scan_insn. */
b1a9f6a0
RH
102static rtx debug_insn;
103rtx current_output_insn;
3cf2715d
DE
104
105/* Line number of last NOTE. */
106static int last_linenum;
107
eac40081
RK
108/* Highest line number in current block. */
109static int high_block_linenum;
110
111/* Likewise for function. */
112static int high_function_linenum;
113
3cf2715d 114/* Filename of last NOTE. */
3cce094d 115static const char *last_filename;
3cf2715d
DE
116
117/* Number of basic blocks seen so far;
118 used if profile_block_flag is set. */
119static int count_basic_blocks;
120
9e2f9a7f 121/* Number of instrumented arcs when profile_arc_flag is set. */
51891abe 122extern int count_instrumented_edges;
9e2f9a7f 123
fc470718
R
124extern int length_unit_log; /* This is defined in insn-attrtab.c. */
125
3cf2715d
DE
126/* Nonzero while outputting an `asm' with operands.
127 This means that inconsistencies are the user's fault, so don't abort.
128 The precise value is the insn being output, to pass to error_for_asm. */
129static rtx this_is_asm_operands;
130
131/* Number of operands of this insn, for an `asm' with operands. */
22bf4422 132static unsigned int insn_noperands;
3cf2715d
DE
133
134/* Compare optimization flag. */
135
136static rtx last_ignored_compare = 0;
137
138/* Flag indicating this insn is the start of a new basic block. */
139
140static int new_block = 1;
141
3cf2715d
DE
142/* Assign a unique number to each insn that is output.
143 This can be used to generate unique local labels. */
144
145static int insn_counter = 0;
146
147#ifdef HAVE_cc0
148/* This variable contains machine-dependent flags (defined in tm.h)
149 set and examined by output routines
150 that describe how to interpret the condition codes properly. */
151
152CC_STATUS cc_status;
153
154/* During output of an insn, this contains a copy of cc_status
155 from before the insn. */
156
157CC_STATUS cc_prev_status;
158#endif
159
160/* Indexed by hardware reg number, is 1 if that register is ever
161 used in the current function.
162
163 In life_analysis, or in stupid_life_analysis, this is set
164 up to record the hard regs used explicitly. Reload adds
165 in the hard regs used for holding pseudo regs. Final uses
166 it to generate the code in the function prologue and epilogue
167 to save and restore registers as needed. */
168
169char regs_ever_live[FIRST_PSEUDO_REGISTER];
170
171/* Nonzero means current function must be given a frame pointer.
172 Set in stmt.c if anything is allocated on the stack there.
173 Set in reload1.c if anything is allocated on the stack there. */
174
175int frame_pointer_needed;
176
8480e480
CC
177/* Assign unique numbers to labels generated for profiling. */
178
179int profile_label_no;
180
18c038b9 181/* Number of unmatched NOTE_INSN_BLOCK_BEG notes we have seen. */
3cf2715d
DE
182
183static int block_depth;
184
185/* Nonzero if have enabled APP processing of our assembler output. */
186
187static int app_on;
188
189/* If we are outputting an insn sequence, this contains the sequence rtx.
190 Zero otherwise. */
191
192rtx final_sequence;
193
194#ifdef ASSEMBLER_DIALECT
195
196/* Number of the assembler dialect to use, starting at 0. */
197static int dialect_number;
198#endif
199
200/* Indexed by line number, nonzero if there is a note for that line. */
201
202static char *line_note_exists;
203
afe48e06
RH
204#ifdef HAVE_conditional_execution
205/* Nonnull if the insn currently being emitted was a COND_EXEC pattern. */
206rtx current_insn_predicate;
207#endif
208
3cf2715d
DE
209/* Linked list to hold line numbers for each basic block. */
210
f5d927c0
KH
211struct bb_list
212{
3cf2715d
DE
213 struct bb_list *next; /* pointer to next basic block */
214 int line_num; /* line number */
215 int file_label_num; /* LPBC<n> label # for stored filename */
216 int func_label_num; /* LPBC<n> label # for stored function name */
217};
218
219static struct bb_list *bb_head = 0; /* Head of basic block list */
220static struct bb_list **bb_tail = &bb_head; /* Ptr to store next bb ptr */
221static int bb_file_label_num = -1; /* Current label # for file */
222static int bb_func_label_num = -1; /* Current label # for func */
223
224/* Linked list to hold the strings for each file and function name output. */
225
f5d927c0
KH
226struct bb_str
227{
3cf2715d 228 struct bb_str *next; /* pointer to next string */
9b3142b3 229 const char *string; /* string */
3cf2715d
DE
230 int label_num; /* label number */
231 int length; /* string length */
232};
233
3cf2715d
DE
234static struct bb_str *sbb_head = 0; /* Head of string list. */
235static struct bb_str **sbb_tail = &sbb_head; /* Ptr to store next bb str */
236static int sbb_label_num = 0; /* Last label used */
237
1d300e19 238#ifdef HAVE_ATTR_length
711d877c
KG
239static int asm_insn_count PARAMS ((rtx));
240#endif
241static void profile_function PARAMS ((FILE *));
242static void profile_after_prologue PARAMS ((FILE *));
243static void add_bb PARAMS ((FILE *));
244static int add_bb_string PARAMS ((const char *, int));
653e276c 245static void notice_source_line PARAMS ((rtx));
49d801d3 246static rtx walk_alter_subreg PARAMS ((rtx *));
711d877c 247static void output_asm_name PARAMS ((void));
998d7deb 248static tree get_mem_expr_from_op PARAMS ((rtx, int *));
4f9b4029 249static void output_asm_operand_names PARAMS ((rtx *, int *, int));
711d877c 250static void output_operand PARAMS ((rtx, int));
e9a25f70 251#ifdef LEAF_REGISTERS
711d877c 252static void leaf_renumber_regs PARAMS ((rtx));
e9a25f70
JL
253#endif
254#ifdef HAVE_cc0
711d877c 255static int alter_cond PARAMS ((rtx));
e9a25f70 256#endif
ca3075bd 257#ifndef ADDR_VEC_ALIGN
711d877c 258static int final_addr_vec_align PARAMS ((rtx));
ca3075bd 259#endif
7bdb32b9 260#ifdef HAVE_ATTR_length
711d877c 261static int align_fuzz PARAMS ((rtx, rtx, int, unsigned));
7bdb32b9 262#endif
3cf2715d
DE
263\f
264/* Initialize data in final at the beginning of a compilation. */
265
266void
267init_final (filename)
6a651371 268 const char *filename ATTRIBUTE_UNUSED;
3cf2715d 269{
3cf2715d 270 app_on = 0;
3cf2715d
DE
271 final_sequence = 0;
272
273#ifdef ASSEMBLER_DIALECT
274 dialect_number = ASSEMBLER_DIALECT;
275#endif
276}
277
278/* Called at end of source file,
279 to output the block-profiling table for this entire compilation. */
280
281void
282end_final (filename)
f5d927c0 283 const char *filename;
3cf2715d
DE
284{
285 int i;
286
9e2f9a7f 287 if (profile_block_flag || profile_arc_flag)
3cf2715d
DE
288 {
289 char name[20];
290 int align = exact_log2 (BIGGEST_ALIGNMENT / BITS_PER_UNIT);
9e2f9a7f 291 int size, rounded;
3cf2715d
DE
292 struct bb_list *ptr;
293 struct bb_str *sptr;
9e2f9a7f 294 int long_bytes = LONG_TYPE_SIZE / BITS_PER_UNIT;
b2aec5c0 295 int gcov_type_bytes = GCOV_TYPE_SIZE / BITS_PER_UNIT;
9e2f9a7f 296 int pointer_bytes = POINTER_SIZE / BITS_PER_UNIT;
c8af3574 297 unsigned int align2 = LONG_TYPE_SIZE;
9e2f9a7f
DE
298
299 if (profile_block_flag)
300 size = long_bytes * count_basic_blocks;
301 else
b2aec5c0 302 size = gcov_type_bytes * count_instrumented_edges;
9e2f9a7f 303 rounded = size;
3cf2715d
DE
304
305 rounded += (BIGGEST_ALIGNMENT / BITS_PER_UNIT) - 1;
306 rounded = (rounded / (BIGGEST_ALIGNMENT / BITS_PER_UNIT)
307 * (BIGGEST_ALIGNMENT / BITS_PER_UNIT));
308
c8af3574
RH
309 /* ??? This _really_ ought to be done with a structure layout
310 and with assemble_constructor. If long_bytes != pointer_bytes
311 we'll be emitting unaligned data at some point. */
312 if (long_bytes != pointer_bytes)
313 abort ();
314
3cf2715d
DE
315 data_section ();
316
47431dff
RK
317 /* Output the main header, of 11 words:
318 0: 1 if this file is initialized, else 0.
3cf2715d
DE
319 1: address of file name (LPBX1).
320 2: address of table of counts (LPBX2).
321 3: number of counts in the table.
322 4: always 0, for compatibility with Sun.
323
324 The following are GNU extensions:
325
326 5: address of table of start addrs of basic blocks (LPBX3).
327 6: Number of bytes in this header.
328 7: address of table of function names (LPBX4).
329 8: address of table of line numbers (LPBX5) or 0.
47431dff 330 9: address of table of file names (LPBX6) or 0.
0f41302f 331 10: space reserved for basic block profiling. */
3cf2715d
DE
332
333 ASM_OUTPUT_ALIGN (asm_out_file, align);
334
335 ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 0);
3cf2715d 336
c8af3574
RH
337 /* Zero word. */
338 assemble_integer (const0_rtx, long_bytes, align2, 1);
339
340 /* Address of filename. */
3cf2715d 341 ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 1);
c8af3574
RH
342 assemble_integer (gen_rtx_SYMBOL_REF (Pmode, name), pointer_bytes,
343 align2, 1);
3cf2715d 344
c8af3574 345 /* Address of count table. */
3cf2715d 346 ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 2);
c8af3574
RH
347 assemble_integer (gen_rtx_SYMBOL_REF (Pmode, name), pointer_bytes,
348 align2, 1);
3cf2715d 349
c8af3574 350 /* Count of the # of basic blocks or # of instrumented arcs. */
c8af3574
RH
351 assemble_integer (GEN_INT (profile_block_flag
352 ? count_basic_blocks
353 : count_instrumented_edges),
354 long_bytes, align2, 1);
3cf2715d 355
c8af3574
RH
356 /* Zero word (link field). */
357 assemble_integer (const0_rtx, pointer_bytes, align2, 1);
3cf2715d
DE
358
359 /* address of basic block start address table */
9e2f9a7f
DE
360 if (profile_block_flag)
361 {
362 ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 3);
c8af3574
RH
363 assemble_integer (gen_rtx_SYMBOL_REF (Pmode, name),
364 pointer_bytes, align2, 1);
9e2f9a7f
DE
365 }
366 else
c8af3574 367 assemble_integer (const0_rtx, pointer_bytes, align2, 1);
3cf2715d 368
c8af3574
RH
369 /* Byte count for extended structure. */
370 assemble_integer (GEN_INT (11 * UNITS_PER_WORD), long_bytes, align2, 1);
3cf2715d 371
c8af3574 372 /* Address of function name table. */
9e2f9a7f
DE
373 if (profile_block_flag)
374 {
375 ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 4);
c8af3574
RH
376 assemble_integer (gen_rtx_SYMBOL_REF (Pmode, name),
377 pointer_bytes, align2, 1);
9e2f9a7f
DE
378 }
379 else
c8af3574 380 assemble_integer (const0_rtx, pointer_bytes, align2, 1);
3cf2715d 381
c8af3574 382 /* Address of line number and filename tables if debugging. */
9e2f9a7f 383 if (write_symbols != NO_DEBUG && profile_block_flag)
3cf2715d
DE
384 {
385 ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 5);
c5c76735 386 assemble_integer (gen_rtx_SYMBOL_REF (Pmode, name),
c8af3574 387 pointer_bytes, align2, 1);
3cf2715d 388 ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 6);
c5c76735 389 assemble_integer (gen_rtx_SYMBOL_REF (Pmode, name),
c8af3574 390 pointer_bytes, align2, 1);
3cf2715d
DE
391 }
392 else
393 {
c8af3574
RH
394 assemble_integer (const0_rtx, pointer_bytes, align2, 1);
395 assemble_integer (const0_rtx, pointer_bytes, align2, 1);
3cf2715d
DE
396 }
397
c8af3574
RH
398 /* Space for extension ptr (link field). */
399 assemble_integer (const0_rtx, UNITS_PER_WORD, align2, 1);
47431dff 400
c8af3574
RH
401 /* Output the file name changing the suffix to .d for
402 Sun tcov compatibility. */
3cf2715d
DE
403 ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 1);
404 {
67e23d2f
JW
405 char *cwd = getpwd ();
406 int len = strlen (filename) + strlen (cwd) + 1;
407 char *data_file = (char *) alloca (len + 4);
408
409 strcpy (data_file, cwd);
410 strcat (data_file, "/");
411 strcat (data_file, filename);
3cf2715d 412 strip_off_ending (data_file, len);
9e2f9a7f
DE
413 if (profile_block_flag)
414 strcat (data_file, ".d");
415 else
416 strcat (data_file, ".da");
3cf2715d
DE
417 assemble_string (data_file, strlen (data_file) + 1);
418 }
419
420 /* Make space for the table of counts. */
2786cbad 421 if (size == 0)
3cf2715d
DE
422 {
423 /* Realign data section. */
424 ASM_OUTPUT_ALIGN (asm_out_file, align);
425 ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 2);
426 if (size != 0)
427 assemble_zeros (size);
428 }
429 else
430 {
431 ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 2);
432#ifdef ASM_OUTPUT_SHARED_LOCAL
433 if (flag_shared_data)
434 ASM_OUTPUT_SHARED_LOCAL (asm_out_file, name, size, rounded);
435 else
436#endif
e9a25f70 437#ifdef ASM_OUTPUT_ALIGNED_DECL_LOCAL
f5d927c0
KH
438 ASM_OUTPUT_ALIGNED_DECL_LOCAL (asm_out_file, NULL_TREE, name,
439 size, BIGGEST_ALIGNMENT);
e9a25f70 440#else
3cf2715d
DE
441#ifdef ASM_OUTPUT_ALIGNED_LOCAL
442 ASM_OUTPUT_ALIGNED_LOCAL (asm_out_file, name, size,
443 BIGGEST_ALIGNMENT);
444#else
445 ASM_OUTPUT_LOCAL (asm_out_file, name, size, rounded);
e9a25f70 446#endif
3cf2715d
DE
447#endif
448 }
449
450 /* Output any basic block strings */
9e2f9a7f 451 if (profile_block_flag)
3cf2715d 452 {
9e2f9a7f
DE
453 readonly_data_section ();
454 if (sbb_head)
3cf2715d 455 {
9e2f9a7f
DE
456 ASM_OUTPUT_ALIGN (asm_out_file, align);
457 for (sptr = sbb_head; sptr != 0; sptr = sptr->next)
458 {
459 ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBC",
460 sptr->label_num);
461 assemble_string (sptr->string, sptr->length);
462 }
3cf2715d
DE
463 }
464 }
465
466 /* Output the table of addresses. */
9e2f9a7f 467 if (profile_block_flag)
3cf2715d 468 {
9e2f9a7f
DE
469 /* Realign in new section */
470 ASM_OUTPUT_ALIGN (asm_out_file, align);
471 ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 3);
472 for (i = 0; i < count_basic_blocks; i++)
473 {
474 ASM_GENERATE_INTERNAL_LABEL (name, "LPB", i);
38a448ca 475 assemble_integer (gen_rtx_SYMBOL_REF (Pmode, name),
c8af3574 476 pointer_bytes, align2, 1);
9e2f9a7f 477 }
3cf2715d
DE
478 }
479
480 /* Output the table of function names. */
9e2f9a7f 481 if (profile_block_flag)
3cf2715d 482 {
9e2f9a7f
DE
483 ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 4);
484 for ((ptr = bb_head), (i = 0); ptr != 0; (ptr = ptr->next), i++)
3cf2715d 485 {
9e2f9a7f
DE
486 if (ptr->func_label_num >= 0)
487 {
488 ASM_GENERATE_INTERNAL_LABEL (name, "LPBC",
489 ptr->func_label_num);
38a448ca 490 assemble_integer (gen_rtx_SYMBOL_REF (Pmode, name),
c8af3574 491 pointer_bytes, align2, 1);
9e2f9a7f
DE
492 }
493 else
c8af3574 494 assemble_integer (const0_rtx, pointer_bytes, align2, 1);
3cf2715d 495 }
3cf2715d 496
f5d927c0 497 for (; i < count_basic_blocks; i++)
c8af3574 498 assemble_integer (const0_rtx, pointer_bytes, align2, 1);
9e2f9a7f 499 }
3cf2715d 500
9e2f9a7f 501 if (write_symbols != NO_DEBUG && profile_block_flag)
3cf2715d
DE
502 {
503 /* Output the table of line numbers. */
504 ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 5);
505 for ((ptr = bb_head), (i = 0); ptr != 0; (ptr = ptr->next), i++)
c8af3574 506 assemble_integer (GEN_INT (ptr->line_num), long_bytes, align2, 1);
3cf2715d 507
f5d927c0 508 for (; i < count_basic_blocks; i++)
c8af3574 509 assemble_integer (const0_rtx, long_bytes, align2, 1);
3cf2715d
DE
510
511 /* Output the table of file names. */
512 ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 6);
513 for ((ptr = bb_head), (i = 0); ptr != 0; (ptr = ptr->next), i++)
514 {
515 if (ptr->file_label_num >= 0)
516 {
9e2f9a7f
DE
517 ASM_GENERATE_INTERNAL_LABEL (name, "LPBC",
518 ptr->file_label_num);
38a448ca 519 assemble_integer (gen_rtx_SYMBOL_REF (Pmode, name),
c8af3574 520 pointer_bytes, align2, 1);
3cf2715d
DE
521 }
522 else
c8af3574 523 assemble_integer (const0_rtx, pointer_bytes, align2, 1);
3cf2715d
DE
524 }
525
f5d927c0 526 for (; i < count_basic_blocks; i++)
c8af3574 527 assemble_integer (const0_rtx, pointer_bytes, align2, 1);
3cf2715d
DE
528 }
529
530 /* End with the address of the table of addresses,
531 so we can find it easily, as the last word in the file's text. */
9e2f9a7f
DE
532 if (profile_block_flag)
533 {
534 ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 3);
c8af3574
RH
535 assemble_integer (gen_rtx_SYMBOL_REF (Pmode, name),
536 pointer_bytes, align2, 1);
9e2f9a7f 537 }
3cf2715d
DE
538 }
539}
540
08c148a8 541/* Default target function prologue and epilogue assembler output.
b9f22704 542
08c148a8
NB
543 If not overridden for epilogue code, then the function body itself
544 contains return instructions wherever needed. */
545void
546default_function_pro_epilogue (file, size)
547 FILE *file ATTRIBUTE_UNUSED;
548 HOST_WIDE_INT size ATTRIBUTE_UNUSED;
549{
550}
551
b4c25db2
NB
552/* Default target hook that outputs nothing to a stream. */
553void
554no_asm_to_stream (file)
555 FILE *file ATTRIBUTE_UNUSED;
556{
557}
558
3cf2715d
DE
559/* Enable APP processing of subsequent output.
560 Used before the output from an `asm' statement. */
561
562void
563app_enable ()
564{
565 if (! app_on)
566 {
51723711 567 fputs (ASM_APP_ON, asm_out_file);
3cf2715d
DE
568 app_on = 1;
569 }
570}
571
572/* Disable APP processing of subsequent output.
573 Called from varasm.c before most kinds of output. */
574
575void
576app_disable ()
577{
578 if (app_on)
579 {
51723711 580 fputs (ASM_APP_OFF, asm_out_file);
3cf2715d
DE
581 app_on = 0;
582 }
583}
584\f
f5d927c0 585/* Return the number of slots filled in the current
3cf2715d
DE
586 delayed branch sequence (we don't count the insn needing the
587 delay slot). Zero if not in a delayed branch sequence. */
588
589#ifdef DELAY_SLOTS
590int
591dbr_sequence_length ()
592{
593 if (final_sequence != 0)
594 return XVECLEN (final_sequence, 0) - 1;
595 else
596 return 0;
597}
598#endif
599\f
600/* The next two pages contain routines used to compute the length of an insn
601 and to shorten branches. */
602
603/* Arrays for insn lengths, and addresses. The latter is referenced by
604 `insn_current_length'. */
605
addd7df6 606static int *insn_lengths;
9d98a694
AO
607
608#ifdef HAVE_ATTR_length
609varray_type insn_addresses_;
610#endif
3cf2715d 611
ea3cbda5
R
612/* Max uid for which the above arrays are valid. */
613static int insn_lengths_max_uid;
614
3cf2715d
DE
615/* Address of insn being processed. Used by `insn_current_length'. */
616int insn_current_address;
617
fc470718
R
618/* Address of insn being processed in previous iteration. */
619int insn_last_address;
620
621/* konwn invariant alignment of insn being processed. */
622int insn_current_align;
623
95707627
R
624/* After shorten_branches, for any insn, uid_align[INSN_UID (insn)]
625 gives the next following alignment insn that increases the known
626 alignment, or NULL_RTX if there is no such insn.
627 For any alignment obtained this way, we can again index uid_align with
628 its uid to obtain the next following align that in turn increases the
629 alignment, till we reach NULL_RTX; the sequence obtained this way
630 for each insn we'll call the alignment chain of this insn in the following
631 comments. */
632
f5d927c0
KH
633struct label_alignment
634{
9e423e6d
JW
635 short alignment;
636 short max_skip;
637};
638
639static rtx *uid_align;
640static int *uid_shuid;
641static struct label_alignment *label_align;
95707627 642
3cf2715d
DE
643/* Indicate that branch shortening hasn't yet been done. */
644
645void
646init_insn_lengths ()
647{
95707627
R
648 if (uid_shuid)
649 {
650 free (uid_shuid);
651 uid_shuid = 0;
652 }
653 if (insn_lengths)
654 {
655 free (insn_lengths);
656 insn_lengths = 0;
ea3cbda5 657 insn_lengths_max_uid = 0;
95707627 658 }
9d98a694
AO
659#ifdef HAVE_ATTR_length
660 INSN_ADDRESSES_FREE ();
661#endif
95707627
R
662 if (uid_align)
663 {
664 free (uid_align);
665 uid_align = 0;
666 }
3cf2715d
DE
667}
668
669/* Obtain the current length of an insn. If branch shortening has been done,
670 get its actual length. Otherwise, get its maximum length. */
671
672int
673get_attr_length (insn)
7bdb32b9 674 rtx insn ATTRIBUTE_UNUSED;
3cf2715d
DE
675{
676#ifdef HAVE_ATTR_length
677 rtx body;
678 int i;
679 int length = 0;
680
ea3cbda5 681 if (insn_lengths_max_uid > INSN_UID (insn))
3cf2715d
DE
682 return insn_lengths[INSN_UID (insn)];
683 else
684 switch (GET_CODE (insn))
685 {
686 case NOTE:
687 case BARRIER:
688 case CODE_LABEL:
689 return 0;
690
691 case CALL_INSN:
692 length = insn_default_length (insn);
693 break;
694
695 case JUMP_INSN:
696 body = PATTERN (insn);
697 if (GET_CODE (body) == ADDR_VEC || GET_CODE (body) == ADDR_DIFF_VEC)
698 {
fc470718
R
699 /* Alignment is machine-dependent and should be handled by
700 ADDR_VEC_ALIGN. */
3cf2715d
DE
701 }
702 else
703 length = insn_default_length (insn);
704 break;
705
706 case INSN:
707 body = PATTERN (insn);
708 if (GET_CODE (body) == USE || GET_CODE (body) == CLOBBER)
709 return 0;
710
711 else if (GET_CODE (body) == ASM_INPUT || asm_noperands (body) >= 0)
712 length = asm_insn_count (body) * insn_default_length (insn);
713 else if (GET_CODE (body) == SEQUENCE)
714 for (i = 0; i < XVECLEN (body, 0); i++)
715 length += get_attr_length (XVECEXP (body, 0, i));
716 else
717 length = insn_default_length (insn);
e9a25f70
JL
718 break;
719
720 default:
721 break;
3cf2715d
DE
722 }
723
724#ifdef ADJUST_INSN_LENGTH
725 ADJUST_INSN_LENGTH (insn, length);
726#endif
727 return length;
728#else /* not HAVE_ATTR_length */
729 return 0;
730#endif /* not HAVE_ATTR_length */
731}
732\f
fc470718
R
733/* Code to handle alignment inside shorten_branches. */
734
735/* Here is an explanation how the algorithm in align_fuzz can give
736 proper results:
737
738 Call a sequence of instructions beginning with alignment point X
739 and continuing until the next alignment point `block X'. When `X'
f5d927c0 740 is used in an expression, it means the alignment value of the
fc470718 741 alignment point.
f5d927c0 742
fc470718
R
743 Call the distance between the start of the first insn of block X, and
744 the end of the last insn of block X `IX', for the `inner size of X'.
745 This is clearly the sum of the instruction lengths.
f5d927c0 746
fc470718
R
747 Likewise with the next alignment-delimited block following X, which we
748 shall call block Y.
f5d927c0 749
fc470718
R
750 Call the distance between the start of the first insn of block X, and
751 the start of the first insn of block Y `OX', for the `outer size of X'.
f5d927c0 752
fc470718 753 The estimated padding is then OX - IX.
f5d927c0 754
fc470718 755 OX can be safely estimated as
f5d927c0 756
fc470718
R
757 if (X >= Y)
758 OX = round_up(IX, Y)
759 else
760 OX = round_up(IX, X) + Y - X
f5d927c0 761
fc470718
R
762 Clearly est(IX) >= real(IX), because that only depends on the
763 instruction lengths, and those being overestimated is a given.
f5d927c0 764
fc470718
R
765 Clearly round_up(foo, Z) >= round_up(bar, Z) if foo >= bar, so
766 we needn't worry about that when thinking about OX.
f5d927c0 767
fc470718
R
768 When X >= Y, the alignment provided by Y adds no uncertainty factor
769 for branch ranges starting before X, so we can just round what we have.
770 But when X < Y, we don't know anything about the, so to speak,
771 `middle bits', so we have to assume the worst when aligning up from an
772 address mod X to one mod Y, which is Y - X. */
773
774#ifndef LABEL_ALIGN
efa3896a 775#define LABEL_ALIGN(LABEL) align_labels_log
fc470718
R
776#endif
777
9e423e6d 778#ifndef LABEL_ALIGN_MAX_SKIP
2cca7283 779#define LABEL_ALIGN_MAX_SKIP align_labels_max_skip
9e423e6d
JW
780#endif
781
fc470718 782#ifndef LOOP_ALIGN
efa3896a 783#define LOOP_ALIGN(LABEL) align_loops_log
fc470718
R
784#endif
785
9e423e6d 786#ifndef LOOP_ALIGN_MAX_SKIP
2cca7283 787#define LOOP_ALIGN_MAX_SKIP align_loops_max_skip
9e423e6d
JW
788#endif
789
fc470718 790#ifndef LABEL_ALIGN_AFTER_BARRIER
340f7e7c 791#define LABEL_ALIGN_AFTER_BARRIER(LABEL) 0
fc470718
R
792#endif
793
9e423e6d 794#ifndef LABEL_ALIGN_AFTER_BARRIER_MAX_SKIP
247a370b
JH
795#define LABEL_ALIGN_AFTER_BARRIER_MAX_SKIP 0
796#endif
797
798#ifndef JUMP_ALIGN
799#define JUMP_ALIGN(LABEL) align_jumps_log
800#endif
801
802#ifndef JUMP_ALIGN_MAX_SKIP
2cca7283 803#define JUMP_ALIGN_MAX_SKIP align_jumps_max_skip
9e423e6d
JW
804#endif
805
fc470718 806#ifndef ADDR_VEC_ALIGN
ca3075bd 807static int
fc470718
R
808final_addr_vec_align (addr_vec)
809 rtx addr_vec;
810{
2a841588 811 int align = GET_MODE_SIZE (GET_MODE (PATTERN (addr_vec)));
fc470718
R
812
813 if (align > BIGGEST_ALIGNMENT / BITS_PER_UNIT)
814 align = BIGGEST_ALIGNMENT / BITS_PER_UNIT;
2a841588 815 return exact_log2 (align);
fc470718
R
816
817}
f5d927c0 818
fc470718
R
819#define ADDR_VEC_ALIGN(ADDR_VEC) final_addr_vec_align (ADDR_VEC)
820#endif
821
822#ifndef INSN_LENGTH_ALIGNMENT
823#define INSN_LENGTH_ALIGNMENT(INSN) length_unit_log
824#endif
825
fc470718
R
826#define INSN_SHUID(INSN) (uid_shuid[INSN_UID (INSN)])
827
de7987a6 828static int min_labelno, max_labelno;
fc470718
R
829
830#define LABEL_TO_ALIGNMENT(LABEL) \
9e423e6d
JW
831 (label_align[CODE_LABEL_NUMBER (LABEL) - min_labelno].alignment)
832
833#define LABEL_TO_MAX_SKIP(LABEL) \
834 (label_align[CODE_LABEL_NUMBER (LABEL) - min_labelno].max_skip)
fc470718
R
835
836/* For the benefit of port specific code do this also as a function. */
f5d927c0 837
fc470718
R
838int
839label_to_alignment (label)
840 rtx label;
841{
842 return LABEL_TO_ALIGNMENT (label);
843}
844
845#ifdef HAVE_ATTR_length
846/* The differences in addresses
847 between a branch and its target might grow or shrink depending on
848 the alignment the start insn of the range (the branch for a forward
849 branch or the label for a backward branch) starts out on; if these
850 differences are used naively, they can even oscillate infinitely.
851 We therefore want to compute a 'worst case' address difference that
852 is independent of the alignment the start insn of the range end
853 up on, and that is at least as large as the actual difference.
854 The function align_fuzz calculates the amount we have to add to the
855 naively computed difference, by traversing the part of the alignment
856 chain of the start insn of the range that is in front of the end insn
857 of the range, and considering for each alignment the maximum amount
858 that it might contribute to a size increase.
859
860 For casesi tables, we also want to know worst case minimum amounts of
861 address difference, in case a machine description wants to introduce
862 some common offset that is added to all offsets in a table.
863 For this purpose, align_fuzz with a growth argument of 0 comuptes the
864 appropriate adjustment. */
865
fc470718
R
866/* Compute the maximum delta by which the difference of the addresses of
867 START and END might grow / shrink due to a different address for start
868 which changes the size of alignment insns between START and END.
869 KNOWN_ALIGN_LOG is the alignment known for START.
870 GROWTH should be ~0 if the objective is to compute potential code size
871 increase, and 0 if the objective is to compute potential shrink.
872 The return value is undefined for any other value of GROWTH. */
f5d927c0 873
ca3075bd 874static int
687d0ab6 875align_fuzz (start, end, known_align_log, growth)
fc470718
R
876 rtx start, end;
877 int known_align_log;
878 unsigned growth;
879{
880 int uid = INSN_UID (start);
881 rtx align_label;
882 int known_align = 1 << known_align_log;
883 int end_shuid = INSN_SHUID (end);
884 int fuzz = 0;
885
886 for (align_label = uid_align[uid]; align_label; align_label = uid_align[uid])
887 {
888 int align_addr, new_align;
889
890 uid = INSN_UID (align_label);
9d98a694 891 align_addr = INSN_ADDRESSES (uid) - insn_lengths[uid];
fc470718
R
892 if (uid_shuid[uid] > end_shuid)
893 break;
894 known_align_log = LABEL_TO_ALIGNMENT (align_label);
895 new_align = 1 << known_align_log;
896 if (new_align < known_align)
897 continue;
898 fuzz += (-align_addr ^ growth) & (new_align - known_align);
899 known_align = new_align;
900 }
901 return fuzz;
902}
903
904/* Compute a worst-case reference address of a branch so that it
905 can be safely used in the presence of aligned labels. Since the
906 size of the branch itself is unknown, the size of the branch is
907 not included in the range. I.e. for a forward branch, the reference
908 address is the end address of the branch as known from the previous
909 branch shortening pass, minus a value to account for possible size
910 increase due to alignment. For a backward branch, it is the start
911 address of the branch as known from the current pass, plus a value
912 to account for possible size increase due to alignment.
913 NB.: Therefore, the maximum offset allowed for backward branches needs
914 to exclude the branch size. */
f5d927c0 915
fc470718
R
916int
917insn_current_reference_address (branch)
918 rtx branch;
919{
5527bf14
RH
920 rtx dest, seq;
921 int seq_uid;
922
923 if (! INSN_ADDRESSES_SET_P ())
924 return 0;
925
926 seq = NEXT_INSN (PREV_INSN (branch));
927 seq_uid = INSN_UID (seq);
fc470718
R
928 if (GET_CODE (branch) != JUMP_INSN)
929 /* This can happen for example on the PA; the objective is to know the
930 offset to address something in front of the start of the function.
931 Thus, we can treat it like a backward branch.
932 We assume here that FUNCTION_BOUNDARY / BITS_PER_UNIT is larger than
933 any alignment we'd encounter, so we skip the call to align_fuzz. */
934 return insn_current_address;
935 dest = JUMP_LABEL (branch);
5527bf14 936
b9f22704 937 /* BRANCH has no proper alignment chain set, so use SEQ.
afc6898e
BS
938 BRANCH also has no INSN_SHUID. */
939 if (INSN_SHUID (seq) < INSN_SHUID (dest))
fc470718 940 {
f5d927c0 941 /* Forward branch. */
fc470718 942 return (insn_last_address + insn_lengths[seq_uid]
26024475 943 - align_fuzz (seq, dest, length_unit_log, ~0));
fc470718
R
944 }
945 else
946 {
f5d927c0 947 /* Backward branch. */
fc470718 948 return (insn_current_address
923f7cf9 949 + align_fuzz (dest, seq, length_unit_log, ~0));
fc470718
R
950 }
951}
952#endif /* HAVE_ATTR_length */
953\f
247a370b
JH
954void
955compute_alignments ()
956{
957 int i;
958 int log, max_skip, max_log;
959
960 if (label_align)
961 {
962 free (label_align);
963 label_align = 0;
964 }
965
966 max_labelno = max_label_num ();
967 min_labelno = get_first_label_num ();
968 label_align = (struct label_alignment *)
969 xcalloc (max_labelno - min_labelno + 1, sizeof (struct label_alignment));
970
971 /* If not optimizing or optimizing for size, don't assign any alignments. */
ba712955 972 if (! optimize || optimize_size)
247a370b
JH
973 return;
974
975 for (i = 0; i < n_basic_blocks; i++)
976 {
977 basic_block bb = BASIC_BLOCK (i);
978 rtx label = bb->head;
979 int fallthru_frequency = 0, branch_frequency = 0, has_fallthru = 0;
980 edge e;
981
982 if (GET_CODE (label) != CODE_LABEL)
983 continue;
984 max_log = LABEL_ALIGN (label);
985 max_skip = LABEL_ALIGN_MAX_SKIP;
986
987 for (e = bb->pred; e; e = e->pred_next)
988 {
989 if (e->flags & EDGE_FALLTHRU)
990 has_fallthru = 1, fallthru_frequency += EDGE_FREQUENCY (e);
991 else
992 branch_frequency += EDGE_FREQUENCY (e);
993 }
994
f63d1bf7 995 /* There are two purposes to align block with no fallthru incoming edge:
247a370b
JH
996 1) to avoid fetch stalls when branch destination is near cache boundary
997 2) to improve cache effciency in case the previous block is not executed
998 (so it does not need to be in the cache).
999
1000 We to catch first case, we align frequently executed blocks.
1001 To catch the second, we align blocks that are executed more frequently
eaec9b3d 1002 than the predecessor and the predecessor is likely to not be executed
247a370b
JH
1003 when function is called. */
1004
1005 if (!has_fallthru
1006 && (branch_frequency > BB_FREQ_MAX / 10
1007 || (bb->frequency > BASIC_BLOCK (i - 1)->frequency * 10
1008 && (BASIC_BLOCK (i - 1)->frequency
1009 <= ENTRY_BLOCK_PTR->frequency / 2))))
1010 {
1011 log = JUMP_ALIGN (label);
1012 if (max_log < log)
1013 {
1014 max_log = log;
1015 max_skip = JUMP_ALIGN_MAX_SKIP;
1016 }
1017 }
1018 /* In case block is frequent and reached mostly by non-fallthru edge,
1019 align it. It is most likely an first block of loop. */
1020 if (has_fallthru
1021 && branch_frequency + fallthru_frequency > BB_FREQ_MAX / 10
1022 && branch_frequency > fallthru_frequency * 5)
1023 {
1024 log = LOOP_ALIGN (label);
1025 if (max_log < log)
1026 {
1027 max_log = log;
1028 max_skip = LOOP_ALIGN_MAX_SKIP;
1029 }
1030 }
1031 LABEL_TO_ALIGNMENT (label) = max_log;
1032 LABEL_TO_MAX_SKIP (label) = max_skip;
1033 }
1034}
1035\f
3cf2715d
DE
1036/* Make a pass over all insns and compute their actual lengths by shortening
1037 any branches of variable length if possible. */
1038
1039/* Give a default value for the lowest address in a function. */
1040
1041#ifndef FIRST_INSN_ADDRESS
1042#define FIRST_INSN_ADDRESS 0
1043#endif
1044
fc470718
R
1045/* shorten_branches might be called multiple times: for example, the SH
1046 port splits out-of-range conditional branches in MACHINE_DEPENDENT_REORG.
1047 In order to do this, it needs proper length information, which it obtains
1048 by calling shorten_branches. This cannot be collapsed with
1049 shorten_branches itself into a single pass unless we also want to intergate
1050 reorg.c, since the branch splitting exposes new instructions with delay
1051 slots. */
1052
3cf2715d
DE
1053void
1054shorten_branches (first)
7bdb32b9 1055 rtx first ATTRIBUTE_UNUSED;
3cf2715d 1056{
3cf2715d 1057 rtx insn;
fc470718
R
1058 int max_uid;
1059 int i;
fc470718 1060 int max_log;
9e423e6d 1061 int max_skip;
fc470718
R
1062#ifdef HAVE_ATTR_length
1063#define MAX_CODE_ALIGN 16
1064 rtx seq;
3cf2715d 1065 int something_changed = 1;
3cf2715d
DE
1066 char *varying_length;
1067 rtx body;
1068 int uid;
fc470718 1069 rtx align_tab[MAX_CODE_ALIGN];
3cf2715d 1070
fc470718 1071#endif
3d14e82f 1072
3446405d
JH
1073 /* Compute maximum UID and allocate label_align / uid_shuid. */
1074 max_uid = get_max_uid ();
d9b6874b 1075
3446405d 1076 uid_shuid = (int *) xmalloc (max_uid * sizeof *uid_shuid);
25e22dc0 1077
247a370b
JH
1078 if (max_labelno != max_label_num ())
1079 {
1080 int old = max_labelno;
1081 int n_labels;
1082 int n_old_labels;
1083
1084 max_labelno = max_label_num ();
1085
1086 n_labels = max_labelno - min_labelno + 1;
1087 n_old_labels = old - min_labelno + 1;
1088
1089 label_align = (struct label_alignment *) xrealloc
1090 (label_align, n_labels * sizeof (struct label_alignment));
1091
1092 /* Range of labels grows monotonically in the function. Abort here
1093 means that the initialization of array got lost. */
1094 if (n_old_labels > n_labels)
1095 abort ();
1096
1097 memset (label_align + n_old_labels, 0,
1098 (n_labels - n_old_labels) * sizeof (struct label_alignment));
1099 }
1100
fc470718
R
1101 /* Initialize label_align and set up uid_shuid to be strictly
1102 monotonically rising with insn order. */
e2faec75
R
1103 /* We use max_log here to keep track of the maximum alignment we want to
1104 impose on the next CODE_LABEL (or the current one if we are processing
1105 the CODE_LABEL itself). */
f5d927c0 1106
9e423e6d
JW
1107 max_log = 0;
1108 max_skip = 0;
1109
1110 for (insn = get_insns (), i = 1; insn; insn = NEXT_INSN (insn))
fc470718
R
1111 {
1112 int log;
1113
1114 INSN_SHUID (insn) = i++;
2c3c49de 1115 if (INSN_P (insn))
e2faec75
R
1116 {
1117 /* reorg might make the first insn of a loop being run once only,
1118 and delete the label in front of it. Then we want to apply
1119 the loop alignment to the new label created by reorg, which
1120 is separated by the former loop start insn from the
1121 NOTE_INSN_LOOP_BEG. */
1122 }
fc470718
R
1123 else if (GET_CODE (insn) == CODE_LABEL)
1124 {
1125 rtx next;
247a370b
JH
1126
1127 /* Merge in alignments computed by compute_alignments. */
1128 log = LABEL_TO_ALIGNMENT (insn);
1129 if (max_log < log)
1130 {
1131 max_log = log;
1132 max_skip = LABEL_TO_MAX_SKIP (insn);
1133 }
fc470718
R
1134
1135 log = LABEL_ALIGN (insn);
1136 if (max_log < log)
9e423e6d
JW
1137 {
1138 max_log = log;
1139 max_skip = LABEL_ALIGN_MAX_SKIP;
1140 }
fc470718 1141 next = NEXT_INSN (insn);
75197b37
BS
1142 /* ADDR_VECs only take room if read-only data goes into the text
1143 section. */
1144 if (JUMP_TABLES_IN_TEXT_SECTION
1145#if !defined(READONLY_DATA_SECTION)
1146 || 1
fc470718 1147#endif
75197b37
BS
1148 )
1149 if (next && GET_CODE (next) == JUMP_INSN)
1150 {
1151 rtx nextbody = PATTERN (next);
1152 if (GET_CODE (nextbody) == ADDR_VEC
1153 || GET_CODE (nextbody) == ADDR_DIFF_VEC)
1154 {
1155 log = ADDR_VEC_ALIGN (next);
1156 if (max_log < log)
1157 {
1158 max_log = log;
1159 max_skip = LABEL_ALIGN_MAX_SKIP;
1160 }
1161 }
1162 }
fc470718 1163 LABEL_TO_ALIGNMENT (insn) = max_log;
9e423e6d 1164 LABEL_TO_MAX_SKIP (insn) = max_skip;
fc470718 1165 max_log = 0;
9e423e6d 1166 max_skip = 0;
fc470718
R
1167 }
1168 else if (GET_CODE (insn) == BARRIER)
1169 {
1170 rtx label;
1171
2c3c49de 1172 for (label = insn; label && ! INSN_P (label);
fc470718
R
1173 label = NEXT_INSN (label))
1174 if (GET_CODE (label) == CODE_LABEL)
1175 {
1176 log = LABEL_ALIGN_AFTER_BARRIER (insn);
1177 if (max_log < log)
9e423e6d
JW
1178 {
1179 max_log = log;
1180 max_skip = LABEL_ALIGN_AFTER_BARRIER_MAX_SKIP;
1181 }
fc470718
R
1182 break;
1183 }
1184 }
fc470718
R
1185 }
1186#ifdef HAVE_ATTR_length
1187
1188 /* Allocate the rest of the arrays. */
addd7df6 1189 insn_lengths = (int *) xmalloc (max_uid * sizeof (*insn_lengths));
ea3cbda5 1190 insn_lengths_max_uid = max_uid;
af035616
R
1191 /* Syntax errors can lead to labels being outside of the main insn stream.
1192 Initialize insn_addresses, so that we get reproducible results. */
9d98a694 1193 INSN_ADDRESSES_ALLOC (max_uid);
fc470718 1194
3de90026 1195 varying_length = (char *) xcalloc (max_uid, sizeof (char));
fc470718
R
1196
1197 /* Initialize uid_align. We scan instructions
1198 from end to start, and keep in align_tab[n] the last seen insn
1199 that does an alignment of at least n+1, i.e. the successor
1200 in the alignment chain for an insn that does / has a known
1201 alignment of n. */
3de90026 1202 uid_align = (rtx *) xcalloc (max_uid, sizeof *uid_align);
fc470718 1203
f5d927c0 1204 for (i = MAX_CODE_ALIGN; --i >= 0;)
fc470718
R
1205 align_tab[i] = NULL_RTX;
1206 seq = get_last_insn ();
33f7f353 1207 for (; seq; seq = PREV_INSN (seq))
fc470718
R
1208 {
1209 int uid = INSN_UID (seq);
1210 int log;
fc470718
R
1211 log = (GET_CODE (seq) == CODE_LABEL ? LABEL_TO_ALIGNMENT (seq) : 0);
1212 uid_align[uid] = align_tab[0];
fc470718
R
1213 if (log)
1214 {
1215 /* Found an alignment label. */
1216 uid_align[uid] = align_tab[log];
1217 for (i = log - 1; i >= 0; i--)
1218 align_tab[i] = seq;
1219 }
33f7f353
JR
1220 }
1221#ifdef CASE_VECTOR_SHORTEN_MODE
1222 if (optimize)
1223 {
1224 /* Look for ADDR_DIFF_VECs, and initialize their minimum and maximum
1225 label fields. */
1226
1227 int min_shuid = INSN_SHUID (get_insns ()) - 1;
1228 int max_shuid = INSN_SHUID (get_last_insn ()) + 1;
1229 int rel;
1230
1231 for (insn = first; insn != 0; insn = NEXT_INSN (insn))
fc470718 1232 {
33f7f353
JR
1233 rtx min_lab = NULL_RTX, max_lab = NULL_RTX, pat;
1234 int len, i, min, max, insn_shuid;
1235 int min_align;
1236 addr_diff_vec_flags flags;
1237
1238 if (GET_CODE (insn) != JUMP_INSN
1239 || GET_CODE (PATTERN (insn)) != ADDR_DIFF_VEC)
1240 continue;
1241 pat = PATTERN (insn);
1242 len = XVECLEN (pat, 1);
1243 if (len <= 0)
1244 abort ();
1245 min_align = MAX_CODE_ALIGN;
1246 for (min = max_shuid, max = min_shuid, i = len - 1; i >= 0; i--)
1247 {
1248 rtx lab = XEXP (XVECEXP (pat, 1, i), 0);
1249 int shuid = INSN_SHUID (lab);
1250 if (shuid < min)
1251 {
1252 min = shuid;
1253 min_lab = lab;
1254 }
1255 if (shuid > max)
1256 {
1257 max = shuid;
1258 max_lab = lab;
1259 }
1260 if (min_align > LABEL_TO_ALIGNMENT (lab))
1261 min_align = LABEL_TO_ALIGNMENT (lab);
1262 }
1263 XEXP (pat, 2) = gen_rtx_LABEL_REF (VOIDmode, min_lab);
1264 XEXP (pat, 3) = gen_rtx_LABEL_REF (VOIDmode, max_lab);
1265 insn_shuid = INSN_SHUID (insn);
1266 rel = INSN_SHUID (XEXP (XEXP (pat, 0), 0));
1267 flags.min_align = min_align;
1268 flags.base_after_vec = rel > insn_shuid;
1269 flags.min_after_vec = min > insn_shuid;
1270 flags.max_after_vec = max > insn_shuid;
1271 flags.min_after_base = min > rel;
1272 flags.max_after_base = max > rel;
1273 ADDR_DIFF_VEC_FLAGS (pat) = flags;
fc470718
R
1274 }
1275 }
33f7f353 1276#endif /* CASE_VECTOR_SHORTEN_MODE */
3cf2715d 1277
3cf2715d
DE
1278 /* Compute initial lengths, addresses, and varying flags for each insn. */
1279 for (insn_current_address = FIRST_INSN_ADDRESS, insn = first;
1280 insn != 0;
1281 insn_current_address += insn_lengths[uid], insn = NEXT_INSN (insn))
1282 {
1283 uid = INSN_UID (insn);
fc470718 1284
3cf2715d 1285 insn_lengths[uid] = 0;
fc470718
R
1286
1287 if (GET_CODE (insn) == CODE_LABEL)
1288 {
1289 int log = LABEL_TO_ALIGNMENT (insn);
1290 if (log)
1291 {
1292 int align = 1 << log;
ecb06768 1293 int new_address = (insn_current_address + align - 1) & -align;
fc470718 1294 insn_lengths[uid] = new_address - insn_current_address;
fc470718
R
1295 }
1296 }
1297
9d98a694 1298 INSN_ADDRESSES (uid) = insn_current_address;
f5d927c0 1299
3cf2715d
DE
1300 if (GET_CODE (insn) == NOTE || GET_CODE (insn) == BARRIER
1301 || GET_CODE (insn) == CODE_LABEL)
1302 continue;
04da53bd
R
1303 if (INSN_DELETED_P (insn))
1304 continue;
3cf2715d
DE
1305
1306 body = PATTERN (insn);
1307 if (GET_CODE (body) == ADDR_VEC || GET_CODE (body) == ADDR_DIFF_VEC)
5a32a90c
JR
1308 {
1309 /* This only takes room if read-only data goes into the text
1310 section. */
75197b37
BS
1311 if (JUMP_TABLES_IN_TEXT_SECTION
1312#if !defined(READONLY_DATA_SECTION)
1313 || 1
1314#endif
1315 )
1316 insn_lengths[uid] = (XVECLEN (body,
1317 GET_CODE (body) == ADDR_DIFF_VEC)
1318 * GET_MODE_SIZE (GET_MODE (body)));
5a32a90c 1319 /* Alignment is handled by ADDR_VEC_ALIGN. */
5a32a90c 1320 }
a30caf5c 1321 else if (GET_CODE (body) == ASM_INPUT || asm_noperands (body) >= 0)
3cf2715d
DE
1322 insn_lengths[uid] = asm_insn_count (body) * insn_default_length (insn);
1323 else if (GET_CODE (body) == SEQUENCE)
1324 {
1325 int i;
1326 int const_delay_slots;
1327#ifdef DELAY_SLOTS
1328 const_delay_slots = const_num_delay_slots (XVECEXP (body, 0, 0));
1329#else
1330 const_delay_slots = 0;
1331#endif
1332 /* Inside a delay slot sequence, we do not do any branch shortening
1333 if the shortening could change the number of delay slots
0f41302f 1334 of the branch. */
3cf2715d
DE
1335 for (i = 0; i < XVECLEN (body, 0); i++)
1336 {
1337 rtx inner_insn = XVECEXP (body, 0, i);
1338 int inner_uid = INSN_UID (inner_insn);
1339 int inner_length;
1340
a30caf5c
DC
1341 if (GET_CODE (body) == ASM_INPUT
1342 || asm_noperands (PATTERN (XVECEXP (body, 0, i))) >= 0)
3cf2715d
DE
1343 inner_length = (asm_insn_count (PATTERN (inner_insn))
1344 * insn_default_length (inner_insn));
1345 else
1346 inner_length = insn_default_length (inner_insn);
f5d927c0 1347
3cf2715d
DE
1348 insn_lengths[inner_uid] = inner_length;
1349 if (const_delay_slots)
1350 {
1351 if ((varying_length[inner_uid]
1352 = insn_variable_length_p (inner_insn)) != 0)
1353 varying_length[uid] = 1;
9d98a694
AO
1354 INSN_ADDRESSES (inner_uid) = (insn_current_address
1355 + insn_lengths[uid]);
3cf2715d
DE
1356 }
1357 else
1358 varying_length[inner_uid] = 0;
1359 insn_lengths[uid] += inner_length;
1360 }
1361 }
1362 else if (GET_CODE (body) != USE && GET_CODE (body) != CLOBBER)
1363 {
1364 insn_lengths[uid] = insn_default_length (insn);
1365 varying_length[uid] = insn_variable_length_p (insn);
1366 }
1367
1368 /* If needed, do any adjustment. */
1369#ifdef ADJUST_INSN_LENGTH
1370 ADJUST_INSN_LENGTH (insn, insn_lengths[uid]);
04b6000c
VM
1371 if (insn_lengths[uid] < 0)
1372 fatal_insn ("Negative insn length", insn);
3cf2715d
DE
1373#endif
1374 }
1375
1376 /* Now loop over all the insns finding varying length insns. For each,
1377 get the current insn length. If it has changed, reflect the change.
1378 When nothing changes for a full pass, we are done. */
1379
1380 while (something_changed)
1381 {
1382 something_changed = 0;
fc470718 1383 insn_current_align = MAX_CODE_ALIGN - 1;
3cf2715d
DE
1384 for (insn_current_address = FIRST_INSN_ADDRESS, insn = first;
1385 insn != 0;
1386 insn = NEXT_INSN (insn))
1387 {
1388 int new_length;
b729186a 1389#ifdef ADJUST_INSN_LENGTH
3cf2715d 1390 int tmp_length;
b729186a 1391#endif
fc470718 1392 int length_align;
3cf2715d
DE
1393
1394 uid = INSN_UID (insn);
fc470718
R
1395
1396 if (GET_CODE (insn) == CODE_LABEL)
1397 {
1398 int log = LABEL_TO_ALIGNMENT (insn);
1399 if (log > insn_current_align)
1400 {
1401 int align = 1 << log;
ecb06768 1402 int new_address= (insn_current_address + align - 1) & -align;
fc470718
R
1403 insn_lengths[uid] = new_address - insn_current_address;
1404 insn_current_align = log;
1405 insn_current_address = new_address;
1406 }
1407 else
1408 insn_lengths[uid] = 0;
9d98a694 1409 INSN_ADDRESSES (uid) = insn_current_address;
fc470718
R
1410 continue;
1411 }
1412
1413 length_align = INSN_LENGTH_ALIGNMENT (insn);
1414 if (length_align < insn_current_align)
1415 insn_current_align = length_align;
1416
9d98a694
AO
1417 insn_last_address = INSN_ADDRESSES (uid);
1418 INSN_ADDRESSES (uid) = insn_current_address;
fc470718 1419
5e75ef4a 1420#ifdef CASE_VECTOR_SHORTEN_MODE
33f7f353
JR
1421 if (optimize && GET_CODE (insn) == JUMP_INSN
1422 && GET_CODE (PATTERN (insn)) == ADDR_DIFF_VEC)
1423 {
33f7f353
JR
1424 rtx body = PATTERN (insn);
1425 int old_length = insn_lengths[uid];
1426 rtx rel_lab = XEXP (XEXP (body, 0), 0);
1427 rtx min_lab = XEXP (XEXP (body, 2), 0);
1428 rtx max_lab = XEXP (XEXP (body, 3), 0);
9d98a694
AO
1429 int rel_addr = INSN_ADDRESSES (INSN_UID (rel_lab));
1430 int min_addr = INSN_ADDRESSES (INSN_UID (min_lab));
1431 int max_addr = INSN_ADDRESSES (INSN_UID (max_lab));
33f7f353
JR
1432 rtx prev;
1433 int rel_align = 0;
950a3816
KG
1434 addr_diff_vec_flags flags;
1435
1436 /* Avoid automatic aggregate initialization. */
1437 flags = ADDR_DIFF_VEC_FLAGS (body);
33f7f353
JR
1438
1439 /* Try to find a known alignment for rel_lab. */
1440 for (prev = rel_lab;
1441 prev
1442 && ! insn_lengths[INSN_UID (prev)]
1443 && ! (varying_length[INSN_UID (prev)] & 1);
1444 prev = PREV_INSN (prev))
1445 if (varying_length[INSN_UID (prev)] & 2)
1446 {
1447 rel_align = LABEL_TO_ALIGNMENT (prev);
1448 break;
1449 }
1450
1451 /* See the comment on addr_diff_vec_flags in rtl.h for the
1452 meaning of the flags values. base: REL_LAB vec: INSN */
1453 /* Anything after INSN has still addresses from the last
1454 pass; adjust these so that they reflect our current
1455 estimate for this pass. */
1456 if (flags.base_after_vec)
1457 rel_addr += insn_current_address - insn_last_address;
1458 if (flags.min_after_vec)
1459 min_addr += insn_current_address - insn_last_address;
1460 if (flags.max_after_vec)
1461 max_addr += insn_current_address - insn_last_address;
1462 /* We want to know the worst case, i.e. lowest possible value
1463 for the offset of MIN_LAB. If MIN_LAB is after REL_LAB,
1464 its offset is positive, and we have to be wary of code shrink;
1465 otherwise, it is negative, and we have to be vary of code
1466 size increase. */
1467 if (flags.min_after_base)
1468 {
1469 /* If INSN is between REL_LAB and MIN_LAB, the size
1470 changes we are about to make can change the alignment
1471 within the observed offset, therefore we have to break
1472 it up into two parts that are independent. */
1473 if (! flags.base_after_vec && flags.min_after_vec)
1474 {
1475 min_addr -= align_fuzz (rel_lab, insn, rel_align, 0);
1476 min_addr -= align_fuzz (insn, min_lab, 0, 0);
1477 }
1478 else
1479 min_addr -= align_fuzz (rel_lab, min_lab, rel_align, 0);
1480 }
1481 else
1482 {
1483 if (flags.base_after_vec && ! flags.min_after_vec)
1484 {
1485 min_addr -= align_fuzz (min_lab, insn, 0, ~0);
1486 min_addr -= align_fuzz (insn, rel_lab, 0, ~0);
1487 }
1488 else
1489 min_addr -= align_fuzz (min_lab, rel_lab, 0, ~0);
1490 }
1491 /* Likewise, determine the highest lowest possible value
1492 for the offset of MAX_LAB. */
1493 if (flags.max_after_base)
1494 {
1495 if (! flags.base_after_vec && flags.max_after_vec)
1496 {
1497 max_addr += align_fuzz (rel_lab, insn, rel_align, ~0);
1498 max_addr += align_fuzz (insn, max_lab, 0, ~0);
1499 }
1500 else
1501 max_addr += align_fuzz (rel_lab, max_lab, rel_align, ~0);
1502 }
1503 else
1504 {
1505 if (flags.base_after_vec && ! flags.max_after_vec)
1506 {
1507 max_addr += align_fuzz (max_lab, insn, 0, 0);
1508 max_addr += align_fuzz (insn, rel_lab, 0, 0);
1509 }
1510 else
1511 max_addr += align_fuzz (max_lab, rel_lab, 0, 0);
1512 }
1513 PUT_MODE (body, CASE_VECTOR_SHORTEN_MODE (min_addr - rel_addr,
1514 max_addr - rel_addr,
1515 body));
75197b37
BS
1516 if (JUMP_TABLES_IN_TEXT_SECTION
1517#if !defined(READONLY_DATA_SECTION)
1518 || 1
33f7f353 1519#endif
75197b37
BS
1520 )
1521 {
1522 insn_lengths[uid]
1523 = (XVECLEN (body, 1) * GET_MODE_SIZE (GET_MODE (body)));
1524 insn_current_address += insn_lengths[uid];
1525 if (insn_lengths[uid] != old_length)
1526 something_changed = 1;
1527 }
1528
33f7f353 1529 continue;
33f7f353 1530 }
5e75ef4a
JL
1531#endif /* CASE_VECTOR_SHORTEN_MODE */
1532
1533 if (! (varying_length[uid]))
3cf2715d 1534 {
674fc07d
GS
1535 if (GET_CODE (insn) == INSN
1536 && GET_CODE (PATTERN (insn)) == SEQUENCE)
1537 {
1538 int i;
1539
1540 body = PATTERN (insn);
1541 for (i = 0; i < XVECLEN (body, 0); i++)
1542 {
1543 rtx inner_insn = XVECEXP (body, 0, i);
1544 int inner_uid = INSN_UID (inner_insn);
1545
1546 INSN_ADDRESSES (inner_uid) = insn_current_address;
1547
1548 insn_current_address += insn_lengths[inner_uid];
1549 }
1550 }
1551 else
1552 insn_current_address += insn_lengths[uid];
1553
3cf2715d
DE
1554 continue;
1555 }
674fc07d 1556
3cf2715d
DE
1557 if (GET_CODE (insn) == INSN && GET_CODE (PATTERN (insn)) == SEQUENCE)
1558 {
1559 int i;
f5d927c0 1560
3cf2715d
DE
1561 body = PATTERN (insn);
1562 new_length = 0;
1563 for (i = 0; i < XVECLEN (body, 0); i++)
1564 {
1565 rtx inner_insn = XVECEXP (body, 0, i);
1566 int inner_uid = INSN_UID (inner_insn);
1567 int inner_length;
1568
9d98a694 1569 INSN_ADDRESSES (inner_uid) = insn_current_address;
3cf2715d
DE
1570
1571 /* insn_current_length returns 0 for insns with a
1572 non-varying length. */
1573 if (! varying_length[inner_uid])
1574 inner_length = insn_lengths[inner_uid];
1575 else
1576 inner_length = insn_current_length (inner_insn);
1577
1578 if (inner_length != insn_lengths[inner_uid])
1579 {
1580 insn_lengths[inner_uid] = inner_length;
1581 something_changed = 1;
1582 }
1583 insn_current_address += insn_lengths[inner_uid];
1584 new_length += inner_length;
1585 }
1586 }
1587 else
1588 {
1589 new_length = insn_current_length (insn);
1590 insn_current_address += new_length;
1591 }
1592
3cf2715d
DE
1593#ifdef ADJUST_INSN_LENGTH
1594 /* If needed, do any adjustment. */
1595 tmp_length = new_length;
1596 ADJUST_INSN_LENGTH (insn, new_length);
1597 insn_current_address += (new_length - tmp_length);
3cf2715d
DE
1598#endif
1599
1600 if (new_length != insn_lengths[uid])
1601 {
1602 insn_lengths[uid] = new_length;
1603 something_changed = 1;
1604 }
1605 }
bb4aaf18
TG
1606 /* For a non-optimizing compile, do only a single pass. */
1607 if (!optimize)
1608 break;
3cf2715d 1609 }
fc470718
R
1610
1611 free (varying_length);
1612
3cf2715d
DE
1613#endif /* HAVE_ATTR_length */
1614}
1615
1616#ifdef HAVE_ATTR_length
1617/* Given the body of an INSN known to be generated by an ASM statement, return
1618 the number of machine instructions likely to be generated for this insn.
1619 This is used to compute its length. */
1620
1621static int
1622asm_insn_count (body)
1623 rtx body;
1624{
3cce094d 1625 const char *template;
3cf2715d
DE
1626 int count = 1;
1627
5d0930ea
DE
1628 if (GET_CODE (body) == ASM_INPUT)
1629 template = XSTR (body, 0);
1630 else
df4ae160 1631 template = decode_asm_operands (body, NULL, NULL, NULL, NULL);
5d0930ea 1632
f5d927c0
KH
1633 for (; *template; template++)
1634 if (IS_ASM_LOGICAL_LINE_SEPARATOR (*template) || *template == '\n')
3cf2715d
DE
1635 count++;
1636
1637 return count;
1638}
1639#endif
1640\f
1641/* Output assembler code for the start of a function,
1642 and initialize some of the variables in this file
1643 for the new function. The label for the function and associated
1644 assembler pseudo-ops have already been output in `assemble_start_function'.
1645
1646 FIRST is the first insn of the rtl for the function being compiled.
1647 FILE is the file to write assembler code to.
1648 OPTIMIZE is nonzero if we should eliminate redundant
1649 test and compare insns. */
1650
1651void
1652final_start_function (first, file, optimize)
1653 rtx first;
1654 FILE *file;
6a651371 1655 int optimize ATTRIBUTE_UNUSED;
3cf2715d
DE
1656{
1657 block_depth = 0;
1658
1659 this_is_asm_operands = 0;
1660
1661#ifdef NON_SAVING_SETJMP
1662 /* A function that calls setjmp should save and restore all the
1663 call-saved registers on a system where longjmp clobbers them. */
1664 if (NON_SAVING_SETJMP && current_function_calls_setjmp)
1665 {
1666 int i;
1667
1668 for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
252f342a 1669 if (!call_used_regs[i])
3cf2715d
DE
1670 regs_ever_live[i] = 1;
1671 }
1672#endif
f5d927c0 1673
3cf2715d 1674 if (NOTE_LINE_NUMBER (first) != NOTE_INSN_DELETED)
653e276c
NB
1675 notice_source_line (first);
1676 high_block_linenum = high_function_linenum = last_linenum;
eac40081 1677
653e276c 1678 (*debug_hooks->begin_prologue) (last_linenum, last_filename);
d291dd49 1679
653e276c 1680#if defined (DWARF2_UNWIND_INFO) || defined (IA64_UNWIND_INFO)
7a0c8d71 1681 if (write_symbols != DWARF2_DEBUG && write_symbols != VMS_AND_DWARF2_DEBUG)
653e276c 1682 dwarf2out_begin_prologue (0, NULL);
f5d927c0 1683#endif
3cf2715d
DE
1684
1685#ifdef LEAF_REG_REMAP
54ff41b7 1686 if (current_function_uses_only_leaf_regs)
3cf2715d
DE
1687 leaf_renumber_regs (first);
1688#endif
1689
1690 /* The Sun386i and perhaps other machines don't work right
1691 if the profiling code comes after the prologue. */
1692#ifdef PROFILE_BEFORE_PROLOGUE
1693 if (profile_flag)
1694 profile_function (file);
1695#endif /* PROFILE_BEFORE_PROLOGUE */
1696
0021b564
JM
1697#if defined (DWARF2_UNWIND_INFO) && defined (HAVE_prologue)
1698 if (dwarf2out_do_frame ())
1699 dwarf2out_frame_debug (NULL_RTX);
1700#endif
1701
18c038b9
MM
1702 /* If debugging, assign block numbers to all of the blocks in this
1703 function. */
1704 if (write_symbols)
1705 {
3ac79482 1706 remove_unnecessary_notes ();
a20612aa
RH
1707 reorder_blocks ();
1708 number_blocks (current_function_decl);
18c038b9
MM
1709 /* We never actually put out begin/end notes for the top-level
1710 block in the function. But, conceptually, that block is
1711 always needed. */
1712 TREE_ASM_WRITTEN (DECL_INITIAL (current_function_decl)) = 1;
1713 }
1714
3cf2715d 1715 /* First output the function prologue: code to set up the stack frame. */
f6897b10 1716 (*targetm.asm_out.function_prologue) (file, get_frame_size ());
3cf2715d 1717
7a0c8d71
DR
1718#ifdef VMS_DEBUGGING_INFO
1719 /* Output label after the prologue of the function. */
1720 if (write_symbols == VMS_DEBUG || write_symbols == VMS_AND_DWARF2_DEBUG)
1721 vmsdbgout_after_prologue ();
1722#endif
1723
3cf2715d
DE
1724 /* If the machine represents the prologue as RTL, the profiling code must
1725 be emitted when NOTE_INSN_PROLOGUE_END is scanned. */
1726#ifdef HAVE_prologue
1727 if (! HAVE_prologue)
1728#endif
1729 profile_after_prologue (file);
1730
1731 profile_label_no++;
1732
1733 /* If we are doing basic block profiling, remember a printable version
1734 of the function name. */
1735 if (profile_block_flag)
1736 {
f5d927c0
KH
1737 bb_func_label_num =
1738 add_bb_string ((*decl_printable_name) (current_function_decl, 2),
1739 FALSE);
3cf2715d
DE
1740 }
1741}
1742
1743static void
1744profile_after_prologue (file)
7bdb32b9 1745 FILE *file ATTRIBUTE_UNUSED;
3cf2715d
DE
1746{
1747#ifdef FUNCTION_BLOCK_PROFILER
1748 if (profile_block_flag)
1749 {
47431dff 1750 FUNCTION_BLOCK_PROFILER (file, count_basic_blocks);
3cf2715d
DE
1751 }
1752#endif /* FUNCTION_BLOCK_PROFILER */
1753
1754#ifndef PROFILE_BEFORE_PROLOGUE
1755 if (profile_flag)
1756 profile_function (file);
1757#endif /* not PROFILE_BEFORE_PROLOGUE */
1758}
1759
1760static void
1761profile_function (file)
1762 FILE *file;
1763{
dcacfa04 1764#ifndef NO_PROFILE_COUNTERS
9e2f9a7f 1765 int align = MIN (BIGGEST_ALIGNMENT, LONG_TYPE_SIZE);
dcacfa04 1766#endif
b729186a
JL
1767#if defined(ASM_OUTPUT_REG_PUSH)
1768#if defined(STRUCT_VALUE_INCOMING_REGNUM) || defined(STRUCT_VALUE_REGNUM)
3cf2715d 1769 int sval = current_function_returns_struct;
b729186a
JL
1770#endif
1771#if defined(STATIC_CHAIN_INCOMING_REGNUM) || defined(STATIC_CHAIN_REGNUM)
3cf2715d 1772 int cxt = current_function_needs_context;
b729186a
JL
1773#endif
1774#endif /* ASM_OUTPUT_REG_PUSH */
3cf2715d 1775
dcacfa04 1776#ifndef NO_PROFILE_COUNTERS
3cf2715d
DE
1777 data_section ();
1778 ASM_OUTPUT_ALIGN (file, floor_log2 (align / BITS_PER_UNIT));
1779 ASM_OUTPUT_INTERNAL_LABEL (file, "LP", profile_label_no);
c8af3574 1780 assemble_integer (const0_rtx, LONG_TYPE_SIZE / BITS_PER_UNIT, align, 1);
dcacfa04 1781#endif
3cf2715d 1782
499df339 1783 function_section (current_function_decl);
3cf2715d 1784
65ed39df 1785#if defined(STRUCT_VALUE_INCOMING_REGNUM) && defined(ASM_OUTPUT_REG_PUSH)
3cf2715d
DE
1786 if (sval)
1787 ASM_OUTPUT_REG_PUSH (file, STRUCT_VALUE_INCOMING_REGNUM);
1788#else
65ed39df 1789#if defined(STRUCT_VALUE_REGNUM) && defined(ASM_OUTPUT_REG_PUSH)
3cf2715d 1790 if (sval)
51723711
KG
1791 {
1792 ASM_OUTPUT_REG_PUSH (file, STRUCT_VALUE_REGNUM);
1793 }
3cf2715d
DE
1794#endif
1795#endif
1796
65ed39df 1797#if defined(STATIC_CHAIN_INCOMING_REGNUM) && defined(ASM_OUTPUT_REG_PUSH)
3cf2715d
DE
1798 if (cxt)
1799 ASM_OUTPUT_REG_PUSH (file, STATIC_CHAIN_INCOMING_REGNUM);
1800#else
65ed39df 1801#if defined(STATIC_CHAIN_REGNUM) && defined(ASM_OUTPUT_REG_PUSH)
3cf2715d 1802 if (cxt)
51723711
KG
1803 {
1804 ASM_OUTPUT_REG_PUSH (file, STATIC_CHAIN_REGNUM);
1805 }
3cf2715d
DE
1806#endif
1807#endif
3cf2715d
DE
1808
1809 FUNCTION_PROFILER (file, profile_label_no);
1810
65ed39df 1811#if defined(STATIC_CHAIN_INCOMING_REGNUM) && defined(ASM_OUTPUT_REG_PUSH)
3cf2715d
DE
1812 if (cxt)
1813 ASM_OUTPUT_REG_POP (file, STATIC_CHAIN_INCOMING_REGNUM);
1814#else
65ed39df 1815#if defined(STATIC_CHAIN_REGNUM) && defined(ASM_OUTPUT_REG_PUSH)
3cf2715d 1816 if (cxt)
51723711
KG
1817 {
1818 ASM_OUTPUT_REG_POP (file, STATIC_CHAIN_REGNUM);
1819 }
3cf2715d
DE
1820#endif
1821#endif
3cf2715d 1822
65ed39df 1823#if defined(STRUCT_VALUE_INCOMING_REGNUM) && defined(ASM_OUTPUT_REG_PUSH)
3cf2715d
DE
1824 if (sval)
1825 ASM_OUTPUT_REG_POP (file, STRUCT_VALUE_INCOMING_REGNUM);
1826#else
65ed39df 1827#if defined(STRUCT_VALUE_REGNUM) && defined(ASM_OUTPUT_REG_PUSH)
3cf2715d 1828 if (sval)
51723711
KG
1829 {
1830 ASM_OUTPUT_REG_POP (file, STRUCT_VALUE_REGNUM);
1831 }
3cf2715d
DE
1832#endif
1833#endif
1834}
1835
1836/* Output assembler code for the end of a function.
1837 For clarity, args are same as those of `final_start_function'
1838 even though not all of them are needed. */
1839
1840void
e2a12aca 1841final_end_function ()
3cf2715d 1842{
be1bb652 1843 app_disable ();
3cf2715d 1844
e2a12aca 1845 (*debug_hooks->end_function) (high_function_linenum);
3cf2715d 1846
3cf2715d
DE
1847 /* Finally, output the function epilogue:
1848 code to restore the stack frame and return to the caller. */
e2a12aca 1849 (*targetm.asm_out.function_epilogue) (asm_out_file, get_frame_size ());
3cf2715d 1850
e2a12aca
NB
1851 /* And debug output. */
1852 (*debug_hooks->end_epilogue) ();
3cf2715d 1853
e2a12aca 1854#if defined (DWARF2_UNWIND_INFO)
7a0c8d71
DR
1855 if (write_symbols != DWARF2_DEBUG && write_symbols != VMS_AND_DWARF2_DEBUG
1856 && dwarf2out_do_frame ())
9a666dda
JM
1857 dwarf2out_end_epilogue ();
1858#endif
1859
3cf2715d 1860 bb_func_label_num = -1; /* not in function, nuke label # */
3cf2715d
DE
1861}
1862\f
1863/* Add a block to the linked list that remembers the current line/file/function
1864 for basic block profiling. Emit the label in front of the basic block and
1865 the instructions that increment the count field. */
1866
1867static void
1868add_bb (file)
1869 FILE *file;
1870{
f5d927c0
KH
1871 struct bb_list *ptr =
1872 (struct bb_list *) permalloc (sizeof (struct bb_list));
3cf2715d
DE
1873
1874 /* Add basic block to linked list. */
1875 ptr->next = 0;
1876 ptr->line_num = last_linenum;
1877 ptr->file_label_num = bb_file_label_num;
1878 ptr->func_label_num = bb_func_label_num;
1879 *bb_tail = ptr;
1880 bb_tail = &ptr->next;
1881
1882 /* Enable the table of basic-block use counts
1883 to point at the code it applies to. */
1884 ASM_OUTPUT_INTERNAL_LABEL (file, "LPB", count_basic_blocks);
1885
1886 /* Before first insn of this basic block, increment the
1887 count of times it was entered. */
1888#ifdef BLOCK_PROFILER
1889 BLOCK_PROFILER (file, count_basic_blocks);
9e2f9a7f
DE
1890#endif
1891#ifdef HAVE_cc0
3cf2715d
DE
1892 CC_STATUS_INIT;
1893#endif
1894
1895 new_block = 0;
1896 count_basic_blocks++;
1897}
1898
1899/* Add a string to be used for basic block profiling. */
1900
1901static int
1902add_bb_string (string, perm_p)
9b3142b3 1903 const char *string;
3cf2715d
DE
1904 int perm_p;
1905{
1906 int len;
1907 struct bb_str *ptr = 0;
1908
1909 if (!string)
1910 {
1911 string = "<unknown>";
1912 perm_p = TRUE;
1913 }
1914
1915 /* Allocate a new string if the current string isn't permanent. If
1916 the string is permanent search for the same string in other
1917 allocations. */
1918
1919 len = strlen (string) + 1;
1920 if (!perm_p)
1921 {
1922 char *p = (char *) permalloc (len);
4e135bdd 1923 memcpy (p, string, len);
3cf2715d
DE
1924 string = p;
1925 }
1926 else
0f41302f 1927 for (ptr = sbb_head; ptr != (struct bb_str *) 0; ptr = ptr->next)
3cf2715d
DE
1928 if (ptr->string == string)
1929 break;
1930
1931 /* Allocate a new string block if we need to. */
1932 if (!ptr)
1933 {
1934 ptr = (struct bb_str *) permalloc (sizeof (*ptr));
1935 ptr->next = 0;
1936 ptr->length = len;
1937 ptr->label_num = sbb_label_num++;
1938 ptr->string = string;
1939 *sbb_tail = ptr;
1940 sbb_tail = &ptr->next;
1941 }
1942
1943 return ptr->label_num;
1944}
3cf2715d
DE
1945\f
1946/* Output assembler code for some insns: all or part of a function.
1947 For description of args, see `final_start_function', above.
1948
1949 PRESCAN is 1 if we are not really outputting,
1950 just scanning as if we were outputting.
1951 Prescanning deletes and rearranges insns just like ordinary output.
1952 PRESCAN is -2 if we are outputting after having prescanned.
1953 In this case, don't try to delete or rearrange insns
1954 because that has already been done.
1955 Prescanning is done only on certain machines. */
1956
1957void
1958final (first, file, optimize, prescan)
1959 rtx first;
1960 FILE *file;
1961 int optimize;
1962 int prescan;
1963{
b3694847 1964 rtx insn;
3cf2715d 1965 int max_line = 0;
a8c3510c 1966 int max_uid = 0;
3cf2715d
DE
1967
1968 last_ignored_compare = 0;
1969 new_block = 1;
1970
1971 /* Make a map indicating which line numbers appear in this function.
1972 When producing SDB debugging info, delete troublesome line number
1973 notes from inlined functions in other files as well as duplicate
1974 line number notes. */
1975#ifdef SDB_DEBUGGING_INFO
1976 if (write_symbols == SDB_DEBUG)
1977 {
1978 rtx last = 0;
1979 for (insn = first; insn; insn = NEXT_INSN (insn))
1980 if (GET_CODE (insn) == NOTE && NOTE_LINE_NUMBER (insn) > 0)
1981 {
1982 if ((RTX_INTEGRATED_P (insn)
1983 && strcmp (NOTE_SOURCE_FILE (insn), main_input_filename) != 0)
1984 || (last != 0
1985 && NOTE_LINE_NUMBER (insn) == NOTE_LINE_NUMBER (last)
1986 && NOTE_SOURCE_FILE (insn) == NOTE_SOURCE_FILE (last)))
1987 {
2e106602 1988 delete_insn (insn); /* Use delete_note. */
3cf2715d
DE
1989 continue;
1990 }
1991 last = insn;
1992 if (NOTE_LINE_NUMBER (insn) > max_line)
1993 max_line = NOTE_LINE_NUMBER (insn);
1994 }
1995 }
1996 else
1997#endif
1998 {
1999 for (insn = first; insn; insn = NEXT_INSN (insn))
2000 if (GET_CODE (insn) == NOTE && NOTE_LINE_NUMBER (insn) > max_line)
2001 max_line = NOTE_LINE_NUMBER (insn);
2002 }
2003
bedda2da 2004 line_note_exists = (char *) xcalloc (max_line + 1, sizeof (char));
3cf2715d
DE
2005
2006 for (insn = first; insn; insn = NEXT_INSN (insn))
a8c3510c
AM
2007 {
2008 if (INSN_UID (insn) > max_uid) /* find largest UID */
f5d927c0 2009 max_uid = INSN_UID (insn);
a8c3510c 2010 if (GET_CODE (insn) == NOTE && NOTE_LINE_NUMBER (insn) > 0)
f5d927c0 2011 line_note_exists[NOTE_LINE_NUMBER (insn)] = 1;
9ef4c6ef
JC
2012#ifdef HAVE_cc0
2013 /* If CC tracking across branches is enabled, record the insn which
2014 jumps to each branch only reached from one place. */
7ad7f828 2015 if (optimize && GET_CODE (insn) == JUMP_INSN)
9ef4c6ef
JC
2016 {
2017 rtx lab = JUMP_LABEL (insn);
2018 if (lab && LABEL_NUSES (lab) == 1)
2019 {
2020 LABEL_REFS (lab) = insn;
2021 }
2022 }
2023#endif
a8c3510c
AM
2024 }
2025
3cf2715d
DE
2026 init_recog ();
2027
2028 CC_STATUS_INIT;
2029
2030 /* Output the insns. */
2031 for (insn = NEXT_INSN (first); insn;)
2f16edb1
TG
2032 {
2033#ifdef HAVE_ATTR_length
b9f22704 2034 if ((unsigned) INSN_UID (insn) >= INSN_ADDRESSES_SIZE ())
0ac76ad9
RH
2035 {
2036#ifdef STACK_REGS
2037 /* Irritatingly, the reg-stack pass is creating new instructions
2038 and because of REG_DEAD note abuse it has to run after
2039 shorten_branches. Fake address of -1 then. */
2040 insn_current_address = -1;
2041#else
2042 /* This can be triggered by bugs elsewhere in the compiler if
2043 new insns are created after init_insn_lengths is called. */
2044 abort ();
2f16edb1 2045#endif
0ac76ad9
RH
2046 }
2047 else
9d98a694 2048 insn_current_address = INSN_ADDRESSES (INSN_UID (insn));
0ac76ad9
RH
2049#endif /* HAVE_ATTR_length */
2050
2f16edb1
TG
2051 insn = final_scan_insn (insn, file, optimize, prescan, 0);
2052 }
3cf2715d
DE
2053
2054 /* Do basic-block profiling here
2055 if the last insn was a conditional branch. */
2056 if (profile_block_flag && new_block)
2057 add_bb (file);
a8c3510c 2058
bedda2da
MM
2059 free (line_note_exists);
2060 line_note_exists = NULL;
3cf2715d
DE
2061}
2062\f
4bbf910e
RH
2063const char *
2064get_insn_template (code, insn)
2065 int code;
2066 rtx insn;
2067{
2068 const void *output = insn_data[code].output;
2069 switch (insn_data[code].output_format)
2070 {
2071 case INSN_OUTPUT_FORMAT_SINGLE:
2072 return (const char *) output;
2073 case INSN_OUTPUT_FORMAT_MULTI:
f5d927c0 2074 return ((const char *const *) output)[which_alternative];
4bbf910e
RH
2075 case INSN_OUTPUT_FORMAT_FUNCTION:
2076 if (insn == NULL)
2077 abort ();
f5d927c0 2078 return (*(insn_output_fn) output) (recog_data.operand, insn);
4bbf910e
RH
2079
2080 default:
2081 abort ();
2082 }
2083}
f5d927c0 2084
3cf2715d
DE
2085/* The final scan for one insn, INSN.
2086 Args are same as in `final', except that INSN
2087 is the insn being scanned.
2088 Value returned is the next insn to be scanned.
2089
2090 NOPEEPHOLES is the flag to disallow peephole processing (currently
2091 used for within delayed branch sequence output). */
2092
2093rtx
2094final_scan_insn (insn, file, optimize, prescan, nopeepholes)
2095 rtx insn;
2096 FILE *file;
272df862 2097 int optimize ATTRIBUTE_UNUSED;
3cf2715d 2098 int prescan;
272df862 2099 int nopeepholes ATTRIBUTE_UNUSED;
3cf2715d 2100{
90ca38bb
MM
2101#ifdef HAVE_cc0
2102 rtx set;
2103#endif
2104
3cf2715d
DE
2105 insn_counter++;
2106
2107 /* Ignore deleted insns. These can occur when we split insns (due to a
2108 template of "#") while not optimizing. */
2109 if (INSN_DELETED_P (insn))
2110 return NEXT_INSN (insn);
2111
2112 switch (GET_CODE (insn))
2113 {
2114 case NOTE:
2115 if (prescan > 0)
2116 break;
2117
be1bb652
RH
2118 switch (NOTE_LINE_NUMBER (insn))
2119 {
2120 case NOTE_INSN_DELETED:
2121 case NOTE_INSN_LOOP_BEG:
2122 case NOTE_INSN_LOOP_END:
2123 case NOTE_INSN_LOOP_CONT:
2124 case NOTE_INSN_LOOP_VTOP:
2125 case NOTE_INSN_FUNCTION_END:
be1bb652
RH
2126 case NOTE_INSN_REPEATED_LINE_NUMBER:
2127 case NOTE_INSN_RANGE_BEG:
2128 case NOTE_INSN_RANGE_END:
2129 case NOTE_INSN_LIVE:
2130 case NOTE_INSN_EXPECTED_VALUE:
2131 break;
3cf2715d 2132
be1bb652 2133 case NOTE_INSN_BASIC_BLOCK:
ad0fc698
JW
2134#ifdef IA64_UNWIND_INFO
2135 IA64_UNWIND_EMIT (asm_out_file, insn);
2136#endif
be1bb652
RH
2137 if (flag_debug_asm)
2138 fprintf (asm_out_file, "\t%s basic block %d\n",
2139 ASM_COMMENT_START, NOTE_BASIC_BLOCK (insn)->index);
2140 break;
3cf2715d 2141
be1bb652 2142 case NOTE_INSN_EH_REGION_BEG:
52a11cbf
RH
2143 ASM_OUTPUT_DEBUG_LABEL (asm_out_file, "LEHB",
2144 NOTE_EH_HANDLER (insn));
3d195391 2145 break;
3d195391 2146
be1bb652 2147 case NOTE_INSN_EH_REGION_END:
52a11cbf
RH
2148 ASM_OUTPUT_DEBUG_LABEL (asm_out_file, "LEHE",
2149 NOTE_EH_HANDLER (insn));
3d195391 2150 break;
3d195391 2151
be1bb652 2152 case NOTE_INSN_PROLOGUE_END:
b9f22704 2153 (*targetm.asm_out.function_end_prologue) (file);
3cf2715d
DE
2154 profile_after_prologue (file);
2155 break;
3cf2715d 2156
be1bb652 2157 case NOTE_INSN_EPILOGUE_BEG:
b9f22704 2158 (*targetm.asm_out.function_begin_epilogue) (file);
be1bb652 2159 break;
3cf2715d 2160
be1bb652 2161 case NOTE_INSN_FUNCTION_BEG:
653e276c
NB
2162 app_disable ();
2163 (*debug_hooks->end_prologue) (last_linenum);
3cf2715d 2164 break;
be1bb652
RH
2165
2166 case NOTE_INSN_BLOCK_BEG:
2167 if (debug_info_level == DINFO_LEVEL_NORMAL
3cf2715d 2168 || debug_info_level == DINFO_LEVEL_VERBOSE
3cf2715d 2169 || write_symbols == DWARF_DEBUG
7a0c8d71
DR
2170 || write_symbols == DWARF2_DEBUG
2171 || write_symbols == VMS_AND_DWARF2_DEBUG
2172 || write_symbols == VMS_DEBUG)
be1bb652
RH
2173 {
2174 int n = BLOCK_NUMBER (NOTE_BLOCK (insn));
3cf2715d 2175
be1bb652
RH
2176 app_disable ();
2177 ++block_depth;
2178 high_block_linenum = last_linenum;
eac40081 2179
a5a42b92 2180 /* Output debugging info about the symbol-block beginning. */
e2a12aca 2181 (*debug_hooks->begin_block) (last_linenum, n);
3cf2715d 2182
be1bb652
RH
2183 /* Mark this block as output. */
2184 TREE_ASM_WRITTEN (NOTE_BLOCK (insn)) = 1;
2185 }
2186 break;
18c038b9 2187
be1bb652
RH
2188 case NOTE_INSN_BLOCK_END:
2189 if (debug_info_level == DINFO_LEVEL_NORMAL
2190 || debug_info_level == DINFO_LEVEL_VERBOSE
2191 || write_symbols == DWARF_DEBUG
7a0c8d71
DR
2192 || write_symbols == DWARF2_DEBUG
2193 || write_symbols == VMS_AND_DWARF2_DEBUG
2194 || write_symbols == VMS_DEBUG)
be1bb652
RH
2195 {
2196 int n = BLOCK_NUMBER (NOTE_BLOCK (insn));
3cf2715d 2197
be1bb652
RH
2198 app_disable ();
2199
2200 /* End of a symbol-block. */
2201 --block_depth;
2202 if (block_depth < 0)
2203 abort ();
3cf2715d 2204
e2a12aca 2205 (*debug_hooks->end_block) (high_block_linenum, n);
be1bb652
RH
2206 }
2207 break;
2208
2209 case NOTE_INSN_DELETED_LABEL:
2210 /* Emit the label. We may have deleted the CODE_LABEL because
2211 the label could be proved to be unreachable, though still
2212 referenced (in the form of having its address taken. */
8215347e 2213 ASM_OUTPUT_DEBUG_LABEL (file, "L", CODE_LABEL_NUMBER (insn));
be1bb652 2214 break;
3cf2715d 2215
21835d9b
JJ
2216 case 0:
2217 break;
2218
be1bb652
RH
2219 default:
2220 if (NOTE_LINE_NUMBER (insn) <= 0)
2221 abort ();
3cf2715d 2222
be1bb652
RH
2223 /* This note is a line-number. */
2224 {
b3694847 2225 rtx note;
be1bb652
RH
2226 int note_after = 0;
2227
f5d927c0 2228 /* If there is anything real after this note, output it.
be1bb652
RH
2229 If another line note follows, omit this one. */
2230 for (note = NEXT_INSN (insn); note; note = NEXT_INSN (note))
2231 {
2232 if (GET_CODE (note) != NOTE && GET_CODE (note) != CODE_LABEL)
3cf2715d 2233 break;
3cf2715d 2234
be1bb652
RH
2235 /* These types of notes can be significant
2236 so make sure the preceding line number stays. */
2237 else if (GET_CODE (note) == NOTE
2238 && (NOTE_LINE_NUMBER (note) == NOTE_INSN_BLOCK_BEG
2239 || NOTE_LINE_NUMBER (note) == NOTE_INSN_BLOCK_END
2240 || NOTE_LINE_NUMBER (note) == NOTE_INSN_FUNCTION_BEG))
2241 break;
2242 else if (GET_CODE (note) == NOTE && NOTE_LINE_NUMBER (note) > 0)
2243 {
2244 /* Another line note follows; we can delete this note
2245 if no intervening line numbers have notes elsewhere. */
2246 int num;
2247 for (num = NOTE_LINE_NUMBER (insn) + 1;
2248 num < NOTE_LINE_NUMBER (note);
2249 num++)
2250 if (line_note_exists[num])
2251 break;
2252
2253 if (num >= NOTE_LINE_NUMBER (note))
2254 note_after = 1;
2255 break;
2256 }
2257 }
2258
2259 /* Output this line note if it is the first or the last line
2260 note in a row. */
2261 if (!note_after)
653e276c
NB
2262 {
2263 notice_source_line (insn);
2264 (*debug_hooks->source_line) (last_linenum, last_filename);
2265 }
be1bb652 2266 }
f5d927c0 2267 break;
3cf2715d
DE
2268 }
2269 break;
2270
2271 case BARRIER:
f73ad30e 2272#if defined (DWARF2_UNWIND_INFO)
fbfa55b0 2273 if (dwarf2out_do_frame ())
be1bb652 2274 dwarf2out_frame_debug (insn);
3cf2715d
DE
2275#endif
2276 break;
2277
2278 case CODE_LABEL:
1dd8faa8
R
2279 /* The target port might emit labels in the output function for
2280 some insn, e.g. sh.c output_branchy_insn. */
de7987a6
R
2281 if (CODE_LABEL_NUMBER (insn) <= max_labelno)
2282 {
2283 int align = LABEL_TO_ALIGNMENT (insn);
50b2596f 2284#ifdef ASM_OUTPUT_MAX_SKIP_ALIGN
9e423e6d 2285 int max_skip = LABEL_TO_MAX_SKIP (insn);
50b2596f 2286#endif
fc470718 2287
1dd8faa8 2288 if (align && NEXT_INSN (insn))
40cdfca6 2289 {
9e423e6d 2290#ifdef ASM_OUTPUT_MAX_SKIP_ALIGN
40cdfca6 2291 ASM_OUTPUT_MAX_SKIP_ALIGN (file, align, max_skip);
9e423e6d 2292#else
40cdfca6 2293 ASM_OUTPUT_ALIGN (file, align);
9e423e6d 2294#endif
40cdfca6 2295 }
de7987a6 2296 }
9ef4c6ef 2297#ifdef HAVE_cc0
3cf2715d 2298 CC_STATUS_INIT;
9ef4c6ef
JC
2299 /* If this label is reached from only one place, set the condition
2300 codes from the instruction just before the branch. */
7ad7f828
JC
2301
2302 /* Disabled because some insns set cc_status in the C output code
2303 and NOTICE_UPDATE_CC alone can set incorrect status. */
2304 if (0 /* optimize && LABEL_NUSES (insn) == 1*/)
9ef4c6ef
JC
2305 {
2306 rtx jump = LABEL_REFS (insn);
2307 rtx barrier = prev_nonnote_insn (insn);
2308 rtx prev;
2309 /* If the LABEL_REFS field of this label has been set to point
2310 at a branch, the predecessor of the branch is a regular
2311 insn, and that branch is the only way to reach this label,
2312 set the condition codes based on the branch and its
2313 predecessor. */
2314 if (barrier && GET_CODE (barrier) == BARRIER
2315 && jump && GET_CODE (jump) == JUMP_INSN
2316 && (prev = prev_nonnote_insn (jump))
2317 && GET_CODE (prev) == INSN)
2318 {
2319 NOTICE_UPDATE_CC (PATTERN (prev), prev);
2320 NOTICE_UPDATE_CC (PATTERN (jump), jump);
2321 }
2322 }
2323#endif
3cf2715d
DE
2324 if (prescan > 0)
2325 break;
2326 new_block = 1;
03ffa171
RK
2327
2328#ifdef FINAL_PRESCAN_LABEL
df4ae160 2329 FINAL_PRESCAN_INSN (insn, NULL, 0);
03ffa171
RK
2330#endif
2331
e1772ac0
NB
2332 if (LABEL_NAME (insn))
2333 (*debug_hooks->label) (insn);
2334
3cf2715d
DE
2335 if (app_on)
2336 {
51723711 2337 fputs (ASM_APP_OFF, file);
3cf2715d
DE
2338 app_on = 0;
2339 }
2340 if (NEXT_INSN (insn) != 0
2341 && GET_CODE (NEXT_INSN (insn)) == JUMP_INSN)
2342 {
2343 rtx nextbody = PATTERN (NEXT_INSN (insn));
2344
2345 /* If this label is followed by a jump-table,
2346 make sure we put the label in the read-only section. Also
2347 possibly write the label and jump table together. */
2348
2349 if (GET_CODE (nextbody) == ADDR_VEC
2350 || GET_CODE (nextbody) == ADDR_DIFF_VEC)
2351 {
e0d80184
DM
2352#if defined(ASM_OUTPUT_ADDR_VEC) || defined(ASM_OUTPUT_ADDR_DIFF_VEC)
2353 /* In this case, the case vector is being moved by the
2354 target, so don't output the label at all. Leave that
2355 to the back end macros. */
2356#else
75197b37
BS
2357 if (! JUMP_TABLES_IN_TEXT_SECTION)
2358 {
340f7e7c
RH
2359 int log_align;
2360
75197b37 2361 readonly_data_section ();
340f7e7c
RH
2362
2363#ifdef ADDR_VEC_ALIGN
3e4eece3 2364 log_align = ADDR_VEC_ALIGN (NEXT_INSN (insn));
340f7e7c
RH
2365#else
2366 log_align = exact_log2 (BIGGEST_ALIGNMENT / BITS_PER_UNIT);
2367#endif
2368 ASM_OUTPUT_ALIGN (file, log_align);
75197b37
BS
2369 }
2370 else
2371 function_section (current_function_decl);
2372
3cf2715d
DE
2373#ifdef ASM_OUTPUT_CASE_LABEL
2374 ASM_OUTPUT_CASE_LABEL (file, "L", CODE_LABEL_NUMBER (insn),
2375 NEXT_INSN (insn));
2376#else
f5d927c0
KH
2377 if (LABEL_ALTERNATE_NAME (insn))
2378 ASM_OUTPUT_ALTERNATE_LABEL_NAME (file, insn);
2379 else
2380 ASM_OUTPUT_INTERNAL_LABEL (file, "L", CODE_LABEL_NUMBER (insn));
e0d80184 2381#endif
3cf2715d
DE
2382#endif
2383 break;
2384 }
2385 }
8cd0faaf 2386 if (LABEL_ALTERNATE_NAME (insn))
f5d927c0 2387 ASM_OUTPUT_ALTERNATE_LABEL_NAME (file, insn);
8cd0faaf 2388 else
f5d927c0 2389 ASM_OUTPUT_INTERNAL_LABEL (file, "L", CODE_LABEL_NUMBER (insn));
3cf2715d
DE
2390 break;
2391
2392 default:
2393 {
b3694847 2394 rtx body = PATTERN (insn);
3cf2715d 2395 int insn_code_number;
9b3142b3 2396 const char *template;
3cf2715d
DE
2397 rtx note;
2398
2399 /* An INSN, JUMP_INSN or CALL_INSN.
2400 First check for special kinds that recog doesn't recognize. */
2401
2402 if (GET_CODE (body) == USE /* These are just declarations */
2403 || GET_CODE (body) == CLOBBER)
2404 break;
2405
2406#ifdef HAVE_cc0
2407 /* If there is a REG_CC_SETTER note on this insn, it means that
2408 the setting of the condition code was done in the delay slot
2409 of the insn that branched here. So recover the cc status
2410 from the insn that set it. */
2411
2412 note = find_reg_note (insn, REG_CC_SETTER, NULL_RTX);
2413 if (note)
2414 {
2415 NOTICE_UPDATE_CC (PATTERN (XEXP (note, 0)), XEXP (note, 0));
2416 cc_prev_status = cc_status;
2417 }
2418#endif
2419
2420 /* Detect insns that are really jump-tables
2421 and output them as such. */
2422
2423 if (GET_CODE (body) == ADDR_VEC || GET_CODE (body) == ADDR_DIFF_VEC)
2424 {
7f7f8214 2425#if !(defined(ASM_OUTPUT_ADDR_VEC) || defined(ASM_OUTPUT_ADDR_DIFF_VEC))
b3694847 2426 int vlen, idx;
7f7f8214 2427#endif
3cf2715d
DE
2428
2429 if (prescan > 0)
2430 break;
2431
2432 if (app_on)
2433 {
51723711 2434 fputs (ASM_APP_OFF, file);
3cf2715d
DE
2435 app_on = 0;
2436 }
2437
e0d80184
DM
2438#if defined(ASM_OUTPUT_ADDR_VEC) || defined(ASM_OUTPUT_ADDR_DIFF_VEC)
2439 if (GET_CODE (body) == ADDR_VEC)
2440 {
2441#ifdef ASM_OUTPUT_ADDR_VEC
2442 ASM_OUTPUT_ADDR_VEC (PREV_INSN (insn), body);
2443#else
f5d927c0 2444 abort ();
e0d80184
DM
2445#endif
2446 }
2447 else
2448 {
2449#ifdef ASM_OUTPUT_ADDR_DIFF_VEC
2450 ASM_OUTPUT_ADDR_DIFF_VEC (PREV_INSN (insn), body);
2451#else
f5d927c0 2452 abort ();
e0d80184
DM
2453#endif
2454 }
2455#else
3cf2715d
DE
2456 vlen = XVECLEN (body, GET_CODE (body) == ADDR_DIFF_VEC);
2457 for (idx = 0; idx < vlen; idx++)
2458 {
2459 if (GET_CODE (body) == ADDR_VEC)
2460 {
2461#ifdef ASM_OUTPUT_ADDR_VEC_ELT
2462 ASM_OUTPUT_ADDR_VEC_ELT
2463 (file, CODE_LABEL_NUMBER (XEXP (XVECEXP (body, 0, idx), 0)));
2464#else
2465 abort ();
2466#endif
2467 }
2468 else
2469 {
2470#ifdef ASM_OUTPUT_ADDR_DIFF_ELT
2471 ASM_OUTPUT_ADDR_DIFF_ELT
2472 (file,
33f7f353 2473 body,
3cf2715d
DE
2474 CODE_LABEL_NUMBER (XEXP (XVECEXP (body, 1, idx), 0)),
2475 CODE_LABEL_NUMBER (XEXP (XEXP (body, 0), 0)));
2476#else
2477 abort ();
2478#endif
2479 }
2480 }
2481#ifdef ASM_OUTPUT_CASE_END
2482 ASM_OUTPUT_CASE_END (file,
2483 CODE_LABEL_NUMBER (PREV_INSN (insn)),
2484 insn);
e0d80184 2485#endif
3cf2715d
DE
2486#endif
2487
4d1065ed 2488 function_section (current_function_decl);
3cf2715d
DE
2489
2490 break;
2491 }
2492
2493 /* Do basic-block profiling when we reach a new block.
2494 Done here to avoid jump tables. */
2495 if (profile_block_flag && new_block)
2496 add_bb (file);
2497
2498 if (GET_CODE (body) == ASM_INPUT)
2499 {
36d7136e
RH
2500 const char *string = XSTR (body, 0);
2501
3cf2715d
DE
2502 /* There's no telling what that did to the condition codes. */
2503 CC_STATUS_INIT;
2504 if (prescan > 0)
2505 break;
36d7136e
RH
2506
2507 if (string[0])
3cf2715d 2508 {
36d7136e
RH
2509 if (! app_on)
2510 {
2511 fputs (ASM_APP_ON, file);
2512 app_on = 1;
2513 }
2514 fprintf (asm_out_file, "\t%s\n", string);
3cf2715d 2515 }
3cf2715d
DE
2516 break;
2517 }
2518
2519 /* Detect `asm' construct with operands. */
2520 if (asm_noperands (body) >= 0)
2521 {
22bf4422 2522 unsigned int noperands = asm_noperands (body);
3cf2715d 2523 rtx *ops = (rtx *) alloca (noperands * sizeof (rtx));
3cce094d 2524 const char *string;
3cf2715d
DE
2525
2526 /* There's no telling what that did to the condition codes. */
2527 CC_STATUS_INIT;
2528 if (prescan > 0)
2529 break;
2530
3cf2715d 2531 /* Get out the operand values. */
df4ae160 2532 string = decode_asm_operands (body, ops, NULL, NULL, NULL);
3cf2715d
DE
2533 /* Inhibit aborts on what would otherwise be compiler bugs. */
2534 insn_noperands = noperands;
2535 this_is_asm_operands = insn;
2536
2537 /* Output the insn using them. */
36d7136e
RH
2538 if (string[0])
2539 {
2540 if (! app_on)
2541 {
2542 fputs (ASM_APP_ON, file);
2543 app_on = 1;
2544 }
2545 output_asm_insn (string, ops);
2546 }
2547
3cf2715d
DE
2548 this_is_asm_operands = 0;
2549 break;
2550 }
2551
2552 if (prescan <= 0 && app_on)
2553 {
51723711 2554 fputs (ASM_APP_OFF, file);
3cf2715d
DE
2555 app_on = 0;
2556 }
2557
2558 if (GET_CODE (body) == SEQUENCE)
2559 {
2560 /* A delayed-branch sequence */
b3694847 2561 int i;
3cf2715d
DE
2562 rtx next;
2563
2564 if (prescan > 0)
2565 break;
2566 final_sequence = body;
2567
2568 /* The first insn in this SEQUENCE might be a JUMP_INSN that will
2569 force the restoration of a comparison that was previously
2570 thought unnecessary. If that happens, cancel this sequence
2571 and cause that insn to be restored. */
2572
2573 next = final_scan_insn (XVECEXP (body, 0, 0), file, 0, prescan, 1);
2574 if (next != XVECEXP (body, 0, 1))
2575 {
2576 final_sequence = 0;
2577 return next;
2578 }
2579
2580 for (i = 1; i < XVECLEN (body, 0); i++)
c7eee2df
RK
2581 {
2582 rtx insn = XVECEXP (body, 0, i);
2583 rtx next = NEXT_INSN (insn);
2584 /* We loop in case any instruction in a delay slot gets
2585 split. */
2586 do
2587 insn = final_scan_insn (insn, file, 0, prescan, 1);
2588 while (insn != next);
2589 }
3cf2715d
DE
2590#ifdef DBR_OUTPUT_SEQEND
2591 DBR_OUTPUT_SEQEND (file);
2592#endif
2593 final_sequence = 0;
2594
2595 /* If the insn requiring the delay slot was a CALL_INSN, the
2596 insns in the delay slot are actually executed before the
2597 called function. Hence we don't preserve any CC-setting
2598 actions in these insns and the CC must be marked as being
2599 clobbered by the function. */
2600 if (GET_CODE (XVECEXP (body, 0, 0)) == CALL_INSN)
b729186a
JL
2601 {
2602 CC_STATUS_INIT;
2603 }
3cf2715d
DE
2604
2605 /* Following a conditional branch sequence, we have a new basic
2606 block. */
2607 if (profile_block_flag)
2608 {
2609 rtx insn = XVECEXP (body, 0, 0);
2610 rtx body = PATTERN (insn);
2611
2612 if ((GET_CODE (insn) == JUMP_INSN && GET_CODE (body) == SET
2613 && GET_CODE (SET_SRC (body)) != LABEL_REF)
2614 || (GET_CODE (insn) == JUMP_INSN
2615 && GET_CODE (body) == PARALLEL
2616 && GET_CODE (XVECEXP (body, 0, 0)) == SET
2617 && GET_CODE (SET_SRC (XVECEXP (body, 0, 0))) != LABEL_REF))
2618 new_block = 1;
2619 }
2620 break;
2621 }
2622
2623 /* We have a real machine instruction as rtl. */
2624
2625 body = PATTERN (insn);
2626
2627#ifdef HAVE_cc0
f5d927c0 2628 set = single_set (insn);
b88c92cc 2629
3cf2715d
DE
2630 /* Check for redundant test and compare instructions
2631 (when the condition codes are already set up as desired).
2632 This is done only when optimizing; if not optimizing,
2633 it should be possible for the user to alter a variable
2634 with the debugger in between statements
2635 and the next statement should reexamine the variable
2636 to compute the condition codes. */
2637
30f5e9f5 2638 if (optimize)
3cf2715d 2639 {
b88c92cc 2640#if 0
f5d927c0 2641 rtx set = single_set (insn);
b88c92cc 2642#endif
30f5e9f5
RK
2643
2644 if (set
2645 && GET_CODE (SET_DEST (set)) == CC0
2646 && insn != last_ignored_compare)
3cf2715d 2647 {
30f5e9f5 2648 if (GET_CODE (SET_SRC (set)) == SUBREG)
49d801d3 2649 SET_SRC (set) = alter_subreg (&SET_SRC (set));
30f5e9f5
RK
2650 else if (GET_CODE (SET_SRC (set)) == COMPARE)
2651 {
2652 if (GET_CODE (XEXP (SET_SRC (set), 0)) == SUBREG)
2653 XEXP (SET_SRC (set), 0)
49d801d3 2654 = alter_subreg (&XEXP (SET_SRC (set), 0));
30f5e9f5
RK
2655 if (GET_CODE (XEXP (SET_SRC (set), 1)) == SUBREG)
2656 XEXP (SET_SRC (set), 1)
49d801d3 2657 = alter_subreg (&XEXP (SET_SRC (set), 1));
30f5e9f5
RK
2658 }
2659 if ((cc_status.value1 != 0
2660 && rtx_equal_p (SET_SRC (set), cc_status.value1))
2661 || (cc_status.value2 != 0
2662 && rtx_equal_p (SET_SRC (set), cc_status.value2)))
3cf2715d 2663 {
30f5e9f5
RK
2664 /* Don't delete insn if it has an addressing side-effect. */
2665 if (! FIND_REG_INC_NOTE (insn, 0)
2666 /* or if anything in it is volatile. */
2667 && ! volatile_refs_p (PATTERN (insn)))
2668 {
2669 /* We don't really delete the insn; just ignore it. */
2670 last_ignored_compare = insn;
2671 break;
2672 }
3cf2715d
DE
2673 }
2674 }
2675 }
2676#endif
2677
2678 /* Following a conditional branch, we have a new basic block.
2679 But if we are inside a sequence, the new block starts after the
2680 last insn of the sequence. */
2681 if (profile_block_flag && final_sequence == 0
2682 && ((GET_CODE (insn) == JUMP_INSN && GET_CODE (body) == SET
2683 && GET_CODE (SET_SRC (body)) != LABEL_REF)
2684 || (GET_CODE (insn) == JUMP_INSN && GET_CODE (body) == PARALLEL
2685 && GET_CODE (XVECEXP (body, 0, 0)) == SET
2686 && GET_CODE (SET_SRC (XVECEXP (body, 0, 0))) != LABEL_REF)))
2687 new_block = 1;
2688
2689#ifndef STACK_REGS
2690 /* Don't bother outputting obvious no-ops, even without -O.
2691 This optimization is fast and doesn't interfere with debugging.
2692 Don't do this if the insn is in a delay slot, since this
2693 will cause an improper number of delay insns to be written. */
2694 if (final_sequence == 0
2695 && prescan >= 0
2696 && GET_CODE (insn) == INSN && GET_CODE (body) == SET
2697 && GET_CODE (SET_SRC (body)) == REG
2698 && GET_CODE (SET_DEST (body)) == REG
2699 && REGNO (SET_SRC (body)) == REGNO (SET_DEST (body)))
2700 break;
2701#endif
2702
2703#ifdef HAVE_cc0
2704 /* If this is a conditional branch, maybe modify it
2705 if the cc's are in a nonstandard state
2706 so that it accomplishes the same thing that it would
2707 do straightforwardly if the cc's were set up normally. */
2708
2709 if (cc_status.flags != 0
2710 && GET_CODE (insn) == JUMP_INSN
2711 && GET_CODE (body) == SET
2712 && SET_DEST (body) == pc_rtx
2713 && GET_CODE (SET_SRC (body)) == IF_THEN_ELSE
de2b56f9 2714 && GET_RTX_CLASS (GET_CODE (XEXP (SET_SRC (body), 0))) == '<'
fff752ad 2715 && XEXP (XEXP (SET_SRC (body), 0), 0) == cc0_rtx
3cf2715d
DE
2716 /* This is done during prescan; it is not done again
2717 in final scan when prescan has been done. */
2718 && prescan >= 0)
2719 {
2720 /* This function may alter the contents of its argument
2721 and clear some of the cc_status.flags bits.
2722 It may also return 1 meaning condition now always true
2723 or -1 meaning condition now always false
2724 or 2 meaning condition nontrivial but altered. */
b3694847 2725 int result = alter_cond (XEXP (SET_SRC (body), 0));
3cf2715d
DE
2726 /* If condition now has fixed value, replace the IF_THEN_ELSE
2727 with its then-operand or its else-operand. */
2728 if (result == 1)
2729 SET_SRC (body) = XEXP (SET_SRC (body), 1);
2730 if (result == -1)
2731 SET_SRC (body) = XEXP (SET_SRC (body), 2);
2732
2733 /* The jump is now either unconditional or a no-op.
2734 If it has become a no-op, don't try to output it.
2735 (It would not be recognized.) */
2736 if (SET_SRC (body) == pc_rtx)
2737 {
ca6c03ca 2738 delete_insn (insn);
3cf2715d
DE
2739 break;
2740 }
2741 else if (GET_CODE (SET_SRC (body)) == RETURN)
2742 /* Replace (set (pc) (return)) with (return). */
2743 PATTERN (insn) = body = SET_SRC (body);
2744
2745 /* Rerecognize the instruction if it has changed. */
2746 if (result != 0)
2747 INSN_CODE (insn) = -1;
2748 }
2749
2750 /* Make same adjustments to instructions that examine the
462da2af
SC
2751 condition codes without jumping and instructions that
2752 handle conditional moves (if this machine has either one). */
3cf2715d
DE
2753
2754 if (cc_status.flags != 0
b88c92cc 2755 && set != 0)
3cf2715d 2756 {
462da2af 2757 rtx cond_rtx, then_rtx, else_rtx;
f5d927c0 2758
462da2af 2759 if (GET_CODE (insn) != JUMP_INSN
b88c92cc 2760 && GET_CODE (SET_SRC (set)) == IF_THEN_ELSE)
462da2af 2761 {
b88c92cc
RK
2762 cond_rtx = XEXP (SET_SRC (set), 0);
2763 then_rtx = XEXP (SET_SRC (set), 1);
2764 else_rtx = XEXP (SET_SRC (set), 2);
462da2af
SC
2765 }
2766 else
2767 {
b88c92cc 2768 cond_rtx = SET_SRC (set);
462da2af
SC
2769 then_rtx = const_true_rtx;
2770 else_rtx = const0_rtx;
2771 }
f5d927c0 2772
462da2af 2773 switch (GET_CODE (cond_rtx))
3cf2715d
DE
2774 {
2775 case GTU:
2776 case GT:
2777 case LTU:
2778 case LT:
2779 case GEU:
2780 case GE:
2781 case LEU:
2782 case LE:
2783 case EQ:
2784 case NE:
2785 {
b3694847 2786 int result;
462da2af 2787 if (XEXP (cond_rtx, 0) != cc0_rtx)
3cf2715d 2788 break;
462da2af 2789 result = alter_cond (cond_rtx);
3cf2715d 2790 if (result == 1)
b88c92cc 2791 validate_change (insn, &SET_SRC (set), then_rtx, 0);
3cf2715d 2792 else if (result == -1)
b88c92cc 2793 validate_change (insn, &SET_SRC (set), else_rtx, 0);
3cf2715d
DE
2794 else if (result == 2)
2795 INSN_CODE (insn) = -1;
b88c92cc 2796 if (SET_DEST (set) == SET_SRC (set))
ca6c03ca 2797 delete_insn (insn);
3cf2715d 2798 }
e9a25f70
JL
2799 break;
2800
2801 default:
2802 break;
3cf2715d
DE
2803 }
2804 }
462da2af 2805
3cf2715d
DE
2806#endif
2807
ede7cd44 2808#ifdef HAVE_peephole
3cf2715d
DE
2809 /* Do machine-specific peephole optimizations if desired. */
2810
2811 if (optimize && !flag_no_peephole && !nopeepholes)
2812 {
2813 rtx next = peephole (insn);
2814 /* When peepholing, if there were notes within the peephole,
2815 emit them before the peephole. */
2816 if (next != 0 && next != NEXT_INSN (insn))
2817 {
2818 rtx prev = PREV_INSN (insn);
3cf2715d
DE
2819
2820 for (note = NEXT_INSN (insn); note != next;
2821 note = NEXT_INSN (note))
2822 final_scan_insn (note, file, optimize, prescan, nopeepholes);
2823
2824 /* In case this is prescan, put the notes
2825 in proper position for later rescan. */
2826 note = NEXT_INSN (insn);
2827 PREV_INSN (note) = prev;
2828 NEXT_INSN (prev) = note;
2829 NEXT_INSN (PREV_INSN (next)) = insn;
2830 PREV_INSN (insn) = PREV_INSN (next);
2831 NEXT_INSN (insn) = next;
2832 PREV_INSN (next) = insn;
2833 }
2834
2835 /* PEEPHOLE might have changed this. */
2836 body = PATTERN (insn);
2837 }
ede7cd44 2838#endif
3cf2715d
DE
2839
2840 /* Try to recognize the instruction.
2841 If successful, verify that the operands satisfy the
2842 constraints for the instruction. Crash if they don't,
2843 since `reload' should have changed them so that they do. */
2844
2845 insn_code_number = recog_memoized (insn);
0304f787 2846 cleanup_subreg_operands (insn);
3cf2715d 2847
c349e40b
SC
2848 /* Dump the insn in the assembly for debugging. */
2849 if (flag_dump_rtl_in_asm)
2850 {
2851 print_rtx_head = ASM_COMMENT_START;
2852 print_rtl_single (asm_out_file, insn);
2853 print_rtx_head = "";
2854 }
b9f22704 2855
6c698a6d 2856 if (! constrain_operands_cached (1))
3cf2715d 2857 fatal_insn_not_found (insn);
3cf2715d
DE
2858
2859 /* Some target machines need to prescan each insn before
2860 it is output. */
2861
2862#ifdef FINAL_PRESCAN_INSN
1ccbefce 2863 FINAL_PRESCAN_INSN (insn, recog_data.operand, recog_data.n_operands);
3cf2715d
DE
2864#endif
2865
afe48e06
RH
2866#ifdef HAVE_conditional_execution
2867 if (GET_CODE (PATTERN (insn)) == COND_EXEC)
2868 current_insn_predicate = COND_EXEC_TEST (PATTERN (insn));
2869 else
2870 current_insn_predicate = NULL_RTX;
2871#endif
2872
3cf2715d
DE
2873#ifdef HAVE_cc0
2874 cc_prev_status = cc_status;
2875
2876 /* Update `cc_status' for this instruction.
2877 The instruction's output routine may change it further.
2878 If the output routine for a jump insn needs to depend
2879 on the cc status, it should look at cc_prev_status. */
2880
2881 NOTICE_UPDATE_CC (body, insn);
2882#endif
2883
b1a9f6a0 2884 current_output_insn = debug_insn = insn;
3cf2715d 2885
f73ad30e 2886#if defined (DWARF2_UNWIND_INFO)
fbfa55b0 2887 if (GET_CODE (insn) == CALL_INSN && dwarf2out_do_frame ())
b57d9225
JM
2888 dwarf2out_frame_debug (insn);
2889#endif
2890
4bbf910e
RH
2891 /* Find the proper template for this insn. */
2892 template = get_insn_template (insn_code_number, insn);
3cf2715d 2893
4bbf910e
RH
2894 /* If the C code returns 0, it means that it is a jump insn
2895 which follows a deleted test insn, and that test insn
2896 needs to be reinserted. */
3cf2715d
DE
2897 if (template == 0)
2898 {
efd0378b
HPN
2899 rtx prev;
2900
4bbf910e
RH
2901 if (prev_nonnote_insn (insn) != last_ignored_compare)
2902 abort ();
2903 new_block = 0;
efd0378b
HPN
2904
2905 /* We have already processed the notes between the setter and
2906 the user. Make sure we don't process them again, this is
2907 particularly important if one of the notes is a block
2908 scope note or an EH note. */
2909 for (prev = insn;
2910 prev != last_ignored_compare;
2911 prev = PREV_INSN (prev))
2912 {
2913 if (GET_CODE (prev) == NOTE)
ca6c03ca 2914 delete_insn (prev); /* Use delete_note. */
efd0378b
HPN
2915 }
2916
2917 return prev;
3cf2715d
DE
2918 }
2919
2920 /* If the template is the string "#", it means that this insn must
2921 be split. */
2922 if (template[0] == '#' && template[1] == '\0')
2923 {
2924 rtx new = try_split (body, insn, 0);
2925
2926 /* If we didn't split the insn, go away. */
2927 if (new == insn && PATTERN (new) == body)
cf879efa 2928 fatal_insn ("Could not split insn", insn);
f5d927c0 2929
3d14e82f
JW
2930#ifdef HAVE_ATTR_length
2931 /* This instruction should have been split in shorten_branches,
2932 to ensure that we would have valid length info for the
2933 splitees. */
2934 abort ();
2935#endif
2936
3cf2715d
DE
2937 new_block = 0;
2938 return new;
2939 }
f5d927c0 2940
3cf2715d
DE
2941 if (prescan > 0)
2942 break;
2943
ce152ef8
AM
2944#ifdef IA64_UNWIND_INFO
2945 IA64_UNWIND_EMIT (asm_out_file, insn);
2946#endif
3cf2715d
DE
2947 /* Output assembler code from the template. */
2948
1ccbefce 2949 output_asm_insn (template, recog_data.operand);
3cf2715d 2950
0021b564 2951#if defined (DWARF2_UNWIND_INFO)
0021b564 2952#if defined (HAVE_prologue)
fbfa55b0
RH
2953 if (GET_CODE (insn) == INSN && dwarf2out_do_frame ())
2954 dwarf2out_frame_debug (insn);
2955#else
2956 if (!ACCUMULATE_OUTGOING_ARGS
2957 && GET_CODE (insn) == INSN
2958 && dwarf2out_do_frame ())
2959 dwarf2out_frame_debug (insn);
0021b564
JM
2960#endif
2961#endif
469ac993 2962
3cf2715d
DE
2963#if 0
2964 /* It's not at all clear why we did this and doing so interferes
2965 with tests we'd like to do to use REG_WAS_0 notes, so let's try
2966 with this out. */
2967
2968 /* Mark this insn as having been output. */
2969 INSN_DELETED_P (insn) = 1;
2970#endif
2971
4a8d0c9c
RH
2972 /* Emit information for vtable gc. */
2973 note = find_reg_note (insn, REG_VTABLE_REF, NULL_RTX);
2974 if (note)
2975 assemble_vtable_entry (XEXP (XEXP (note, 0), 0),
2976 INTVAL (XEXP (XEXP (note, 0), 1)));
2977
b1a9f6a0 2978 current_output_insn = debug_insn = 0;
3cf2715d
DE
2979 }
2980 }
2981 return NEXT_INSN (insn);
2982}
2983\f
2984/* Output debugging info to the assembler file FILE
2985 based on the NOTE-insn INSN, assumed to be a line number. */
2986
2987static void
653e276c 2988notice_source_line (insn)
3cf2715d
DE
2989 rtx insn;
2990{
b3694847 2991 const char *filename = NOTE_SOURCE_FILE (insn);
3cf2715d
DE
2992
2993 /* Remember filename for basic block profiling.
2994 Filenames are allocated on the permanent obstack
2995 or are passed in ARGV, so we don't have to save
2996 the string. */
2997
2998 if (profile_block_flag && last_filename != filename)
2999 bb_file_label_num = add_bb_string (filename, TRUE);
3000
3001 last_filename = filename;
3002 last_linenum = NOTE_LINE_NUMBER (insn);
eac40081
RK
3003 high_block_linenum = MAX (last_linenum, high_block_linenum);
3004 high_function_linenum = MAX (last_linenum, high_function_linenum);
3cf2715d
DE
3005}
3006\f
0304f787
JL
3007/* For each operand in INSN, simplify (subreg (reg)) so that it refers
3008 directly to the desired hard register. */
f5d927c0 3009
0304f787
JL
3010void
3011cleanup_subreg_operands (insn)
3012 rtx insn;
3013{
f62a15e3 3014 int i;
6c698a6d 3015 extract_insn_cached (insn);
1ccbefce 3016 for (i = 0; i < recog_data.n_operands; i++)
0304f787 3017 {
1ccbefce 3018 if (GET_CODE (recog_data.operand[i]) == SUBREG)
49d801d3 3019 recog_data.operand[i] = alter_subreg (recog_data.operand_loc[i]);
1ccbefce 3020 else if (GET_CODE (recog_data.operand[i]) == PLUS
04337620
BS
3021 || GET_CODE (recog_data.operand[i]) == MULT
3022 || GET_CODE (recog_data.operand[i]) == MEM)
49d801d3 3023 recog_data.operand[i] = walk_alter_subreg (recog_data.operand_loc[i]);
0304f787
JL
3024 }
3025
1ccbefce 3026 for (i = 0; i < recog_data.n_dups; i++)
0304f787 3027 {
1ccbefce 3028 if (GET_CODE (*recog_data.dup_loc[i]) == SUBREG)
49d801d3 3029 *recog_data.dup_loc[i] = alter_subreg (recog_data.dup_loc[i]);
1ccbefce 3030 else if (GET_CODE (*recog_data.dup_loc[i]) == PLUS
04337620
BS
3031 || GET_CODE (*recog_data.dup_loc[i]) == MULT
3032 || GET_CODE (*recog_data.dup_loc[i]) == MEM)
49d801d3 3033 *recog_data.dup_loc[i] = walk_alter_subreg (recog_data.dup_loc[i]);
0304f787
JL
3034 }
3035}
3036
3cf2715d
DE
3037/* If X is a SUBREG, replace it with a REG or a MEM,
3038 based on the thing it is a subreg of. */
3039
3040rtx
49d801d3
JH
3041alter_subreg (xp)
3042 rtx *xp;
3cf2715d 3043{
49d801d3 3044 rtx x = *xp;
b3694847 3045 rtx y = SUBREG_REG (x);
f5963e61 3046
49d801d3
JH
3047 /* simplify_subreg does not remove subreg from volatile references.
3048 We are required to. */
3049 if (GET_CODE (y) == MEM)
3050 *xp = adjust_address (y, GET_MODE (x), SUBREG_BYTE (x));
3051 else
fea54805
RK
3052 {
3053 rtx new = simplify_subreg (GET_MODE (x), y, GET_MODE (y),
3054 SUBREG_BYTE (x));
3055
3056 if (new != 0)
3057 *xp = new;
3058 /* Simplify_subreg can't handle some REG cases, but we have to. */
3059 else if (GET_CODE (y) == REG)
3060 {
3061 REGNO (x) = subreg_hard_regno (x, 1);
3062 PUT_CODE (x, REG);
3063 ORIGINAL_REGNO (x) = ORIGINAL_REGNO (y);
3064 /* This field has a different meaning for REGs and SUBREGs. Make
3065 sure to clear it! */
3066 x->used = 0;
3067 }
3068 else
3069 abort ();
3070 }
3071
49d801d3 3072 return *xp;
3cf2715d
DE
3073}
3074
3075/* Do alter_subreg on all the SUBREGs contained in X. */
3076
3077static rtx
49d801d3
JH
3078walk_alter_subreg (xp)
3079 rtx *xp;
3cf2715d 3080{
49d801d3 3081 rtx x = *xp;
3cf2715d
DE
3082 switch (GET_CODE (x))
3083 {
3084 case PLUS:
3085 case MULT:
49d801d3
JH
3086 XEXP (x, 0) = walk_alter_subreg (&XEXP (x, 0));
3087 XEXP (x, 1) = walk_alter_subreg (&XEXP (x, 1));
3cf2715d
DE
3088 break;
3089
3090 case MEM:
49d801d3 3091 XEXP (x, 0) = walk_alter_subreg (&XEXP (x, 0));
3cf2715d
DE
3092 break;
3093
3094 case SUBREG:
49d801d3 3095 return alter_subreg (xp);
f5d927c0 3096
e9a25f70
JL
3097 default:
3098 break;
3cf2715d
DE
3099 }
3100
5bc72aeb 3101 return *xp;
3cf2715d
DE
3102}
3103\f
3104#ifdef HAVE_cc0
3105
3106/* Given BODY, the body of a jump instruction, alter the jump condition
3107 as required by the bits that are set in cc_status.flags.
3108 Not all of the bits there can be handled at this level in all cases.
3109
3110 The value is normally 0.
3111 1 means that the condition has become always true.
3112 -1 means that the condition has become always false.
3113 2 means that COND has been altered. */
3114
3115static int
3116alter_cond (cond)
b3694847 3117 rtx cond;
3cf2715d
DE
3118{
3119 int value = 0;
3120
3121 if (cc_status.flags & CC_REVERSED)
3122 {
3123 value = 2;
3124 PUT_CODE (cond, swap_condition (GET_CODE (cond)));
3125 }
3126
3127 if (cc_status.flags & CC_INVERTED)
3128 {
3129 value = 2;
3130 PUT_CODE (cond, reverse_condition (GET_CODE (cond)));
3131 }
3132
3133 if (cc_status.flags & CC_NOT_POSITIVE)
3134 switch (GET_CODE (cond))
3135 {
3136 case LE:
3137 case LEU:
3138 case GEU:
3139 /* Jump becomes unconditional. */
3140 return 1;
3141
3142 case GT:
3143 case GTU:
3144 case LTU:
3145 /* Jump becomes no-op. */
3146 return -1;
3147
3148 case GE:
3149 PUT_CODE (cond, EQ);
3150 value = 2;
3151 break;
3152
3153 case LT:
3154 PUT_CODE (cond, NE);
3155 value = 2;
3156 break;
f5d927c0 3157
e9a25f70
JL
3158 default:
3159 break;
3cf2715d
DE
3160 }
3161
3162 if (cc_status.flags & CC_NOT_NEGATIVE)
3163 switch (GET_CODE (cond))
3164 {
3165 case GE:
3166 case GEU:
3167 /* Jump becomes unconditional. */
3168 return 1;
3169
3170 case LT:
3171 case LTU:
3172 /* Jump becomes no-op. */
3173 return -1;
3174
3175 case LE:
3176 case LEU:
3177 PUT_CODE (cond, EQ);
3178 value = 2;
3179 break;
3180
3181 case GT:
3182 case GTU:
3183 PUT_CODE (cond, NE);
3184 value = 2;
3185 break;
f5d927c0 3186
e9a25f70
JL
3187 default:
3188 break;
3cf2715d
DE
3189 }
3190
3191 if (cc_status.flags & CC_NO_OVERFLOW)
3192 switch (GET_CODE (cond))
3193 {
3194 case GEU:
3195 /* Jump becomes unconditional. */
3196 return 1;
3197
3198 case LEU:
3199 PUT_CODE (cond, EQ);
3200 value = 2;
3201 break;
3202
3203 case GTU:
3204 PUT_CODE (cond, NE);
3205 value = 2;
3206 break;
3207
3208 case LTU:
3209 /* Jump becomes no-op. */
3210 return -1;
f5d927c0 3211
e9a25f70
JL
3212 default:
3213 break;
3cf2715d
DE
3214 }
3215
3216 if (cc_status.flags & (CC_Z_IN_NOT_N | CC_Z_IN_N))
3217 switch (GET_CODE (cond))
3218 {
e9a25f70 3219 default:
3cf2715d
DE
3220 abort ();
3221
3222 case NE:
3223 PUT_CODE (cond, cc_status.flags & CC_Z_IN_N ? GE : LT);
3224 value = 2;
3225 break;
3226
3227 case EQ:
3228 PUT_CODE (cond, cc_status.flags & CC_Z_IN_N ? LT : GE);
3229 value = 2;
3230 break;
3231 }
3232
3233 if (cc_status.flags & CC_NOT_SIGNED)
3234 /* The flags are valid if signed condition operators are converted
3235 to unsigned. */
3236 switch (GET_CODE (cond))
3237 {
3238 case LE:
3239 PUT_CODE (cond, LEU);
3240 value = 2;
3241 break;
3242
3243 case LT:
3244 PUT_CODE (cond, LTU);
3245 value = 2;
3246 break;
3247
3248 case GT:
3249 PUT_CODE (cond, GTU);
3250 value = 2;
3251 break;
3252
3253 case GE:
3254 PUT_CODE (cond, GEU);
3255 value = 2;
3256 break;
e9a25f70
JL
3257
3258 default:
3259 break;
3cf2715d
DE
3260 }
3261
3262 return value;
3263}
3264#endif
3265\f
3266/* Report inconsistency between the assembler template and the operands.
3267 In an `asm', it's the user's fault; otherwise, the compiler's fault. */
3268
3269void
ab87f8c8
JL
3270output_operand_lossage (msgid)
3271 const char *msgid;
3cf2715d
DE
3272{
3273 if (this_is_asm_operands)
ab87f8c8 3274 error_for_asm (this_is_asm_operands, "invalid `asm': %s", _(msgid));
3cf2715d 3275 else
651a788e 3276 internal_error ("output_operand: %s", _(msgid));
3cf2715d
DE
3277}
3278\f
3279/* Output of assembler code from a template, and its subroutines. */
3280
0d4903b8
RK
3281/* Annotate the assembly with a comment describing the pattern and
3282 alternative used. */
3283
3284static void
3285output_asm_name ()
3286{
3287 if (debug_insn)
3288 {
3289 int num = INSN_CODE (debug_insn);
3290 fprintf (asm_out_file, "\t%s %d\t%s",
3291 ASM_COMMENT_START, INSN_UID (debug_insn),
3292 insn_data[num].name);
3293 if (insn_data[num].n_alternatives > 1)
3294 fprintf (asm_out_file, "/%d", which_alternative + 1);
3295#ifdef HAVE_ATTR_length
3296 fprintf (asm_out_file, "\t[length = %d]",
3297 get_attr_length (debug_insn));
3298#endif
3299 /* Clear this so only the first assembler insn
3300 of any rtl insn will get the special comment for -dp. */
3301 debug_insn = 0;
3302 }
3303}
3304
998d7deb
RH
3305/* If OP is a REG or MEM and we can find a MEM_EXPR corresponding to it
3306 or its address, return that expr . Set *PADDRESSP to 1 if the expr
c5adc06a
RK
3307 corresponds to the address of the object and 0 if to the object. */
3308
3309static tree
998d7deb 3310get_mem_expr_from_op (op, paddressp)
c5adc06a
RK
3311 rtx op;
3312 int *paddressp;
3313{
998d7deb 3314 tree expr;
c5adc06a
RK
3315 int inner_addressp;
3316
3317 *paddressp = 0;
3318
1285011e 3319 if (GET_CODE (op) == REG && ORIGINAL_REGNO (op) >= FIRST_PSEUDO_REGISTER)
c5adc06a
RK
3320 return REGNO_DECL (ORIGINAL_REGNO (op));
3321 else if (GET_CODE (op) != MEM)
3322 return 0;
3323
998d7deb
RH
3324 if (MEM_EXPR (op) != 0)
3325 return MEM_EXPR (op);
c5adc06a
RK
3326
3327 /* Otherwise we have an address, so indicate it and look at the address. */
3328 *paddressp = 1;
3329 op = XEXP (op, 0);
3330
3331 /* First check if we have a decl for the address, then look at the right side
3332 if it is a PLUS. Otherwise, strip off arithmetic and keep looking.
3333 But don't allow the address to itself be indirect. */
998d7deb
RH
3334 if ((expr = get_mem_expr_from_op (op, &inner_addressp)) && ! inner_addressp)
3335 return expr;
c5adc06a 3336 else if (GET_CODE (op) == PLUS
998d7deb
RH
3337 && (expr = get_mem_expr_from_op (XEXP (op, 1), &inner_addressp)))
3338 return expr;
c5adc06a
RK
3339
3340 while (GET_RTX_CLASS (GET_CODE (op)) == '1'
3341 || GET_RTX_CLASS (GET_CODE (op)) == '2')
3342 op = XEXP (op, 0);
3343
998d7deb
RH
3344 expr = get_mem_expr_from_op (op, &inner_addressp);
3345 return inner_addressp ? 0 : expr;
c5adc06a
RK
3346}
3347
4f9b4029
RK
3348/* Output operand names for assembler instructions. OPERANDS is the
3349 operand vector, OPORDER is the order to write the operands, and NOPS
3350 is the number of operands to write. */
3351
3352static void
3353output_asm_operand_names (operands, oporder, nops)
3354 rtx *operands;
3355 int *oporder;
3356 int nops;
3357{
3358 int wrote = 0;
3359 int i;
3360
3361 for (i = 0; i < nops; i++)
3362 {
3363 int addressp;
998d7deb 3364 tree expr = get_mem_expr_from_op (operands[oporder[i]], &addressp);
4f9b4029 3365
998d7deb 3366 if (expr)
4f9b4029 3367 {
998d7deb 3368 fprintf (asm_out_file, "%c%s %s",
1285011e 3369 wrote ? ',' : '\t', wrote ? "" : ASM_COMMENT_START,
998d7deb
RH
3370 addressp ? "*" : "");
3371 print_mem_expr (asm_out_file, expr);
4f9b4029
RK
3372 wrote = 1;
3373 }
3374 }
3375}
3376
3cf2715d
DE
3377/* Output text from TEMPLATE to the assembler output file,
3378 obeying %-directions to substitute operands taken from
3379 the vector OPERANDS.
3380
3381 %N (for N a digit) means print operand N in usual manner.
3382 %lN means require operand N to be a CODE_LABEL or LABEL_REF
3383 and print the label name with no punctuation.
3384 %cN means require operand N to be a constant
3385 and print the constant expression with no punctuation.
3386 %aN means expect operand N to be a memory address
3387 (not a memory reference!) and print a reference
3388 to that address.
3389 %nN means expect operand N to be a constant
3390 and print a constant expression for minus the value
3391 of the operand, with no other punctuation. */
3392
3393void
3394output_asm_insn (template, operands)
9b3142b3 3395 const char *template;
3cf2715d
DE
3396 rtx *operands;
3397{
b3694847
SS
3398 const char *p;
3399 int c;
8554d9a4
JJ
3400#ifdef ASSEMBLER_DIALECT
3401 int dialect = 0;
3402#endif
0d4903b8 3403 int oporder[MAX_RECOG_OPERANDS];
4f9b4029 3404 char opoutput[MAX_RECOG_OPERANDS];
0d4903b8 3405 int ops = 0;
3cf2715d
DE
3406
3407 /* An insn may return a null string template
3408 in a case where no assembler code is needed. */
3409 if (*template == 0)
3410 return;
3411
4f9b4029 3412 memset (opoutput, 0, sizeof opoutput);
3cf2715d
DE
3413 p = template;
3414 putc ('\t', asm_out_file);
3415
3416#ifdef ASM_OUTPUT_OPCODE
3417 ASM_OUTPUT_OPCODE (asm_out_file, p);
3418#endif
3419
b729186a 3420 while ((c = *p++))
3cf2715d
DE
3421 switch (c)
3422 {
3cf2715d 3423 case '\n':
4f9b4029
RK
3424 if (flag_verbose_asm)
3425 output_asm_operand_names (operands, oporder, ops);
0d4903b8
RK
3426 if (flag_print_asm_name)
3427 output_asm_name ();
3428
4f9b4029
RK
3429 ops = 0;
3430 memset (opoutput, 0, sizeof opoutput);
3431
3cf2715d 3432 putc (c, asm_out_file);
cb649530 3433#ifdef ASM_OUTPUT_OPCODE
3cf2715d
DE
3434 while ((c = *p) == '\t')
3435 {
3436 putc (c, asm_out_file);
3437 p++;
3438 }
3439 ASM_OUTPUT_OPCODE (asm_out_file, p);
3cf2715d 3440#endif
cb649530 3441 break;
3cf2715d
DE
3442
3443#ifdef ASSEMBLER_DIALECT
3444 case '{':
b729186a 3445 {
b3694847 3446 int i;
f5d927c0 3447
8554d9a4
JJ
3448 if (dialect)
3449 output_operand_lossage ("nested assembly dialect alternatives");
3450 else
3451 dialect = 1;
3452
b729186a
JL
3453 /* If we want the first dialect, do nothing. Otherwise, skip
3454 DIALECT_NUMBER of strings ending with '|'. */
3455 for (i = 0; i < dialect_number; i++)
3456 {
463a8384 3457 while (*p && *p != '}' && *p++ != '|')
b729186a 3458 ;
463a8384
BS
3459 if (*p == '}')
3460 break;
b729186a
JL
3461 if (*p == '|')
3462 p++;
3463 }
8554d9a4
JJ
3464
3465 if (*p == '\0')
3466 output_operand_lossage ("unterminated assembly dialect alternative");
b729186a 3467 }
3cf2715d
DE
3468 break;
3469
3470 case '|':
8554d9a4
JJ
3471 if (dialect)
3472 {
3473 /* Skip to close brace. */
3474 do
3475 {
3476 if (*p == '\0')
3477 {
3478 output_operand_lossage ("unterminated assembly dialect alternative");
3479 break;
3480 }
3481 }
3482 while (*p++ != '}');
3483 dialect = 0;
3484 }
3485 else
3486 putc (c, asm_out_file);
3cf2715d
DE
3487 break;
3488
3489 case '}':
8554d9a4
JJ
3490 if (! dialect)
3491 putc (c, asm_out_file);
3492 dialect = 0;
3cf2715d
DE
3493 break;
3494#endif
3495
3496 case '%':
3497 /* %% outputs a single %. */
3498 if (*p == '%')
3499 {
3500 p++;
3501 putc (c, asm_out_file);
3502 }
3503 /* %= outputs a number which is unique to each insn in the entire
3504 compilation. This is useful for making local labels that are
3505 referred to more than once in a given insn. */
3506 else if (*p == '=')
3507 {
3508 p++;
3509 fprintf (asm_out_file, "%d", insn_counter);
3510 }
3511 /* % followed by a letter and some digits
3512 outputs an operand in a special way depending on the letter.
3513 Letters `acln' are implemented directly.
3514 Other letters are passed to `output_operand' so that
3515 the PRINT_OPERAND macro can define them. */
0df6c2c7 3516 else if (ISALPHA (*p))
3cf2715d
DE
3517 {
3518 int letter = *p++;
3519 c = atoi (p);
3520
0df6c2c7 3521 if (! ISDIGIT (*p))
3cf2715d 3522 output_operand_lossage ("operand number missing after %-letter");
0d4903b8
RK
3523 else if (this_is_asm_operands
3524 && (c < 0 || (unsigned int) c >= insn_noperands))
3cf2715d
DE
3525 output_operand_lossage ("operand number out of range");
3526 else if (letter == 'l')
3527 output_asm_label (operands[c]);
3528 else if (letter == 'a')
3529 output_address (operands[c]);
3530 else if (letter == 'c')
3531 {
3532 if (CONSTANT_ADDRESS_P (operands[c]))
3533 output_addr_const (asm_out_file, operands[c]);
3534 else
3535 output_operand (operands[c], 'c');
3536 }
3537 else if (letter == 'n')
3538 {
3539 if (GET_CODE (operands[c]) == CONST_INT)
21e3a81b 3540 fprintf (asm_out_file, HOST_WIDE_INT_PRINT_DEC,
3cf2715d
DE
3541 - INTVAL (operands[c]));
3542 else
3543 {
3544 putc ('-', asm_out_file);
3545 output_addr_const (asm_out_file, operands[c]);
3546 }
3547 }
3548 else
3549 output_operand (operands[c], letter);
f5d927c0 3550
4f9b4029
RK
3551 if (!opoutput[c])
3552 oporder[ops++] = c;
3553 opoutput[c] = 1;
0d4903b8 3554
0df6c2c7 3555 while (ISDIGIT (c = *p))
f5d927c0 3556 p++;
3cf2715d
DE
3557 }
3558 /* % followed by a digit outputs an operand the default way. */
0df6c2c7 3559 else if (ISDIGIT (*p))
3cf2715d
DE
3560 {
3561 c = atoi (p);
f5d927c0
KH
3562 if (this_is_asm_operands
3563 && (c < 0 || (unsigned int) c >= insn_noperands))
3cf2715d
DE
3564 output_operand_lossage ("operand number out of range");
3565 else
3566 output_operand (operands[c], 0);
0d4903b8 3567
4f9b4029
RK
3568 if (!opoutput[c])
3569 oporder[ops++] = c;
3570 opoutput[c] = 1;
3571
0df6c2c7 3572 while (ISDIGIT (c = *p))
f5d927c0 3573 p++;
3cf2715d
DE
3574 }
3575 /* % followed by punctuation: output something for that
3576 punctuation character alone, with no operand.
3577 The PRINT_OPERAND macro decides what is actually done. */
3578#ifdef PRINT_OPERAND_PUNCT_VALID_P
f5d927c0 3579 else if (PRINT_OPERAND_PUNCT_VALID_P ((unsigned char) *p))
3cf2715d
DE
3580 output_operand (NULL_RTX, *p++);
3581#endif
3582 else
3583 output_operand_lossage ("invalid %%-code");
3584 break;
3585
3586 default:
3587 putc (c, asm_out_file);
3588 }
3589
0d4903b8
RK
3590 /* Write out the variable names for operands, if we know them. */
3591 if (flag_verbose_asm)
4f9b4029 3592 output_asm_operand_names (operands, oporder, ops);
0d4903b8
RK
3593 if (flag_print_asm_name)
3594 output_asm_name ();
3cf2715d
DE
3595
3596 putc ('\n', asm_out_file);
3597}
3598\f
3599/* Output a LABEL_REF, or a bare CODE_LABEL, as an assembler symbol. */
3600
3601void
3602output_asm_label (x)
3603 rtx x;
3604{
3605 char buf[256];
3606
3607 if (GET_CODE (x) == LABEL_REF)
be1bb652
RH
3608 x = XEXP (x, 0);
3609 if (GET_CODE (x) == CODE_LABEL
3610 || (GET_CODE (x) == NOTE
3611 && NOTE_LINE_NUMBER (x) == NOTE_INSN_DELETED_LABEL))
3cf2715d
DE
3612 ASM_GENERATE_INTERNAL_LABEL (buf, "L", CODE_LABEL_NUMBER (x));
3613 else
3614 output_operand_lossage ("`%l' operand isn't a label");
3615
3616 assemble_name (asm_out_file, buf);
3617}
3618
3619/* Print operand X using machine-dependent assembler syntax.
3620 The macro PRINT_OPERAND is defined just to control this function.
3621 CODE is a non-digit that preceded the operand-number in the % spec,
3622 such as 'z' if the spec was `%z3'. CODE is 0 if there was no char
3623 between the % and the digits.
3624 When CODE is a non-letter, X is 0.
3625
3626 The meanings of the letters are machine-dependent and controlled
3627 by PRINT_OPERAND. */
3628
3629static void
3630output_operand (x, code)
3631 rtx x;
962f1324 3632 int code ATTRIBUTE_UNUSED;
3cf2715d
DE
3633{
3634 if (x && GET_CODE (x) == SUBREG)
49d801d3 3635 x = alter_subreg (&x);
3cf2715d
DE
3636
3637 /* If X is a pseudo-register, abort now rather than writing trash to the
3638 assembler file. */
3639
3640 if (x && GET_CODE (x) == REG && REGNO (x) >= FIRST_PSEUDO_REGISTER)
3641 abort ();
3642
3643 PRINT_OPERAND (asm_out_file, x, code);
3644}
3645
3646/* Print a memory reference operand for address X
3647 using machine-dependent assembler syntax.
3648 The macro PRINT_OPERAND_ADDRESS exists just to control this function. */
3649
3650void
3651output_address (x)
3652 rtx x;
3653{
49d801d3 3654 walk_alter_subreg (&x);
3cf2715d
DE
3655 PRINT_OPERAND_ADDRESS (asm_out_file, x);
3656}
3657\f
3658/* Print an integer constant expression in assembler syntax.
3659 Addition and subtraction are the only arithmetic
3660 that may appear in these expressions. */
3661
3662void
3663output_addr_const (file, x)
3664 FILE *file;
3665 rtx x;
3666{
3667 char buf[256];
3668
3669 restart:
3670 switch (GET_CODE (x))
3671 {
3672 case PC:
eac50d7a 3673 putc ('.', file);
3cf2715d
DE
3674 break;
3675
3676 case SYMBOL_REF:
99c8c61c
AO
3677#ifdef ASM_OUTPUT_SYMBOL_REF
3678 ASM_OUTPUT_SYMBOL_REF (file, x);
3679#else
3cf2715d 3680 assemble_name (file, XSTR (x, 0));
99c8c61c 3681#endif
3cf2715d
DE
3682 break;
3683
3684 case LABEL_REF:
422be3c3
AO
3685 x = XEXP (x, 0);
3686 /* Fall through. */
3cf2715d
DE
3687 case CODE_LABEL:
3688 ASM_GENERATE_INTERNAL_LABEL (buf, "L", CODE_LABEL_NUMBER (x));
2f0b7af6
GK
3689#ifdef ASM_OUTPUT_LABEL_REF
3690 ASM_OUTPUT_LABEL_REF (file, buf);
3691#else
3cf2715d 3692 assemble_name (file, buf);
2f0b7af6 3693#endif
3cf2715d
DE
3694 break;
3695
3696 case CONST_INT:
21e3a81b 3697 fprintf (file, HOST_WIDE_INT_PRINT_DEC, INTVAL (x));
3cf2715d
DE
3698 break;
3699
3700 case CONST:
3701 /* This used to output parentheses around the expression,
3702 but that does not work on the 386 (either ATT or BSD assembler). */
3703 output_addr_const (file, XEXP (x, 0));
3704 break;
3705
3706 case CONST_DOUBLE:
3707 if (GET_MODE (x) == VOIDmode)
3708 {
3709 /* We can use %d if the number is one word and positive. */
3710 if (CONST_DOUBLE_HIGH (x))
21e3a81b 3711 fprintf (file, HOST_WIDE_INT_PRINT_DOUBLE_HEX,
3cf2715d 3712 CONST_DOUBLE_HIGH (x), CONST_DOUBLE_LOW (x));
f5d927c0 3713 else if (CONST_DOUBLE_LOW (x) < 0)
21e3a81b 3714 fprintf (file, HOST_WIDE_INT_PRINT_HEX, CONST_DOUBLE_LOW (x));
3cf2715d 3715 else
21e3a81b 3716 fprintf (file, HOST_WIDE_INT_PRINT_DEC, CONST_DOUBLE_LOW (x));
3cf2715d
DE
3717 }
3718 else
3719 /* We can't handle floating point constants;
3720 PRINT_OPERAND must handle them. */
3721 output_operand_lossage ("floating constant misused");
3722 break;
3723
3724 case PLUS:
3725 /* Some assemblers need integer constants to appear last (eg masm). */
3726 if (GET_CODE (XEXP (x, 0)) == CONST_INT)
3727 {
3728 output_addr_const (file, XEXP (x, 1));
3729 if (INTVAL (XEXP (x, 0)) >= 0)
3730 fprintf (file, "+");
3731 output_addr_const (file, XEXP (x, 0));
3732 }
3733 else
3734 {
3735 output_addr_const (file, XEXP (x, 0));
08106825
AO
3736 if (GET_CODE (XEXP (x, 1)) != CONST_INT
3737 || INTVAL (XEXP (x, 1)) >= 0)
3cf2715d
DE
3738 fprintf (file, "+");
3739 output_addr_const (file, XEXP (x, 1));
3740 }
3741 break;
3742
3743 case MINUS:
3744 /* Avoid outputting things like x-x or x+5-x,
3745 since some assemblers can't handle that. */
3746 x = simplify_subtraction (x);
3747 if (GET_CODE (x) != MINUS)
3748 goto restart;
3749
3750 output_addr_const (file, XEXP (x, 0));
3751 fprintf (file, "-");
422be3c3
AO
3752 if ((GET_CODE (XEXP (x, 1)) == CONST_INT
3753 && INTVAL (XEXP (x, 1)) < 0)
3754 || GET_CODE (XEXP (x, 1)) != CONST_INT)
3cf2715d 3755 {
17b53c33 3756 fputs (targetm.asm_out.open_paren, file);
3cf2715d 3757 output_addr_const (file, XEXP (x, 1));
17b53c33 3758 fputs (targetm.asm_out.close_paren, file);
3cf2715d
DE
3759 }
3760 else
3761 output_addr_const (file, XEXP (x, 1));
3762 break;
3763
3764 case ZERO_EXTEND:
3765 case SIGN_EXTEND:
3766 output_addr_const (file, XEXP (x, 0));
3767 break;
3768
3769 default:
422be3c3
AO
3770#ifdef OUTPUT_ADDR_CONST_EXTRA
3771 OUTPUT_ADDR_CONST_EXTRA (file, x, fail);
3772 break;
3773
3774 fail:
3775#endif
3cf2715d
DE
3776 output_operand_lossage ("invalid expression as operand");
3777 }
3778}
3779\f
3780/* A poor man's fprintf, with the added features of %I, %R, %L, and %U.
3781 %R prints the value of REGISTER_PREFIX.
3782 %L prints the value of LOCAL_LABEL_PREFIX.
3783 %U prints the value of USER_LABEL_PREFIX.
3784 %I prints the value of IMMEDIATE_PREFIX.
3785 %O runs ASM_OUTPUT_OPCODE to transform what follows in the string.
3786 Also supported are %d, %x, %s, %e, %f, %g and %%.
3787
3788 We handle alternate assembler dialects here, just like output_asm_insn. */
3789
3790void
711d877c 3791asm_fprintf VPARAMS ((FILE *file, const char *p, ...))
3cf2715d 3792{
3cf2715d
DE
3793 char buf[10];
3794 char *q, c;
3cf2715d 3795
7a75edb7
AJ
3796 VA_OPEN (argptr, p);
3797 VA_FIXEDARG (argptr, FILE *, file);
3798 VA_FIXEDARG (argptr, const char *, p);
3cf2715d
DE
3799
3800 buf[0] = '%';
3801
b729186a 3802 while ((c = *p++))
3cf2715d
DE
3803 switch (c)
3804 {
3805#ifdef ASSEMBLER_DIALECT
3806 case '{':
b729186a
JL
3807 {
3808 int i;
3cf2715d 3809
b729186a
JL
3810 /* If we want the first dialect, do nothing. Otherwise, skip
3811 DIALECT_NUMBER of strings ending with '|'. */
3812 for (i = 0; i < dialect_number; i++)
3813 {
3814 while (*p && *p++ != '|')
3815 ;
3816
3817 if (*p == '|')
3818 p++;
f5d927c0 3819 }
b729186a 3820 }
3cf2715d
DE
3821 break;
3822
3823 case '|':
3824 /* Skip to close brace. */
3825 while (*p && *p++ != '}')
3826 ;
3827 break;
3828
3829 case '}':
3830 break;
3831#endif
3832
3833 case '%':
3834 c = *p++;
3835 q = &buf[1];
0df6c2c7 3836 while (ISDIGIT (c) || c == '.')
3cf2715d
DE
3837 {
3838 *q++ = c;
3839 c = *p++;
3840 }
3841 switch (c)
3842 {
3843 case '%':
3844 fprintf (file, "%%");
3845 break;
3846
3847 case 'd': case 'i': case 'u':
3848 case 'x': case 'p': case 'X':
3849 case 'o':
3850 *q++ = c;
3851 *q = 0;
3852 fprintf (file, buf, va_arg (argptr, int));
3853 break;
3854
3855 case 'w':
3856 /* This is a prefix to the 'd', 'i', 'u', 'x', 'p', and 'X' cases,
3857 but we do not check for those cases. It means that the value
3858 is a HOST_WIDE_INT, which may be either `int' or `long'. */
3859
21e3a81b
RK
3860#if HOST_BITS_PER_WIDE_INT == HOST_BITS_PER_INT
3861#else
3862#if HOST_BITS_PER_WIDE_INT == HOST_BITS_PER_LONG
3863 *q++ = 'l';
3864#else
3865 *q++ = 'l';
3cf2715d 3866 *q++ = 'l';
21e3a81b 3867#endif
3cf2715d
DE
3868#endif
3869
3870 *q++ = *p++;
3871 *q = 0;
3872 fprintf (file, buf, va_arg (argptr, HOST_WIDE_INT));
3873 break;
3874
3875 case 'l':
3876 *q++ = c;
3877 *q++ = *p++;
3878 *q = 0;
3879 fprintf (file, buf, va_arg (argptr, long));
3880 break;
3881
3882 case 'e':
3883 case 'f':
3884 case 'g':
3885 *q++ = c;
3886 *q = 0;
3887 fprintf (file, buf, va_arg (argptr, double));
3888 break;
3889
3890 case 's':
3891 *q++ = c;
3892 *q = 0;
3893 fprintf (file, buf, va_arg (argptr, char *));
3894 break;
3895
3896 case 'O':
3897#ifdef ASM_OUTPUT_OPCODE
3898 ASM_OUTPUT_OPCODE (asm_out_file, p);
3899#endif
3900 break;
3901
3902 case 'R':
3903#ifdef REGISTER_PREFIX
3904 fprintf (file, "%s", REGISTER_PREFIX);
3905#endif
3906 break;
3907
3908 case 'I':
3909#ifdef IMMEDIATE_PREFIX
3910 fprintf (file, "%s", IMMEDIATE_PREFIX);
3911#endif
3912 break;
3913
3914 case 'L':
3915#ifdef LOCAL_LABEL_PREFIX
3916 fprintf (file, "%s", LOCAL_LABEL_PREFIX);
3917#endif
3918 break;
3919
3920 case 'U':
19283265 3921 fputs (user_label_prefix, file);
3cf2715d
DE
3922 break;
3923
fe0503ea
NC
3924#ifdef ASM_FPRINTF_EXTENSIONS
3925 /* Upper case letters are reserved for general use by asm_fprintf
3926 and so are not available to target specific code. In order to
3927 prevent the ASM_FPRINTF_EXTENSIONS macro from using them then,
3928 they are defined here. As they get turned into real extensions
3929 to asm_fprintf they should be removed from this list. */
3930 case 'A': case 'B': case 'C': case 'D': case 'E':
3931 case 'F': case 'G': case 'H': case 'J': case 'K':
3932 case 'M': case 'N': case 'P': case 'Q': case 'S':
3933 case 'T': case 'V': case 'W': case 'Y': case 'Z':
3934 break;
f5d927c0 3935
fe0503ea
NC
3936 ASM_FPRINTF_EXTENSIONS (file, argptr, p)
3937#endif
3cf2715d
DE
3938 default:
3939 abort ();
3940 }
3941 break;
3942
3943 default:
3944 fputc (c, file);
3945 }
7a75edb7 3946 VA_CLOSE (argptr);
3cf2715d
DE
3947}
3948\f
3949/* Split up a CONST_DOUBLE or integer constant rtx
3950 into two rtx's for single words,
3951 storing in *FIRST the word that comes first in memory in the target
3952 and in *SECOND the other. */
3953
3954void
3955split_double (value, first, second)
3956 rtx value;
3957 rtx *first, *second;
3958{
3959 if (GET_CODE (value) == CONST_INT)
3960 {
5a1a6efd 3961 if (HOST_BITS_PER_WIDE_INT >= (2 * BITS_PER_WORD))
f76b9db2 3962 {
5a1a6efd 3963 /* In this case the CONST_INT holds both target words.
27eef9ce
JC
3964 Extract the bits from it into two word-sized pieces.
3965 Sign extend each half to HOST_WIDE_INT. */
7f251dee
AO
3966 unsigned HOST_WIDE_INT low, high;
3967 unsigned HOST_WIDE_INT mask, sign_bit, sign_extend;
3968
3969 /* Set sign_bit to the most significant bit of a word. */
3970 sign_bit = 1;
3971 sign_bit <<= BITS_PER_WORD - 1;
3972
3973 /* Set mask so that all bits of the word are set. We could
3974 have used 1 << BITS_PER_WORD instead of basing the
3975 calculation on sign_bit. However, on machines where
3976 HOST_BITS_PER_WIDE_INT == BITS_PER_WORD, it could cause a
3977 compiler warning, even though the code would never be
3978 executed. */
3979 mask = sign_bit << 1;
3980 mask--;
3981
3982 /* Set sign_extend as any remaining bits. */
3983 sign_extend = ~mask;
f5d927c0 3984
7f251dee
AO
3985 /* Pick the lower word and sign-extend it. */
3986 low = INTVAL (value);
3987 low &= mask;
3988 if (low & sign_bit)
3989 low |= sign_extend;
3990
3991 /* Pick the higher word, shifted to the least significant
3992 bits, and sign-extend it. */
3993 high = INTVAL (value);
3994 high >>= BITS_PER_WORD - 1;
3995 high >>= 1;
3996 high &= mask;
3997 if (high & sign_bit)
3998 high |= sign_extend;
3999
4000 /* Store the words in the target machine order. */
5a1a6efd
RK
4001 if (WORDS_BIG_ENDIAN)
4002 {
7f251dee
AO
4003 *first = GEN_INT (high);
4004 *second = GEN_INT (low);
5a1a6efd
RK
4005 }
4006 else
4007 {
7f251dee
AO
4008 *first = GEN_INT (low);
4009 *second = GEN_INT (high);
5a1a6efd 4010 }
f76b9db2
ILT
4011 }
4012 else
4013 {
5a1a6efd
RK
4014 /* The rule for using CONST_INT for a wider mode
4015 is that we regard the value as signed.
4016 So sign-extend it. */
4017 rtx high = (INTVAL (value) < 0 ? constm1_rtx : const0_rtx);
4018 if (WORDS_BIG_ENDIAN)
4019 {
4020 *first = high;
4021 *second = value;
4022 }
4023 else
4024 {
4025 *first = value;
4026 *second = high;
4027 }
f76b9db2 4028 }
3cf2715d
DE
4029 }
4030 else if (GET_CODE (value) != CONST_DOUBLE)
4031 {
f76b9db2
ILT
4032 if (WORDS_BIG_ENDIAN)
4033 {
4034 *first = const0_rtx;
4035 *second = value;
4036 }
4037 else
4038 {
4039 *first = value;
4040 *second = const0_rtx;
4041 }
3cf2715d
DE
4042 }
4043 else if (GET_MODE (value) == VOIDmode
4044 /* This is the old way we did CONST_DOUBLE integers. */
4045 || GET_MODE_CLASS (GET_MODE (value)) == MODE_INT)
4046 {
4047 /* In an integer, the words are defined as most and least significant.
4048 So order them by the target's convention. */
f76b9db2
ILT
4049 if (WORDS_BIG_ENDIAN)
4050 {
4051 *first = GEN_INT (CONST_DOUBLE_HIGH (value));
4052 *second = GEN_INT (CONST_DOUBLE_LOW (value));
4053 }
4054 else
4055 {
4056 *first = GEN_INT (CONST_DOUBLE_LOW (value));
4057 *second = GEN_INT (CONST_DOUBLE_HIGH (value));
4058 }
3cf2715d
DE
4059 }
4060 else
4061 {
4062#ifdef REAL_ARITHMETIC
f5d927c0
KH
4063 REAL_VALUE_TYPE r;
4064 long l[2];
3cf2715d
DE
4065 REAL_VALUE_FROM_CONST_DOUBLE (r, value);
4066
4067 /* Note, this converts the REAL_VALUE_TYPE to the target's
4068 format, splits up the floating point double and outputs
4069 exactly 32 bits of it into each of l[0] and l[1] --
0f41302f 4070 not necessarily BITS_PER_WORD bits. */
3cf2715d
DE
4071 REAL_VALUE_TO_TARGET_DOUBLE (r, l);
4072
b5a3eb84
JW
4073 /* If 32 bits is an entire word for the target, but not for the host,
4074 then sign-extend on the host so that the number will look the same
4075 way on the host that it would on the target. See for instance
4076 simplify_unary_operation. The #if is needed to avoid compiler
4077 warnings. */
4078
4079#if HOST_BITS_PER_LONG > 32
4080 if (BITS_PER_WORD < HOST_BITS_PER_LONG && BITS_PER_WORD == 32)
4081 {
4082 if (l[0] & ((long) 1 << 31))
4083 l[0] |= ((long) (-1) << 32);
4084 if (l[1] & ((long) 1 << 31))
4085 l[1] |= ((long) (-1) << 32);
4086 }
4087#endif
4088
3cf2715d
DE
4089 *first = GEN_INT ((HOST_WIDE_INT) l[0]);
4090 *second = GEN_INT ((HOST_WIDE_INT) l[1]);
4091#else
4092 if ((HOST_FLOAT_FORMAT != TARGET_FLOAT_FORMAT
4093 || HOST_BITS_PER_WIDE_INT != BITS_PER_WORD)
4094 && ! flag_pretend_float)
7f251dee 4095 abort ();
3cf2715d 4096
f76b9db2
ILT
4097 if (
4098#ifdef HOST_WORDS_BIG_ENDIAN
4099 WORDS_BIG_ENDIAN
3cf2715d 4100#else
f76b9db2 4101 ! WORDS_BIG_ENDIAN
3cf2715d 4102#endif
f76b9db2
ILT
4103 )
4104 {
4105 /* Host and target agree => no need to swap. */
4106 *first = GEN_INT (CONST_DOUBLE_LOW (value));
4107 *second = GEN_INT (CONST_DOUBLE_HIGH (value));
4108 }
4109 else
4110 {
4111 *second = GEN_INT (CONST_DOUBLE_LOW (value));
4112 *first = GEN_INT (CONST_DOUBLE_HIGH (value));
4113 }
3cf2715d
DE
4114#endif /* no REAL_ARITHMETIC */
4115 }
4116}
4117\f
4118/* Return nonzero if this function has no function calls. */
4119
4120int
4121leaf_function_p ()
4122{
4123 rtx insn;
b660f82f 4124 rtx link;
3cf2715d 4125
9e2f9a7f 4126 if (profile_flag || profile_block_flag || profile_arc_flag)
3cf2715d
DE
4127 return 0;
4128
4129 for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
4130 {
7d167afd
JJ
4131 if (GET_CODE (insn) == CALL_INSN
4132 && ! SIBLING_CALL_P (insn))
3cf2715d
DE
4133 return 0;
4134 if (GET_CODE (insn) == INSN
4135 && GET_CODE (PATTERN (insn)) == SEQUENCE
0a1c58a2
JL
4136 && GET_CODE (XVECEXP (PATTERN (insn), 0, 0)) == CALL_INSN
4137 && ! SIBLING_CALL_P (XVECEXP (PATTERN (insn), 0, 0)))
3cf2715d
DE
4138 return 0;
4139 }
b660f82f
JW
4140 for (link = current_function_epilogue_delay_list;
4141 link;
4142 link = XEXP (link, 1))
3cf2715d 4143 {
b660f82f
JW
4144 insn = XEXP (link, 0);
4145
4146 if (GET_CODE (insn) == CALL_INSN
7d167afd 4147 && ! SIBLING_CALL_P (insn))
3cf2715d 4148 return 0;
b660f82f
JW
4149 if (GET_CODE (insn) == INSN
4150 && GET_CODE (PATTERN (insn)) == SEQUENCE
4151 && GET_CODE (XVECEXP (PATTERN (insn), 0, 0)) == CALL_INSN
4152 && ! SIBLING_CALL_P (XVECEXP (PATTERN (insn), 0, 0)))
3cf2715d
DE
4153 return 0;
4154 }
4155
4156 return 1;
4157}
4158
ef6257cd
JH
4159/* Return 1 if branch is an forward branch.
4160 Uses insn_shuid array, so it works only in the final pass. May be used by
4161 output templates to customary add branch prediction hints.
4162 */
4163int
4164final_forward_branch_p (insn)
4165 rtx insn;
4166{
4167 int insn_id, label_id;
4168 if (!uid_shuid)
4169 abort ();
4170 insn_id = INSN_SHUID (insn);
4171 label_id = INSN_SHUID (JUMP_LABEL (insn));
4172 /* We've hit some insns that does not have id information available. */
4173 if (!insn_id || !label_id)
4174 abort ();
4175 return insn_id < label_id;
4176}
4177
3cf2715d
DE
4178/* On some machines, a function with no call insns
4179 can run faster if it doesn't create its own register window.
4180 When output, the leaf function should use only the "output"
4181 registers. Ordinarily, the function would be compiled to use
4182 the "input" registers to find its arguments; it is a candidate
4183 for leaf treatment if it uses only the "input" registers.
4184 Leaf function treatment means renumbering so the function
4185 uses the "output" registers instead. */
4186
4187#ifdef LEAF_REGISTERS
4188
3cf2715d
DE
4189/* Return 1 if this function uses only the registers that can be
4190 safely renumbered. */
4191
4192int
4193only_leaf_regs_used ()
4194{
4195 int i;
7d167afd 4196 char *permitted_reg_in_leaf_functions = LEAF_REGISTERS;
3cf2715d
DE
4197
4198 for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
e5e809f4
JL
4199 if ((regs_ever_live[i] || global_regs[i])
4200 && ! permitted_reg_in_leaf_functions[i])
4201 return 0;
4202
4203 if (current_function_uses_pic_offset_table
4204 && pic_offset_table_rtx != 0
4205 && GET_CODE (pic_offset_table_rtx) == REG
4206 && ! permitted_reg_in_leaf_functions[REGNO (pic_offset_table_rtx)])
4207 return 0;
4208
3cf2715d
DE
4209 return 1;
4210}
4211
4212/* Scan all instructions and renumber all registers into those
4213 available in leaf functions. */
4214
4215static void
4216leaf_renumber_regs (first)
4217 rtx first;
4218{
4219 rtx insn;
4220
4221 /* Renumber only the actual patterns.
4222 The reg-notes can contain frame pointer refs,
4223 and renumbering them could crash, and should not be needed. */
4224 for (insn = first; insn; insn = NEXT_INSN (insn))
2c3c49de 4225 if (INSN_P (insn))
3cf2715d 4226 leaf_renumber_regs_insn (PATTERN (insn));
f5d927c0
KH
4227 for (insn = current_function_epilogue_delay_list;
4228 insn;
4229 insn = XEXP (insn, 1))
2c3c49de 4230 if (INSN_P (XEXP (insn, 0)))
3cf2715d
DE
4231 leaf_renumber_regs_insn (PATTERN (XEXP (insn, 0)));
4232}
4233
4234/* Scan IN_RTX and its subexpressions, and renumber all regs into those
4235 available in leaf functions. */
4236
4237void
4238leaf_renumber_regs_insn (in_rtx)
b3694847 4239 rtx in_rtx;
3cf2715d 4240{
b3694847
SS
4241 int i, j;
4242 const char *format_ptr;
3cf2715d
DE
4243
4244 if (in_rtx == 0)
4245 return;
4246
4247 /* Renumber all input-registers into output-registers.
4248 renumbered_regs would be 1 for an output-register;
4249 they */
4250
4251 if (GET_CODE (in_rtx) == REG)
4252 {
4253 int newreg;
4254
4255 /* Don't renumber the same reg twice. */
4256 if (in_rtx->used)
4257 return;
4258
4259 newreg = REGNO (in_rtx);
4260 /* Don't try to renumber pseudo regs. It is possible for a pseudo reg
4261 to reach here as part of a REG_NOTE. */
4262 if (newreg >= FIRST_PSEUDO_REGISTER)
4263 {
4264 in_rtx->used = 1;
4265 return;
4266 }
4267 newreg = LEAF_REG_REMAP (newreg);
4268 if (newreg < 0)
4269 abort ();
4270 regs_ever_live[REGNO (in_rtx)] = 0;
4271 regs_ever_live[newreg] = 1;
4272 REGNO (in_rtx) = newreg;
4273 in_rtx->used = 1;
4274 }
4275
2c3c49de 4276 if (INSN_P (in_rtx))
3cf2715d
DE
4277 {
4278 /* Inside a SEQUENCE, we find insns.
4279 Renumber just the patterns of these insns,
4280 just as we do for the top-level insns. */
4281 leaf_renumber_regs_insn (PATTERN (in_rtx));
4282 return;
4283 }
4284
4285 format_ptr = GET_RTX_FORMAT (GET_CODE (in_rtx));
4286
4287 for (i = 0; i < GET_RTX_LENGTH (GET_CODE (in_rtx)); i++)
4288 switch (*format_ptr++)
4289 {
4290 case 'e':
4291 leaf_renumber_regs_insn (XEXP (in_rtx, i));
4292 break;
4293
4294 case 'E':
4295 if (NULL != XVEC (in_rtx, i))
4296 {
4297 for (j = 0; j < XVECLEN (in_rtx, i); j++)
4298 leaf_renumber_regs_insn (XVECEXP (in_rtx, i, j));
4299 }
4300 break;
4301
4302 case 'S':
4303 case 's':
4304 case '0':
4305 case 'i':
4306 case 'w':
4307 case 'n':
4308 case 'u':
4309 break;
4310
4311 default:
4312 abort ();
4313 }
4314}
4315#endif