OSDN Git Service

(split_double): Handle CONST_INT that holds both words.
[pf3gnuchains/gcc-fork.git] / gcc / final.c
1 /* Convert RTL to assembler code and output it, for GNU compiler.
2    Copyright (C) 1987, 88, 89, 92, 93, 94, 1995 Free Software Foundation, Inc.
3
4 This file is part of GNU CC.
5
6 GNU CC is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2, or (at your option)
9 any later version.
10
11 GNU CC is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with GNU CC; see the file COPYING.  If not, write to
18 the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.  */
19
20
21 /* This is the final pass of the compiler.
22    It looks at the rtl code for a function and outputs assembler code.
23
24    Call `final_start_function' to output the assembler code for function entry,
25    `final' to output assembler code for some RTL code,
26    `final_end_function' to output assembler code for function exit.
27    If a function is compiled in several pieces, each piece is
28    output separately with `final'.
29
30    Some optimizations are also done at this level.
31    Move instructions that were made unnecessary by good register allocation
32    are detected and omitted from the output.  (Though most of these
33    are removed by the last jump pass.)
34
35    Instructions to set the condition codes are omitted when it can be
36    seen that the condition codes already had the desired values.
37
38    In some cases it is sufficient if the inherited condition codes
39    have related values, but this may require the following insn
40    (the one that tests the condition codes) to be modified.
41
42    The code for the function prologue and epilogue are generated
43    directly as assembler code by the macros FUNCTION_PROLOGUE and
44    FUNCTION_EPILOGUE.  Those instructions never exist as rtl.  */
45
46 #include "config.h"
47 #ifdef __STDC__
48 #include <stdarg.h>
49 #else
50 #include <varargs.h>
51 #endif
52 #include <stdio.h>
53 #include <ctype.h>
54
55 #include "tree.h"
56 #include "rtl.h"
57 #include "regs.h"
58 #include "insn-config.h"
59 #include "insn-flags.h"
60 #include "insn-attr.h"
61 #include "insn-codes.h"
62 #include "recog.h"
63 #include "conditions.h"
64 #include "flags.h"
65 #include "real.h"
66 #include "hard-reg-set.h"
67 #include "defaults.h"
68 #include "output.h"
69
70 /* Get N_SLINE and N_SOL from stab.h if we can expect the file to exist.  */
71 #if defined (DBX_DEBUGGING_INFO) || defined (XCOFF_DEBUGGING_INFO)
72 #if defined (USG) || defined (NO_STAB_H)
73 #include "gstab.h"  /* If doing DBX on sysV, use our own stab.h.  */
74 #else
75 #include <stab.h>  /* On BSD, use the system's stab.h.  */
76 #endif /* not USG */
77 #endif /* DBX_DEBUGGING_INFO || XCOFF_DEBUGGING_INFO */
78
79 #ifdef XCOFF_DEBUGGING_INFO
80 #include "xcoffout.h"
81 #endif
82
83 /* .stabd code for line number.  */
84 #ifndef N_SLINE
85 #define N_SLINE 0x44
86 #endif
87
88 /* .stabs code for included file name.  */
89 #ifndef N_SOL
90 #define N_SOL 0x84
91 #endif
92
93 #ifndef INT_TYPE_SIZE
94 #define INT_TYPE_SIZE BITS_PER_WORD
95 #endif
96
97 /* If we aren't using cc0, CC_STATUS_INIT shouldn't exist.  So define a
98    null default for it to save conditionalization later.  */
99 #ifndef CC_STATUS_INIT
100 #define CC_STATUS_INIT
101 #endif
102
103 /* How to start an assembler comment.  */
104 #ifndef ASM_COMMENT_START
105 #define ASM_COMMENT_START ";#"
106 #endif
107
108 /* Is the given character a logical line separator for the assembler?  */
109 #ifndef IS_ASM_LOGICAL_LINE_SEPARATOR
110 #define IS_ASM_LOGICAL_LINE_SEPARATOR(C) ((C) == ';')
111 #endif
112
113 /* Nonzero means this function is a leaf function, with no function calls. 
114    This variable exists to be examined in FUNCTION_PROLOGUE
115    and FUNCTION_EPILOGUE.  Always zero, unless set by some action.  */
116 int leaf_function;
117
118 /* Last insn processed by final_scan_insn.  */
119 static rtx debug_insn = 0;
120
121 /* Line number of last NOTE.  */
122 static int last_linenum;
123
124 /* Highest line number in current block.  */
125 static int high_block_linenum;
126
127 /* Likewise for function.  */
128 static int high_function_linenum;
129
130 /* Filename of last NOTE.  */
131 static char *last_filename;
132
133 /* Number of basic blocks seen so far;
134    used if profile_block_flag is set.  */
135 static int count_basic_blocks;
136
137 /* Nonzero while outputting an `asm' with operands.
138    This means that inconsistencies are the user's fault, so don't abort.
139    The precise value is the insn being output, to pass to error_for_asm.  */
140 static rtx this_is_asm_operands;
141
142 /* Number of operands of this insn, for an `asm' with operands.  */
143 static int insn_noperands;
144
145 /* Compare optimization flag.  */
146
147 static rtx last_ignored_compare = 0;
148
149 /* Flag indicating this insn is the start of a new basic block.  */
150
151 static int new_block = 1;
152
153 /* All the symbol-blocks (levels of scoping) in the compilation
154    are assigned sequence numbers in order of appearance of the
155    beginnings of the symbol-blocks.  Both final and dbxout do this,
156    and assume that they will both give the same number to each block.
157    Final uses these sequence numbers to generate assembler label names
158    LBBnnn and LBEnnn for the beginning and end of the symbol-block.
159    Dbxout uses the sequence numbers to generate references to the same labels
160    from the dbx debugging information.
161
162    Sdb records this level at the beginning of each function,
163    in order to find the current level when recursing down declarations.
164    It outputs the block beginning and endings
165    at the point in the asm file where the blocks would begin and end.  */
166
167 int next_block_index;
168
169 /* Assign a unique number to each insn that is output.
170    This can be used to generate unique local labels.  */
171
172 static int insn_counter = 0;
173
174 #ifdef HAVE_cc0
175 /* This variable contains machine-dependent flags (defined in tm.h)
176    set and examined by output routines
177    that describe how to interpret the condition codes properly.  */
178
179 CC_STATUS cc_status;
180
181 /* During output of an insn, this contains a copy of cc_status
182    from before the insn.  */
183
184 CC_STATUS cc_prev_status;
185 #endif
186
187 /* Indexed by hardware reg number, is 1 if that register is ever
188    used in the current function.
189
190    In life_analysis, or in stupid_life_analysis, this is set
191    up to record the hard regs used explicitly.  Reload adds
192    in the hard regs used for holding pseudo regs.  Final uses
193    it to generate the code in the function prologue and epilogue
194    to save and restore registers as needed.  */
195
196 char regs_ever_live[FIRST_PSEUDO_REGISTER];
197
198 /* Nonzero means current function must be given a frame pointer.
199    Set in stmt.c if anything is allocated on the stack there.
200    Set in reload1.c if anything is allocated on the stack there.  */
201
202 int frame_pointer_needed;
203
204 /* Assign unique numbers to labels generated for profiling.  */
205
206 int profile_label_no;
207
208 /* Length so far allocated in PENDING_BLOCKS.  */
209
210 static int max_block_depth;
211
212 /* Stack of sequence numbers of symbol-blocks of which we have seen the
213    beginning but not yet the end.  Sequence numbers are assigned at
214    the beginning; this stack allows us to find the sequence number
215    of a block that is ending.  */
216
217 static int *pending_blocks;
218
219 /* Number of elements currently in use in PENDING_BLOCKS.  */
220
221 static int block_depth;
222
223 /* Nonzero if have enabled APP processing of our assembler output.  */
224
225 static int app_on;
226
227 /* If we are outputting an insn sequence, this contains the sequence rtx.
228    Zero otherwise.  */
229
230 rtx final_sequence;
231
232 #ifdef ASSEMBLER_DIALECT
233
234 /* Number of the assembler dialect to use, starting at 0.  */
235 static int dialect_number;
236 #endif
237
238 /* Indexed by line number, nonzero if there is a note for that line.  */
239
240 static char *line_note_exists;
241
242 /* Linked list to hold line numbers for each basic block.  */
243
244 struct bb_list {
245   struct bb_list *next;         /* pointer to next basic block */
246   int line_num;                 /* line number */
247   int file_label_num;           /* LPBC<n> label # for stored filename */
248   int func_label_num;           /* LPBC<n> label # for stored function name */
249 };
250
251 static struct bb_list *bb_head  = 0;            /* Head of basic block list */
252 static struct bb_list **bb_tail = &bb_head;     /* Ptr to store next bb ptr */
253 static int bb_file_label_num    = -1;           /* Current label # for file */
254 static int bb_func_label_num    = -1;           /* Current label # for func */
255
256 /* Linked list to hold the strings for each file and function name output.  */
257
258 struct bb_str {
259   struct bb_str *next;          /* pointer to next string */
260   char *string;                 /* string */
261   int label_num;                /* label number */
262   int length;                   /* string length */
263 };
264
265 extern rtx peephole             PROTO((rtx));
266
267 static struct bb_str *sbb_head  = 0;            /* Head of string list.  */
268 static struct bb_str **sbb_tail = &sbb_head;    /* Ptr to store next bb str */
269 static int sbb_label_num        = 0;            /* Last label used */
270
271 static int asm_insn_count       PROTO((rtx));
272 static void profile_function    PROTO((FILE *));
273 static void profile_after_prologue PROTO((FILE *));
274 static void add_bb              PROTO((FILE *));
275 static int add_bb_string        PROTO((char *, int));
276 static void output_source_line  PROTO((FILE *, rtx));
277 static rtx walk_alter_subreg    PROTO((rtx));
278 static int alter_cond           PROTO((rtx));
279 static void output_operand      PROTO((rtx, int));
280 static void leaf_renumber_regs  PROTO((rtx));
281
282 extern char *getpwd ();
283 \f
284 /* Initialize data in final at the beginning of a compilation.  */
285
286 void
287 init_final (filename)
288      char *filename;
289 {
290   next_block_index = 2;
291   app_on = 0;
292   max_block_depth = 20;
293   pending_blocks = (int *) xmalloc (20 * sizeof *pending_blocks);
294   final_sequence = 0;
295
296 #ifdef ASSEMBLER_DIALECT
297   dialect_number = ASSEMBLER_DIALECT;
298 #endif
299 }
300
301 /* Called at end of source file,
302    to output the block-profiling table for this entire compilation.  */
303
304 void
305 end_final (filename)
306      char *filename;
307 {
308   int i;
309
310   if (profile_block_flag)
311     {
312       char name[20];
313       int align = exact_log2 (BIGGEST_ALIGNMENT / BITS_PER_UNIT);
314       int size = (POINTER_SIZE / BITS_PER_UNIT) * count_basic_blocks;
315       int rounded = size;
316       struct bb_list *ptr;
317       struct bb_str *sptr;
318
319       rounded += (BIGGEST_ALIGNMENT / BITS_PER_UNIT) - 1;
320       rounded = (rounded / (BIGGEST_ALIGNMENT / BITS_PER_UNIT)
321                  * (BIGGEST_ALIGNMENT / BITS_PER_UNIT));
322
323       data_section ();
324
325       /* Output the main header, of 10 words:
326          0:  1 if this file's initialized, else 0.
327          1:  address of file name (LPBX1).
328          2:  address of table of counts (LPBX2).
329          3:  number of counts in the table.
330          4:  always 0, for compatibility with Sun.
331
332          The following are GNU extensions:
333
334          5:  address of table of start addrs of basic blocks (LPBX3).
335          6:  Number of bytes in this header.
336          7:  address of table of function names (LPBX4).
337          8:  address of table of line numbers (LPBX5) or 0.
338          9:  address of table of file names (LPBX6) or 0.  */
339
340       ASM_OUTPUT_ALIGN (asm_out_file, align);
341
342       ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 0);
343       /* zero word */
344       assemble_integer (const0_rtx, UNITS_PER_WORD, 1);
345
346       /* address of filename */
347       ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 1);
348       assemble_integer (gen_rtx (SYMBOL_REF, Pmode, name), UNITS_PER_WORD, 1);
349
350       /* address of count table */
351       ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 2);
352       assemble_integer (gen_rtx (SYMBOL_REF, Pmode, name), UNITS_PER_WORD, 1);
353
354       /* count of the # of basic blocks */
355       assemble_integer (GEN_INT (count_basic_blocks), UNITS_PER_WORD, 1);
356
357       /* zero word (link field) */
358       assemble_integer (const0_rtx, UNITS_PER_WORD, 1);
359
360       /* address of basic block start address table */
361       ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 3);
362       assemble_integer (gen_rtx (SYMBOL_REF, Pmode, name), UNITS_PER_WORD, 1);
363
364       /* byte count for extended structure.  */
365       assemble_integer (GEN_INT (10 * UNITS_PER_WORD), UNITS_PER_WORD, 1);
366
367       /* address of function name table */
368       ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 4);
369       assemble_integer (gen_rtx (SYMBOL_REF, Pmode, name), UNITS_PER_WORD, 1);
370
371       /* address of line number and filename tables if debugging.  */
372       if (write_symbols != NO_DEBUG)
373         {
374           ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 5);
375           assemble_integer (gen_rtx (SYMBOL_REF, Pmode, name), UNITS_PER_WORD, 1);
376           ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 6);
377           assemble_integer (gen_rtx (SYMBOL_REF, Pmode, name), UNITS_PER_WORD, 1);
378         }
379       else
380         {
381           assemble_integer (const0_rtx, UNITS_PER_WORD, 1);
382           assemble_integer (const0_rtx, UNITS_PER_WORD, 1);
383         }
384
385       /* Output the file name changing the suffix to .d for Sun tcov
386          compatibility.  */
387       ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 1);
388       {
389         char *cwd = getpwd ();
390         int len = strlen (filename) + strlen (cwd) + 1;
391         char *data_file = (char *) alloca (len + 4);
392
393         strcpy (data_file, cwd);
394         strcat (data_file, "/");
395         strcat (data_file, filename);
396         strip_off_ending (data_file, len);
397         strcat (data_file, ".d");
398         assemble_string (data_file, strlen (data_file) + 1);
399       }
400
401       /* Make space for the table of counts.  */
402       if (flag_no_common || size == 0)
403         {
404           /* Realign data section.  */
405           ASM_OUTPUT_ALIGN (asm_out_file, align);
406           ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 2);
407           if (size != 0)
408             assemble_zeros (size);
409         }
410       else
411         {
412           ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 2);
413 #ifdef ASM_OUTPUT_SHARED_LOCAL
414           if (flag_shared_data)
415             ASM_OUTPUT_SHARED_LOCAL (asm_out_file, name, size, rounded);
416           else
417 #endif
418 #ifdef ASM_OUTPUT_ALIGNED_LOCAL
419             ASM_OUTPUT_ALIGNED_LOCAL (asm_out_file, name, size,
420                                       BIGGEST_ALIGNMENT);
421 #else
422             ASM_OUTPUT_LOCAL (asm_out_file, name, size, rounded);
423 #endif
424         }
425
426       /* Output any basic block strings */
427       readonly_data_section ();
428       if (sbb_head)
429         {
430           ASM_OUTPUT_ALIGN (asm_out_file, align);
431           for (sptr = sbb_head; sptr != 0; sptr = sptr->next)
432             {
433               ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBC", sptr->label_num);
434               assemble_string (sptr->string, sptr->length);
435             }
436         }
437
438       /* Output the table of addresses.  */
439       /* Realign in new section */
440       ASM_OUTPUT_ALIGN (asm_out_file, align);
441       ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 3);
442       for (i = 0; i < count_basic_blocks; i++)
443         {
444           ASM_GENERATE_INTERNAL_LABEL (name, "LPB", i);
445           assemble_integer (gen_rtx (SYMBOL_REF, Pmode, name),
446                             UNITS_PER_WORD, 1);
447         }
448
449       /* Output the table of function names.  */
450       ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 4);
451       for ((ptr = bb_head), (i = 0); ptr != 0; (ptr = ptr->next), i++)
452         {
453           if (ptr->func_label_num >= 0)
454             {
455               ASM_GENERATE_INTERNAL_LABEL (name, "LPBC", ptr->func_label_num);
456               assemble_integer (gen_rtx (SYMBOL_REF, Pmode, name),
457                                 UNITS_PER_WORD, 1);
458             }
459           else
460             assemble_integer (const0_rtx, UNITS_PER_WORD, 1);
461         }
462
463       for ( ; i < count_basic_blocks; i++)
464         assemble_integer (const0_rtx, UNITS_PER_WORD, 1);
465
466       if (write_symbols != NO_DEBUG)
467         {
468           /* Output the table of line numbers.  */
469           ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 5);
470           for ((ptr = bb_head), (i = 0); ptr != 0; (ptr = ptr->next), i++)
471             assemble_integer (GEN_INT (ptr->line_num), UNITS_PER_WORD, 1);
472
473           for ( ; i < count_basic_blocks; i++)
474             assemble_integer (const0_rtx, UNITS_PER_WORD, 1);
475
476           /* Output the table of file names.  */
477           ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, "LPBX", 6);
478           for ((ptr = bb_head), (i = 0); ptr != 0; (ptr = ptr->next), i++)
479             {
480               if (ptr->file_label_num >= 0)
481                 {
482                   ASM_GENERATE_INTERNAL_LABEL (name, "LPBC", ptr->file_label_num);
483                   assemble_integer (gen_rtx (SYMBOL_REF, Pmode, name),
484                                     UNITS_PER_WORD, 1);
485                 }
486               else
487                 assemble_integer (const0_rtx, UNITS_PER_WORD, 1);
488             }
489
490           for ( ; i < count_basic_blocks; i++)
491             assemble_integer (const0_rtx, UNITS_PER_WORD, 1);
492         }
493
494       /* End with the address of the table of addresses,
495          so we can find it easily, as the last word in the file's text.  */
496       ASM_GENERATE_INTERNAL_LABEL (name, "LPBX", 3);
497       assemble_integer (gen_rtx (SYMBOL_REF, Pmode, name), UNITS_PER_WORD, 1);
498     }
499 }
500
501 /* Enable APP processing of subsequent output.
502    Used before the output from an `asm' statement.  */
503
504 void
505 app_enable ()
506 {
507   if (! app_on)
508     {
509       fprintf (asm_out_file, ASM_APP_ON);
510       app_on = 1;
511     }
512 }
513
514 /* Disable APP processing of subsequent output.
515    Called from varasm.c before most kinds of output.  */
516
517 void
518 app_disable ()
519 {
520   if (app_on)
521     {
522       fprintf (asm_out_file, ASM_APP_OFF);
523       app_on = 0;
524     }
525 }
526 \f
527 /* Return the number of slots filled in the current 
528    delayed branch sequence (we don't count the insn needing the
529    delay slot).   Zero if not in a delayed branch sequence.  */
530
531 #ifdef DELAY_SLOTS
532 int
533 dbr_sequence_length ()
534 {
535   if (final_sequence != 0)
536     return XVECLEN (final_sequence, 0) - 1;
537   else
538     return 0;
539 }
540 #endif
541 \f
542 /* The next two pages contain routines used to compute the length of an insn
543    and to shorten branches.  */
544
545 /* Arrays for insn lengths, and addresses.  The latter is referenced by
546    `insn_current_length'.  */
547
548 static short *insn_lengths;
549 int *insn_addresses;
550
551 /* Address of insn being processed.  Used by `insn_current_length'.  */
552 int insn_current_address;
553
554 /* Indicate that branch shortening hasn't yet been done.  */
555
556 void
557 init_insn_lengths ()
558 {
559   insn_lengths = 0;
560 }
561
562 /* Obtain the current length of an insn.  If branch shortening has been done,
563    get its actual length.  Otherwise, get its maximum length.  */
564
565 int
566 get_attr_length (insn)
567      rtx insn;
568 {
569 #ifdef HAVE_ATTR_length
570   rtx body;
571   int i;
572   int length = 0;
573
574   if (insn_lengths)
575     return insn_lengths[INSN_UID (insn)];
576   else
577     switch (GET_CODE (insn))
578       {
579       case NOTE:
580       case BARRIER:
581       case CODE_LABEL:
582         return 0;
583
584       case CALL_INSN:
585         length = insn_default_length (insn);
586         break;
587
588       case JUMP_INSN:
589         body = PATTERN (insn);
590         if (GET_CODE (body) == ADDR_VEC || GET_CODE (body) == ADDR_DIFF_VEC)
591           {
592             /* This only takes room if jump tables go into the text section.  */
593 #if !defined(READONLY_DATA_SECTION) || defined(JUMP_TABLES_IN_TEXT_SECTION)
594             length = (XVECLEN (body, GET_CODE (body) == ADDR_DIFF_VEC)
595                       * GET_MODE_SIZE (GET_MODE (body)));
596
597             /* Be pessimistic and assume worst-case alignment.  */
598             length += (GET_MODE_SIZE (GET_MODE (body)) - 1);
599 #else
600             return 0;
601 #endif
602           }
603         else
604           length = insn_default_length (insn);
605         break;
606
607       case INSN:
608         body = PATTERN (insn);
609         if (GET_CODE (body) == USE || GET_CODE (body) == CLOBBER)
610           return 0;
611
612         else if (GET_CODE (body) == ASM_INPUT || asm_noperands (body) >= 0)
613           length = asm_insn_count (body) * insn_default_length (insn);
614         else if (GET_CODE (body) == SEQUENCE)
615           for (i = 0; i < XVECLEN (body, 0); i++)
616             length += get_attr_length (XVECEXP (body, 0, i));
617         else
618           length = insn_default_length (insn);
619       }
620
621 #ifdef ADJUST_INSN_LENGTH
622   ADJUST_INSN_LENGTH (insn, length);
623 #endif
624   return length;
625 #else /* not HAVE_ATTR_length */
626   return 0;
627 #endif /* not HAVE_ATTR_length */
628 }
629 \f
630 /* Make a pass over all insns and compute their actual lengths by shortening
631    any branches of variable length if possible.  */
632
633 /* Give a default value for the lowest address in a function.  */
634
635 #ifndef FIRST_INSN_ADDRESS
636 #define FIRST_INSN_ADDRESS 0
637 #endif
638
639 void
640 shorten_branches (first)
641      rtx first;
642 {
643 #ifdef HAVE_ATTR_length
644   rtx insn;
645   int something_changed = 1;
646   int max_uid = 0;
647   char *varying_length;
648   rtx body;
649   int uid;
650
651   /* Compute maximum UID and allocate arrays.  */
652   for (insn = first; insn; insn = NEXT_INSN (insn))
653     if (INSN_UID (insn) > max_uid)
654       max_uid = INSN_UID (insn);
655
656   max_uid++;
657   insn_lengths = (short *) oballoc (max_uid * sizeof (short));
658   insn_addresses = (int *) oballoc (max_uid * sizeof (int));
659   varying_length = (char *) oballoc (max_uid * sizeof (char));
660
661   /* Compute initial lengths, addresses, and varying flags for each insn.  */
662   for (insn_current_address = FIRST_INSN_ADDRESS, insn = first;
663        insn != 0;
664        insn_current_address += insn_lengths[uid], insn = NEXT_INSN (insn))
665     {
666       uid = INSN_UID (insn);
667       insn_addresses[uid] = insn_current_address;
668       insn_lengths[uid] = 0;
669       varying_length[uid] = 0;
670       
671       if (GET_CODE (insn) == NOTE || GET_CODE (insn) == BARRIER
672           || GET_CODE (insn) == CODE_LABEL)
673         continue;
674
675       body = PATTERN (insn);
676       if (GET_CODE (body) == ADDR_VEC || GET_CODE (body) == ADDR_DIFF_VEC)
677         {
678           /* This only takes room if read-only data goes into the text
679              section.  */
680 #if !defined(READONLY_DATA_SECTION) || defined(JUMP_TABLES_IN_TEXT_SECTION)
681           int unitsize = GET_MODE_SIZE (GET_MODE (body));
682
683           insn_lengths[uid] = (XVECLEN (body, GET_CODE (body) == ADDR_DIFF_VEC)
684                                * GET_MODE_SIZE (GET_MODE (body)));
685
686           /* Account for possible alignment.  */
687           insn_lengths[uid]
688             += unitsize - (insn_current_address & (unitsize - 1));
689 #else
690           ;
691 #endif
692         }
693       else if (asm_noperands (body) >= 0)
694         insn_lengths[uid] = asm_insn_count (body) * insn_default_length (insn);
695       else if (GET_CODE (body) == SEQUENCE)
696         {
697           int i;
698           int const_delay_slots;
699 #ifdef DELAY_SLOTS
700           const_delay_slots = const_num_delay_slots (XVECEXP (body, 0, 0));
701 #else
702           const_delay_slots = 0;
703 #endif
704           /* Inside a delay slot sequence, we do not do any branch shortening
705              if the shortening could change the number of delay slots
706              of the branch. */
707           for (i = 0; i < XVECLEN (body, 0); i++)
708             {
709               rtx inner_insn = XVECEXP (body, 0, i);
710               int inner_uid = INSN_UID (inner_insn);
711               int inner_length;
712
713               if (asm_noperands (PATTERN (XVECEXP (body, 0, i))) >= 0)
714                 inner_length = (asm_insn_count (PATTERN (inner_insn))
715                                 * insn_default_length (inner_insn));
716               else
717                 inner_length = insn_default_length (inner_insn);
718               
719               insn_lengths[inner_uid] = inner_length;
720               if (const_delay_slots)
721                 {
722                   if ((varying_length[inner_uid]
723                        = insn_variable_length_p (inner_insn)) != 0)
724                     varying_length[uid] = 1;
725                   insn_addresses[inner_uid] = (insn_current_address +
726                                                insn_lengths[uid]);
727                 }
728               else
729                 varying_length[inner_uid] = 0;
730               insn_lengths[uid] += inner_length;
731             }
732         }
733       else if (GET_CODE (body) != USE && GET_CODE (body) != CLOBBER)
734         {
735           insn_lengths[uid] = insn_default_length (insn);
736           varying_length[uid] = insn_variable_length_p (insn);
737         }
738
739       /* If needed, do any adjustment.  */
740 #ifdef ADJUST_INSN_LENGTH
741       ADJUST_INSN_LENGTH (insn, insn_lengths[uid]);
742 #endif
743     }
744
745   /* Now loop over all the insns finding varying length insns.  For each,
746      get the current insn length.  If it has changed, reflect the change.
747      When nothing changes for a full pass, we are done.  */
748
749   while (something_changed)
750     {
751       something_changed = 0;
752       for (insn_current_address = FIRST_INSN_ADDRESS, insn = first;
753            insn != 0;
754            insn = NEXT_INSN (insn))
755         {
756           int new_length;
757           int tmp_length;
758
759           uid = INSN_UID (insn);
760           insn_addresses[uid] = insn_current_address;
761           if (! varying_length[uid])
762             {
763               insn_current_address += insn_lengths[uid];
764               continue;
765             }
766           if (GET_CODE (insn) == INSN && GET_CODE (PATTERN (insn)) == SEQUENCE)
767             {
768               int i;
769               
770               body = PATTERN (insn);
771               new_length = 0;
772               for (i = 0; i < XVECLEN (body, 0); i++)
773                 {
774                   rtx inner_insn = XVECEXP (body, 0, i);
775                   int inner_uid = INSN_UID (inner_insn);
776                   int inner_length;
777
778                   insn_addresses[inner_uid] = insn_current_address;
779
780                   /* insn_current_length returns 0 for insns with a
781                      non-varying length.  */
782                   if (! varying_length[inner_uid])
783                     inner_length = insn_lengths[inner_uid];
784                   else
785                     inner_length = insn_current_length (inner_insn);
786
787                   if (inner_length != insn_lengths[inner_uid])
788                     {
789                       insn_lengths[inner_uid] = inner_length;
790                       something_changed = 1;
791                     }
792                   insn_current_address += insn_lengths[inner_uid];
793                   new_length += inner_length;
794                 }
795             }
796           else
797             {
798               new_length = insn_current_length (insn);
799               insn_current_address += new_length;
800             }
801
802 #ifdef SHORTEN_WITH_ADJUST_INSN_LENGTH
803 #ifdef ADJUST_INSN_LENGTH
804           /* If needed, do any adjustment.  */
805           tmp_length = new_length;
806           ADJUST_INSN_LENGTH (insn, new_length);
807           insn_current_address += (new_length - tmp_length);
808 #endif
809 #endif
810
811           if (new_length != insn_lengths[uid])
812             {
813               insn_lengths[uid] = new_length;
814               something_changed = 1;
815             }
816         }
817     }
818 #endif /* HAVE_ATTR_length */
819 }
820
821 #ifdef HAVE_ATTR_length
822 /* Given the body of an INSN known to be generated by an ASM statement, return
823    the number of machine instructions likely to be generated for this insn.
824    This is used to compute its length.  */
825
826 static int
827 asm_insn_count (body)
828      rtx body;
829 {
830   char *template;
831   int count = 1;
832
833   if (GET_CODE (body) == ASM_INPUT)
834     template = XSTR (body, 0);
835   else
836     template = decode_asm_operands (body, NULL_PTR, NULL_PTR,
837                                     NULL_PTR, NULL_PTR);
838
839   for ( ; *template; template++)
840     if (IS_ASM_LOGICAL_LINE_SEPARATOR(*template) || *template == '\n')
841       count++;
842
843   return count;
844 }
845 #endif
846 \f
847 /* Output assembler code for the start of a function,
848    and initialize some of the variables in this file
849    for the new function.  The label for the function and associated
850    assembler pseudo-ops have already been output in `assemble_start_function'.
851
852    FIRST is the first insn of the rtl for the function being compiled.
853    FILE is the file to write assembler code to.
854    OPTIMIZE is nonzero if we should eliminate redundant
855      test and compare insns.  */
856
857 void
858 final_start_function (first, file, optimize)
859      rtx first;
860      FILE *file;
861      int optimize;
862 {
863   block_depth = 0;
864
865   this_is_asm_operands = 0;
866
867 #ifdef NON_SAVING_SETJMP
868   /* A function that calls setjmp should save and restore all the
869      call-saved registers on a system where longjmp clobbers them.  */
870   if (NON_SAVING_SETJMP && current_function_calls_setjmp)
871     {
872       int i;
873
874       for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
875         if (!call_used_regs[i] && !call_fixed_regs[i])
876           regs_ever_live[i] = 1;
877     }
878 #endif
879   
880   /* Initial line number is supposed to be output
881      before the function's prologue and label
882      so that the function's address will not appear to be
883      in the last statement of the preceding function.  */
884   if (NOTE_LINE_NUMBER (first) != NOTE_INSN_DELETED)
885     {
886       last_linenum = high_block_linenum = high_function_linenum
887         = NOTE_LINE_NUMBER (first);
888
889       if (write_symbols == SDB_DEBUG)
890         /* For sdb, let's not, but say we did.
891            We need to set last_linenum for sdbout_function_begin,
892            but we can't have an actual line number before the .bf symbol.
893            (sdb_begin_function_line is not set,
894            and other compilers don't do it.)  */
895         ;
896 #ifdef XCOFF_DEBUGGING_INFO
897       else if (write_symbols == XCOFF_DEBUG)
898         xcoffout_output_first_source_line (file, last_linenum);
899 #endif    
900       else
901         output_source_line (file, first);
902     }
903
904 #ifdef LEAF_REG_REMAP
905   if (leaf_function)
906     leaf_renumber_regs (first);
907 #endif
908
909   /* The Sun386i and perhaps other machines don't work right
910      if the profiling code comes after the prologue.  */
911 #ifdef PROFILE_BEFORE_PROLOGUE
912   if (profile_flag)
913     profile_function (file);
914 #endif /* PROFILE_BEFORE_PROLOGUE */
915
916 #ifdef FUNCTION_PROLOGUE
917   /* First output the function prologue: code to set up the stack frame.  */
918   FUNCTION_PROLOGUE (file, get_frame_size ());
919 #endif
920
921 #if defined (SDB_DEBUGGING_INFO) || defined (XCOFF_DEBUGGING_INFO)
922   if (write_symbols == SDB_DEBUG || write_symbols == XCOFF_DEBUG)
923     next_block_index = 1;
924 #endif
925
926   /* If the machine represents the prologue as RTL, the profiling code must
927      be emitted when NOTE_INSN_PROLOGUE_END is scanned.  */
928 #ifdef HAVE_prologue
929   if (! HAVE_prologue)
930 #endif
931     profile_after_prologue (file);
932
933   profile_label_no++;
934
935   /* If we are doing basic block profiling, remember a printable version
936      of the function name.  */
937   if (profile_block_flag)
938     {
939       char *junk = "function";
940       bb_func_label_num =
941         add_bb_string ((*decl_printable_name) (current_function_decl, &junk), FALSE);
942     }
943 }
944
945 static void
946 profile_after_prologue (file)
947      FILE *file;
948 {
949 #ifdef FUNCTION_BLOCK_PROFILER
950   if (profile_block_flag)
951     {
952       FUNCTION_BLOCK_PROFILER (file, profile_label_no);
953     }
954 #endif /* FUNCTION_BLOCK_PROFILER */
955
956 #ifndef PROFILE_BEFORE_PROLOGUE
957   if (profile_flag)
958     profile_function (file);
959 #endif /* not PROFILE_BEFORE_PROLOGUE */
960 }
961
962 static void
963 profile_function (file)
964      FILE *file;
965 {
966   int align = MIN (BIGGEST_ALIGNMENT, POINTER_SIZE);
967   int sval = current_function_returns_struct;
968   int cxt = current_function_needs_context;
969
970   data_section ();
971   ASM_OUTPUT_ALIGN (file, floor_log2 (align / BITS_PER_UNIT));
972   ASM_OUTPUT_INTERNAL_LABEL (file, "LP", profile_label_no);
973   assemble_integer (const0_rtx, POINTER_SIZE / BITS_PER_UNIT, 1);
974
975   text_section ();
976
977 #ifdef STRUCT_VALUE_INCOMING_REGNUM
978   if (sval)
979     ASM_OUTPUT_REG_PUSH (file, STRUCT_VALUE_INCOMING_REGNUM);
980 #else
981 #ifdef STRUCT_VALUE_REGNUM
982   if (sval)
983     ASM_OUTPUT_REG_PUSH (file, STRUCT_VALUE_REGNUM);
984 #endif
985 #endif
986
987 #if 0
988 #ifdef STATIC_CHAIN_INCOMING_REGNUM
989   if (cxt)
990     ASM_OUTPUT_REG_PUSH (file, STATIC_CHAIN_INCOMING_REGNUM);
991 #else
992 #ifdef STATIC_CHAIN_REGNUM
993   if (cxt)
994     ASM_OUTPUT_REG_PUSH (file, STATIC_CHAIN_REGNUM);
995 #endif
996 #endif
997 #endif                          /* 0 */
998
999   FUNCTION_PROFILER (file, profile_label_no);
1000
1001 #if 0
1002 #ifdef STATIC_CHAIN_INCOMING_REGNUM
1003   if (cxt)
1004     ASM_OUTPUT_REG_POP (file, STATIC_CHAIN_INCOMING_REGNUM);
1005 #else
1006 #ifdef STATIC_CHAIN_REGNUM
1007   if (cxt)
1008     ASM_OUTPUT_REG_POP (file, STATIC_CHAIN_REGNUM);
1009 #endif
1010 #endif
1011 #endif                          /* 0 */
1012
1013 #ifdef STRUCT_VALUE_INCOMING_REGNUM
1014   if (sval)
1015     ASM_OUTPUT_REG_POP (file, STRUCT_VALUE_INCOMING_REGNUM);
1016 #else
1017 #ifdef STRUCT_VALUE_REGNUM
1018   if (sval)
1019     ASM_OUTPUT_REG_POP (file, STRUCT_VALUE_REGNUM);
1020 #endif
1021 #endif
1022 }
1023
1024 /* Output assembler code for the end of a function.
1025    For clarity, args are same as those of `final_start_function'
1026    even though not all of them are needed.  */
1027
1028 void
1029 final_end_function (first, file, optimize)
1030      rtx first;
1031      FILE *file;
1032      int optimize;
1033 {
1034   if (app_on)
1035     {
1036       fprintf (file, ASM_APP_OFF);
1037       app_on = 0;
1038     }
1039
1040 #ifdef SDB_DEBUGGING_INFO
1041   if (write_symbols == SDB_DEBUG)
1042     sdbout_end_function (high_function_linenum);
1043 #endif
1044
1045 #ifdef DWARF_DEBUGGING_INFO
1046   if (write_symbols == DWARF_DEBUG)
1047     dwarfout_end_function ();
1048 #endif
1049
1050 #ifdef XCOFF_DEBUGGING_INFO
1051   if (write_symbols == XCOFF_DEBUG)
1052     xcoffout_end_function (file, high_function_linenum);
1053 #endif
1054
1055 #ifdef FUNCTION_EPILOGUE
1056   /* Finally, output the function epilogue:
1057      code to restore the stack frame and return to the caller.  */
1058   FUNCTION_EPILOGUE (file, get_frame_size ());
1059 #endif
1060
1061 #ifdef SDB_DEBUGGING_INFO
1062   if (write_symbols == SDB_DEBUG)
1063     sdbout_end_epilogue ();
1064 #endif
1065
1066 #ifdef DWARF_DEBUGGING_INFO
1067   if (write_symbols == DWARF_DEBUG)
1068     dwarfout_end_epilogue ();
1069 #endif
1070
1071 #ifdef XCOFF_DEBUGGING_INFO
1072   if (write_symbols == XCOFF_DEBUG)
1073     xcoffout_end_epilogue (file);
1074 #endif
1075
1076   bb_func_label_num = -1;       /* not in function, nuke label # */
1077
1078   /* If FUNCTION_EPILOGUE is not defined, then the function body
1079      itself contains return instructions wherever needed.  */
1080 }
1081 \f
1082 /* Add a block to the linked list that remembers the current line/file/function
1083    for basic block profiling.  Emit the label in front of the basic block and
1084    the instructions that increment the count field.  */
1085
1086 static void
1087 add_bb (file)
1088      FILE *file;
1089 {
1090   struct bb_list *ptr = (struct bb_list *) permalloc (sizeof (struct bb_list));
1091
1092   /* Add basic block to linked list.  */
1093   ptr->next = 0;
1094   ptr->line_num = last_linenum;
1095   ptr->file_label_num = bb_file_label_num;
1096   ptr->func_label_num = bb_func_label_num;
1097   *bb_tail = ptr;
1098   bb_tail = &ptr->next;
1099
1100   /* Enable the table of basic-block use counts
1101      to point at the code it applies to.  */
1102   ASM_OUTPUT_INTERNAL_LABEL (file, "LPB", count_basic_blocks);
1103
1104   /* Before first insn of this basic block, increment the
1105      count of times it was entered.  */
1106 #ifdef BLOCK_PROFILER
1107   BLOCK_PROFILER (file, count_basic_blocks);
1108   CC_STATUS_INIT;
1109 #endif
1110
1111   new_block = 0;
1112   count_basic_blocks++;
1113 }
1114
1115 /* Add a string to be used for basic block profiling.  */
1116
1117 static int
1118 add_bb_string (string, perm_p)
1119      char *string;
1120      int perm_p;
1121 {
1122   int len;
1123   struct bb_str *ptr = 0;
1124
1125   if (!string)
1126     {
1127       string = "<unknown>";
1128       perm_p = TRUE;
1129     }
1130
1131   /* Allocate a new string if the current string isn't permanent.  If
1132      the string is permanent search for the same string in other
1133      allocations.  */
1134
1135   len = strlen (string) + 1;
1136   if (!perm_p)
1137     {
1138       char *p = (char *) permalloc (len);
1139       bcopy (string, p, len);
1140       string = p;
1141     }
1142   else
1143     for (ptr = sbb_head; ptr != (struct bb_str *)0; ptr = ptr->next)
1144       if (ptr->string == string)
1145         break;
1146
1147   /* Allocate a new string block if we need to.  */
1148   if (!ptr)
1149     {
1150       ptr = (struct bb_str *) permalloc (sizeof (*ptr));
1151       ptr->next = 0;
1152       ptr->length = len;
1153       ptr->label_num = sbb_label_num++;
1154       ptr->string = string;
1155       *sbb_tail = ptr;
1156       sbb_tail = &ptr->next;
1157     }
1158
1159   return ptr->label_num;
1160 }
1161
1162 \f
1163 /* Output assembler code for some insns: all or part of a function.
1164    For description of args, see `final_start_function', above.
1165
1166    PRESCAN is 1 if we are not really outputting,
1167      just scanning as if we were outputting.
1168    Prescanning deletes and rearranges insns just like ordinary output.
1169    PRESCAN is -2 if we are outputting after having prescanned.
1170    In this case, don't try to delete or rearrange insns
1171    because that has already been done.
1172    Prescanning is done only on certain machines.  */
1173
1174 void
1175 final (first, file, optimize, prescan)
1176      rtx first;
1177      FILE *file;
1178      int optimize;
1179      int prescan;
1180 {
1181   register rtx insn;
1182   int max_line = 0;
1183
1184   last_ignored_compare = 0;
1185   new_block = 1;
1186
1187   /* Make a map indicating which line numbers appear in this function.
1188      When producing SDB debugging info, delete troublesome line number
1189      notes from inlined functions in other files as well as duplicate
1190      line number notes.  */
1191 #ifdef SDB_DEBUGGING_INFO
1192   if (write_symbols == SDB_DEBUG)
1193     {
1194       rtx last = 0;
1195       for (insn = first; insn; insn = NEXT_INSN (insn))
1196         if (GET_CODE (insn) == NOTE && NOTE_LINE_NUMBER (insn) > 0)
1197           {
1198             if ((RTX_INTEGRATED_P (insn)
1199                  && strcmp (NOTE_SOURCE_FILE (insn), main_input_filename) != 0)
1200                  || (last != 0
1201                      && NOTE_LINE_NUMBER (insn) == NOTE_LINE_NUMBER (last)
1202                      && NOTE_SOURCE_FILE (insn) == NOTE_SOURCE_FILE (last)))
1203               {
1204                 NOTE_LINE_NUMBER (insn) = NOTE_INSN_DELETED;
1205                 NOTE_SOURCE_FILE (insn) = 0;
1206                 continue;
1207               }
1208             last = insn;
1209             if (NOTE_LINE_NUMBER (insn) > max_line)
1210               max_line = NOTE_LINE_NUMBER (insn);
1211           }
1212     }
1213   else
1214 #endif
1215     {
1216       for (insn = first; insn; insn = NEXT_INSN (insn))
1217         if (GET_CODE (insn) == NOTE && NOTE_LINE_NUMBER (insn) > max_line)
1218           max_line = NOTE_LINE_NUMBER (insn);
1219     }
1220
1221   line_note_exists = (char *) oballoc (max_line + 1);
1222   bzero (line_note_exists, max_line + 1);
1223
1224   for (insn = first; insn; insn = NEXT_INSN (insn))
1225     if (GET_CODE (insn) == NOTE && NOTE_LINE_NUMBER (insn) > 0)
1226       line_note_exists[NOTE_LINE_NUMBER (insn)] = 1;
1227
1228   init_recog ();
1229
1230   CC_STATUS_INIT;
1231
1232   /* Output the insns.  */
1233   for (insn = NEXT_INSN (first); insn;)
1234     insn = final_scan_insn (insn, file, optimize, prescan, 0);
1235
1236   /* Do basic-block profiling here
1237      if the last insn was a conditional branch.  */
1238   if (profile_block_flag && new_block)
1239     add_bb (file);
1240 }
1241 \f
1242 /* The final scan for one insn, INSN.
1243    Args are same as in `final', except that INSN
1244    is the insn being scanned.
1245    Value returned is the next insn to be scanned.
1246
1247    NOPEEPHOLES is the flag to disallow peephole processing (currently
1248    used for within delayed branch sequence output).  */
1249
1250 rtx
1251 final_scan_insn (insn, file, optimize, prescan, nopeepholes)
1252      rtx insn;
1253      FILE *file;
1254      int optimize;
1255      int prescan;
1256      int nopeepholes;
1257 {
1258   register int i;
1259   insn_counter++;
1260
1261   /* Ignore deleted insns.  These can occur when we split insns (due to a
1262      template of "#") while not optimizing.  */
1263   if (INSN_DELETED_P (insn))
1264     return NEXT_INSN (insn);
1265
1266   switch (GET_CODE (insn))
1267     {
1268     case NOTE:
1269       if (prescan > 0)
1270         break;
1271
1272       /* Align the beginning of a loop, for higher speed
1273          on certain machines.  */
1274
1275       if (NOTE_LINE_NUMBER (insn) == NOTE_INSN_LOOP_BEG && optimize > 0)
1276         {
1277 #ifdef ASM_OUTPUT_LOOP_ALIGN
1278           rtx next = next_nonnote_insn (insn);
1279           if (next && GET_CODE (next) == CODE_LABEL)
1280             {
1281               ASM_OUTPUT_LOOP_ALIGN (asm_out_file);
1282             }
1283 #endif
1284           break;
1285         }
1286       if (NOTE_LINE_NUMBER (insn) == NOTE_INSN_LOOP_END)
1287         break;
1288
1289       if (NOTE_LINE_NUMBER (insn) == NOTE_INSN_PROLOGUE_END)
1290         {
1291 #ifdef FUNCTION_END_PROLOGUE
1292           FUNCTION_END_PROLOGUE (file);
1293 #endif
1294           profile_after_prologue (file);
1295           break;
1296         }
1297
1298 #ifdef FUNCTION_BEGIN_EPILOGUE
1299       if (NOTE_LINE_NUMBER (insn) == NOTE_INSN_EPILOGUE_BEG)
1300         {
1301           FUNCTION_BEGIN_EPILOGUE (file);
1302           break;
1303         }
1304 #endif
1305
1306       if (write_symbols == NO_DEBUG)
1307         break;
1308       if (NOTE_LINE_NUMBER (insn) == NOTE_INSN_FUNCTION_BEG)
1309         {
1310 #ifdef SDB_DEBUGGING_INFO
1311           if (write_symbols == SDB_DEBUG)
1312             sdbout_begin_function (last_linenum);
1313 #endif
1314 #ifdef XCOFF_DEBUGGING_INFO
1315           if (write_symbols == XCOFF_DEBUG)
1316             xcoffout_begin_function (file, last_linenum);
1317 #endif
1318 #ifdef DWARF_DEBUGGING_INFO
1319           if (write_symbols == DWARF_DEBUG)
1320             dwarfout_begin_function ();
1321 #endif
1322           break;
1323         }
1324       if (NOTE_LINE_NUMBER (insn) == NOTE_INSN_DELETED)
1325         break;                  /* An insn that was "deleted" */
1326       if (app_on)
1327         {
1328           fprintf (file, ASM_APP_OFF);
1329           app_on = 0;
1330         }
1331       if (NOTE_LINE_NUMBER (insn) == NOTE_INSN_BLOCK_BEG
1332           && (debug_info_level == DINFO_LEVEL_NORMAL
1333               || debug_info_level == DINFO_LEVEL_VERBOSE
1334 #ifdef DWARF_DEBUGGING_INFO
1335               || write_symbols == DWARF_DEBUG
1336 #endif
1337              )
1338          )
1339         {
1340           /* Beginning of a symbol-block.  Assign it a sequence number
1341              and push the number onto the stack PENDING_BLOCKS.  */
1342
1343           if (block_depth == max_block_depth)
1344             {
1345               /* PENDING_BLOCKS is full; make it longer.  */
1346               max_block_depth *= 2;
1347               pending_blocks
1348                 = (int *) xrealloc (pending_blocks,
1349                                     max_block_depth * sizeof (int));
1350             }
1351           pending_blocks[block_depth++] = next_block_index;
1352
1353           high_block_linenum = last_linenum;
1354
1355           /* Output debugging info about the symbol-block beginning.  */
1356
1357 #ifdef SDB_DEBUGGING_INFO
1358           if (write_symbols == SDB_DEBUG)
1359             sdbout_begin_block (file, last_linenum, next_block_index);
1360 #endif
1361 #ifdef XCOFF_DEBUGGING_INFO
1362           if (write_symbols == XCOFF_DEBUG)
1363             xcoffout_begin_block (file, last_linenum, next_block_index);
1364 #endif
1365 #ifdef DBX_DEBUGGING_INFO
1366           if (write_symbols == DBX_DEBUG)
1367             ASM_OUTPUT_INTERNAL_LABEL (file, "LBB", next_block_index);
1368 #endif
1369 #ifdef DWARF_DEBUGGING_INFO
1370           if (write_symbols == DWARF_DEBUG && block_depth > 1)
1371             dwarfout_begin_block (next_block_index);
1372 #endif
1373
1374           next_block_index++;
1375         }
1376       else if (NOTE_LINE_NUMBER (insn) == NOTE_INSN_BLOCK_END
1377                && (debug_info_level == DINFO_LEVEL_NORMAL
1378                    || debug_info_level == DINFO_LEVEL_VERBOSE
1379 #ifdef DWARF_DEBUGGING_INFO
1380                    || write_symbols == DWARF_DEBUG
1381 #endif
1382                   )
1383               )
1384         {
1385           /* End of a symbol-block.  Pop its sequence number off
1386              PENDING_BLOCKS and output debugging info based on that.  */
1387
1388           --block_depth;
1389
1390 #ifdef XCOFF_DEBUGGING_INFO
1391           if (write_symbols == XCOFF_DEBUG && block_depth >= 0)
1392             xcoffout_end_block (file, high_block_linenum,
1393                                 pending_blocks[block_depth]);
1394 #endif
1395 #ifdef DBX_DEBUGGING_INFO
1396           if (write_symbols == DBX_DEBUG && block_depth >= 0)
1397             ASM_OUTPUT_INTERNAL_LABEL (file, "LBE",
1398                                        pending_blocks[block_depth]);
1399 #endif
1400 #ifdef SDB_DEBUGGING_INFO
1401           if (write_symbols == SDB_DEBUG && block_depth >= 0)
1402             sdbout_end_block (file, high_block_linenum,
1403                               pending_blocks[block_depth]);
1404 #endif
1405 #ifdef DWARF_DEBUGGING_INFO
1406           if (write_symbols == DWARF_DEBUG && block_depth >= 1)
1407             dwarfout_end_block (pending_blocks[block_depth]);
1408 #endif
1409         }
1410       else if (NOTE_LINE_NUMBER (insn) == NOTE_INSN_DELETED_LABEL
1411                && (debug_info_level == DINFO_LEVEL_NORMAL
1412                    || debug_info_level == DINFO_LEVEL_VERBOSE))
1413         {
1414 #ifdef DWARF_DEBUGGING_INFO
1415           if (write_symbols == DWARF_DEBUG)
1416             dwarfout_label (insn);
1417 #endif
1418         }
1419       else if (NOTE_LINE_NUMBER (insn) > 0)
1420         /* This note is a line-number.  */
1421         {
1422           register rtx note;
1423
1424 #if 0 /* This is what we used to do.  */
1425           output_source_line (file, insn);
1426 #endif
1427           int note_after = 0;
1428
1429           /* If there is anything real after this note,
1430              output it.  If another line note follows, omit this one.  */
1431           for (note = NEXT_INSN (insn); note; note = NEXT_INSN (note))
1432             {
1433               if (GET_CODE (note) != NOTE && GET_CODE (note) != CODE_LABEL)
1434                 break;
1435               /* These types of notes can be significant
1436                  so make sure the preceding line number stays.  */
1437               else if (GET_CODE (note) == NOTE
1438                        && (NOTE_LINE_NUMBER (note) == NOTE_INSN_BLOCK_BEG
1439                            || NOTE_LINE_NUMBER (note) == NOTE_INSN_BLOCK_END
1440                            || NOTE_LINE_NUMBER (note) == NOTE_INSN_FUNCTION_BEG))
1441                 break;
1442               else if (GET_CODE (note) == NOTE && NOTE_LINE_NUMBER (note) > 0)
1443                 {
1444                   /* Another line note follows; we can delete this note
1445                      if no intervening line numbers have notes elsewhere.  */
1446                   int num;
1447                   for (num = NOTE_LINE_NUMBER (insn) + 1;
1448                        num < NOTE_LINE_NUMBER (note);
1449                        num++)
1450                     if (line_note_exists[num])
1451                       break;
1452
1453                   if (num >= NOTE_LINE_NUMBER (note))
1454                     note_after = 1;
1455                   break;
1456                 }
1457             }
1458
1459           /* Output this line note
1460              if it is the first or the last line note in a row.  */
1461           if (!note_after)
1462             output_source_line (file, insn);
1463         }
1464       break;
1465
1466     case BARRIER:
1467 #ifdef ASM_OUTPUT_ALIGN_CODE
1468       /* Don't litter the assembler output with needless alignments.  A
1469          BARRIER will be placed at the end of every function if HAVE_epilogue
1470          is true.  */    
1471       if (NEXT_INSN (insn))
1472         ASM_OUTPUT_ALIGN_CODE (file);
1473 #endif
1474       break;
1475
1476     case CODE_LABEL:
1477       CC_STATUS_INIT;
1478       if (prescan > 0)
1479         break;
1480       new_block = 1;
1481 #ifdef SDB_DEBUGGING_INFO
1482       if (write_symbols == SDB_DEBUG && LABEL_NAME (insn))
1483         sdbout_label (insn);
1484 #endif
1485 #ifdef DWARF_DEBUGGING_INFO
1486       if (write_symbols == DWARF_DEBUG && LABEL_NAME (insn))
1487         dwarfout_label (insn);
1488 #endif
1489       if (app_on)
1490         {
1491           fprintf (file, ASM_APP_OFF);
1492           app_on = 0;
1493         }
1494       if (NEXT_INSN (insn) != 0
1495           && GET_CODE (NEXT_INSN (insn)) == JUMP_INSN)
1496         {
1497           rtx nextbody = PATTERN (NEXT_INSN (insn));
1498
1499           /* If this label is followed by a jump-table,
1500              make sure we put the label in the read-only section.  Also
1501              possibly write the label and jump table together.  */
1502
1503           if (GET_CODE (nextbody) == ADDR_VEC
1504               || GET_CODE (nextbody) == ADDR_DIFF_VEC)
1505             {
1506 #ifndef JUMP_TABLES_IN_TEXT_SECTION
1507               readonly_data_section ();
1508 #ifdef READONLY_DATA_SECTION
1509               ASM_OUTPUT_ALIGN (file,
1510                                 exact_log2 (BIGGEST_ALIGNMENT
1511                                             / BITS_PER_UNIT));
1512 #endif /* READONLY_DATA_SECTION */
1513 #else /* JUMP_TABLES_IN_TEXT_SECTION */
1514               function_section (current_function_decl);
1515 #endif /* JUMP_TABLES_IN_TEXT_SECTION */
1516 #ifdef ASM_OUTPUT_CASE_LABEL
1517               ASM_OUTPUT_CASE_LABEL (file, "L", CODE_LABEL_NUMBER (insn),
1518                                      NEXT_INSN (insn));
1519 #else
1520               ASM_OUTPUT_INTERNAL_LABEL (file, "L", CODE_LABEL_NUMBER (insn));
1521 #endif
1522               break;
1523             }
1524         }
1525
1526       ASM_OUTPUT_INTERNAL_LABEL (file, "L", CODE_LABEL_NUMBER (insn));
1527       break;
1528
1529     default:
1530       {
1531         register rtx body = PATTERN (insn);
1532         int insn_code_number;
1533         char *template;
1534         rtx note;
1535
1536         /* An INSN, JUMP_INSN or CALL_INSN.
1537            First check for special kinds that recog doesn't recognize.  */
1538
1539         if (GET_CODE (body) == USE /* These are just declarations */
1540             || GET_CODE (body) == CLOBBER)
1541           break;
1542
1543 #ifdef HAVE_cc0
1544         /* If there is a REG_CC_SETTER note on this insn, it means that
1545            the setting of the condition code was done in the delay slot
1546            of the insn that branched here.  So recover the cc status
1547            from the insn that set it.  */
1548
1549         note = find_reg_note (insn, REG_CC_SETTER, NULL_RTX);
1550         if (note)
1551           {
1552             NOTICE_UPDATE_CC (PATTERN (XEXP (note, 0)), XEXP (note, 0));
1553             cc_prev_status = cc_status;
1554           }
1555 #endif
1556
1557         /* Detect insns that are really jump-tables
1558            and output them as such.  */
1559
1560         if (GET_CODE (body) == ADDR_VEC || GET_CODE (body) == ADDR_DIFF_VEC)
1561           {
1562             register int vlen, idx;
1563
1564             if (prescan > 0)
1565               break;
1566
1567             if (app_on)
1568               {
1569                 fprintf (file, ASM_APP_OFF);
1570                 app_on = 0;
1571               }
1572
1573             vlen = XVECLEN (body, GET_CODE (body) == ADDR_DIFF_VEC);
1574             for (idx = 0; idx < vlen; idx++)
1575               {
1576                 if (GET_CODE (body) == ADDR_VEC)
1577                   {
1578 #ifdef ASM_OUTPUT_ADDR_VEC_ELT
1579                     ASM_OUTPUT_ADDR_VEC_ELT
1580                       (file, CODE_LABEL_NUMBER (XEXP (XVECEXP (body, 0, idx), 0)));
1581 #else
1582                     abort ();
1583 #endif
1584                   }
1585                 else
1586                   {
1587 #ifdef ASM_OUTPUT_ADDR_DIFF_ELT
1588                     ASM_OUTPUT_ADDR_DIFF_ELT
1589                       (file,
1590                        CODE_LABEL_NUMBER (XEXP (XVECEXP (body, 1, idx), 0)),
1591                        CODE_LABEL_NUMBER (XEXP (XEXP (body, 0), 0)));
1592 #else
1593                     abort ();
1594 #endif
1595                   }
1596               }
1597 #ifdef ASM_OUTPUT_CASE_END
1598             ASM_OUTPUT_CASE_END (file,
1599                                  CODE_LABEL_NUMBER (PREV_INSN (insn)),
1600                                  insn);
1601 #endif
1602
1603             function_section (current_function_decl);
1604
1605             break;
1606           }
1607
1608         /* Do basic-block profiling when we reach a new block.
1609            Done here to avoid jump tables.  */
1610         if (profile_block_flag && new_block)
1611           add_bb (file);
1612
1613         if (GET_CODE (body) == ASM_INPUT)
1614           {
1615             /* There's no telling what that did to the condition codes.  */
1616             CC_STATUS_INIT;
1617             if (prescan > 0)
1618               break;
1619             if (! app_on)
1620               {
1621                 fprintf (file, ASM_APP_ON);
1622                 app_on = 1;
1623               }
1624             fprintf (asm_out_file, "\t%s\n", XSTR (body, 0));
1625             break;
1626           }
1627
1628         /* Detect `asm' construct with operands.  */
1629         if (asm_noperands (body) >= 0)
1630           {
1631             int noperands = asm_noperands (body);
1632             rtx *ops = (rtx *) alloca (noperands * sizeof (rtx));
1633             char *string;
1634
1635             /* There's no telling what that did to the condition codes.  */
1636             CC_STATUS_INIT;
1637             if (prescan > 0)
1638               break;
1639
1640             if (! app_on)
1641               {
1642                 fprintf (file, ASM_APP_ON);
1643                 app_on = 1;
1644               }
1645
1646             /* Get out the operand values.  */
1647             string = decode_asm_operands (body, ops, NULL_PTR,
1648                                           NULL_PTR, NULL_PTR);
1649             /* Inhibit aborts on what would otherwise be compiler bugs.  */
1650             insn_noperands = noperands;
1651             this_is_asm_operands = insn;
1652
1653             /* Output the insn using them.  */
1654             output_asm_insn (string, ops);
1655             this_is_asm_operands = 0;
1656             break;
1657           }
1658
1659         if (prescan <= 0 && app_on)
1660           {
1661             fprintf (file, ASM_APP_OFF);
1662             app_on = 0;
1663           }
1664
1665         if (GET_CODE (body) == SEQUENCE)
1666           {
1667             /* A delayed-branch sequence */
1668             register int i;
1669             rtx next;
1670
1671             if (prescan > 0)
1672               break;
1673             final_sequence = body;
1674
1675             /* The first insn in this SEQUENCE might be a JUMP_INSN that will
1676                force the restoration of a comparison that was previously
1677                thought unnecessary.  If that happens, cancel this sequence
1678                and cause that insn to be restored.  */
1679
1680             next = final_scan_insn (XVECEXP (body, 0, 0), file, 0, prescan, 1);
1681             if (next != XVECEXP (body, 0, 1))
1682               {
1683                 final_sequence = 0;
1684                 return next;
1685               }
1686
1687             for (i = 1; i < XVECLEN (body, 0); i++)
1688               final_scan_insn (XVECEXP (body, 0, i), file, 0, prescan, 1);
1689 #ifdef DBR_OUTPUT_SEQEND
1690             DBR_OUTPUT_SEQEND (file);
1691 #endif
1692             final_sequence = 0;
1693
1694             /* If the insn requiring the delay slot was a CALL_INSN, the
1695                insns in the delay slot are actually executed before the
1696                called function.  Hence we don't preserve any CC-setting
1697                actions in these insns and the CC must be marked as being
1698                clobbered by the function.  */
1699             if (GET_CODE (XVECEXP (body, 0, 0)) == CALL_INSN)
1700               CC_STATUS_INIT;
1701
1702             /* Following a conditional branch sequence, we have a new basic
1703                block.  */
1704             if (profile_block_flag)
1705               {
1706                 rtx insn = XVECEXP (body, 0, 0);
1707                 rtx body = PATTERN (insn);
1708
1709                 if ((GET_CODE (insn) == JUMP_INSN && GET_CODE (body) == SET
1710                      && GET_CODE (SET_SRC (body)) != LABEL_REF)
1711                     || (GET_CODE (insn) == JUMP_INSN
1712                         && GET_CODE (body) == PARALLEL
1713                         && GET_CODE (XVECEXP (body, 0, 0)) == SET
1714                         && GET_CODE (SET_SRC (XVECEXP (body, 0, 0))) != LABEL_REF))
1715                   new_block = 1;
1716               }
1717             break;
1718           }
1719
1720         /* We have a real machine instruction as rtl.  */
1721
1722         body = PATTERN (insn);
1723
1724 #ifdef HAVE_cc0
1725         /* Check for redundant test and compare instructions
1726            (when the condition codes are already set up as desired).
1727            This is done only when optimizing; if not optimizing,
1728            it should be possible for the user to alter a variable
1729            with the debugger in between statements
1730            and the next statement should reexamine the variable
1731            to compute the condition codes.  */
1732
1733         if (optimize
1734             && GET_CODE (body) == SET
1735             && GET_CODE (SET_DEST (body)) == CC0
1736             && insn != last_ignored_compare)
1737           {
1738             if (GET_CODE (SET_SRC (body)) == SUBREG)
1739               SET_SRC (body) = alter_subreg (SET_SRC (body));
1740             else if (GET_CODE (SET_SRC (body)) == COMPARE)
1741               {
1742                 if (GET_CODE (XEXP (SET_SRC (body), 0)) == SUBREG)
1743                   XEXP (SET_SRC (body), 0)
1744                     = alter_subreg (XEXP (SET_SRC (body), 0));
1745                 if (GET_CODE (XEXP (SET_SRC (body), 1)) == SUBREG)
1746                   XEXP (SET_SRC (body), 1)
1747                     = alter_subreg (XEXP (SET_SRC (body), 1));
1748               }
1749             if ((cc_status.value1 != 0
1750                  && rtx_equal_p (SET_SRC (body), cc_status.value1))
1751                 || (cc_status.value2 != 0
1752                     && rtx_equal_p (SET_SRC (body), cc_status.value2)))
1753               {
1754                 /* Don't delete insn if it has an addressing side-effect.  */
1755                 if (! FIND_REG_INC_NOTE (insn, 0)
1756                     /* or if anything in it is volatile.  */
1757                     && ! volatile_refs_p (PATTERN (insn)))
1758                   {
1759                     /* We don't really delete the insn; just ignore it.  */
1760                     last_ignored_compare = insn;
1761                     break;
1762                   }
1763               }
1764           }
1765 #endif
1766
1767         /* Following a conditional branch, we have a new basic block.
1768            But if we are inside a sequence, the new block starts after the
1769            last insn of the sequence.  */
1770         if (profile_block_flag && final_sequence == 0
1771             && ((GET_CODE (insn) == JUMP_INSN && GET_CODE (body) == SET
1772                  && GET_CODE (SET_SRC (body)) != LABEL_REF)
1773                 || (GET_CODE (insn) == JUMP_INSN && GET_CODE (body) == PARALLEL
1774                     && GET_CODE (XVECEXP (body, 0, 0)) == SET
1775                     && GET_CODE (SET_SRC (XVECEXP (body, 0, 0))) != LABEL_REF)))
1776           new_block = 1;
1777
1778 #ifndef STACK_REGS
1779         /* Don't bother outputting obvious no-ops, even without -O.
1780            This optimization is fast and doesn't interfere with debugging.
1781            Don't do this if the insn is in a delay slot, since this
1782            will cause an improper number of delay insns to be written.  */
1783         if (final_sequence == 0
1784             && prescan >= 0
1785             && GET_CODE (insn) == INSN && GET_CODE (body) == SET
1786             && GET_CODE (SET_SRC (body)) == REG
1787             && GET_CODE (SET_DEST (body)) == REG
1788             && REGNO (SET_SRC (body)) == REGNO (SET_DEST (body)))
1789           break;
1790 #endif
1791
1792 #ifdef HAVE_cc0
1793         /* If this is a conditional branch, maybe modify it
1794            if the cc's are in a nonstandard state
1795            so that it accomplishes the same thing that it would
1796            do straightforwardly if the cc's were set up normally.  */
1797
1798         if (cc_status.flags != 0
1799             && GET_CODE (insn) == JUMP_INSN
1800             && GET_CODE (body) == SET
1801             && SET_DEST (body) == pc_rtx
1802             && GET_CODE (SET_SRC (body)) == IF_THEN_ELSE
1803             /* This is done during prescan; it is not done again
1804                in final scan when prescan has been done.  */
1805             && prescan >= 0)
1806           {
1807             /* This function may alter the contents of its argument
1808                and clear some of the cc_status.flags bits.
1809                It may also return 1 meaning condition now always true
1810                or -1 meaning condition now always false
1811                or 2 meaning condition nontrivial but altered.  */
1812             register int result = alter_cond (XEXP (SET_SRC (body), 0));
1813             /* If condition now has fixed value, replace the IF_THEN_ELSE
1814                with its then-operand or its else-operand.  */
1815             if (result == 1)
1816               SET_SRC (body) = XEXP (SET_SRC (body), 1);
1817             if (result == -1)
1818               SET_SRC (body) = XEXP (SET_SRC (body), 2);
1819
1820             /* The jump is now either unconditional or a no-op.
1821                If it has become a no-op, don't try to output it.
1822                (It would not be recognized.)  */
1823             if (SET_SRC (body) == pc_rtx)
1824               {
1825                 PUT_CODE (insn, NOTE);
1826                 NOTE_LINE_NUMBER (insn) = NOTE_INSN_DELETED;
1827                 NOTE_SOURCE_FILE (insn) = 0;
1828                 break;
1829               }
1830             else if (GET_CODE (SET_SRC (body)) == RETURN)
1831               /* Replace (set (pc) (return)) with (return).  */
1832               PATTERN (insn) = body = SET_SRC (body);
1833
1834             /* Rerecognize the instruction if it has changed.  */
1835             if (result != 0)
1836               INSN_CODE (insn) = -1;
1837           }
1838
1839         /* Make same adjustments to instructions that examine the
1840            condition codes without jumping (if this machine has them).  */
1841
1842         if (cc_status.flags != 0
1843             && GET_CODE (body) == SET)
1844           {
1845             switch (GET_CODE (SET_SRC (body)))
1846               {
1847               case GTU:
1848               case GT:
1849               case LTU:
1850               case LT:
1851               case GEU:
1852               case GE:
1853               case LEU:
1854               case LE:
1855               case EQ:
1856               case NE:
1857                 {
1858                   register int result;
1859                   if (XEXP (SET_SRC (body), 0) != cc0_rtx)
1860                     break;
1861                   result = alter_cond (SET_SRC (body));
1862                   if (result == 1)
1863                     validate_change (insn, &SET_SRC (body), const_true_rtx, 0);
1864                   else if (result == -1)
1865                     validate_change (insn, &SET_SRC (body), const0_rtx, 0);
1866                   else if (result == 2)
1867                     INSN_CODE (insn) = -1;
1868                 }
1869               }
1870           }
1871 #endif
1872
1873         /* Do machine-specific peephole optimizations if desired.  */
1874
1875         if (optimize && !flag_no_peephole && !nopeepholes)
1876           {
1877             rtx next = peephole (insn);
1878             /* When peepholing, if there were notes within the peephole,
1879                emit them before the peephole.  */
1880             if (next != 0 && next != NEXT_INSN (insn))
1881               {
1882                 rtx prev = PREV_INSN (insn);
1883                 rtx note;
1884
1885                 for (note = NEXT_INSN (insn); note != next;
1886                      note = NEXT_INSN (note))
1887                   final_scan_insn (note, file, optimize, prescan, nopeepholes);
1888
1889                 /* In case this is prescan, put the notes
1890                    in proper position for later rescan.  */
1891                 note = NEXT_INSN (insn);
1892                 PREV_INSN (note) = prev;
1893                 NEXT_INSN (prev) = note;
1894                 NEXT_INSN (PREV_INSN (next)) = insn;
1895                 PREV_INSN (insn) = PREV_INSN (next);
1896                 NEXT_INSN (insn) = next;
1897                 PREV_INSN (next) = insn;
1898               }
1899
1900             /* PEEPHOLE might have changed this.  */
1901             body = PATTERN (insn);
1902           }
1903
1904         /* Try to recognize the instruction.
1905            If successful, verify that the operands satisfy the
1906            constraints for the instruction.  Crash if they don't,
1907            since `reload' should have changed them so that they do.  */
1908
1909         insn_code_number = recog_memoized (insn);
1910         insn_extract (insn);
1911         for (i = 0; i < insn_n_operands[insn_code_number]; i++)
1912           {
1913             if (GET_CODE (recog_operand[i]) == SUBREG)
1914               recog_operand[i] = alter_subreg (recog_operand[i]);
1915             else if (GET_CODE (recog_operand[i]) == PLUS
1916                      || GET_CODE (recog_operand[i]) == MULT)
1917               recog_operand[i] = walk_alter_subreg (recog_operand[i]);
1918           }
1919
1920         for (i = 0; i < insn_n_dups[insn_code_number]; i++)
1921           {
1922             if (GET_CODE (*recog_dup_loc[i]) == SUBREG)
1923               *recog_dup_loc[i] = alter_subreg (*recog_dup_loc[i]);
1924             else if (GET_CODE (*recog_dup_loc[i]) == PLUS
1925                      || GET_CODE (*recog_dup_loc[i]) == MULT)
1926               *recog_dup_loc[i] = walk_alter_subreg (*recog_dup_loc[i]);
1927           }
1928
1929 #ifdef REGISTER_CONSTRAINTS
1930         if (! constrain_operands (insn_code_number, 1))
1931           fatal_insn_not_found (insn);
1932 #endif
1933
1934         /* Some target machines need to prescan each insn before
1935            it is output.  */
1936
1937 #ifdef FINAL_PRESCAN_INSN
1938         FINAL_PRESCAN_INSN (insn, recog_operand,
1939                             insn_n_operands[insn_code_number]);
1940 #endif
1941
1942 #ifdef HAVE_cc0
1943         cc_prev_status = cc_status;
1944
1945         /* Update `cc_status' for this instruction.
1946            The instruction's output routine may change it further.
1947            If the output routine for a jump insn needs to depend
1948            on the cc status, it should look at cc_prev_status.  */
1949
1950         NOTICE_UPDATE_CC (body, insn);
1951 #endif
1952
1953         debug_insn = insn;
1954
1955         /* If the proper template needs to be chosen by some C code,
1956            run that code and get the real template.  */
1957
1958         template = insn_template[insn_code_number];
1959         if (template == 0)
1960           {
1961             template = (*insn_outfun[insn_code_number]) (recog_operand, insn);
1962
1963             /* If the C code returns 0, it means that it is a jump insn
1964                which follows a deleted test insn, and that test insn
1965                needs to be reinserted.  */
1966             if (template == 0)
1967               {
1968                 if (prev_nonnote_insn (insn) != last_ignored_compare)
1969                   abort ();
1970                 new_block = 0;
1971                 return prev_nonnote_insn (insn);
1972               }
1973           }
1974
1975         /* If the template is the string "#", it means that this insn must
1976            be split.  */
1977         if (template[0] == '#' && template[1] == '\0')
1978           {
1979             rtx new = try_split (body, insn, 0);
1980
1981             /* If we didn't split the insn, go away.  */
1982             if (new == insn && PATTERN (new) == body)
1983               abort ();
1984               
1985             new_block = 0;
1986             return new;
1987           }
1988         
1989         if (prescan > 0)
1990           break;
1991
1992         /* Output assembler code from the template.  */
1993
1994         output_asm_insn (template, recog_operand);
1995
1996 #if 0
1997         /* It's not at all clear why we did this and doing so interferes
1998            with tests we'd like to do to use REG_WAS_0 notes, so let's try
1999            with this out.  */
2000
2001         /* Mark this insn as having been output.  */
2002         INSN_DELETED_P (insn) = 1;
2003 #endif
2004
2005         debug_insn = 0;
2006       }
2007     }
2008   return NEXT_INSN (insn);
2009 }
2010 \f
2011 /* Output debugging info to the assembler file FILE
2012    based on the NOTE-insn INSN, assumed to be a line number.  */
2013
2014 static void
2015 output_source_line (file, insn)
2016      FILE *file;
2017      rtx insn;
2018 {
2019   register char *filename = NOTE_SOURCE_FILE (insn);
2020
2021   /* Remember filename for basic block profiling.
2022      Filenames are allocated on the permanent obstack
2023      or are passed in ARGV, so we don't have to save
2024      the string.  */
2025
2026   if (profile_block_flag && last_filename != filename)
2027     bb_file_label_num = add_bb_string (filename, TRUE);
2028
2029   last_filename = filename;
2030   last_linenum = NOTE_LINE_NUMBER (insn);
2031   high_block_linenum = MAX (last_linenum, high_block_linenum);
2032   high_function_linenum = MAX (last_linenum, high_function_linenum);
2033
2034   if (write_symbols != NO_DEBUG)
2035     {
2036 #ifdef SDB_DEBUGGING_INFO
2037       if (write_symbols == SDB_DEBUG
2038 #if 0 /* People like having line numbers even in wrong file!  */
2039           /* COFF can't handle multiple source files--lose, lose.  */
2040           && !strcmp (filename, main_input_filename)
2041 #endif
2042           /* COFF relative line numbers must be positive.  */
2043           && last_linenum > sdb_begin_function_line)
2044         {
2045 #ifdef ASM_OUTPUT_SOURCE_LINE
2046           ASM_OUTPUT_SOURCE_LINE (file, last_linenum);
2047 #else
2048           fprintf (file, "\t.ln\t%d\n",
2049                    ((sdb_begin_function_line > -1)
2050                     ? last_linenum - sdb_begin_function_line : 1));
2051 #endif
2052         }
2053 #endif
2054
2055 #if defined (DBX_DEBUGGING_INFO)
2056       if (write_symbols == DBX_DEBUG)
2057         dbxout_source_line (file, filename, NOTE_LINE_NUMBER (insn));
2058 #endif
2059
2060 #if defined (XCOFF_DEBUGGING_INFO)
2061       if (write_symbols == XCOFF_DEBUG)
2062         xcoffout_source_line (file, filename, insn);
2063 #endif
2064
2065 #ifdef DWARF_DEBUGGING_INFO
2066       if (write_symbols == DWARF_DEBUG)
2067         dwarfout_line (filename, NOTE_LINE_NUMBER (insn));
2068 #endif
2069     }
2070 }
2071 \f
2072 /* If X is a SUBREG, replace it with a REG or a MEM,
2073    based on the thing it is a subreg of.  */
2074
2075 rtx
2076 alter_subreg (x)
2077      register rtx x;
2078 {
2079   register rtx y = SUBREG_REG (x);
2080   if (GET_CODE (y) == SUBREG)
2081     y = alter_subreg (y);
2082
2083   if (GET_CODE (y) == REG)
2084     {
2085       /* If the containing reg really gets a hard reg, so do we.  */
2086       PUT_CODE (x, REG);
2087       REGNO (x) = REGNO (y) + SUBREG_WORD (x);
2088     }
2089   else if (GET_CODE (y) == MEM)
2090     {
2091       register int offset = SUBREG_WORD (x) * UNITS_PER_WORD;
2092       if (BYTES_BIG_ENDIAN)
2093         offset -= (MIN (UNITS_PER_WORD, GET_MODE_SIZE (GET_MODE (x)))
2094                    - MIN (UNITS_PER_WORD, GET_MODE_SIZE (GET_MODE (y))));
2095       PUT_CODE (x, MEM);
2096       MEM_VOLATILE_P (x) = MEM_VOLATILE_P (y);
2097       XEXP (x, 0) = plus_constant (XEXP (y, 0), offset);
2098     }
2099
2100   return x;
2101 }
2102
2103 /* Do alter_subreg on all the SUBREGs contained in X.  */
2104
2105 static rtx
2106 walk_alter_subreg (x)
2107      rtx x;
2108 {
2109   switch (GET_CODE (x))
2110     {
2111     case PLUS:
2112     case MULT:
2113       XEXP (x, 0) = walk_alter_subreg (XEXP (x, 0));
2114       XEXP (x, 1) = walk_alter_subreg (XEXP (x, 1));
2115       break;
2116
2117     case MEM:
2118       XEXP (x, 0) = walk_alter_subreg (XEXP (x, 0));
2119       break;
2120
2121     case SUBREG:
2122       return alter_subreg (x);
2123     }
2124
2125   return x;
2126 }
2127 \f
2128 #ifdef HAVE_cc0
2129
2130 /* Given BODY, the body of a jump instruction, alter the jump condition
2131    as required by the bits that are set in cc_status.flags.
2132    Not all of the bits there can be handled at this level in all cases.
2133
2134    The value is normally 0.
2135    1 means that the condition has become always true.
2136    -1 means that the condition has become always false.
2137    2 means that COND has been altered.  */
2138
2139 static int
2140 alter_cond (cond)
2141      register rtx cond;
2142 {
2143   int value = 0;
2144
2145   if (cc_status.flags & CC_REVERSED)
2146     {
2147       value = 2;
2148       PUT_CODE (cond, swap_condition (GET_CODE (cond)));
2149     }
2150
2151   if (cc_status.flags & CC_INVERTED)
2152     {
2153       value = 2;
2154       PUT_CODE (cond, reverse_condition (GET_CODE (cond)));
2155     }
2156
2157   if (cc_status.flags & CC_NOT_POSITIVE)
2158     switch (GET_CODE (cond))
2159       {
2160       case LE:
2161       case LEU:
2162       case GEU:
2163         /* Jump becomes unconditional.  */
2164         return 1;
2165
2166       case GT:
2167       case GTU:
2168       case LTU:
2169         /* Jump becomes no-op.  */
2170         return -1;
2171
2172       case GE:
2173         PUT_CODE (cond, EQ);
2174         value = 2;
2175         break;
2176
2177       case LT:
2178         PUT_CODE (cond, NE);
2179         value = 2;
2180         break;
2181       }
2182
2183   if (cc_status.flags & CC_NOT_NEGATIVE)
2184     switch (GET_CODE (cond))
2185       {
2186       case GE:
2187       case GEU:
2188         /* Jump becomes unconditional.  */
2189         return 1;
2190
2191       case LT:
2192       case LTU:
2193         /* Jump becomes no-op.  */
2194         return -1;
2195
2196       case LE:
2197       case LEU:
2198         PUT_CODE (cond, EQ);
2199         value = 2;
2200         break;
2201
2202       case GT:
2203       case GTU:
2204         PUT_CODE (cond, NE);
2205         value = 2;
2206         break;
2207       }
2208
2209   if (cc_status.flags & CC_NO_OVERFLOW)
2210     switch (GET_CODE (cond))
2211       {
2212       case GEU:
2213         /* Jump becomes unconditional.  */
2214         return 1;
2215
2216       case LEU:
2217         PUT_CODE (cond, EQ);
2218         value = 2;
2219         break;
2220
2221       case GTU:
2222         PUT_CODE (cond, NE);
2223         value = 2;
2224         break;
2225
2226       case LTU:
2227         /* Jump becomes no-op.  */
2228         return -1;
2229       }
2230
2231   if (cc_status.flags & (CC_Z_IN_NOT_N | CC_Z_IN_N))
2232     switch (GET_CODE (cond))
2233       {
2234       case LE:
2235       case LEU:
2236       case GE:
2237       case GEU:
2238       case LT:
2239       case LTU:
2240       case GT:
2241       case GTU:
2242         abort ();
2243
2244       case NE:
2245         PUT_CODE (cond, cc_status.flags & CC_Z_IN_N ? GE : LT);
2246         value = 2;
2247         break;
2248
2249       case EQ:
2250         PUT_CODE (cond, cc_status.flags & CC_Z_IN_N ? LT : GE);
2251         value = 2;
2252         break;
2253       }
2254
2255   if (cc_status.flags & CC_NOT_SIGNED)
2256     /* The flags are valid if signed condition operators are converted
2257        to unsigned.  */
2258     switch (GET_CODE (cond))
2259       {
2260       case LE:
2261         PUT_CODE (cond, LEU);
2262         value = 2;
2263         break;
2264
2265       case LT:
2266         PUT_CODE (cond, LTU);
2267         value = 2;
2268         break;
2269
2270       case GT:
2271         PUT_CODE (cond, GTU);
2272         value = 2;
2273         break;
2274
2275       case GE:
2276         PUT_CODE (cond, GEU);
2277         value = 2;
2278         break;
2279       }
2280
2281   return value;
2282 }
2283 #endif
2284 \f
2285 /* Report inconsistency between the assembler template and the operands.
2286    In an `asm', it's the user's fault; otherwise, the compiler's fault.  */
2287
2288 void
2289 output_operand_lossage (str)
2290      char *str;
2291 {
2292   if (this_is_asm_operands)
2293     error_for_asm (this_is_asm_operands, "invalid `asm': %s", str);
2294   else
2295     abort ();
2296 }
2297 \f
2298 /* Output of assembler code from a template, and its subroutines.  */
2299
2300 /* Output text from TEMPLATE to the assembler output file,
2301    obeying %-directions to substitute operands taken from
2302    the vector OPERANDS.
2303
2304    %N (for N a digit) means print operand N in usual manner.
2305    %lN means require operand N to be a CODE_LABEL or LABEL_REF
2306       and print the label name with no punctuation.
2307    %cN means require operand N to be a constant
2308       and print the constant expression with no punctuation.
2309    %aN means expect operand N to be a memory address
2310       (not a memory reference!) and print a reference
2311       to that address.
2312    %nN means expect operand N to be a constant
2313       and print a constant expression for minus the value
2314       of the operand, with no other punctuation.  */
2315
2316 void
2317 output_asm_insn (template, operands)
2318      char *template;
2319      rtx *operands;
2320 {
2321   register char *p;
2322   register int c, i;
2323
2324   /* An insn may return a null string template
2325      in a case where no assembler code is needed.  */
2326   if (*template == 0)
2327     return;
2328
2329   p = template;
2330   putc ('\t', asm_out_file);
2331
2332 #ifdef ASM_OUTPUT_OPCODE
2333   ASM_OUTPUT_OPCODE (asm_out_file, p);
2334 #endif
2335
2336   while (c = *p++)
2337     switch (c)
2338       {
2339 #ifdef ASM_OUTPUT_OPCODE
2340       case '\n':
2341         putc (c, asm_out_file);
2342         while ((c = *p) == '\t')
2343           {
2344             putc (c, asm_out_file);
2345             p++;
2346           }
2347         ASM_OUTPUT_OPCODE (asm_out_file, p);
2348         break;
2349 #endif
2350
2351 #ifdef ASSEMBLER_DIALECT
2352       case '{':
2353         /* If we want the first dialect, do nothing.  Otherwise, skip
2354            DIALECT_NUMBER of strings ending with '|'.  */
2355         for (i = 0; i < dialect_number; i++)
2356           {
2357             while (*p && *p++ != '|')
2358               ;
2359
2360             if (*p == '|')
2361               p++;
2362           }
2363         break;
2364
2365       case '|':
2366         /* Skip to close brace.  */
2367         while (*p && *p++ != '}')
2368           ;
2369         break;
2370
2371       case '}':
2372         break;
2373 #endif
2374
2375       case '%':
2376         /* %% outputs a single %.  */
2377         if (*p == '%')
2378           {
2379             p++;
2380             putc (c, asm_out_file);
2381           }
2382         /* %= outputs a number which is unique to each insn in the entire
2383            compilation.  This is useful for making local labels that are
2384            referred to more than once in a given insn.  */
2385         else if (*p == '=')
2386           {
2387             p++;
2388             fprintf (asm_out_file, "%d", insn_counter);
2389           }
2390         /* % followed by a letter and some digits
2391            outputs an operand in a special way depending on the letter.
2392            Letters `acln' are implemented directly.
2393            Other letters are passed to `output_operand' so that
2394            the PRINT_OPERAND macro can define them.  */
2395         else if ((*p >= 'a' && *p <= 'z')
2396                  || (*p >= 'A' && *p <= 'Z'))
2397           {
2398             int letter = *p++;
2399             c = atoi (p);
2400
2401             if (! (*p >= '0' && *p <= '9'))
2402               output_operand_lossage ("operand number missing after %-letter");
2403             else if (this_is_asm_operands && c >= (unsigned) insn_noperands)
2404               output_operand_lossage ("operand number out of range");
2405             else if (letter == 'l')
2406               output_asm_label (operands[c]);
2407             else if (letter == 'a')
2408               output_address (operands[c]);
2409             else if (letter == 'c')
2410               {
2411                 if (CONSTANT_ADDRESS_P (operands[c]))
2412                   output_addr_const (asm_out_file, operands[c]);
2413                 else
2414                   output_operand (operands[c], 'c');
2415               }
2416             else if (letter == 'n')
2417               {
2418                 if (GET_CODE (operands[c]) == CONST_INT)
2419                   fprintf (asm_out_file,
2420 #if HOST_BITS_PER_WIDE_INT == HOST_BITS_PER_INT
2421                            "%d",
2422 #else
2423                            "%ld",
2424 #endif
2425                            - INTVAL (operands[c]));
2426                 else
2427                   {
2428                     putc ('-', asm_out_file);
2429                     output_addr_const (asm_out_file, operands[c]);
2430                   }
2431               }
2432             else
2433               output_operand (operands[c], letter);
2434             
2435             while ((c = *p) >= '0' && c <= '9') p++;
2436           }
2437         /* % followed by a digit outputs an operand the default way.  */
2438         else if (*p >= '0' && *p <= '9')
2439           {
2440             c = atoi (p);
2441             if (this_is_asm_operands && c >= (unsigned) insn_noperands)
2442               output_operand_lossage ("operand number out of range");
2443             else
2444               output_operand (operands[c], 0);
2445             while ((c = *p) >= '0' && c <= '9') p++;
2446           }
2447         /* % followed by punctuation: output something for that
2448            punctuation character alone, with no operand.
2449            The PRINT_OPERAND macro decides what is actually done.  */
2450 #ifdef PRINT_OPERAND_PUNCT_VALID_P
2451         else if (PRINT_OPERAND_PUNCT_VALID_P (*p))
2452           output_operand (NULL_RTX, *p++);
2453 #endif
2454         else
2455           output_operand_lossage ("invalid %%-code");
2456         break;
2457
2458       default:
2459         putc (c, asm_out_file);
2460       }
2461
2462   if (flag_print_asm_name)
2463     {
2464       /* Annotate the assembly with a comment describing the pattern and
2465          alternative used.  */
2466       if (debug_insn)
2467         {
2468           register int num = INSN_CODE (debug_insn);
2469           fprintf (asm_out_file, " %s %d %s", 
2470                    ASM_COMMENT_START, INSN_UID (debug_insn), insn_name[num]);
2471           if (insn_n_alternatives[num] > 1)
2472             fprintf (asm_out_file, "/%d", which_alternative + 1);
2473
2474           /* Clear this so only the first assembler insn
2475              of any rtl insn will get the special comment for -dp.  */
2476           debug_insn = 0;
2477         }
2478     }
2479
2480   putc ('\n', asm_out_file);
2481 }
2482 \f
2483 /* Output a LABEL_REF, or a bare CODE_LABEL, as an assembler symbol.  */
2484
2485 void
2486 output_asm_label (x)
2487      rtx x;
2488 {
2489   char buf[256];
2490
2491   if (GET_CODE (x) == LABEL_REF)
2492     ASM_GENERATE_INTERNAL_LABEL (buf, "L", CODE_LABEL_NUMBER (XEXP (x, 0)));
2493   else if (GET_CODE (x) == CODE_LABEL)
2494     ASM_GENERATE_INTERNAL_LABEL (buf, "L", CODE_LABEL_NUMBER (x));
2495   else
2496     output_operand_lossage ("`%l' operand isn't a label");
2497
2498   assemble_name (asm_out_file, buf);
2499 }
2500
2501 /* Print operand X using machine-dependent assembler syntax.
2502    The macro PRINT_OPERAND is defined just to control this function.
2503    CODE is a non-digit that preceded the operand-number in the % spec,
2504    such as 'z' if the spec was `%z3'.  CODE is 0 if there was no char
2505    between the % and the digits.
2506    When CODE is a non-letter, X is 0.
2507
2508    The meanings of the letters are machine-dependent and controlled
2509    by PRINT_OPERAND.  */
2510
2511 static void
2512 output_operand (x, code)
2513      rtx x;
2514      int code;
2515 {
2516   if (x && GET_CODE (x) == SUBREG)
2517     x = alter_subreg (x);
2518
2519   /* If X is a pseudo-register, abort now rather than writing trash to the
2520      assembler file.  */
2521
2522   if (x && GET_CODE (x) == REG && REGNO (x) >= FIRST_PSEUDO_REGISTER)
2523     abort ();
2524
2525   PRINT_OPERAND (asm_out_file, x, code);
2526 }
2527
2528 /* Print a memory reference operand for address X
2529    using machine-dependent assembler syntax.
2530    The macro PRINT_OPERAND_ADDRESS exists just to control this function.  */
2531
2532 void
2533 output_address (x)
2534      rtx x;
2535 {
2536   walk_alter_subreg (x);
2537   PRINT_OPERAND_ADDRESS (asm_out_file, x);
2538 }
2539 \f
2540 /* Print an integer constant expression in assembler syntax.
2541    Addition and subtraction are the only arithmetic
2542    that may appear in these expressions.  */
2543
2544 void
2545 output_addr_const (file, x)
2546      FILE *file;
2547      rtx x;
2548 {
2549   char buf[256];
2550
2551  restart:
2552   switch (GET_CODE (x))
2553     {
2554     case PC:
2555       if (flag_pic)
2556         putc ('.', file);
2557       else
2558         abort ();
2559       break;
2560
2561     case SYMBOL_REF:
2562       assemble_name (file, XSTR (x, 0));
2563       break;
2564
2565     case LABEL_REF:
2566       ASM_GENERATE_INTERNAL_LABEL (buf, "L", CODE_LABEL_NUMBER (XEXP (x, 0)));
2567       assemble_name (file, buf);
2568       break;
2569
2570     case CODE_LABEL:
2571       ASM_GENERATE_INTERNAL_LABEL (buf, "L", CODE_LABEL_NUMBER (x));
2572       assemble_name (file, buf);
2573       break;
2574
2575     case CONST_INT:
2576       fprintf (file,
2577 #if HOST_BITS_PER_WIDE_INT == HOST_BITS_PER_INT
2578                "%d",
2579 #else
2580                "%ld",
2581 #endif
2582                INTVAL (x));
2583       break;
2584
2585     case CONST:
2586       /* This used to output parentheses around the expression,
2587          but that does not work on the 386 (either ATT or BSD assembler).  */
2588       output_addr_const (file, XEXP (x, 0));
2589       break;
2590
2591     case CONST_DOUBLE:
2592       if (GET_MODE (x) == VOIDmode)
2593         {
2594           /* We can use %d if the number is one word and positive.  */
2595           if (CONST_DOUBLE_HIGH (x))
2596             fprintf (file,
2597 #if HOST_BITS_PER_WIDE_INT == 64
2598 #if HOST_BITS_PER_WIDE_INT != HOST_BITS_PER_INT
2599                      "0x%lx%016lx",
2600 #else
2601                      "0x%x%016x",
2602 #endif
2603 #else
2604 #if HOST_BITS_PER_WIDE_INT != HOST_BITS_PER_INT
2605                      "0x%lx%08lx",
2606 #else
2607                      "0x%x%08x",
2608 #endif
2609 #endif
2610                      CONST_DOUBLE_HIGH (x), CONST_DOUBLE_LOW (x));
2611           else if  (CONST_DOUBLE_LOW (x) < 0)
2612             fprintf (file,
2613 #if HOST_BITS_PER_WIDE_INT == HOST_BITS_PER_INT
2614                      "0x%x",
2615 #else
2616                      "0x%lx",
2617 #endif
2618                      CONST_DOUBLE_LOW (x));
2619           else
2620             fprintf (file,
2621 #if HOST_BITS_PER_WIDE_INT == HOST_BITS_PER_INT
2622                      "%d",
2623 #else
2624                      "%ld",
2625 #endif
2626                      CONST_DOUBLE_LOW (x));
2627         }
2628       else
2629         /* We can't handle floating point constants;
2630            PRINT_OPERAND must handle them.  */
2631         output_operand_lossage ("floating constant misused");
2632       break;
2633
2634     case PLUS:
2635       /* Some assemblers need integer constants to appear last (eg masm).  */
2636       if (GET_CODE (XEXP (x, 0)) == CONST_INT)
2637         {
2638           output_addr_const (file, XEXP (x, 1));
2639           if (INTVAL (XEXP (x, 0)) >= 0)
2640             fprintf (file, "+");
2641           output_addr_const (file, XEXP (x, 0));
2642         }
2643       else
2644         {
2645           output_addr_const (file, XEXP (x, 0));
2646           if (INTVAL (XEXP (x, 1)) >= 0)
2647             fprintf (file, "+");
2648           output_addr_const (file, XEXP (x, 1));
2649         }
2650       break;
2651
2652     case MINUS:
2653       /* Avoid outputting things like x-x or x+5-x,
2654          since some assemblers can't handle that.  */
2655       x = simplify_subtraction (x);
2656       if (GET_CODE (x) != MINUS)
2657         goto restart;
2658
2659       output_addr_const (file, XEXP (x, 0));
2660       fprintf (file, "-");
2661       if (GET_CODE (XEXP (x, 1)) == CONST_INT
2662           && INTVAL (XEXP (x, 1)) < 0)
2663         {
2664           fprintf (file, ASM_OPEN_PAREN);
2665           output_addr_const (file, XEXP (x, 1));
2666           fprintf (file, ASM_CLOSE_PAREN);
2667         }
2668       else
2669         output_addr_const (file, XEXP (x, 1));
2670       break;
2671
2672     case ZERO_EXTEND:
2673     case SIGN_EXTEND:
2674       output_addr_const (file, XEXP (x, 0));
2675       break;
2676
2677     default:
2678       output_operand_lossage ("invalid expression as operand");
2679     }
2680 }
2681 \f
2682 /* A poor man's fprintf, with the added features of %I, %R, %L, and %U.
2683    %R prints the value of REGISTER_PREFIX.
2684    %L prints the value of LOCAL_LABEL_PREFIX.
2685    %U prints the value of USER_LABEL_PREFIX.
2686    %I prints the value of IMMEDIATE_PREFIX.
2687    %O runs ASM_OUTPUT_OPCODE to transform what follows in the string.
2688    Also supported are %d, %x, %s, %e, %f, %g and %%.
2689
2690    We handle alternate assembler dialects here, just like output_asm_insn.  */
2691
2692 void
2693 asm_fprintf VPROTO((FILE *file, char *p, ...))
2694 {
2695 #ifndef __STDC__
2696   FILE *file;
2697   char *p;
2698 #endif
2699   va_list argptr;
2700   char buf[10];
2701   char *q, c;
2702   int i;
2703
2704   VA_START (argptr, p);
2705
2706 #ifndef __STDC__
2707   file = va_arg (argptr, FILE*);
2708   p = va_arg (argptr, char*);
2709 #endif
2710
2711   buf[0] = '%';
2712
2713   while (c = *p++)
2714     switch (c)
2715       {
2716 #ifdef ASSEMBLER_DIALECT
2717       case '{':
2718         /* If we want the first dialect, do nothing.  Otherwise, skip
2719            DIALECT_NUMBER of strings ending with '|'.  */
2720         for (i = 0; i < dialect_number; i++)
2721           {
2722             while (*p && *p++ != '|')
2723               ;
2724
2725             if (*p == '|')
2726               p++;
2727           }
2728         break;
2729
2730       case '|':
2731         /* Skip to close brace.  */
2732         while (*p && *p++ != '}')
2733           ;
2734         break;
2735
2736       case '}':
2737         break;
2738 #endif
2739
2740       case '%':
2741         c = *p++;
2742         q = &buf[1];
2743         while ((c >= '0' && c <= '9') || c == '.')
2744           {
2745             *q++ = c;
2746             c = *p++;
2747           }
2748         switch (c)
2749           {
2750           case '%':
2751             fprintf (file, "%%");
2752             break;
2753
2754           case 'd':  case 'i':  case 'u':
2755           case 'x':  case 'p':  case 'X':
2756           case 'o':
2757             *q++ = c;
2758             *q = 0;
2759             fprintf (file, buf, va_arg (argptr, int));
2760             break;
2761
2762           case 'w':
2763             /* This is a prefix to the 'd', 'i', 'u', 'x', 'p', and 'X' cases,
2764                but we do not check for those cases.  It means that the value
2765                is a HOST_WIDE_INT, which may be either `int' or `long'.  */
2766
2767 #if HOST_BITS_PER_WIDE_INT != HOST_BITS_PER_INT
2768             *q++ = 'l';
2769 #endif
2770
2771             *q++ = *p++;
2772             *q = 0;
2773             fprintf (file, buf, va_arg (argptr, HOST_WIDE_INT));
2774             break;
2775
2776           case 'l':
2777             *q++ = c;
2778             *q++ = *p++;
2779             *q = 0;
2780             fprintf (file, buf, va_arg (argptr, long));
2781             break;
2782
2783           case 'e':
2784           case 'f':
2785           case 'g':
2786             *q++ = c;
2787             *q = 0;
2788             fprintf (file, buf, va_arg (argptr, double));
2789             break;
2790
2791           case 's':
2792             *q++ = c;
2793             *q = 0;
2794             fprintf (file, buf, va_arg (argptr, char *));
2795             break;
2796
2797           case 'O':
2798 #ifdef ASM_OUTPUT_OPCODE
2799             ASM_OUTPUT_OPCODE (asm_out_file, p);
2800 #endif
2801             break;
2802
2803           case 'R':
2804 #ifdef REGISTER_PREFIX
2805             fprintf (file, "%s", REGISTER_PREFIX);
2806 #endif
2807             break;
2808
2809           case 'I':
2810 #ifdef IMMEDIATE_PREFIX
2811             fprintf (file, "%s", IMMEDIATE_PREFIX);
2812 #endif
2813             break;
2814
2815           case 'L':
2816 #ifdef LOCAL_LABEL_PREFIX
2817             fprintf (file, "%s", LOCAL_LABEL_PREFIX);
2818 #endif
2819             break;
2820
2821           case 'U':
2822 #ifdef USER_LABEL_PREFIX
2823             fprintf (file, "%s", USER_LABEL_PREFIX);
2824 #endif
2825             break;
2826
2827           default:
2828             abort ();
2829           }
2830         break;
2831
2832       default:
2833         fputc (c, file);
2834       }
2835 }
2836 \f
2837 /* Split up a CONST_DOUBLE or integer constant rtx
2838    into two rtx's for single words,
2839    storing in *FIRST the word that comes first in memory in the target
2840    and in *SECOND the other.  */
2841
2842 void
2843 split_double (value, first, second)
2844      rtx value;
2845      rtx *first, *second;
2846 {
2847   if (GET_CODE (value) == CONST_INT)
2848     {
2849       if (HOST_BITS_PER_WIDE_INT >= (2 * BITS_PER_WORD))
2850         {
2851           /* In this case the CONST_INT holds both target words.
2852              Extract the bits from it into two word-sized pieces.  */
2853           rtx low, high;
2854           HOST_WIDE_INT word_mask;
2855           /* Avoid warnings for shift count >= BITS_PER_WORD.  */
2856           int shift_count = BITS_PER_WORD - 1;
2857
2858           word_mask = (HOST_WIDE_INT) 1 << shift_count;
2859           word_mask |= word_mask - 1;
2860           low = GEN_INT (INTVAL (value) & word_mask);
2861           high = GEN_INT ((INTVAL (value) >> (shift_count + 1)) & word_mask);
2862           if (WORDS_BIG_ENDIAN)
2863             {
2864               *first = high;
2865               *second = low;
2866             }
2867           else
2868             {
2869               *first = low;
2870               *second = high;
2871             }
2872         }
2873       else
2874         {
2875           /* The rule for using CONST_INT for a wider mode
2876              is that we regard the value as signed.
2877              So sign-extend it.  */
2878           rtx high = (INTVAL (value) < 0 ? constm1_rtx : const0_rtx);
2879           if (WORDS_BIG_ENDIAN)
2880             {
2881               *first = high;
2882               *second = value;
2883             }
2884           else
2885             {
2886               *first = value;
2887               *second = high;
2888             }
2889         }
2890     }
2891   else if (GET_CODE (value) != CONST_DOUBLE)
2892     {
2893       if (WORDS_BIG_ENDIAN)
2894         {
2895           *first = const0_rtx;
2896           *second = value;
2897         }
2898       else
2899         {
2900           *first = value;
2901           *second = const0_rtx;
2902         }
2903     }
2904   else if (GET_MODE (value) == VOIDmode
2905            /* This is the old way we did CONST_DOUBLE integers.  */
2906            || GET_MODE_CLASS (GET_MODE (value)) == MODE_INT)
2907     {
2908       /* In an integer, the words are defined as most and least significant.
2909          So order them by the target's convention.  */
2910       if (WORDS_BIG_ENDIAN)
2911         {
2912           *first = GEN_INT (CONST_DOUBLE_HIGH (value));
2913           *second = GEN_INT (CONST_DOUBLE_LOW (value));
2914         }
2915       else
2916         {
2917           *first = GEN_INT (CONST_DOUBLE_LOW (value));
2918           *second = GEN_INT (CONST_DOUBLE_HIGH (value));
2919         }
2920     }
2921   else
2922     {
2923 #ifdef REAL_ARITHMETIC
2924       REAL_VALUE_TYPE r; long l[2];
2925       REAL_VALUE_FROM_CONST_DOUBLE (r, value);
2926
2927       /* Note, this converts the REAL_VALUE_TYPE to the target's
2928          format, splits up the floating point double and outputs
2929          exactly 32 bits of it into each of l[0] and l[1] --
2930          not necessarily BITS_PER_WORD bits. */
2931       REAL_VALUE_TO_TARGET_DOUBLE (r, l);
2932
2933       *first = GEN_INT ((HOST_WIDE_INT) l[0]);
2934       *second = GEN_INT ((HOST_WIDE_INT) l[1]);
2935 #else
2936       if ((HOST_FLOAT_FORMAT != TARGET_FLOAT_FORMAT
2937            || HOST_BITS_PER_WIDE_INT != BITS_PER_WORD)
2938           && ! flag_pretend_float)
2939       abort ();
2940
2941       if (
2942 #ifdef HOST_WORDS_BIG_ENDIAN
2943           WORDS_BIG_ENDIAN
2944 #else
2945           ! WORDS_BIG_ENDIAN
2946 #endif
2947           )
2948         {
2949           /* Host and target agree => no need to swap.  */
2950           *first = GEN_INT (CONST_DOUBLE_LOW (value));
2951           *second = GEN_INT (CONST_DOUBLE_HIGH (value));
2952         }
2953       else
2954         {
2955           *second = GEN_INT (CONST_DOUBLE_LOW (value));
2956           *first = GEN_INT (CONST_DOUBLE_HIGH (value));
2957         }
2958 #endif /* no REAL_ARITHMETIC */
2959     }
2960 }
2961 \f
2962 /* Return nonzero if this function has no function calls.  */
2963
2964 int
2965 leaf_function_p ()
2966 {
2967   rtx insn;
2968
2969   if (profile_flag || profile_block_flag)
2970     return 0;
2971
2972   for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
2973     {
2974       if (GET_CODE (insn) == CALL_INSN)
2975         return 0;
2976       if (GET_CODE (insn) == INSN
2977           && GET_CODE (PATTERN (insn)) == SEQUENCE
2978           && GET_CODE (XVECEXP (PATTERN (insn), 0, 0)) == CALL_INSN)
2979         return 0;
2980     }
2981   for (insn = current_function_epilogue_delay_list; insn; insn = XEXP (insn, 1))
2982     {
2983       if (GET_CODE (XEXP (insn, 0)) == CALL_INSN)
2984         return 0;
2985       if (GET_CODE (XEXP (insn, 0)) == INSN
2986           && GET_CODE (PATTERN (XEXP (insn, 0))) == SEQUENCE
2987           && GET_CODE (XVECEXP (PATTERN (XEXP (insn, 0)), 0, 0)) == CALL_INSN)
2988         return 0;
2989     }
2990
2991   return 1;
2992 }
2993
2994 /* On some machines, a function with no call insns
2995    can run faster if it doesn't create its own register window.
2996    When output, the leaf function should use only the "output"
2997    registers.  Ordinarily, the function would be compiled to use
2998    the "input" registers to find its arguments; it is a candidate
2999    for leaf treatment if it uses only the "input" registers.
3000    Leaf function treatment means renumbering so the function
3001    uses the "output" registers instead.  */
3002
3003 #ifdef LEAF_REGISTERS
3004
3005 static char permitted_reg_in_leaf_functions[] = LEAF_REGISTERS;
3006
3007 /* Return 1 if this function uses only the registers that can be
3008    safely renumbered.  */
3009
3010 int
3011 only_leaf_regs_used ()
3012 {
3013   int i;
3014
3015   for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
3016     {
3017       if ((regs_ever_live[i] || global_regs[i])
3018           && ! permitted_reg_in_leaf_functions[i])
3019         return 0;
3020     }
3021   return 1;
3022 }
3023
3024 /* Scan all instructions and renumber all registers into those
3025    available in leaf functions.  */
3026
3027 static void
3028 leaf_renumber_regs (first)
3029      rtx first;
3030 {
3031   rtx insn;
3032
3033   /* Renumber only the actual patterns.
3034      The reg-notes can contain frame pointer refs,
3035      and renumbering them could crash, and should not be needed.  */
3036   for (insn = first; insn; insn = NEXT_INSN (insn))
3037     if (GET_RTX_CLASS (GET_CODE (insn)) == 'i')
3038       leaf_renumber_regs_insn (PATTERN (insn));
3039   for (insn = current_function_epilogue_delay_list; insn; insn = XEXP (insn, 1))
3040     if (GET_RTX_CLASS (GET_CODE (XEXP (insn, 0))) == 'i')
3041       leaf_renumber_regs_insn (PATTERN (XEXP (insn, 0)));
3042 }
3043
3044 /* Scan IN_RTX and its subexpressions, and renumber all regs into those
3045    available in leaf functions.  */
3046
3047 void
3048 leaf_renumber_regs_insn (in_rtx)
3049      register rtx in_rtx;
3050 {
3051   register int i, j;
3052   register char *format_ptr;
3053
3054   if (in_rtx == 0)
3055     return;
3056
3057   /* Renumber all input-registers into output-registers.
3058      renumbered_regs would be 1 for an output-register;
3059      they  */
3060
3061   if (GET_CODE (in_rtx) == REG)
3062     {
3063       int newreg;
3064
3065       /* Don't renumber the same reg twice.  */
3066       if (in_rtx->used)
3067         return;
3068
3069       newreg = REGNO (in_rtx);
3070       /* Don't try to renumber pseudo regs.  It is possible for a pseudo reg
3071          to reach here as part of a REG_NOTE.  */
3072       if (newreg >= FIRST_PSEUDO_REGISTER)
3073         {
3074           in_rtx->used = 1;
3075           return;
3076         }
3077       newreg = LEAF_REG_REMAP (newreg);
3078       if (newreg < 0)
3079         abort ();
3080       regs_ever_live[REGNO (in_rtx)] = 0;
3081       regs_ever_live[newreg] = 1;
3082       REGNO (in_rtx) = newreg;
3083       in_rtx->used = 1;
3084     }
3085
3086   if (GET_RTX_CLASS (GET_CODE (in_rtx)) == 'i')
3087     {
3088       /* Inside a SEQUENCE, we find insns.
3089          Renumber just the patterns of these insns,
3090          just as we do for the top-level insns.  */
3091       leaf_renumber_regs_insn (PATTERN (in_rtx));
3092       return;
3093     }
3094
3095   format_ptr = GET_RTX_FORMAT (GET_CODE (in_rtx));
3096
3097   for (i = 0; i < GET_RTX_LENGTH (GET_CODE (in_rtx)); i++)
3098     switch (*format_ptr++)
3099       {
3100       case 'e':
3101         leaf_renumber_regs_insn (XEXP (in_rtx, i));
3102         break;
3103
3104       case 'E':
3105         if (NULL != XVEC (in_rtx, i))
3106           {
3107             for (j = 0; j < XVECLEN (in_rtx, i); j++)
3108               leaf_renumber_regs_insn (XVECEXP (in_rtx, i, j));
3109           }
3110         break;
3111
3112       case 'S':
3113       case 's':
3114       case '0':
3115       case 'i':
3116       case 'w':
3117       case 'n':
3118       case 'u':
3119         break;
3120
3121       default:
3122         abort ();
3123       }
3124 }
3125 #endif