OSDN Git Service

91th Cygnus<->FSF quick merge
[pf3gnuchains/gcc-fork.git] / gcc / jump.c
1 /* Optimize jump instructions, for GNU compiler.
2    Copyright (C) 1987, 88, 89, 91-96, 1997 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, 59 Temple Place - Suite 330,
19 Boston, MA 02111-1307, USA.  */
20
21
22 /* This is the jump-optimization pass of the compiler.
23    It is run two or three times: once before cse, sometimes once after cse,
24    and once after reload (before final).
25
26    jump_optimize deletes unreachable code and labels that are not used.
27    It also deletes jumps that jump to the following insn,
28    and simplifies jumps around unconditional jumps and jumps
29    to unconditional jumps.
30
31    Each CODE_LABEL has a count of the times it is used
32    stored in the LABEL_NUSES internal field, and each JUMP_INSN
33    has one label that it refers to stored in the
34    JUMP_LABEL internal field.  With this we can detect labels that
35    become unused because of the deletion of all the jumps that
36    formerly used them.  The JUMP_LABEL info is sometimes looked
37    at by later passes.
38
39    Optionally, cross-jumping can be done.  Currently it is done
40    only the last time (when after reload and before final).
41    In fact, the code for cross-jumping now assumes that register
42    allocation has been done, since it uses `rtx_renumbered_equal_p'.
43
44    Jump optimization is done after cse when cse's constant-propagation
45    causes jumps to become unconditional or to be deleted.
46
47    Unreachable loops are not detected here, because the labels
48    have references and the insns appear reachable from the labels.
49    find_basic_blocks in flow.c finds and deletes such loops.
50
51    The subroutines delete_insn, redirect_jump, and invert_jump are used
52    from other passes as well.  */
53
54 #include "config.h"
55 #include "rtl.h"
56 #include "flags.h"
57 #include "hard-reg-set.h"
58 #include "regs.h"
59 #include "insn-config.h"
60 #include "insn-flags.h"
61 #include "expr.h"
62 #include "real.h"
63 #include "except.h"
64
65 /* ??? Eventually must record somehow the labels used by jumps
66    from nested functions.  */
67 /* Pre-record the next or previous real insn for each label?
68    No, this pass is very fast anyway.  */
69 /* Condense consecutive labels?
70    This would make life analysis faster, maybe.  */
71 /* Optimize jump y; x: ... y: jumpif... x?
72    Don't know if it is worth bothering with.  */
73 /* Optimize two cases of conditional jump to conditional jump?
74    This can never delete any instruction or make anything dead,
75    or even change what is live at any point.
76    So perhaps let combiner do it.  */
77
78 /* Vector indexed by uid.
79    For each CODE_LABEL, index by its uid to get first unconditional jump
80    that jumps to the label.
81    For each JUMP_INSN, index by its uid to get the next unconditional jump
82    that jumps to the same label.
83    Element 0 is the start of a chain of all return insns.
84    (It is safe to use element 0 because insn uid 0 is not used.  */
85
86 static rtx *jump_chain;
87
88 /* List of labels referred to from initializers.
89    These can never be deleted.  */
90 rtx forced_labels;
91
92 /* Maximum index in jump_chain.  */
93
94 static int max_jump_chain;
95
96 /* Set nonzero by jump_optimize if control can fall through
97    to the end of the function.  */
98 int can_reach_end;
99
100 /* Indicates whether death notes are significant in cross jump analysis.
101    Normally they are not significant, because of A and B jump to C,
102    and R dies in A, it must die in B.  But this might not be true after
103    stack register conversion, and we must compare death notes in that
104    case.  */
105
106 static int cross_jump_death_matters = 0;
107
108 static int duplicate_loop_exit_test     PROTO((rtx));
109 static void find_cross_jump             PROTO((rtx, rtx, int, rtx *, rtx *));
110 static void do_cross_jump               PROTO((rtx, rtx, rtx));
111 static int jump_back_p                  PROTO((rtx, rtx));
112 static int tension_vector_labels        PROTO((rtx, int));
113 static void mark_jump_label             PROTO((rtx, rtx, int));
114 static void delete_computation          PROTO((rtx));
115 static void delete_from_jump_chain      PROTO((rtx));
116 static int delete_labelref_insn         PROTO((rtx, rtx, int));
117 static void redirect_tablejump          PROTO((rtx, rtx));
118 \f
119 /* Delete no-op jumps and optimize jumps to jumps
120    and jumps around jumps.
121    Delete unused labels and unreachable code.
122
123    If CROSS_JUMP is 1, detect matching code
124    before a jump and its destination and unify them.
125    If CROSS_JUMP is 2, do cross-jumping, but pay attention to death notes.
126
127    If NOOP_MOVES is nonzero, delete no-op move insns.
128
129    If AFTER_REGSCAN is nonzero, then this jump pass is being run immediately
130    after regscan, and it is safe to use regno_first_uid and regno_last_uid.
131
132    If `optimize' is zero, don't change any code,
133    just determine whether control drops off the end of the function.
134    This case occurs when we have -W and not -O.
135    It works because `delete_insn' checks the value of `optimize'
136    and refrains from actually deleting when that is 0.  */
137
138 void
139 jump_optimize (f, cross_jump, noop_moves, after_regscan)
140      rtx f;
141      int cross_jump;
142      int noop_moves;
143      int after_regscan;
144 {
145   register rtx insn, next, note;
146   int changed;
147   int first = 1;
148   int max_uid = 0;
149   rtx last_insn;
150
151   cross_jump_death_matters = (cross_jump == 2);
152
153   /* Initialize LABEL_NUSES and JUMP_LABEL fields.  Delete any REG_LABEL
154      notes whose labels don't occur in the insn any more.  */
155
156   for (insn = f; insn; insn = NEXT_INSN (insn))
157     {
158       if (GET_CODE (insn) == CODE_LABEL)
159         LABEL_NUSES (insn) = (LABEL_PRESERVE_P (insn) != 0);
160       else if (GET_CODE (insn) == JUMP_INSN)
161         JUMP_LABEL (insn) = 0;
162       else if (GET_CODE (insn) == INSN || GET_CODE (insn) == CALL_INSN)
163         for (note = REG_NOTES (insn); note; note = next)
164           {
165             next = XEXP (note, 1);
166             if (REG_NOTE_KIND (note) == REG_LABEL
167                 && ! reg_mentioned_p (XEXP (note, 0), PATTERN (insn)))
168               remove_note (insn, note);
169           }
170
171       if (INSN_UID (insn) > max_uid)
172         max_uid = INSN_UID (insn);
173     }
174
175   max_uid++;
176
177   /* Delete insns following barriers, up to next label.  */
178
179   for (insn = f; insn;)
180     {
181       if (GET_CODE (insn) == BARRIER)
182         {
183           insn = NEXT_INSN (insn);
184           while (insn != 0 && GET_CODE (insn) != CODE_LABEL)
185             {
186               if (GET_CODE (insn) == NOTE
187                   && NOTE_LINE_NUMBER (insn) != NOTE_INSN_FUNCTION_END)
188                 insn = NEXT_INSN (insn);
189               else
190                 insn = delete_insn (insn);
191             }
192           /* INSN is now the code_label.  */
193         }
194       else
195         insn = NEXT_INSN (insn);
196     }
197
198   /* Leave some extra room for labels and duplicate exit test insns
199      we make.  */
200   max_jump_chain = max_uid * 14 / 10;
201   jump_chain = (rtx *) alloca (max_jump_chain * sizeof (rtx));
202   bzero ((char *) jump_chain, max_jump_chain * sizeof (rtx));
203
204   /* Mark the label each jump jumps to.
205      Combine consecutive labels, and count uses of labels.
206
207      For each label, make a chain (using `jump_chain')
208      of all the *unconditional* jumps that jump to it;
209      also make a chain of all returns.  */
210
211   for (insn = f; insn; insn = NEXT_INSN (insn))
212     if (GET_RTX_CLASS (GET_CODE (insn)) == 'i'
213         && ! INSN_DELETED_P (insn))
214       {
215         mark_jump_label (PATTERN (insn), insn, cross_jump);
216         if (GET_CODE (insn) == JUMP_INSN)
217           {
218             if (JUMP_LABEL (insn) != 0 && simplejump_p (insn))
219               {
220                 jump_chain[INSN_UID (insn)]
221                   = jump_chain[INSN_UID (JUMP_LABEL (insn))];
222                 jump_chain[INSN_UID (JUMP_LABEL (insn))] = insn;
223               }
224             if (GET_CODE (PATTERN (insn)) == RETURN)
225               {
226                 jump_chain[INSN_UID (insn)] = jump_chain[0];
227                 jump_chain[0] = insn;
228               }
229           }
230       }
231
232   /* Keep track of labels used from static data;
233      they cannot ever be deleted.  */
234
235   for (insn = forced_labels; insn; insn = XEXP (insn, 1))
236     LABEL_NUSES (XEXP (insn, 0))++;
237
238   check_exception_handler_labels ();
239
240   /* Keep track of labels used for marking handlers for exception
241      regions; they cannot usually be deleted.  */
242
243   for (insn = exception_handler_labels; insn; insn = XEXP (insn, 1))
244     LABEL_NUSES (XEXP (insn, 0))++;
245
246   exception_optimize ();
247
248   /* Delete all labels already not referenced.
249      Also find the last insn.  */
250
251   last_insn = 0;
252   for (insn = f; insn; )
253     {
254       if (GET_CODE (insn) == CODE_LABEL && LABEL_NUSES (insn) == 0)
255         insn = delete_insn (insn);
256       else
257         {
258           last_insn = insn;
259           insn = NEXT_INSN (insn);
260         }
261     }
262
263   if (!optimize)
264     {
265       /* See if there is still a NOTE_INSN_FUNCTION_END in this function.
266          If so record that this function can drop off the end.  */
267
268       insn = last_insn;
269       {
270         int n_labels = 1;
271         while (insn
272                /* One label can follow the end-note: the return label.  */
273                && ((GET_CODE (insn) == CODE_LABEL && n_labels-- > 0)
274                    /* Ordinary insns can follow it if returning a structure.  */
275                    || GET_CODE (insn) == INSN
276                    /* If machine uses explicit RETURN insns, no epilogue,
277                       then one of them follows the note.  */
278                    || (GET_CODE (insn) == JUMP_INSN
279                        && GET_CODE (PATTERN (insn)) == RETURN)
280                    /* A barrier can follow the return insn.  */
281                    || GET_CODE (insn) == BARRIER
282                    /* Other kinds of notes can follow also.  */
283                    || (GET_CODE (insn) == NOTE
284                        && NOTE_LINE_NUMBER (insn) != NOTE_INSN_FUNCTION_END)))
285           insn = PREV_INSN (insn);
286       }
287
288       /* Report if control can fall through at the end of the function.  */
289       if (insn && GET_CODE (insn) == NOTE
290           && NOTE_LINE_NUMBER (insn) == NOTE_INSN_FUNCTION_END
291           && ! INSN_DELETED_P (insn))
292         can_reach_end = 1;
293
294       /* Zero the "deleted" flag of all the "deleted" insns.  */
295       for (insn = f; insn; insn = NEXT_INSN (insn))
296         INSN_DELETED_P (insn) = 0;
297       return;
298     }
299
300 #ifdef HAVE_return
301   if (HAVE_return)
302     {
303       /* If we fall through to the epilogue, see if we can insert a RETURN insn
304          in front of it.  If the machine allows it at this point (we might be
305          after reload for a leaf routine), it will improve optimization for it
306          to be there.  */
307       insn = get_last_insn ();
308       while (insn && GET_CODE (insn) == NOTE)
309         insn = PREV_INSN (insn);
310
311       if (insn && GET_CODE (insn) != BARRIER)
312         {
313           emit_jump_insn (gen_return ());
314           emit_barrier ();
315         }
316     }
317 #endif
318
319   if (noop_moves)
320     for (insn = f; insn; )
321       {
322         next = NEXT_INSN (insn);
323
324         if (GET_CODE (insn) == INSN)
325           {
326             register rtx body = PATTERN (insn);
327
328 /* Combine stack_adjusts with following push_insns.  */
329 #ifdef PUSH_ROUNDING
330             if (GET_CODE (body) == SET
331                 && SET_DEST (body) == stack_pointer_rtx
332                 && GET_CODE (SET_SRC (body)) == PLUS
333                 && XEXP (SET_SRC (body), 0) == stack_pointer_rtx
334                 && GET_CODE (XEXP (SET_SRC (body), 1)) == CONST_INT
335                 && INTVAL (XEXP (SET_SRC (body), 1)) > 0)
336               {
337                 rtx p;
338                 rtx stack_adjust_insn = insn;
339                 int stack_adjust_amount = INTVAL (XEXP (SET_SRC (body), 1));
340                 int total_pushed = 0;
341                 int pushes = 0;
342
343                 /* Find all successive push insns.  */
344                 p = insn;
345                 /* Don't convert more than three pushes;
346                    that starts adding too many displaced addresses
347                    and the whole thing starts becoming a losing
348                    proposition.  */
349                 while (pushes < 3)
350                   {
351                     rtx pbody, dest;
352                     p = next_nonnote_insn (p);
353                     if (p == 0 || GET_CODE (p) != INSN)
354                       break;
355                     pbody = PATTERN (p);
356                     if (GET_CODE (pbody) != SET)
357                       break;
358                     dest = SET_DEST (pbody);
359                     /* Allow a no-op move between the adjust and the push.  */
360                     if (GET_CODE (dest) == REG
361                         && GET_CODE (SET_SRC (pbody)) == REG
362                         && REGNO (dest) == REGNO (SET_SRC (pbody)))
363                       continue;
364                     if (! (GET_CODE (dest) == MEM
365                            && GET_CODE (XEXP (dest, 0)) == POST_INC
366                            && XEXP (XEXP (dest, 0), 0) == stack_pointer_rtx))
367                       break;
368                     pushes++;
369                     if (total_pushed + GET_MODE_SIZE (GET_MODE (SET_DEST (pbody)))
370                         > stack_adjust_amount)
371                       break;
372                     total_pushed += GET_MODE_SIZE (GET_MODE (SET_DEST (pbody)));
373                   }
374
375                 /* Discard the amount pushed from the stack adjust;
376                    maybe eliminate it entirely.  */
377                 if (total_pushed >= stack_adjust_amount)
378                   {
379                     delete_computation (stack_adjust_insn);
380                     total_pushed = stack_adjust_amount;
381                   }
382                 else
383                   XEXP (SET_SRC (PATTERN (stack_adjust_insn)), 1)
384                     = GEN_INT (stack_adjust_amount - total_pushed);
385
386                 /* Change the appropriate push insns to ordinary stores.  */
387                 p = insn;
388                 while (total_pushed > 0)
389                   {
390                     rtx pbody, dest;
391                     p = next_nonnote_insn (p);
392                     if (GET_CODE (p) != INSN)
393                       break;
394                     pbody = PATTERN (p);
395                     if (GET_CODE (pbody) == SET)
396                       break;
397                     dest = SET_DEST (pbody);
398                     if (! (GET_CODE (dest) == MEM
399                            && GET_CODE (XEXP (dest, 0)) == POST_INC
400                            && XEXP (XEXP (dest, 0), 0) == stack_pointer_rtx))
401                       break;
402                     total_pushed -= GET_MODE_SIZE (GET_MODE (SET_DEST (pbody)));
403                     /* If this push doesn't fully fit in the space
404                        of the stack adjust that we deleted,
405                        make another stack adjust here for what we
406                        didn't use up.  There should be peepholes
407                        to recognize the resulting sequence of insns.  */
408                     if (total_pushed < 0)
409                       {
410                         emit_insn_before (gen_add2_insn (stack_pointer_rtx,
411                                                          GEN_INT (- total_pushed)),
412                                           p);
413                         break;
414                       }
415                     XEXP (dest, 0)
416                       = plus_constant (stack_pointer_rtx, total_pushed);
417                   }
418               }
419 #endif
420
421             /* Detect and delete no-op move instructions
422                resulting from not allocating a parameter in a register.  */
423
424             if (GET_CODE (body) == SET
425                 && (SET_DEST (body) == SET_SRC (body)
426                     || (GET_CODE (SET_DEST (body)) == MEM
427                         && GET_CODE (SET_SRC (body)) == MEM
428                         && rtx_equal_p (SET_SRC (body), SET_DEST (body))))
429                 && ! (GET_CODE (SET_DEST (body)) == MEM
430                       && MEM_VOLATILE_P (SET_DEST (body)))
431                 && ! (GET_CODE (SET_SRC (body)) == MEM
432                       && MEM_VOLATILE_P (SET_SRC (body))))
433               delete_computation (insn);
434
435             /* Detect and ignore no-op move instructions
436                resulting from smart or fortuitous register allocation.  */
437
438             else if (GET_CODE (body) == SET)
439               {
440                 int sreg = true_regnum (SET_SRC (body));
441                 int dreg = true_regnum (SET_DEST (body));
442
443                 if (sreg == dreg && sreg >= 0)
444                   delete_insn (insn);
445                 else if (sreg >= 0 && dreg >= 0)
446                   {
447                     rtx trial;
448                     rtx tem = find_equiv_reg (NULL_RTX, insn, 0,
449                                               sreg, NULL_PTR, dreg,
450                                               GET_MODE (SET_SRC (body)));
451
452                     if (tem != 0 &&
453                         GET_MODE (tem) == GET_MODE (SET_DEST (body)))
454                       {
455                         /* DREG may have been the target of a REG_DEAD note in
456                            the insn which makes INSN redundant.  If so, reorg
457                            would still think it is dead.  So search for such a
458                            note and delete it if we find it.  */
459                         if (! find_regno_note (insn, REG_UNUSED, dreg))
460                           for (trial = prev_nonnote_insn (insn);
461                                trial && GET_CODE (trial) != CODE_LABEL;
462                                trial = prev_nonnote_insn (trial))
463                             if (find_regno_note (trial, REG_DEAD, dreg))
464                               {
465                                 remove_death (dreg, trial);
466                                 break;
467                               }
468 #ifdef PRESERVE_DEATH_INFO_REGNO_P
469                         /* Deleting insn could lose a death-note for SREG
470                            so don't do it if final needs accurate
471                            death-notes.  */
472                         if (PRESERVE_DEATH_INFO_REGNO_P (sreg)
473                             && (trial = find_regno_note (insn, REG_DEAD, sreg)))
474                           {
475                             /* Change this into a USE so that we won't emit
476                                code for it, but still can keep the note.  */
477                             PATTERN (insn)
478                               = gen_rtx (USE, VOIDmode, XEXP (trial, 0));
479                             INSN_CODE (insn) = -1;
480                             /* Remove all reg notes but the REG_DEAD one.  */
481                             REG_NOTES (insn) = trial;
482                             XEXP (trial, 1) = NULL_RTX;
483                           }
484                         else
485 #endif
486                           delete_insn (insn);
487                       }
488                   }
489                 else if (dreg >= 0 && CONSTANT_P (SET_SRC (body))
490                          && find_equiv_reg (SET_SRC (body), insn, 0, dreg,
491                                             NULL_PTR, 0,
492                                             GET_MODE (SET_DEST (body))))
493                   {
494                     /* This handles the case where we have two consecutive
495                        assignments of the same constant to pseudos that didn't
496                        get a hard reg.  Each SET from the constant will be
497                        converted into a SET of the spill register and an
498                        output reload will be made following it.  This produces
499                        two loads of the same constant into the same spill
500                        register.  */
501
502                     rtx in_insn = insn;
503
504                     /* Look back for a death note for the first reg.
505                        If there is one, it is no longer accurate.  */
506                     while (in_insn && GET_CODE (in_insn) != CODE_LABEL)
507                       {
508                         if ((GET_CODE (in_insn) == INSN
509                              || GET_CODE (in_insn) == JUMP_INSN)
510                             && find_regno_note (in_insn, REG_DEAD, dreg))
511                           {
512                             remove_death (dreg, in_insn);
513                             break;
514                           }
515                         in_insn = PREV_INSN (in_insn);
516                       }
517
518                     /* Delete the second load of the value.  */
519                     delete_insn (insn);
520                   }
521               }
522             else if (GET_CODE (body) == PARALLEL)
523               {
524                 /* If each part is a set between two identical registers or
525                    a USE or CLOBBER, delete the insn.  */
526                 int i, sreg, dreg;
527                 rtx tem;
528
529                 for (i = XVECLEN (body, 0) - 1; i >= 0; i--)
530                   {
531                     tem = XVECEXP (body, 0, i);
532                     if (GET_CODE (tem) == USE || GET_CODE (tem) == CLOBBER)
533                       continue;
534
535                     if (GET_CODE (tem) != SET
536                         || (sreg = true_regnum (SET_SRC (tem))) < 0
537                         || (dreg = true_regnum (SET_DEST (tem))) < 0
538                         || dreg != sreg)
539                       break;
540                   }
541                   
542                 if (i < 0)
543                   delete_insn (insn);
544               }
545             /* Also delete insns to store bit fields if they are no-ops.  */
546             /* Not worth the hair to detect this in the big-endian case.  */
547             else if (! BYTES_BIG_ENDIAN
548                      && GET_CODE (body) == SET
549                      && GET_CODE (SET_DEST (body)) == ZERO_EXTRACT
550                      && XEXP (SET_DEST (body), 2) == const0_rtx
551                      && XEXP (SET_DEST (body), 0) == SET_SRC (body)
552                      && ! (GET_CODE (SET_SRC (body)) == MEM
553                            && MEM_VOLATILE_P (SET_SRC (body))))
554               delete_insn (insn);
555           }
556       insn = next;
557     }
558
559   /* If we haven't yet gotten to reload and we have just run regscan,
560      delete any insn that sets a register that isn't used elsewhere.
561      This helps some of the optimizations below by having less insns
562      being jumped around.  */
563
564   if (! reload_completed && after_regscan)
565     for (insn = f; insn; insn = next)
566       {
567         rtx set = single_set (insn);
568
569         next = NEXT_INSN (insn);
570
571         if (set && GET_CODE (SET_DEST (set)) == REG
572             && REGNO (SET_DEST (set)) >= FIRST_PSEUDO_REGISTER
573             && regno_first_uid[REGNO (SET_DEST (set))] == INSN_UID (insn)
574             /* We use regno_last_note_uid so as not to delete the setting
575                of a reg that's used in notes.  A subsequent optimization
576                might arrange to use that reg for real.  */             
577             && regno_last_note_uid[REGNO (SET_DEST (set))] == INSN_UID (insn)
578             && ! side_effects_p (SET_SRC (set))
579             && ! find_reg_note (insn, REG_RETVAL, 0))
580           delete_insn (insn);
581       }
582
583   /* Now iterate optimizing jumps until nothing changes over one pass.  */
584   changed = 1;
585   while (changed)
586     {
587       changed = 0;
588
589       for (insn = f; insn; insn = next)
590         {
591           rtx reallabelprev;
592           rtx temp, temp1, temp2, temp3, temp4, temp5, temp6;
593           rtx nlabel;
594           int this_is_simplejump, this_is_condjump, reversep;
595           int this_is_condjump_in_parallel;
596 #if 0
597           /* If NOT the first iteration, if this is the last jump pass
598              (just before final), do the special peephole optimizations.
599              Avoiding the first iteration gives ordinary jump opts
600              a chance to work before peephole opts.  */
601
602           if (reload_completed && !first && !flag_no_peephole)
603             if (GET_CODE (insn) == INSN || GET_CODE (insn) == JUMP_INSN)
604               peephole (insn);
605 #endif
606
607           /* That could have deleted some insns after INSN, so check now
608              what the following insn is.  */
609
610           next = NEXT_INSN (insn);
611
612           /* See if this is a NOTE_INSN_LOOP_BEG followed by an unconditional
613              jump.  Try to optimize by duplicating the loop exit test if so.
614              This is only safe immediately after regscan, because it uses
615              the values of regno_first_uid and regno_last_uid.  */
616           if (after_regscan && GET_CODE (insn) == NOTE
617               && NOTE_LINE_NUMBER (insn) == NOTE_INSN_LOOP_BEG
618               && (temp1 = next_nonnote_insn (insn)) != 0
619               && simplejump_p (temp1))
620             {
621               temp = PREV_INSN (insn);
622               if (duplicate_loop_exit_test (insn))
623                 {
624                   changed = 1;
625                   next = NEXT_INSN (temp);
626                   continue;
627                 }
628             }
629
630           if (GET_CODE (insn) != JUMP_INSN)
631             continue;
632
633           this_is_simplejump = simplejump_p (insn);
634           this_is_condjump = condjump_p (insn);
635           this_is_condjump_in_parallel = condjump_in_parallel_p (insn);
636
637           /* Tension the labels in dispatch tables.  */
638
639           if (GET_CODE (PATTERN (insn)) == ADDR_VEC)
640             changed |= tension_vector_labels (PATTERN (insn), 0);
641           if (GET_CODE (PATTERN (insn)) == ADDR_DIFF_VEC)
642             changed |= tension_vector_labels (PATTERN (insn), 1);
643
644           /* If a dispatch table always goes to the same place,
645              get rid of it and replace the insn that uses it.  */
646
647           if (GET_CODE (PATTERN (insn)) == ADDR_VEC
648               || GET_CODE (PATTERN (insn)) == ADDR_DIFF_VEC)
649             {
650               int i;
651               rtx pat = PATTERN (insn);
652               int diff_vec_p = GET_CODE (PATTERN (insn)) == ADDR_DIFF_VEC;
653               int len = XVECLEN (pat, diff_vec_p);
654               rtx dispatch = prev_real_insn (insn);
655
656               for (i = 0; i < len; i++)
657                 if (XEXP (XVECEXP (pat, diff_vec_p, i), 0)
658                     != XEXP (XVECEXP (pat, diff_vec_p, 0), 0))
659                   break;
660               if (i == len
661                   && dispatch != 0
662                   && GET_CODE (dispatch) == JUMP_INSN
663                   && JUMP_LABEL (dispatch) != 0
664                   /* Don't mess with a casesi insn.  */
665                   && !(GET_CODE (PATTERN (dispatch)) == SET
666                        && (GET_CODE (SET_SRC (PATTERN (dispatch)))
667                            == IF_THEN_ELSE))
668                   && next_real_insn (JUMP_LABEL (dispatch)) == insn)
669                 {
670                   redirect_tablejump (dispatch,
671                                       XEXP (XVECEXP (pat, diff_vec_p, 0), 0));
672                   changed = 1;
673                 }
674             }
675
676           reallabelprev = prev_active_insn (JUMP_LABEL (insn));
677
678           /* If a jump references the end of the function, try to turn
679              it into a RETURN insn, possibly a conditional one.  */
680           if (JUMP_LABEL (insn)
681               && (next_active_insn (JUMP_LABEL (insn)) == 0
682                   || GET_CODE (PATTERN (next_active_insn (JUMP_LABEL (insn))))
683                       == RETURN))
684             changed |= redirect_jump (insn, NULL_RTX);
685
686           /* Detect jump to following insn.  */
687           if (reallabelprev == insn && condjump_p (insn))
688             {
689               next = next_real_insn (JUMP_LABEL (insn));
690               delete_jump (insn);
691               changed = 1;
692               continue;
693             }
694
695           /* If we have an unconditional jump preceded by a USE, try to put
696              the USE before the target and jump there.  This simplifies many
697              of the optimizations below since we don't have to worry about
698              dealing with these USE insns.  We only do this if the label
699              being branch to already has the identical USE or if code
700              never falls through to that label.  */
701
702           if (this_is_simplejump
703               && (temp = prev_nonnote_insn (insn)) != 0
704               && GET_CODE (temp) == INSN && GET_CODE (PATTERN (temp)) == USE
705               && (temp1 = prev_nonnote_insn (JUMP_LABEL (insn))) != 0
706               && (GET_CODE (temp1) == BARRIER
707                   || (GET_CODE (temp1) == INSN
708                       && rtx_equal_p (PATTERN (temp), PATTERN (temp1))))
709               /* Don't do this optimization if we have a loop containing only
710                  the USE instruction, and the loop start label has a usage
711                  count of 1.  This is because we will redo this optimization
712                  everytime through the outer loop, and jump opt will never
713                  exit.  */
714               && ! ((temp2 = prev_nonnote_insn (temp)) != 0
715                     && temp2 == JUMP_LABEL (insn)
716                     && LABEL_NUSES (temp2) == 1))
717             {
718               if (GET_CODE (temp1) == BARRIER)
719                 {
720                   emit_insn_after (PATTERN (temp), temp1);
721                   temp1 = NEXT_INSN (temp1);
722                 }
723
724               delete_insn (temp);
725               redirect_jump (insn, get_label_before (temp1));
726               reallabelprev = prev_real_insn (temp1);
727               changed = 1;
728             }
729
730           /* Simplify   if (...) x = a; else x = b; by converting it
731              to         x = b; if (...) x = a;
732              if B is sufficiently simple, the test doesn't involve X,
733              and nothing in the test modifies B or X.
734
735              If we have small register classes, we also can't do this if X
736              is a hard register.
737
738              If the "x = b;" insn has any REG_NOTES, we don't do this because
739              of the possibility that we are running after CSE and there is a
740              REG_EQUAL note that is only valid if the branch has already been
741              taken.  If we move the insn with the REG_EQUAL note, we may
742              fold the comparison to always be false in a later CSE pass.
743              (We could also delete the REG_NOTES when moving the insn, but it
744              seems simpler to not move it.)  An exception is that we can move
745              the insn if the only note is a REG_EQUAL or REG_EQUIV whose
746              value is the same as "b".
747
748              INSN is the branch over the `else' part. 
749
750              We set:
751
752              TEMP to the jump insn preceding "x = a;"
753              TEMP1 to X
754              TEMP2 to the insn that sets "x = b;"
755              TEMP3 to the insn that sets "x = a;"
756              TEMP4 to the set of "x = b";  */
757
758           if (this_is_simplejump
759               && (temp3 = prev_active_insn (insn)) != 0
760               && GET_CODE (temp3) == INSN
761               && (temp4 = single_set (temp3)) != 0
762               && GET_CODE (temp1 = SET_DEST (temp4)) == REG
763 #ifdef SMALL_REGISTER_CLASSES
764               && (! SMALL_REGISTER_CLASSES
765                   || REGNO (temp1) >= FIRST_PSEUDO_REGISTER)
766 #endif
767               && (temp2 = next_active_insn (insn)) != 0
768               && GET_CODE (temp2) == INSN
769               && (temp4 = single_set (temp2)) != 0
770               && rtx_equal_p (SET_DEST (temp4), temp1)
771               && (GET_CODE (SET_SRC (temp4)) == REG
772                   || GET_CODE (SET_SRC (temp4)) == SUBREG
773                   || CONSTANT_P (SET_SRC (temp4)))
774               && (REG_NOTES (temp2) == 0
775                   || ((REG_NOTE_KIND (REG_NOTES (temp2)) == REG_EQUAL
776                        || REG_NOTE_KIND (REG_NOTES (temp2)) == REG_EQUIV)
777                       && XEXP (REG_NOTES (temp2), 1) == 0
778                       && rtx_equal_p (XEXP (REG_NOTES (temp2), 0),
779                                       SET_SRC (temp4))))
780               && (temp = prev_active_insn (temp3)) != 0
781               && condjump_p (temp) && ! simplejump_p (temp)
782               /* TEMP must skip over the "x = a;" insn */
783               && prev_real_insn (JUMP_LABEL (temp)) == insn
784               && no_labels_between_p (insn, JUMP_LABEL (temp))
785               /* There must be no other entries to the "x = b;" insn.  */
786               && no_labels_between_p (JUMP_LABEL (temp), temp2)
787               /* INSN must either branch to the insn after TEMP2 or the insn
788                  after TEMP2 must branch to the same place as INSN.  */
789               && (reallabelprev == temp2
790                   || ((temp5 = next_active_insn (temp2)) != 0
791                       && simplejump_p (temp5)
792                       && JUMP_LABEL (temp5) == JUMP_LABEL (insn))))
793             {
794               /* The test expression, X, may be a complicated test with
795                  multiple branches.  See if we can find all the uses of
796                  the label that TEMP branches to without hitting a CALL_INSN
797                  or a jump to somewhere else.  */
798               rtx target = JUMP_LABEL (temp);
799               int nuses = LABEL_NUSES (target);
800               rtx p, q;
801
802               /* Set P to the first jump insn that goes around "x = a;".  */
803               for (p = temp; nuses && p; p = prev_nonnote_insn (p))
804                 {
805                   if (GET_CODE (p) == JUMP_INSN)
806                     {
807                       if (condjump_p (p) && ! simplejump_p (p)
808                           && JUMP_LABEL (p) == target)
809                         {
810                           nuses--;
811                           if (nuses == 0)
812                             break;
813                         }
814                       else
815                         break;
816                     }
817                   else if (GET_CODE (p) == CALL_INSN)
818                     break;
819                 }
820
821 #ifdef HAVE_cc0
822               /* We cannot insert anything between a set of cc and its use
823                  so if P uses cc0, we must back up to the previous insn.  */
824               q = prev_nonnote_insn (p);
825               if (q && GET_RTX_CLASS (GET_CODE (q)) == 'i'
826                   && sets_cc0_p (PATTERN (q)))
827                 p = q;
828 #endif
829
830               if (p)
831                 p = PREV_INSN (p);
832
833               /* If we found all the uses and there was no data conflict, we
834                  can move the assignment unless we can branch into the middle
835                  from somewhere.  */
836               if (nuses == 0 && p
837                   && no_labels_between_p (p, insn)
838                   && ! reg_referenced_between_p (temp1, p, NEXT_INSN (temp3))
839                   && ! reg_set_between_p (temp1, p, temp3)
840                   && (GET_CODE (SET_SRC (temp4)) == CONST_INT
841                       || ! reg_set_between_p (SET_SRC (temp4), p, temp2)))
842                 {
843                   emit_insn_after_with_line_notes (PATTERN (temp2), p, temp2);
844                   delete_insn (temp2);
845
846                   /* Set NEXT to an insn that we know won't go away.  */
847                   next = next_active_insn (insn);
848
849                   /* Delete the jump around the set.  Note that we must do
850                      this before we redirect the test jumps so that it won't
851                      delete the code immediately following the assignment
852                      we moved (which might be a jump).  */
853
854                   delete_insn (insn);
855
856                   /* We either have two consecutive labels or a jump to
857                      a jump, so adjust all the JUMP_INSNs to branch to where
858                      INSN branches to.  */
859                   for (p = NEXT_INSN (p); p != next; p = NEXT_INSN (p))
860                     if (GET_CODE (p) == JUMP_INSN)
861                       redirect_jump (p, target);
862
863                   changed = 1;
864                   continue;
865                 }
866             }
867
868           /* Simplify   if (...) { x = a; goto l; } x = b; by converting it
869              to         x = a; if (...) goto l; x = b;
870              if A is sufficiently simple, the test doesn't involve X,
871              and nothing in the test modifies A or X.
872
873              If we have small register classes, we also can't do this if X
874              is a hard register.
875
876              If the "x = a;" insn has any REG_NOTES, we don't do this because
877              of the possibility that we are running after CSE and there is a
878              REG_EQUAL note that is only valid if the branch has already been
879              taken.  If we move the insn with the REG_EQUAL note, we may
880              fold the comparison to always be false in a later CSE pass.
881              (We could also delete the REG_NOTES when moving the insn, but it
882              seems simpler to not move it.)  An exception is that we can move
883              the insn if the only note is a REG_EQUAL or REG_EQUIV whose
884              value is the same as "a".
885
886              INSN is the goto.
887
888              We set:
889
890              TEMP to the jump insn preceding "x = a;"
891              TEMP1 to X
892              TEMP2 to the insn that sets "x = b;"
893              TEMP3 to the insn that sets "x = a;"
894              TEMP4 to the set of "x = a";  */
895
896           if (this_is_simplejump
897               && (temp2 = next_active_insn (insn)) != 0
898               && GET_CODE (temp2) == INSN
899               && (temp4 = single_set (temp2)) != 0
900               && GET_CODE (temp1 = SET_DEST (temp4)) == REG
901 #ifdef SMALL_REGISTER_CLASSES
902               && (! SMALL_REGISTER_CLASSES
903                   || REGNO (temp1) >= FIRST_PSEUDO_REGISTER)
904 #endif
905
906               && (temp3 = prev_active_insn (insn)) != 0
907               && GET_CODE (temp3) == INSN
908               && (temp4 = single_set (temp3)) != 0
909               && rtx_equal_p (SET_DEST (temp4), temp1)
910               && (GET_CODE (SET_SRC (temp4)) == REG
911                   || GET_CODE (SET_SRC (temp4)) == SUBREG
912                   || CONSTANT_P (SET_SRC (temp4)))
913               && (REG_NOTES (temp3) == 0
914                   || ((REG_NOTE_KIND (REG_NOTES (temp3)) == REG_EQUAL
915                        || REG_NOTE_KIND (REG_NOTES (temp3)) == REG_EQUIV)
916                       && XEXP (REG_NOTES (temp3), 1) == 0
917                       && rtx_equal_p (XEXP (REG_NOTES (temp3), 0),
918                                       SET_SRC (temp4))))
919               && (temp = prev_active_insn (temp3)) != 0
920               && condjump_p (temp) && ! simplejump_p (temp)
921               /* TEMP must skip over the "x = a;" insn */
922               && prev_real_insn (JUMP_LABEL (temp)) == insn
923               && no_labels_between_p (temp, insn))
924             {
925               rtx prev_label = JUMP_LABEL (temp);
926               rtx insert_after = prev_nonnote_insn (temp);
927
928 #ifdef HAVE_cc0
929               /* We cannot insert anything between a set of cc and its use.  */
930               if (insert_after && GET_RTX_CLASS (GET_CODE (insert_after)) == 'i'
931                   && sets_cc0_p (PATTERN (insert_after)))
932                 insert_after = prev_nonnote_insn (insert_after);
933 #endif
934               ++LABEL_NUSES (prev_label);
935
936               if (insert_after
937                   && no_labels_between_p (insert_after, temp)
938                   && ! reg_referenced_between_p (temp1, insert_after, temp3)
939                   && ! reg_referenced_between_p (temp1, temp3,
940                                                  NEXT_INSN (temp2))
941                   && ! reg_set_between_p (temp1, insert_after, temp)
942                   && (GET_CODE (SET_SRC (temp4)) == CONST_INT
943                       || ! reg_set_between_p (SET_SRC (temp4),
944                                               insert_after, temp))
945                   && invert_jump (temp, JUMP_LABEL (insn)))
946                 {
947                   emit_insn_after_with_line_notes (PATTERN (temp3),
948                                                    insert_after, temp3);
949                   delete_insn (temp3);
950                   delete_insn (insn);
951                   /* Set NEXT to an insn that we know won't go away.  */
952                   next = temp2;
953                   changed = 1;
954                 }
955               if (prev_label && --LABEL_NUSES (prev_label) == 0)
956                 delete_insn (prev_label);
957               if (changed)
958                 continue;
959             }
960
961 #ifndef HAVE_cc0
962           /* If we have if (...) x = exp;  and branches are expensive,
963              EXP is a single insn, does not have any side effects, cannot
964              trap, and is not too costly, convert this to
965              t = exp; if (...) x = t;
966
967              Don't do this when we have CC0 because it is unlikely to help
968              and we'd need to worry about where to place the new insn and
969              the potential for conflicts.  We also can't do this when we have
970              notes on the insn for the same reason as above.
971
972              We set:
973
974              TEMP to the "x = exp;" insn.
975              TEMP1 to the single set in the "x = exp; insn.
976              TEMP2 to "x".  */
977
978           if (! reload_completed
979               && this_is_condjump && ! this_is_simplejump
980               && BRANCH_COST >= 3
981               && (temp = next_nonnote_insn (insn)) != 0
982               && GET_CODE (temp) == INSN
983               && REG_NOTES (temp) == 0
984               && (reallabelprev == temp
985                   || ((temp2 = next_active_insn (temp)) != 0
986                       && simplejump_p (temp2)
987                       && JUMP_LABEL (temp2) == JUMP_LABEL (insn)))
988               && (temp1 = single_set (temp)) != 0
989               && (temp2 = SET_DEST (temp1), GET_CODE (temp2) == REG)
990               && GET_MODE_CLASS (GET_MODE (temp2)) == MODE_INT
991 #ifdef SMALL_REGISTER_CLASSES
992               && (! SMALL_REGISTER_CLASSES
993                   || REGNO (temp2) >= FIRST_PSEUDO_REGISTER)
994 #endif
995               && GET_CODE (SET_SRC (temp1)) != REG
996               && GET_CODE (SET_SRC (temp1)) != SUBREG
997               && GET_CODE (SET_SRC (temp1)) != CONST_INT
998               && ! side_effects_p (SET_SRC (temp1))
999               && ! may_trap_p (SET_SRC (temp1))
1000               && rtx_cost (SET_SRC (temp1), SET) < 10)
1001             {
1002               rtx new = gen_reg_rtx (GET_MODE (temp2));
1003
1004               if (validate_change (temp, &SET_DEST (temp1), new, 0))
1005                 {
1006                   next = emit_insn_after (gen_move_insn (temp2, new), insn);
1007                   emit_insn_after_with_line_notes (PATTERN (temp), 
1008                                                    PREV_INSN (insn), temp);
1009                   delete_insn (temp);
1010                   reallabelprev = prev_active_insn (JUMP_LABEL (insn));
1011                 }
1012             }
1013
1014           /* Similarly, if it takes two insns to compute EXP but they
1015              have the same destination.  Here TEMP3 will be the second
1016              insn and TEMP4 the SET from that insn.  */
1017
1018           if (! reload_completed
1019               && this_is_condjump && ! this_is_simplejump
1020               && BRANCH_COST >= 4
1021               && (temp = next_nonnote_insn (insn)) != 0
1022               && GET_CODE (temp) == INSN
1023               && REG_NOTES (temp) == 0
1024               && (temp3 = next_nonnote_insn (temp)) != 0
1025               && GET_CODE (temp3) == INSN
1026               && REG_NOTES (temp3) == 0
1027               && (reallabelprev == temp3
1028                   || ((temp2 = next_active_insn (temp3)) != 0
1029                       && simplejump_p (temp2)
1030                       && JUMP_LABEL (temp2) == JUMP_LABEL (insn)))
1031               && (temp1 = single_set (temp)) != 0
1032               && (temp2 = SET_DEST (temp1), GET_CODE (temp2) == REG)
1033               && GET_MODE_CLASS (GET_MODE (temp2)) == MODE_INT
1034 #ifdef SMALL_REGISTER_CLASSES
1035               && (! SMALL_REGISTER_CLASSES
1036                   || REGNO (temp2) >= FIRST_PSEUDO_REGISTER)
1037 #endif
1038               && ! side_effects_p (SET_SRC (temp1))
1039               && ! may_trap_p (SET_SRC (temp1))
1040               && rtx_cost (SET_SRC (temp1), SET) < 10
1041               && (temp4 = single_set (temp3)) != 0
1042               && rtx_equal_p (SET_DEST (temp4), temp2)
1043               && ! side_effects_p (SET_SRC (temp4))
1044               && ! may_trap_p (SET_SRC (temp4))
1045               && rtx_cost (SET_SRC (temp4), SET) < 10)
1046             {
1047               rtx new = gen_reg_rtx (GET_MODE (temp2));
1048
1049               if (validate_change (temp, &SET_DEST (temp1), new, 0))
1050                 {
1051                   next = emit_insn_after (gen_move_insn (temp2, new), insn);
1052                   emit_insn_after_with_line_notes (PATTERN (temp),
1053                                                    PREV_INSN (insn), temp);
1054                   emit_insn_after_with_line_notes
1055                     (replace_rtx (PATTERN (temp3), temp2, new),
1056                      PREV_INSN (insn), temp3);
1057                   delete_insn (temp);
1058                   delete_insn (temp3);
1059                   reallabelprev = prev_active_insn (JUMP_LABEL (insn));
1060                 }
1061             }
1062
1063           /* Finally, handle the case where two insns are used to 
1064              compute EXP but a temporary register is used.  Here we must
1065              ensure that the temporary register is not used anywhere else.  */
1066
1067           if (! reload_completed
1068               && after_regscan
1069               && this_is_condjump && ! this_is_simplejump
1070               && BRANCH_COST >= 4
1071               && (temp = next_nonnote_insn (insn)) != 0
1072               && GET_CODE (temp) == INSN
1073               && REG_NOTES (temp) == 0
1074               && (temp3 = next_nonnote_insn (temp)) != 0
1075               && GET_CODE (temp3) == INSN
1076               && REG_NOTES (temp3) == 0
1077               && (reallabelprev == temp3
1078                   || ((temp2 = next_active_insn (temp3)) != 0
1079                       && simplejump_p (temp2)
1080                       && JUMP_LABEL (temp2) == JUMP_LABEL (insn)))
1081               && (temp1 = single_set (temp)) != 0
1082               && (temp5 = SET_DEST (temp1),
1083                   (GET_CODE (temp5) == REG
1084                    || (GET_CODE (temp5) == SUBREG
1085                        && (temp5 = SUBREG_REG (temp5),
1086                            GET_CODE (temp5) == REG))))
1087               && REGNO (temp5) >= FIRST_PSEUDO_REGISTER
1088               && regno_first_uid[REGNO (temp5)] == INSN_UID (temp)
1089               && regno_last_uid[REGNO (temp5)] == INSN_UID (temp3)
1090               && ! side_effects_p (SET_SRC (temp1))
1091               && ! may_trap_p (SET_SRC (temp1))
1092               && rtx_cost (SET_SRC (temp1), SET) < 10
1093               && (temp4 = single_set (temp3)) != 0
1094               && (temp2 = SET_DEST (temp4), GET_CODE (temp2) == REG)
1095               && GET_MODE_CLASS (GET_MODE (temp2)) == MODE_INT
1096 #ifdef SMALL_REGISTER_CLASSES
1097               && (! SMALL_REGISTER_CLASSES
1098                   || REGNO (temp2) >= FIRST_PSEUDO_REGISTER)
1099 #endif
1100               && rtx_equal_p (SET_DEST (temp4), temp2)
1101               && ! side_effects_p (SET_SRC (temp4))
1102               && ! may_trap_p (SET_SRC (temp4))
1103               && rtx_cost (SET_SRC (temp4), SET) < 10)
1104             {
1105               rtx new = gen_reg_rtx (GET_MODE (temp2));
1106
1107               if (validate_change (temp3, &SET_DEST (temp4), new, 0))
1108                 {
1109                   next = emit_insn_after (gen_move_insn (temp2, new), insn);
1110                   emit_insn_after_with_line_notes (PATTERN (temp),
1111                                                    PREV_INSN (insn), temp);
1112                   emit_insn_after_with_line_notes (PATTERN (temp3),
1113                                                    PREV_INSN (insn), temp3);
1114                   delete_insn (temp);
1115                   delete_insn (temp3);
1116                   reallabelprev = prev_active_insn (JUMP_LABEL (insn));
1117                 }
1118             }
1119 #endif /* HAVE_cc0 */
1120
1121           /* Try to use a conditional move (if the target has them), or a
1122              store-flag insn.  The general case is:
1123
1124              1) x = a; if (...) x = b; and
1125              2) if (...) x = b;
1126
1127              If the jump would be faster, the machine should not have defined
1128              the movcc or scc insns!.  These cases are often made by the
1129              previous optimization.
1130
1131              The second case is treated as  x = x; if (...) x = b;.
1132
1133              INSN here is the jump around the store.  We set:
1134
1135              TEMP to the "x = b;" insn.
1136              TEMP1 to X.
1137              TEMP2 to B.
1138              TEMP3 to A (X in the second case).
1139              TEMP4 to the condition being tested.
1140              TEMP5 to the earliest insn used to find the condition.  */
1141
1142           if (/* We can't do this after reload has completed.  */
1143               ! reload_completed
1144               && this_is_condjump && ! this_is_simplejump
1145               /* Set TEMP to the "x = b;" insn.  */
1146               && (temp = next_nonnote_insn (insn)) != 0
1147               && GET_CODE (temp) == INSN
1148               && GET_CODE (PATTERN (temp)) == SET
1149               && GET_CODE (temp1 = SET_DEST (PATTERN (temp))) == REG
1150 #ifdef SMALL_REGISTER_CLASSES
1151               && (! SMALL_REGISTER_CLASSES
1152                   || REGNO (temp1) >= FIRST_PSEUDO_REGISTER)
1153 #endif
1154               && (GET_CODE (temp2 = SET_SRC (PATTERN (temp))) == REG
1155                   || GET_CODE (temp2) == SUBREG
1156                   /* ??? How about floating point constants?  */
1157                   || GET_CODE (temp2) == CONST_INT)
1158               /* Allow either form, but prefer the former if both apply. 
1159                  There is no point in using the old value of TEMP1 if
1160                  it is a register, since cse will alias them.  It can
1161                  lose if the old value were a hard register since CSE
1162                  won't replace hard registers.  */
1163               && (((temp3 = reg_set_last (temp1, insn)) != 0)
1164                   /* Make the latter case look like  x = x; if (...) x = b;  */
1165                   || (temp3 = temp1, 1))
1166               /* INSN must either branch to the insn after TEMP or the insn
1167                  after TEMP must branch to the same place as INSN.  */
1168               && (reallabelprev == temp
1169                   || ((temp4 = next_active_insn (temp)) != 0
1170                       && simplejump_p (temp4)
1171                       && JUMP_LABEL (temp4) == JUMP_LABEL (insn)))
1172               && (temp4 = get_condition (insn, &temp5)) != 0
1173               /* We must be comparing objects whose modes imply the size.
1174                  We could handle BLKmode if (1) emit_store_flag could
1175                  and (2) we could find the size reliably.  */
1176               && GET_MODE (XEXP (temp4, 0)) != BLKmode
1177               /* Even if branches are cheap, the store_flag optimization
1178                  can win when the operation to be performed can be
1179                  expressed directly.  */
1180 #ifdef HAVE_cc0
1181               /* If the previous insn sets CC0 and something else, we can't
1182                  do this since we are going to delete that insn.  */
1183
1184               && ! ((temp6 = prev_nonnote_insn (insn)) != 0
1185                     && GET_CODE (temp6) == INSN
1186                     && (sets_cc0_p (PATTERN (temp6)) == -1
1187                         || (sets_cc0_p (PATTERN (temp6)) == 1
1188                             && FIND_REG_INC_NOTE (temp6, NULL_RTX))))
1189 #endif
1190               )
1191             {
1192 #ifdef HAVE_conditional_move
1193               /* First try a conditional move.  */
1194               {
1195                 enum rtx_code code = GET_CODE (temp4);
1196                 rtx var = temp1;
1197                 rtx cond0, cond1, aval, bval;
1198                 rtx target;
1199
1200                 /* Copy the compared variables into cond0 and cond1, so that
1201                    any side effects performed in or after the old comparison,
1202                    will not affect our compare which will come later.  */
1203                 /* ??? Is it possible to just use the comparison in the jump
1204                    insn?  After all, we're going to delete it.  We'd have
1205                    to modify emit_conditional_move to take a comparison rtx
1206                    instead or write a new function.  */
1207                 cond0 = gen_reg_rtx (GET_MODE (XEXP (temp4, 0)));
1208                 /* We want the target to be able to simplify comparisons with
1209                    zero (and maybe other constants as well), so don't create
1210                    pseudos for them.  There's no need to either.  */
1211                 if (GET_CODE (XEXP (temp4, 1)) == CONST_INT
1212                     || GET_CODE (XEXP (temp4, 1)) == CONST_DOUBLE)
1213                   cond1 = XEXP (temp4, 1);
1214                 else
1215                   cond1 = gen_reg_rtx (GET_MODE (XEXP (temp4, 1)));
1216
1217                 aval = temp3;
1218                 bval = temp2;
1219
1220                 start_sequence ();
1221                 target = emit_conditional_move (var, code,
1222                                                 cond0, cond1, VOIDmode,
1223                                                 aval, bval, GET_MODE (var),
1224                                                 (code == LTU || code == GEU
1225                                                  || code == LEU || code == GTU));
1226
1227                 if (target)
1228                   {
1229                     rtx seq1,seq2;
1230
1231                     /* Save the conditional move sequence but don't emit it
1232                        yet.  On some machines, like the alpha, it is possible
1233                        that temp5 == insn, so next generate the sequence that
1234                        saves the compared values and then emit both
1235                        sequences ensuring seq1 occurs before seq2.  */
1236                     seq2 = get_insns ();
1237                     end_sequence ();
1238
1239                     /* Now that we can't fail, generate the copy insns that
1240                        preserve the compared values.  */
1241                     start_sequence ();
1242                     emit_move_insn (cond0, XEXP (temp4, 0));
1243                     if (cond1 != XEXP (temp4, 1))
1244                       emit_move_insn (cond1, XEXP (temp4, 1));
1245                     seq1 = get_insns ();
1246                     end_sequence ();
1247
1248                     emit_insns_before (seq1, temp5);
1249                     /* Insert conditional move after insn, to be sure that
1250                        the jump and a possible compare won't be separated */
1251                     emit_insns_after (seq2, insn);
1252
1253                     /* ??? We can also delete the insn that sets X to A.
1254                        Flow will do it too though.  */
1255                     delete_insn (temp);
1256                     next = NEXT_INSN (insn);
1257                     delete_jump (insn);
1258                     changed = 1;
1259                     continue;
1260                   }
1261                 else
1262                   end_sequence ();
1263               }
1264 #endif
1265
1266               /* That didn't work, try a store-flag insn.
1267
1268                  We further divide the cases into:
1269
1270                  1) x = a; if (...) x = b; and either A or B is zero,
1271                  2) if (...) x = 0; and jumps are expensive,
1272                  3) x = a; if (...) x = b; and A and B are constants where all
1273                  the set bits in A are also set in B and jumps are expensive,
1274                  4) x = a; if (...) x = b; and A and B non-zero, and jumps are
1275                  more expensive, and
1276                  5) if (...) x = b; if jumps are even more expensive.  */
1277
1278               if (GET_MODE_CLASS (GET_MODE (temp1)) == MODE_INT
1279                   && ((GET_CODE (temp3) == CONST_INT)
1280                       /* Make the latter case look like
1281                          x = x; if (...) x = 0;  */
1282                       || (temp3 = temp1,
1283                           ((BRANCH_COST >= 2
1284                             && temp2 == const0_rtx)
1285                            || BRANCH_COST >= 3)))
1286                   /* If B is zero, OK; if A is zero, can only do (1) if we
1287                      can reverse the condition.  See if (3) applies possibly
1288                      by reversing the condition.  Prefer reversing to (4) when
1289                      branches are very expensive.  */
1290                   && (((BRANCH_COST >= 2
1291                         || STORE_FLAG_VALUE == -1
1292                         || (STORE_FLAG_VALUE == 1
1293                          /* Check that the mask is a power of two,
1294                             so that it can probably be generated
1295                             with a shift.  */
1296                             && exact_log2 (INTVAL (temp3)) >= 0))
1297                        && (reversep = 0, temp2 == const0_rtx))
1298                       || ((BRANCH_COST >= 2
1299                            || STORE_FLAG_VALUE == -1
1300                            || (STORE_FLAG_VALUE == 1
1301                                && exact_log2 (INTVAL (temp2)) >= 0))
1302                           && temp3 == const0_rtx
1303                           && (reversep = can_reverse_comparison_p (temp4, insn)))
1304                       || (BRANCH_COST >= 2
1305                           && GET_CODE (temp2) == CONST_INT
1306                           && GET_CODE (temp3) == CONST_INT
1307                           && ((INTVAL (temp2) & INTVAL (temp3)) == INTVAL (temp2)
1308                               || ((INTVAL (temp2) & INTVAL (temp3)) == INTVAL (temp3)
1309                                   && (reversep = can_reverse_comparison_p (temp4,
1310                                                                            insn)))))
1311                       || BRANCH_COST >= 3)
1312                   )
1313                 {
1314                   enum rtx_code code = GET_CODE (temp4);
1315                   rtx uval, cval, var = temp1;
1316                   int normalizep;
1317                   rtx target;
1318
1319                   /* If necessary, reverse the condition.  */
1320                   if (reversep)
1321                     code = reverse_condition (code), uval = temp2, cval = temp3;
1322                   else
1323                     uval = temp3, cval = temp2;
1324
1325                   /* If CVAL is non-zero, normalize to -1.  Otherwise, if UVAL
1326                      is the constant 1, it is best to just compute the result
1327                      directly.  If UVAL is constant and STORE_FLAG_VALUE
1328                      includes all of its bits, it is best to compute the flag
1329                      value unnormalized and `and' it with UVAL.  Otherwise,
1330                      normalize to -1 and `and' with UVAL.  */
1331                   normalizep = (cval != const0_rtx ? -1
1332                                 : (uval == const1_rtx ? 1
1333                                    : (GET_CODE (uval) == CONST_INT
1334                                       && (INTVAL (uval) & ~STORE_FLAG_VALUE) == 0)
1335                                    ? 0 : -1));
1336
1337                   /* We will be putting the store-flag insn immediately in
1338                      front of the comparison that was originally being done,
1339                      so we know all the variables in TEMP4 will be valid.
1340                      However, this might be in front of the assignment of
1341                      A to VAR.  If it is, it would clobber the store-flag
1342                      we will be emitting.
1343
1344                      Therefore, emit into a temporary which will be copied to
1345                      VAR immediately after TEMP.  */
1346
1347                   start_sequence ();
1348                   target = emit_store_flag (gen_reg_rtx (GET_MODE (var)), code,
1349                                             XEXP (temp4, 0), XEXP (temp4, 1),
1350                                             VOIDmode,
1351                                             (code == LTU || code == LEU 
1352                                              || code == GEU || code == GTU),
1353                                             normalizep);
1354                   if (target)
1355                     {
1356                       rtx seq;
1357                       rtx before = insn;
1358
1359                       seq = get_insns ();
1360                       end_sequence ();
1361
1362                       /* Put the store-flag insns in front of the first insn
1363                          used to compute the condition to ensure that we
1364                          use the same values of them as the current 
1365                          comparison.  However, the remainder of the insns we
1366                          generate will be placed directly in front of the
1367                          jump insn, in case any of the pseudos we use
1368                          are modified earlier.  */
1369
1370                       emit_insns_before (seq, temp5);
1371
1372                       start_sequence ();
1373
1374                       /* Both CVAL and UVAL are non-zero.  */
1375                       if (cval != const0_rtx && uval != const0_rtx)
1376                         {
1377                           rtx tem1, tem2;
1378
1379                           tem1 = expand_and (uval, target, NULL_RTX);
1380                           if (GET_CODE (cval) == CONST_INT
1381                               && GET_CODE (uval) == CONST_INT
1382                               && (INTVAL (cval) & INTVAL (uval)) == INTVAL (cval))
1383                             tem2 = cval;
1384                           else
1385                             {
1386                               tem2 = expand_unop (GET_MODE (var), one_cmpl_optab,
1387                                                   target, NULL_RTX, 0);
1388                               tem2 = expand_and (cval, tem2,
1389                                                  (GET_CODE (tem2) == REG
1390                                                   ? tem2 : 0));
1391                             }
1392
1393                           /* If we usually make new pseudos, do so here.  This
1394                              turns out to help machines that have conditional
1395                              move insns.  */
1396                           /* ??? Conditional moves have already been handled.
1397                              This may be obsolete.  */
1398
1399                           if (flag_expensive_optimizations)
1400                             target = 0;
1401
1402                           target = expand_binop (GET_MODE (var), ior_optab,
1403                                                  tem1, tem2, target,
1404                                                  1, OPTAB_WIDEN);
1405                         }
1406                       else if (normalizep != 1)
1407                         {
1408                           /* We know that either CVAL or UVAL is zero.  If
1409                              UVAL is zero, negate TARGET and `and' with CVAL.
1410                              Otherwise, `and' with UVAL.  */
1411                           if (uval == const0_rtx)
1412                             {
1413                               target = expand_unop (GET_MODE (var), one_cmpl_optab,
1414                                                     target, NULL_RTX, 0);
1415                               uval = cval;
1416                             }
1417
1418                           target = expand_and (uval, target,
1419                                                (GET_CODE (target) == REG
1420                                                 && ! preserve_subexpressions_p ()
1421                                                 ? target : NULL_RTX));
1422                         }
1423                   
1424                       emit_move_insn (var, target);
1425                       seq = get_insns ();
1426                       end_sequence ();
1427 #ifdef HAVE_cc0
1428                       /* If INSN uses CC0, we must not separate it from the
1429                          insn that sets cc0.  */
1430                       if (reg_mentioned_p (cc0_rtx, PATTERN (before)))
1431                         before = prev_nonnote_insn (before);
1432 #endif
1433                       emit_insns_before (seq, before);
1434
1435                       delete_insn (temp);
1436                       next = NEXT_INSN (insn);
1437                       delete_jump (insn);
1438                       changed = 1;
1439                       continue;
1440                     }
1441                   else
1442                     end_sequence ();
1443                 }
1444             }
1445
1446           /* If branches are expensive, convert
1447                 if (foo) bar++;    to    bar += (foo != 0);
1448              and similarly for "bar--;" 
1449
1450              INSN is the conditional branch around the arithmetic.  We set:
1451
1452              TEMP is the arithmetic insn.
1453              TEMP1 is the SET doing the arithmetic.
1454              TEMP2 is the operand being incremented or decremented.
1455              TEMP3 to the condition being tested.
1456              TEMP4 to the earliest insn used to find the condition.  */
1457
1458           if ((BRANCH_COST >= 2
1459 #ifdef HAVE_incscc
1460                || HAVE_incscc
1461 #endif
1462 #ifdef HAVE_decscc
1463                || HAVE_decscc
1464 #endif
1465               )
1466               && ! reload_completed
1467               && this_is_condjump && ! this_is_simplejump
1468               && (temp = next_nonnote_insn (insn)) != 0
1469               && (temp1 = single_set (temp)) != 0
1470               && (temp2 = SET_DEST (temp1),
1471                   GET_MODE_CLASS (GET_MODE (temp2)) == MODE_INT)
1472               && GET_CODE (SET_SRC (temp1)) == PLUS
1473               && (XEXP (SET_SRC (temp1), 1) == const1_rtx
1474                   || XEXP (SET_SRC (temp1), 1) == constm1_rtx)
1475               && rtx_equal_p (temp2, XEXP (SET_SRC (temp1), 0))
1476               && ! side_effects_p (temp2)
1477               && ! may_trap_p (temp2)
1478               /* INSN must either branch to the insn after TEMP or the insn
1479                  after TEMP must branch to the same place as INSN.  */
1480               && (reallabelprev == temp
1481                   || ((temp3 = next_active_insn (temp)) != 0
1482                       && simplejump_p (temp3)
1483                       && JUMP_LABEL (temp3) == JUMP_LABEL (insn)))
1484               && (temp3 = get_condition (insn, &temp4)) != 0
1485               /* We must be comparing objects whose modes imply the size.
1486                  We could handle BLKmode if (1) emit_store_flag could
1487                  and (2) we could find the size reliably.  */
1488               && GET_MODE (XEXP (temp3, 0)) != BLKmode
1489               && can_reverse_comparison_p (temp3, insn))
1490             {
1491               rtx temp6, target = 0, seq, init_insn = 0, init = temp2;
1492               enum rtx_code code = reverse_condition (GET_CODE (temp3));
1493
1494               start_sequence ();
1495
1496               /* It must be the case that TEMP2 is not modified in the range
1497                  [TEMP4, INSN).  The one exception we make is if the insn
1498                  before INSN sets TEMP2 to something which is also unchanged
1499                  in that range.  In that case, we can move the initialization
1500                  into our sequence.  */
1501
1502               if ((temp5 = prev_active_insn (insn)) != 0
1503                   && no_labels_between_p (temp5, insn)
1504                   && GET_CODE (temp5) == INSN
1505                   && (temp6 = single_set (temp5)) != 0
1506                   && rtx_equal_p (temp2, SET_DEST (temp6))
1507                   && (CONSTANT_P (SET_SRC (temp6))
1508                       || GET_CODE (SET_SRC (temp6)) == REG
1509                       || GET_CODE (SET_SRC (temp6)) == SUBREG))
1510                 {
1511                   emit_insn (PATTERN (temp5));
1512                   init_insn = temp5;
1513                   init = SET_SRC (temp6);
1514                 }
1515
1516               if (CONSTANT_P (init)
1517                   || ! reg_set_between_p (init, PREV_INSN (temp4), insn))
1518                 target = emit_store_flag (gen_reg_rtx (GET_MODE (temp2)), code,
1519                                           XEXP (temp3, 0), XEXP (temp3, 1),
1520                                           VOIDmode,
1521                                           (code == LTU || code == LEU
1522                                            || code == GTU || code == GEU), 1);
1523
1524               /* If we can do the store-flag, do the addition or
1525                  subtraction.  */
1526
1527               if (target)
1528                 target = expand_binop (GET_MODE (temp2),
1529                                        (XEXP (SET_SRC (temp1), 1) == const1_rtx
1530                                         ? add_optab : sub_optab),
1531                                        temp2, target, temp2, 0, OPTAB_WIDEN);
1532
1533               if (target != 0)
1534                 {
1535                   /* Put the result back in temp2 in case it isn't already.
1536                      Then replace the jump, possible a CC0-setting insn in
1537                      front of the jump, and TEMP, with the sequence we have
1538                      made.  */
1539
1540                   if (target != temp2)
1541                     emit_move_insn (temp2, target);
1542
1543                   seq = get_insns ();
1544                   end_sequence ();
1545
1546                   emit_insns_before (seq, temp4);
1547                   delete_insn (temp);
1548
1549                   if (init_insn)
1550                     delete_insn (init_insn);
1551
1552                   next = NEXT_INSN (insn);
1553 #ifdef HAVE_cc0
1554                   delete_insn (prev_nonnote_insn (insn));
1555 #endif
1556                   delete_insn (insn);
1557                   changed = 1;
1558                   continue;
1559                 }
1560               else
1561                 end_sequence ();
1562             }
1563
1564           /* Simplify   if (...) x = 1; else {...}  if (x) ...
1565              We recognize this case scanning backwards as well.
1566
1567              TEMP is the assignment to x;
1568              TEMP1 is the label at the head of the second if.  */
1569           /* ?? This should call get_condition to find the values being
1570              compared, instead of looking for a COMPARE insn when HAVE_cc0
1571              is not defined.  This would allow it to work on the m88k.  */
1572           /* ?? This optimization is only safe before cse is run if HAVE_cc0
1573              is not defined and the condition is tested by a separate compare
1574              insn.  This is because the code below assumes that the result
1575              of the compare dies in the following branch.
1576
1577              Not only that, but there might be other insns between the
1578              compare and branch whose results are live.  Those insns need
1579              to be executed.
1580
1581              A way to fix this is to move the insns at JUMP_LABEL (insn)
1582              to before INSN.  If we are running before flow, they will
1583              be deleted if they aren't needed.   But this doesn't work
1584              well after flow.
1585
1586              This is really a special-case of jump threading, anyway.  The
1587              right thing to do is to replace this and jump threading with
1588              much simpler code in cse.
1589
1590              This code has been turned off in the non-cc0 case in the
1591              meantime.  */
1592
1593 #ifdef HAVE_cc0
1594           else if (this_is_simplejump
1595                    /* Safe to skip USE and CLOBBER insns here
1596                       since they will not be deleted.  */
1597                    && (temp = prev_active_insn (insn))
1598                    && no_labels_between_p (temp, insn)
1599                    && GET_CODE (temp) == INSN
1600                    && GET_CODE (PATTERN (temp)) == SET
1601                    && GET_CODE (SET_DEST (PATTERN (temp))) == REG
1602                    && CONSTANT_P (SET_SRC (PATTERN (temp)))
1603                    && (temp1 = next_active_insn (JUMP_LABEL (insn)))
1604                    /* If we find that the next value tested is `x'
1605                       (TEMP1 is the insn where this happens), win.  */
1606                    && GET_CODE (temp1) == INSN
1607                    && GET_CODE (PATTERN (temp1)) == SET
1608 #ifdef HAVE_cc0
1609                    /* Does temp1 `tst' the value of x?  */
1610                    && SET_SRC (PATTERN (temp1)) == SET_DEST (PATTERN (temp))
1611                    && SET_DEST (PATTERN (temp1)) == cc0_rtx
1612                    && (temp1 = next_nonnote_insn (temp1))
1613 #else
1614                    /* Does temp1 compare the value of x against zero?  */
1615                    && GET_CODE (SET_SRC (PATTERN (temp1))) == COMPARE
1616                    && XEXP (SET_SRC (PATTERN (temp1)), 1) == const0_rtx
1617                    && (XEXP (SET_SRC (PATTERN (temp1)), 0)
1618                        == SET_DEST (PATTERN (temp)))
1619                    && GET_CODE (SET_DEST (PATTERN (temp1))) == REG
1620                    && (temp1 = find_next_ref (SET_DEST (PATTERN (temp1)), temp1))
1621 #endif
1622                    && condjump_p (temp1))
1623             {
1624               /* Get the if_then_else from the condjump.  */
1625               rtx choice = SET_SRC (PATTERN (temp1));
1626               if (GET_CODE (choice) == IF_THEN_ELSE)
1627                 {
1628                   enum rtx_code code = GET_CODE (XEXP (choice, 0));
1629                   rtx val = SET_SRC (PATTERN (temp));
1630                   rtx cond
1631                     = simplify_relational_operation (code, GET_MODE (SET_DEST (PATTERN (temp))),
1632                                                      val, const0_rtx);
1633                   rtx ultimate;
1634
1635                   if (cond == const_true_rtx)
1636                     ultimate = XEXP (choice, 1);
1637                   else if (cond == const0_rtx)
1638                     ultimate = XEXP (choice, 2);
1639                   else
1640                     ultimate = 0;
1641
1642                   if (ultimate == pc_rtx)
1643                     ultimate = get_label_after (temp1);
1644                   else if (ultimate && GET_CODE (ultimate) != RETURN)
1645                     ultimate = XEXP (ultimate, 0);
1646
1647                   if (ultimate && JUMP_LABEL(insn) != ultimate)
1648                     changed |= redirect_jump (insn, ultimate);
1649                 }
1650             }
1651 #endif
1652
1653 #if 0
1654           /* @@ This needs a bit of work before it will be right.
1655
1656              Any type of comparison can be accepted for the first and
1657              second compare.  When rewriting the first jump, we must
1658              compute the what conditions can reach label3, and use the
1659              appropriate code.  We can not simply reverse/swap the code
1660              of the first jump.  In some cases, the second jump must be
1661              rewritten also.
1662
1663              For example, 
1664              <  == converts to >  ==
1665              <  != converts to ==  >
1666              etc.
1667
1668              If the code is written to only accept an '==' test for the second
1669              compare, then all that needs to be done is to swap the condition
1670              of the first branch.
1671
1672              It is questionable whether we want this optimization anyways,
1673              since if the user wrote code like this because he/she knew that
1674              the jump to label1 is taken most of the time, then rewriting
1675              this gives slower code.  */
1676           /* @@ This should call get_condition to find the values being
1677              compared, instead of looking for a COMPARE insn when HAVE_cc0
1678              is not defined.  This would allow it to work on the m88k.  */
1679           /* @@ This optimization is only safe before cse is run if HAVE_cc0
1680              is not defined and the condition is tested by a separate compare
1681              insn.  This is because the code below assumes that the result
1682              of the compare dies in the following branch.  */
1683
1684           /* Simplify  test a ~= b
1685                        condjump label1;
1686                        test a == b
1687                        condjump label2;
1688                        jump label3;
1689                        label1:
1690
1691              rewriting as
1692                        test a ~~= b
1693                        condjump label3
1694                        test a == b
1695                        condjump label2
1696                        label1:
1697
1698              where ~= is an inequality, e.g. >, and ~~= is the swapped
1699              inequality, e.g. <.
1700
1701              We recognize this case scanning backwards.
1702
1703              TEMP is the conditional jump to `label2';
1704              TEMP1 is the test for `a == b';
1705              TEMP2 is the conditional jump to `label1';
1706              TEMP3 is the test for `a ~= b'.  */
1707           else if (this_is_simplejump
1708                    && (temp = prev_active_insn (insn))
1709                    && no_labels_between_p (temp, insn)
1710                    && condjump_p (temp)
1711                    && (temp1 = prev_active_insn (temp))
1712                    && no_labels_between_p (temp1, temp)
1713                    && GET_CODE (temp1) == INSN
1714                    && GET_CODE (PATTERN (temp1)) == SET
1715 #ifdef HAVE_cc0
1716                    && sets_cc0_p (PATTERN (temp1)) == 1
1717 #else
1718                    && GET_CODE (SET_SRC (PATTERN (temp1))) == COMPARE
1719                    && GET_CODE (SET_DEST (PATTERN (temp1))) == REG
1720                    && (temp == find_next_ref (SET_DEST (PATTERN (temp1)), temp1))
1721 #endif
1722                    && (temp2 = prev_active_insn (temp1))
1723                    && no_labels_between_p (temp2, temp1)
1724                    && condjump_p (temp2)
1725                    && JUMP_LABEL (temp2) == next_nonnote_insn (NEXT_INSN (insn))
1726                    && (temp3 = prev_active_insn (temp2))
1727                    && no_labels_between_p (temp3, temp2)
1728                    && GET_CODE (PATTERN (temp3)) == SET
1729                    && rtx_equal_p (SET_DEST (PATTERN (temp3)),
1730                                    SET_DEST (PATTERN (temp1)))
1731                    && rtx_equal_p (SET_SRC (PATTERN (temp1)),
1732                                    SET_SRC (PATTERN (temp3)))
1733                    && ! inequality_comparisons_p (PATTERN (temp))
1734                    && inequality_comparisons_p (PATTERN (temp2)))
1735             {
1736               rtx fallthrough_label = JUMP_LABEL (temp2);
1737
1738               ++LABEL_NUSES (fallthrough_label);
1739               if (swap_jump (temp2, JUMP_LABEL (insn)))
1740                 {
1741                   delete_insn (insn);
1742                   changed = 1;
1743                 }
1744
1745               if (--LABEL_NUSES (fallthrough_label) == 0)
1746                 delete_insn (fallthrough_label);
1747             }
1748 #endif
1749           /* Simplify  if (...) {... x = 1;} if (x) ...
1750
1751              We recognize this case backwards.
1752
1753              TEMP is the test of `x';
1754              TEMP1 is the assignment to `x' at the end of the
1755              previous statement.  */
1756           /* @@ This should call get_condition to find the values being
1757              compared, instead of looking for a COMPARE insn when HAVE_cc0
1758              is not defined.  This would allow it to work on the m88k.  */
1759           /* @@ This optimization is only safe before cse is run if HAVE_cc0
1760              is not defined and the condition is tested by a separate compare
1761              insn.  This is because the code below assumes that the result
1762              of the compare dies in the following branch.  */
1763
1764           /* ??? This has to be turned off.  The problem is that the
1765              unconditional jump might indirectly end up branching to the
1766              label between TEMP1 and TEMP.  We can't detect this, in general,
1767              since it may become a jump to there after further optimizations.
1768              If that jump is done, it will be deleted, so we will retry
1769              this optimization in the next pass, thus an infinite loop.
1770
1771              The present code prevents this by putting the jump after the
1772              label, but this is not logically correct.  */
1773 #if 0
1774           else if (this_is_condjump
1775                    /* Safe to skip USE and CLOBBER insns here
1776                       since they will not be deleted.  */
1777                    && (temp = prev_active_insn (insn))
1778                    && no_labels_between_p (temp, insn)
1779                    && GET_CODE (temp) == INSN
1780                    && GET_CODE (PATTERN (temp)) == SET
1781 #ifdef HAVE_cc0
1782                    && sets_cc0_p (PATTERN (temp)) == 1
1783                    && GET_CODE (SET_SRC (PATTERN (temp))) == REG
1784 #else
1785                    /* Temp must be a compare insn, we can not accept a register
1786                       to register move here, since it may not be simply a
1787                       tst insn.  */
1788                    && GET_CODE (SET_SRC (PATTERN (temp))) == COMPARE
1789                    && XEXP (SET_SRC (PATTERN (temp)), 1) == const0_rtx
1790                    && GET_CODE (XEXP (SET_SRC (PATTERN (temp)), 0)) == REG
1791                    && GET_CODE (SET_DEST (PATTERN (temp))) == REG
1792                    && insn == find_next_ref (SET_DEST (PATTERN (temp)), temp)
1793 #endif
1794                    /* May skip USE or CLOBBER insns here
1795                       for checking for opportunity, since we
1796                       take care of them later.  */
1797                    && (temp1 = prev_active_insn (temp))
1798                    && GET_CODE (temp1) == INSN
1799                    && GET_CODE (PATTERN (temp1)) == SET
1800 #ifdef HAVE_cc0
1801                    && SET_SRC (PATTERN (temp)) == SET_DEST (PATTERN (temp1))
1802 #else
1803                    && (XEXP (SET_SRC (PATTERN (temp)), 0)
1804                        == SET_DEST (PATTERN (temp1)))
1805 #endif
1806                    && CONSTANT_P (SET_SRC (PATTERN (temp1)))
1807                    /* If this isn't true, cse will do the job.  */
1808                    && ! no_labels_between_p (temp1, temp))
1809             {
1810               /* Get the if_then_else from the condjump.  */
1811               rtx choice = SET_SRC (PATTERN (insn));
1812               if (GET_CODE (choice) == IF_THEN_ELSE
1813                   && (GET_CODE (XEXP (choice, 0)) == EQ
1814                       || GET_CODE (XEXP (choice, 0)) == NE))
1815                 {
1816                   int want_nonzero = (GET_CODE (XEXP (choice, 0)) == NE);
1817                   rtx last_insn;
1818                   rtx ultimate;
1819                   rtx p;
1820
1821                   /* Get the place that condjump will jump to
1822                      if it is reached from here.  */
1823                   if ((SET_SRC (PATTERN (temp1)) != const0_rtx)
1824                       == want_nonzero)
1825                     ultimate = XEXP (choice, 1);
1826                   else
1827                     ultimate = XEXP (choice, 2);
1828                   /* Get it as a CODE_LABEL.  */
1829                   if (ultimate == pc_rtx)
1830                     ultimate = get_label_after (insn);
1831                   else
1832                     /* Get the label out of the LABEL_REF.  */
1833                     ultimate = XEXP (ultimate, 0);
1834
1835                   /* Insert the jump immediately before TEMP, specifically
1836                      after the label that is between TEMP1 and TEMP.  */
1837                   last_insn = PREV_INSN (temp);
1838
1839                   /* If we would be branching to the next insn, the jump
1840                      would immediately be deleted and the re-inserted in
1841                      a subsequent pass over the code.  So don't do anything
1842                      in that case.  */
1843                   if (next_active_insn (last_insn)
1844                       != next_active_insn (ultimate))
1845                     {
1846                       emit_barrier_after (last_insn);
1847                       p = emit_jump_insn_after (gen_jump (ultimate),
1848                                                 last_insn);
1849                       JUMP_LABEL (p) = ultimate;
1850                       ++LABEL_NUSES (ultimate);
1851                       if (INSN_UID (ultimate) < max_jump_chain
1852                           && INSN_CODE (p) < max_jump_chain)
1853                         {
1854                           jump_chain[INSN_UID (p)]
1855                             = jump_chain[INSN_UID (ultimate)];
1856                           jump_chain[INSN_UID (ultimate)] = p;
1857                         }
1858                       changed = 1;
1859                       continue;
1860                     }
1861                 }
1862             }
1863 #endif
1864           /* Detect a conditional jump going to the same place
1865              as an immediately following unconditional jump.  */
1866           else if (this_is_condjump
1867                    && (temp = next_active_insn (insn)) != 0
1868                    && simplejump_p (temp)
1869                    && (next_active_insn (JUMP_LABEL (insn))
1870                        == next_active_insn (JUMP_LABEL (temp))))
1871             {
1872               rtx tem = temp;
1873
1874               /* ??? Optional.  Disables some optimizations, but makes
1875                  gcov output more accurate with -O.  */
1876               if (flag_test_coverage && !reload_completed)
1877                 for (tem = insn; tem != temp; tem = NEXT_INSN (tem))
1878                   if (GET_CODE (tem) == NOTE && NOTE_LINE_NUMBER (tem) > 0)
1879                     break;
1880
1881               if (tem == temp)
1882                 {
1883                   delete_jump (insn);
1884                   changed = 1;
1885                   continue;
1886                 }
1887             }
1888           /* Detect a conditional jump jumping over an unconditional jump.  */
1889
1890           else if ((this_is_condjump || this_is_condjump_in_parallel)
1891                    && ! this_is_simplejump
1892                    && reallabelprev != 0
1893                    && GET_CODE (reallabelprev) == JUMP_INSN
1894                    && prev_active_insn (reallabelprev) == insn
1895                    && no_labels_between_p (insn, reallabelprev)
1896                    && simplejump_p (reallabelprev))
1897             {
1898               /* When we invert the unconditional jump, we will be
1899                  decrementing the usage count of its old label.
1900                  Make sure that we don't delete it now because that
1901                  might cause the following code to be deleted.  */
1902               rtx prev_uses = prev_nonnote_insn (reallabelprev);
1903               rtx prev_label = JUMP_LABEL (insn);
1904
1905               if (prev_label)
1906                 ++LABEL_NUSES (prev_label);
1907
1908               if (invert_jump (insn, JUMP_LABEL (reallabelprev)))
1909                 {
1910                   /* It is very likely that if there are USE insns before
1911                      this jump, they hold REG_DEAD notes.  These REG_DEAD
1912                      notes are no longer valid due to this optimization,
1913                      and will cause the life-analysis that following passes
1914                      (notably delayed-branch scheduling) to think that
1915                      these registers are dead when they are not.
1916
1917                      To prevent this trouble, we just remove the USE insns
1918                      from the insn chain.  */
1919
1920                   while (prev_uses && GET_CODE (prev_uses) == INSN
1921                          && GET_CODE (PATTERN (prev_uses)) == USE)
1922                     {
1923                       rtx useless = prev_uses;
1924                       prev_uses = prev_nonnote_insn (prev_uses);
1925                       delete_insn (useless);
1926                     }
1927
1928                   delete_insn (reallabelprev);
1929                   next = insn;
1930                   changed = 1;
1931                 }
1932
1933               /* We can now safely delete the label if it is unreferenced
1934                  since the delete_insn above has deleted the BARRIER.  */
1935               if (prev_label && --LABEL_NUSES (prev_label) == 0)
1936                 delete_insn (prev_label);
1937               continue;
1938             }
1939           else
1940             {
1941               /* Detect a jump to a jump.  */
1942
1943               nlabel = follow_jumps (JUMP_LABEL (insn));
1944               if (nlabel != JUMP_LABEL (insn)
1945                   && redirect_jump (insn, nlabel))
1946                 {
1947                   changed = 1;
1948                   next = insn;
1949                 }
1950
1951               /* Look for   if (foo) bar; else break;  */
1952               /* The insns look like this:
1953                  insn = condjump label1;
1954                  ...range1 (some insns)...
1955                  jump label2;
1956                  label1:
1957                  ...range2 (some insns)...
1958                  jump somewhere unconditionally
1959                  label2:  */
1960               {
1961                 rtx label1 = next_label (insn);
1962                 rtx range1end = label1 ? prev_active_insn (label1) : 0;
1963                 /* Don't do this optimization on the first round, so that
1964                    jump-around-a-jump gets simplified before we ask here
1965                    whether a jump is unconditional.
1966
1967                    Also don't do it when we are called after reload since
1968                    it will confuse reorg.  */
1969                 if (! first
1970                     && (reload_completed ? ! flag_delayed_branch : 1)
1971                     /* Make sure INSN is something we can invert.  */
1972                     && condjump_p (insn)
1973                     && label1 != 0
1974                     && JUMP_LABEL (insn) == label1
1975                     && LABEL_NUSES (label1) == 1
1976                     && GET_CODE (range1end) == JUMP_INSN
1977                     && simplejump_p (range1end))
1978                   {
1979                     rtx label2 = next_label (label1);
1980                     rtx range2end = label2 ? prev_active_insn (label2) : 0;
1981                     if (range1end != range2end
1982                         && JUMP_LABEL (range1end) == label2
1983                         && GET_CODE (range2end) == JUMP_INSN
1984                         && GET_CODE (NEXT_INSN (range2end)) == BARRIER
1985                         /* Invert the jump condition, so we
1986                            still execute the same insns in each case.  */
1987                         && invert_jump (insn, label1))
1988                       {
1989                         rtx range1beg = next_active_insn (insn);
1990                         rtx range2beg = next_active_insn (label1);
1991                         rtx range1after, range2after;
1992                         rtx range1before, range2before;
1993                         rtx rangenext;
1994
1995                         /* Include in each range any notes before it, to be
1996                            sure that we get the line number note if any, even
1997                            if there are other notes here.  */
1998                         while (PREV_INSN (range1beg)
1999                                && GET_CODE (PREV_INSN (range1beg)) == NOTE)
2000                           range1beg = PREV_INSN (range1beg);
2001
2002                         while (PREV_INSN (range2beg)
2003                                && GET_CODE (PREV_INSN (range2beg)) == NOTE)
2004                           range2beg = PREV_INSN (range2beg);
2005
2006                         /* Don't move NOTEs for blocks or loops; shift them
2007                            outside the ranges, where they'll stay put.  */
2008                         range1beg = squeeze_notes (range1beg, range1end);
2009                         range2beg = squeeze_notes (range2beg, range2end);
2010
2011                         /* Get current surrounds of the 2 ranges.  */
2012                         range1before = PREV_INSN (range1beg);
2013                         range2before = PREV_INSN (range2beg);
2014                         range1after = NEXT_INSN (range1end);
2015                         range2after = NEXT_INSN (range2end);
2016
2017                         /* Splice range2 where range1 was.  */
2018                         NEXT_INSN (range1before) = range2beg;
2019                         PREV_INSN (range2beg) = range1before;
2020                         NEXT_INSN (range2end) = range1after;
2021                         PREV_INSN (range1after) = range2end;
2022                         /* Splice range1 where range2 was.  */
2023                         NEXT_INSN (range2before) = range1beg;
2024                         PREV_INSN (range1beg) = range2before;
2025                         NEXT_INSN (range1end) = range2after;
2026                         PREV_INSN (range2after) = range1end;
2027
2028                         /* Check for a loop end note between the end of
2029                            range2, and the next code label.  If there is one,
2030                            then what we have really seen is
2031                            if (foo) break; end_of_loop;
2032                            and moved the break sequence outside the loop.
2033                            We must move the LOOP_END note to where the
2034                            loop really ends now, or we will confuse loop
2035                            optimization.  Stop if we find a LOOP_BEG note
2036                            first, since we don't want to move the LOOP_END
2037                            note in that case.  */
2038                         for (;range2after != label2; range2after = rangenext)
2039                           {
2040                             rangenext = NEXT_INSN (range2after);
2041                             if (GET_CODE (range2after) == NOTE)
2042                               {
2043                                 if (NOTE_LINE_NUMBER (range2after)
2044                                     == NOTE_INSN_LOOP_END)
2045                                   {
2046                                     NEXT_INSN (PREV_INSN (range2after))
2047                                       = rangenext;
2048                                     PREV_INSN (rangenext)
2049                                       = PREV_INSN (range2after);
2050                                     PREV_INSN (range2after) 
2051                                       = PREV_INSN (range1beg);
2052                                     NEXT_INSN (range2after) = range1beg;
2053                                     NEXT_INSN (PREV_INSN (range1beg))
2054                                       = range2after;
2055                                     PREV_INSN (range1beg) = range2after;
2056                                   }
2057                                 else if (NOTE_LINE_NUMBER (range2after)
2058                                          == NOTE_INSN_LOOP_BEG)
2059                                   break;
2060                               }
2061                           }
2062                         changed = 1;
2063                         continue;
2064                       }
2065                   }
2066               }
2067
2068               /* Now that the jump has been tensioned,
2069                  try cross jumping: check for identical code
2070                  before the jump and before its target label.  */
2071
2072               /* First, cross jumping of conditional jumps:  */
2073
2074               if (cross_jump && condjump_p (insn))
2075                 {
2076                   rtx newjpos, newlpos;
2077                   rtx x = prev_real_insn (JUMP_LABEL (insn));
2078
2079                   /* A conditional jump may be crossjumped
2080                      only if the place it jumps to follows
2081                      an opposing jump that comes back here.  */
2082
2083                   if (x != 0 && ! jump_back_p (x, insn))
2084                     /* We have no opposing jump;
2085                        cannot cross jump this insn.  */
2086                     x = 0;
2087
2088                   newjpos = 0;
2089                   /* TARGET is nonzero if it is ok to cross jump
2090                      to code before TARGET.  If so, see if matches.  */
2091                   if (x != 0)
2092                     find_cross_jump (insn, x, 2,
2093                                      &newjpos, &newlpos);
2094
2095                   if (newjpos != 0)
2096                     {
2097                       do_cross_jump (insn, newjpos, newlpos);
2098                       /* Make the old conditional jump
2099                          into an unconditional one.  */
2100                       SET_SRC (PATTERN (insn))
2101                         = gen_rtx (LABEL_REF, VOIDmode, JUMP_LABEL (insn));
2102                       INSN_CODE (insn) = -1;
2103                       emit_barrier_after (insn);
2104                       /* Add to jump_chain unless this is a new label
2105                          whose UID is too large.  */
2106                       if (INSN_UID (JUMP_LABEL (insn)) < max_jump_chain)
2107                         {
2108                           jump_chain[INSN_UID (insn)]
2109                             = jump_chain[INSN_UID (JUMP_LABEL (insn))];
2110                           jump_chain[INSN_UID (JUMP_LABEL (insn))] = insn;
2111                         }
2112                       changed = 1;
2113                       next = insn;
2114                     }
2115                 }
2116
2117               /* Cross jumping of unconditional jumps:
2118                  a few differences.  */
2119
2120               if (cross_jump && simplejump_p (insn))
2121                 {
2122                   rtx newjpos, newlpos;
2123                   rtx target;
2124
2125                   newjpos = 0;
2126
2127                   /* TARGET is nonzero if it is ok to cross jump
2128                      to code before TARGET.  If so, see if matches.  */
2129                   find_cross_jump (insn, JUMP_LABEL (insn), 1,
2130                                    &newjpos, &newlpos);
2131
2132                   /* If cannot cross jump to code before the label,
2133                      see if we can cross jump to another jump to
2134                      the same label.  */
2135                   /* Try each other jump to this label.  */
2136                   if (INSN_UID (JUMP_LABEL (insn)) < max_uid)
2137                     for (target = jump_chain[INSN_UID (JUMP_LABEL (insn))];
2138                          target != 0 && newjpos == 0;
2139                          target = jump_chain[INSN_UID (target)])
2140                       if (target != insn
2141                           && JUMP_LABEL (target) == JUMP_LABEL (insn)
2142                           /* Ignore TARGET if it's deleted.  */
2143                           && ! INSN_DELETED_P (target))
2144                         find_cross_jump (insn, target, 2,
2145                                          &newjpos, &newlpos);
2146
2147                   if (newjpos != 0)
2148                     {
2149                       do_cross_jump (insn, newjpos, newlpos);
2150                       changed = 1;
2151                       next = insn;
2152                     }
2153                 }
2154
2155               /* This code was dead in the previous jump.c!  */
2156               if (cross_jump && GET_CODE (PATTERN (insn)) == RETURN)
2157                 {
2158                   /* Return insns all "jump to the same place"
2159                      so we can cross-jump between any two of them.  */
2160
2161                   rtx newjpos, newlpos, target;
2162
2163                   newjpos = 0;
2164
2165                   /* If cannot cross jump to code before the label,
2166                      see if we can cross jump to another jump to
2167                      the same label.  */
2168                   /* Try each other jump to this label.  */
2169                   for (target = jump_chain[0];
2170                        target != 0 && newjpos == 0;
2171                        target = jump_chain[INSN_UID (target)])
2172                     if (target != insn
2173                         && ! INSN_DELETED_P (target)
2174                         && GET_CODE (PATTERN (target)) == RETURN)
2175                       find_cross_jump (insn, target, 2,
2176                                        &newjpos, &newlpos);
2177
2178                   if (newjpos != 0)
2179                     {
2180                       do_cross_jump (insn, newjpos, newlpos);
2181                       changed = 1;
2182                       next = insn;
2183                     }
2184                 }
2185             }
2186         }
2187
2188       first = 0;
2189     }
2190
2191   /* Delete extraneous line number notes.
2192      Note that two consecutive notes for different lines are not really
2193      extraneous.  There should be some indication where that line belonged,
2194      even if it became empty.  */
2195
2196   {
2197     rtx last_note = 0;
2198
2199     for (insn = f; insn; insn = NEXT_INSN (insn))
2200       if (GET_CODE (insn) == NOTE && NOTE_LINE_NUMBER (insn) >= 0)
2201         {
2202           /* Delete this note if it is identical to previous note.  */
2203           if (last_note
2204               && NOTE_SOURCE_FILE (insn) == NOTE_SOURCE_FILE (last_note)
2205               && NOTE_LINE_NUMBER (insn) == NOTE_LINE_NUMBER (last_note))
2206             {
2207               delete_insn (insn);
2208               continue;
2209             }
2210
2211           last_note = insn;
2212         }
2213   }
2214
2215 #ifdef HAVE_return
2216   if (HAVE_return)
2217     {
2218       /* If we fall through to the epilogue, see if we can insert a RETURN insn
2219          in front of it.  If the machine allows it at this point (we might be
2220          after reload for a leaf routine), it will improve optimization for it
2221          to be there.  We do this both here and at the start of this pass since
2222          the RETURN might have been deleted by some of our optimizations.  */
2223       insn = get_last_insn ();
2224       while (insn && GET_CODE (insn) == NOTE)
2225         insn = PREV_INSN (insn);
2226
2227       if (insn && GET_CODE (insn) != BARRIER)
2228         {
2229           emit_jump_insn (gen_return ());
2230           emit_barrier ();
2231         }
2232     }
2233 #endif
2234
2235   /* See if there is still a NOTE_INSN_FUNCTION_END in this function.
2236      If so, delete it, and record that this function can drop off the end.  */
2237
2238   insn = last_insn;
2239   {
2240     int n_labels = 1;
2241     while (insn
2242            /* One label can follow the end-note: the return label.  */
2243            && ((GET_CODE (insn) == CODE_LABEL && n_labels-- > 0)
2244                /* Ordinary insns can follow it if returning a structure.  */
2245                || GET_CODE (insn) == INSN
2246                /* If machine uses explicit RETURN insns, no epilogue,
2247                   then one of them follows the note.  */
2248                || (GET_CODE (insn) == JUMP_INSN
2249                    && GET_CODE (PATTERN (insn)) == RETURN)
2250                /* A barrier can follow the return insn.  */
2251                || GET_CODE (insn) == BARRIER
2252                /* Other kinds of notes can follow also.  */
2253                || (GET_CODE (insn) == NOTE
2254                    && NOTE_LINE_NUMBER (insn) != NOTE_INSN_FUNCTION_END)))
2255       insn = PREV_INSN (insn);
2256   }
2257
2258   /* Report if control can fall through at the end of the function.  */
2259   if (insn && GET_CODE (insn) == NOTE
2260       && NOTE_LINE_NUMBER (insn) == NOTE_INSN_FUNCTION_END)
2261     {
2262       can_reach_end = 1;
2263       delete_insn (insn);
2264     }
2265
2266   /* Show JUMP_CHAIN no longer valid.  */
2267   jump_chain = 0;
2268 }
2269 \f
2270 /* LOOP_START is a NOTE_INSN_LOOP_BEG note that is followed by an unconditional
2271    jump.  Assume that this unconditional jump is to the exit test code.  If
2272    the code is sufficiently simple, make a copy of it before INSN,
2273    followed by a jump to the exit of the loop.  Then delete the unconditional
2274    jump after INSN.
2275
2276    Return 1 if we made the change, else 0.
2277
2278    This is only safe immediately after a regscan pass because it uses the
2279    values of regno_first_uid and regno_last_uid.  */
2280
2281 static int
2282 duplicate_loop_exit_test (loop_start)
2283      rtx loop_start;
2284 {
2285   rtx insn, set, reg, p, link;
2286   rtx copy = 0;
2287   int num_insns = 0;
2288   rtx exitcode = NEXT_INSN (JUMP_LABEL (next_nonnote_insn (loop_start)));
2289   rtx lastexit;
2290   int max_reg = max_reg_num ();
2291   rtx *reg_map = 0;
2292
2293   /* Scan the exit code.  We do not perform this optimization if any insn:
2294
2295          is a CALL_INSN
2296          is a CODE_LABEL
2297          has a REG_RETVAL or REG_LIBCALL note (hard to adjust)
2298          is a NOTE_INSN_LOOP_BEG because this means we have a nested loop
2299          is a NOTE_INSN_BLOCK_{BEG,END} because duplicating these notes
2300               are not valid
2301
2302      Also, don't do this if the exit code is more than 20 insns.  */
2303
2304   for (insn = exitcode;
2305        insn
2306        && ! (GET_CODE (insn) == NOTE
2307              && NOTE_LINE_NUMBER (insn) == NOTE_INSN_LOOP_END);
2308        insn = NEXT_INSN (insn))
2309     {
2310       switch (GET_CODE (insn))
2311         {
2312         case CODE_LABEL:
2313         case CALL_INSN:
2314           return 0;
2315         case NOTE:
2316           /* We could be in front of the wrong NOTE_INSN_LOOP_END if there is
2317              a jump immediately after the loop start that branches outside
2318              the loop but within an outer loop, near the exit test.
2319              If we copied this exit test and created a phony
2320              NOTE_INSN_LOOP_VTOP, this could make instructions immediately
2321              before the exit test look like these could be safely moved
2322              out of the loop even if they actually may be never executed.
2323              This can be avoided by checking here for NOTE_INSN_LOOP_CONT.  */
2324
2325           if (NOTE_LINE_NUMBER (insn) == NOTE_INSN_LOOP_BEG
2326               || NOTE_LINE_NUMBER (insn) == NOTE_INSN_BLOCK_BEG
2327               || NOTE_LINE_NUMBER (insn) == NOTE_INSN_BLOCK_END
2328               || NOTE_LINE_NUMBER (insn) == NOTE_INSN_LOOP_CONT)
2329             return 0;
2330           break;
2331         case JUMP_INSN:
2332         case INSN:
2333           if (++num_insns > 20
2334               || find_reg_note (insn, REG_RETVAL, NULL_RTX)
2335               || find_reg_note (insn, REG_LIBCALL, NULL_RTX))
2336             return 0;
2337           break;
2338         }
2339     }
2340
2341   /* Unless INSN is zero, we can do the optimization.  */
2342   if (insn == 0)
2343     return 0;
2344
2345   lastexit = insn;
2346
2347   /* See if any insn sets a register only used in the loop exit code and
2348      not a user variable.  If so, replace it with a new register.  */
2349   for (insn = exitcode; insn != lastexit; insn = NEXT_INSN (insn))
2350     if (GET_CODE (insn) == INSN
2351         && (set = single_set (insn)) != 0
2352         && ((reg = SET_DEST (set), GET_CODE (reg) == REG)
2353             || (GET_CODE (reg) == SUBREG
2354                 && (reg = SUBREG_REG (reg), GET_CODE (reg) == REG)))
2355         && REGNO (reg) >= FIRST_PSEUDO_REGISTER
2356         && regno_first_uid[REGNO (reg)] == INSN_UID (insn))
2357       {
2358         for (p = NEXT_INSN (insn); p != lastexit; p = NEXT_INSN (p))
2359           if (regno_last_uid[REGNO (reg)] == INSN_UID (p))
2360             break;
2361
2362         if (p != lastexit)
2363           {
2364             /* We can do the replacement.  Allocate reg_map if this is the
2365                first replacement we found.  */
2366             if (reg_map == 0)
2367               {
2368                 reg_map = (rtx *) alloca (max_reg * sizeof (rtx));
2369                 bzero ((char *) reg_map, max_reg * sizeof (rtx));
2370               }
2371
2372             REG_LOOP_TEST_P (reg) = 1;
2373
2374             reg_map[REGNO (reg)] = gen_reg_rtx (GET_MODE (reg));
2375           }
2376       }
2377
2378   /* Now copy each insn.  */
2379   for (insn = exitcode; insn != lastexit; insn = NEXT_INSN (insn))
2380     switch (GET_CODE (insn))
2381       {
2382       case BARRIER:
2383         copy = emit_barrier_before (loop_start);
2384         break;
2385       case NOTE:
2386         /* Only copy line-number notes.  */
2387         if (NOTE_LINE_NUMBER (insn) >= 0)
2388           {
2389             copy = emit_note_before (NOTE_LINE_NUMBER (insn), loop_start);
2390             NOTE_SOURCE_FILE (copy) = NOTE_SOURCE_FILE (insn);
2391           }
2392         break;
2393
2394       case INSN:
2395         copy = emit_insn_before (copy_rtx (PATTERN (insn)), loop_start);
2396         if (reg_map)
2397           replace_regs (PATTERN (copy), reg_map, max_reg, 1);
2398
2399         mark_jump_label (PATTERN (copy), copy, 0);
2400
2401         /* Copy all REG_NOTES except REG_LABEL since mark_jump_label will
2402            make them.  */
2403         for (link = REG_NOTES (insn); link; link = XEXP (link, 1))
2404           if (REG_NOTE_KIND (link) != REG_LABEL)
2405             REG_NOTES (copy)
2406               = copy_rtx (gen_rtx (EXPR_LIST, REG_NOTE_KIND (link),
2407                                    XEXP (link, 0), REG_NOTES (copy)));
2408         if (reg_map && REG_NOTES (copy))
2409           replace_regs (REG_NOTES (copy), reg_map, max_reg, 1);
2410         break;
2411
2412       case JUMP_INSN:
2413         copy = emit_jump_insn_before (copy_rtx (PATTERN (insn)), loop_start);
2414         if (reg_map)
2415           replace_regs (PATTERN (copy), reg_map, max_reg, 1);
2416         mark_jump_label (PATTERN (copy), copy, 0);
2417         if (REG_NOTES (insn))
2418           {
2419             REG_NOTES (copy) = copy_rtx (REG_NOTES (insn));
2420             if (reg_map)
2421               replace_regs (REG_NOTES (copy), reg_map, max_reg, 1);
2422           }
2423         
2424         /* If this is a simple jump, add it to the jump chain.  */
2425
2426         if (INSN_UID (copy) < max_jump_chain && JUMP_LABEL (copy)
2427             && simplejump_p (copy))
2428           {
2429             jump_chain[INSN_UID (copy)]
2430               = jump_chain[INSN_UID (JUMP_LABEL (copy))];
2431             jump_chain[INSN_UID (JUMP_LABEL (copy))] = copy;
2432           }
2433         break;
2434
2435       default:
2436         abort ();
2437       }
2438
2439   /* Now clean up by emitting a jump to the end label and deleting the jump
2440      at the start of the loop.  */
2441   if (! copy || GET_CODE (copy) != BARRIER)
2442     {
2443       copy = emit_jump_insn_before (gen_jump (get_label_after (insn)),
2444                                     loop_start);
2445       mark_jump_label (PATTERN (copy), copy, 0);
2446       if (INSN_UID (copy) < max_jump_chain
2447           && INSN_UID (JUMP_LABEL (copy)) < max_jump_chain)
2448         {
2449           jump_chain[INSN_UID (copy)]
2450             = jump_chain[INSN_UID (JUMP_LABEL (copy))];
2451           jump_chain[INSN_UID (JUMP_LABEL (copy))] = copy;
2452         }
2453       emit_barrier_before (loop_start);
2454     }
2455
2456   /* Mark the exit code as the virtual top of the converted loop.  */
2457   emit_note_before (NOTE_INSN_LOOP_VTOP, exitcode);
2458
2459   delete_insn (next_nonnote_insn (loop_start));
2460
2461   return 1;
2462 }
2463 \f
2464 /* Move all block-beg, block-end, loop-beg, loop-cont, loop-vtop, and
2465    loop-end notes between START and END out before START.  Assume that
2466    END is not such a note.  START may be such a note.  Returns the value
2467    of the new starting insn, which may be different if the original start
2468    was such a note.  */
2469
2470 rtx
2471 squeeze_notes (start, end)
2472      rtx start, end;
2473 {
2474   rtx insn;
2475   rtx next;
2476
2477   for (insn = start; insn != end; insn = next)
2478     {
2479       next = NEXT_INSN (insn);
2480       if (GET_CODE (insn) == NOTE
2481           && (NOTE_LINE_NUMBER (insn) == NOTE_INSN_BLOCK_END
2482               || NOTE_LINE_NUMBER (insn) == NOTE_INSN_BLOCK_BEG
2483               || NOTE_LINE_NUMBER (insn) == NOTE_INSN_LOOP_BEG
2484               || NOTE_LINE_NUMBER (insn) == NOTE_INSN_LOOP_END
2485               || NOTE_LINE_NUMBER (insn) == NOTE_INSN_LOOP_CONT
2486               || NOTE_LINE_NUMBER (insn) == NOTE_INSN_LOOP_VTOP))
2487         {
2488           if (insn == start)
2489             start = next;
2490           else
2491             {
2492               rtx prev = PREV_INSN (insn);
2493               PREV_INSN (insn) = PREV_INSN (start);
2494               NEXT_INSN (insn) = start;
2495               NEXT_INSN (PREV_INSN (insn)) = insn;
2496               PREV_INSN (NEXT_INSN (insn)) = insn;
2497               NEXT_INSN (prev) = next;
2498               PREV_INSN (next) = prev;
2499             }
2500         }
2501     }
2502
2503   return start;
2504 }
2505 \f
2506 /* Compare the instructions before insn E1 with those before E2
2507    to find an opportunity for cross jumping.
2508    (This means detecting identical sequences of insns followed by
2509    jumps to the same place, or followed by a label and a jump
2510    to that label, and replacing one with a jump to the other.)
2511
2512    Assume E1 is a jump that jumps to label E2
2513    (that is not always true but it might as well be).
2514    Find the longest possible equivalent sequences
2515    and store the first insns of those sequences into *F1 and *F2.
2516    Store zero there if no equivalent preceding instructions are found.
2517
2518    We give up if we find a label in stream 1.
2519    Actually we could transfer that label into stream 2.  */
2520
2521 static void
2522 find_cross_jump (e1, e2, minimum, f1, f2)
2523      rtx e1, e2;
2524      int minimum;
2525      rtx *f1, *f2;
2526 {
2527   register rtx i1 = e1, i2 = e2;
2528   register rtx p1, p2;
2529   int lose = 0;
2530
2531   rtx last1 = 0, last2 = 0;
2532   rtx afterlast1 = 0, afterlast2 = 0;
2533   rtx prev1;
2534
2535   *f1 = 0;
2536   *f2 = 0;
2537
2538   while (1)
2539     {
2540       i1 = prev_nonnote_insn (i1);
2541
2542       i2 = PREV_INSN (i2);
2543       while (i2 && (GET_CODE (i2) == NOTE || GET_CODE (i2) == CODE_LABEL))
2544         i2 = PREV_INSN (i2);
2545
2546       if (i1 == 0)
2547         break;
2548
2549       /* Don't allow the range of insns preceding E1 or E2
2550          to include the other (E2 or E1).  */
2551       if (i2 == e1 || i1 == e2)
2552         break;
2553
2554       /* If we will get to this code by jumping, those jumps will be
2555          tensioned to go directly to the new label (before I2),
2556          so this cross-jumping won't cost extra.  So reduce the minimum.  */
2557       if (GET_CODE (i1) == CODE_LABEL)
2558         {
2559           --minimum;
2560           break;
2561         }
2562
2563       if (i2 == 0 || GET_CODE (i1) != GET_CODE (i2))
2564         break;
2565
2566       p1 = PATTERN (i1);
2567       p2 = PATTERN (i2);
2568         
2569       /* If this is a CALL_INSN, compare register usage information.
2570          If we don't check this on stack register machines, the two
2571          CALL_INSNs might be merged leaving reg-stack.c with mismatching
2572          numbers of stack registers in the same basic block.
2573          If we don't check this on machines with delay slots, a delay slot may
2574          be filled that clobbers a parameter expected by the subroutine.
2575
2576          ??? We take the simple route for now and assume that if they're
2577          equal, they were constructed identically.  */
2578
2579       if (GET_CODE (i1) == CALL_INSN
2580           && ! rtx_equal_p (CALL_INSN_FUNCTION_USAGE (i1),
2581                             CALL_INSN_FUNCTION_USAGE (i2)))
2582         lose = 1;
2583
2584 #ifdef STACK_REGS
2585       /* If cross_jump_death_matters is not 0, the insn's mode
2586          indicates whether or not the insn contains any stack-like
2587          regs.  */
2588
2589       if (!lose && cross_jump_death_matters && GET_MODE (i1) == QImode)
2590         {
2591           /* If register stack conversion has already been done, then
2592              death notes must also be compared before it is certain that
2593              the two instruction streams match.  */
2594
2595           rtx note;
2596           HARD_REG_SET i1_regset, i2_regset;
2597
2598           CLEAR_HARD_REG_SET (i1_regset);
2599           CLEAR_HARD_REG_SET (i2_regset);
2600
2601           for (note = REG_NOTES (i1); note; note = XEXP (note, 1))
2602             if (REG_NOTE_KIND (note) == REG_DEAD
2603                 && STACK_REG_P (XEXP (note, 0)))
2604               SET_HARD_REG_BIT (i1_regset, REGNO (XEXP (note, 0)));
2605
2606           for (note = REG_NOTES (i2); note; note = XEXP (note, 1))
2607             if (REG_NOTE_KIND (note) == REG_DEAD
2608                 && STACK_REG_P (XEXP (note, 0)))
2609               SET_HARD_REG_BIT (i2_regset, REGNO (XEXP (note, 0)));
2610
2611           GO_IF_HARD_REG_EQUAL (i1_regset, i2_regset, done);
2612
2613           lose = 1;
2614
2615         done:
2616           ;
2617         }
2618 #endif
2619
2620       /* Don't allow old-style asm or volatile extended asms to be accepted
2621          for cross jumping purposes.  It is conceptually correct to allow
2622          them, since cross-jumping preserves the dynamic instruction order
2623          even though it is changing the static instruction order.  However,
2624          if an asm is being used to emit an assembler pseudo-op, such as
2625          the MIPS `.set reorder' pseudo-op, then the static instruction order
2626          matters and it must be preserved.  */
2627       if (GET_CODE (p1) == ASM_INPUT || GET_CODE (p2) == ASM_INPUT
2628           || (GET_CODE (p1) == ASM_OPERANDS && MEM_VOLATILE_P (p1))
2629           || (GET_CODE (p2) == ASM_OPERANDS && MEM_VOLATILE_P (p2)))
2630         lose = 1;
2631
2632       if (lose || GET_CODE (p1) != GET_CODE (p2)
2633           || ! rtx_renumbered_equal_p (p1, p2))
2634         {
2635           /* The following code helps take care of G++ cleanups.  */
2636           rtx equiv1;
2637           rtx equiv2;
2638
2639           if (!lose && GET_CODE (p1) == GET_CODE (p2)
2640               && ((equiv1 = find_reg_note (i1, REG_EQUAL, NULL_RTX)) != 0
2641                   || (equiv1 = find_reg_note (i1, REG_EQUIV, NULL_RTX)) != 0)
2642               && ((equiv2 = find_reg_note (i2, REG_EQUAL, NULL_RTX)) != 0
2643                   || (equiv2 = find_reg_note (i2, REG_EQUIV, NULL_RTX)) != 0)
2644               /* If the equivalences are not to a constant, they may
2645                  reference pseudos that no longer exist, so we can't
2646                  use them.  */
2647               && CONSTANT_P (XEXP (equiv1, 0))
2648               && rtx_equal_p (XEXP (equiv1, 0), XEXP (equiv2, 0)))
2649             {
2650               rtx s1 = single_set (i1);
2651               rtx s2 = single_set (i2);
2652               if (s1 != 0 && s2 != 0
2653                   && rtx_renumbered_equal_p (SET_DEST (s1), SET_DEST (s2)))
2654                 {
2655                   validate_change (i1, &SET_SRC (s1), XEXP (equiv1, 0), 1);
2656                   validate_change (i2, &SET_SRC (s2), XEXP (equiv2, 0), 1);
2657                   if (! rtx_renumbered_equal_p (p1, p2))
2658                     cancel_changes (0);
2659                   else if (apply_change_group ())
2660                     goto win;
2661                 }
2662             }
2663
2664           /* Insns fail to match; cross jumping is limited to the following
2665              insns.  */
2666
2667 #ifdef HAVE_cc0
2668           /* Don't allow the insn after a compare to be shared by
2669              cross-jumping unless the compare is also shared.
2670              Here, if either of these non-matching insns is a compare,
2671              exclude the following insn from possible cross-jumping.  */
2672           if (sets_cc0_p (p1) || sets_cc0_p (p2))
2673             last1 = afterlast1, last2 = afterlast2, ++minimum;
2674 #endif
2675
2676           /* If cross-jumping here will feed a jump-around-jump
2677              optimization, this jump won't cost extra, so reduce
2678              the minimum.  */
2679           if (GET_CODE (i1) == JUMP_INSN
2680               && JUMP_LABEL (i1)
2681               && prev_real_insn (JUMP_LABEL (i1)) == e1)
2682             --minimum;
2683           break;
2684         }
2685
2686     win:
2687       if (GET_CODE (p1) != USE && GET_CODE (p1) != CLOBBER)
2688         {
2689           /* Ok, this insn is potentially includable in a cross-jump here.  */
2690           afterlast1 = last1, afterlast2 = last2;
2691           last1 = i1, last2 = i2, --minimum;
2692         }
2693     }
2694
2695   if (minimum <= 0 && last1 != 0 && last1 != e1)
2696     *f1 = last1, *f2 = last2;
2697 }
2698
2699 static void
2700 do_cross_jump (insn, newjpos, newlpos)
2701      rtx insn, newjpos, newlpos;
2702 {
2703   /* Find an existing label at this point
2704      or make a new one if there is none.  */
2705   register rtx label = get_label_before (newlpos);
2706
2707   /* Make the same jump insn jump to the new point.  */
2708   if (GET_CODE (PATTERN (insn)) == RETURN)
2709     {
2710       /* Remove from jump chain of returns.  */
2711       delete_from_jump_chain (insn);
2712       /* Change the insn.  */
2713       PATTERN (insn) = gen_jump (label);
2714       INSN_CODE (insn) = -1;
2715       JUMP_LABEL (insn) = label;
2716       LABEL_NUSES (label)++;
2717       /* Add to new the jump chain.  */
2718       if (INSN_UID (label) < max_jump_chain
2719           && INSN_UID (insn) < max_jump_chain)
2720         {
2721           jump_chain[INSN_UID (insn)] = jump_chain[INSN_UID (label)];
2722           jump_chain[INSN_UID (label)] = insn;
2723         }
2724     }
2725   else
2726     redirect_jump (insn, label);
2727
2728   /* Delete the matching insns before the jump.  Also, remove any REG_EQUAL
2729      or REG_EQUIV note in the NEWLPOS stream that isn't also present in
2730      the NEWJPOS stream.  */
2731
2732   while (newjpos != insn)
2733     {
2734       rtx lnote;
2735
2736       for (lnote = REG_NOTES (newlpos); lnote; lnote = XEXP (lnote, 1))
2737         if ((REG_NOTE_KIND (lnote) == REG_EQUAL
2738              || REG_NOTE_KIND (lnote) == REG_EQUIV)
2739             && ! find_reg_note (newjpos, REG_EQUAL, XEXP (lnote, 0))
2740             && ! find_reg_note (newjpos, REG_EQUIV, XEXP (lnote, 0)))
2741           remove_note (newlpos, lnote);
2742
2743       delete_insn (newjpos);
2744       newjpos = next_real_insn (newjpos);
2745       newlpos = next_real_insn (newlpos);
2746     }
2747 }
2748 \f
2749 /* Return the label before INSN, or put a new label there.  */
2750
2751 rtx
2752 get_label_before (insn)
2753      rtx insn;
2754 {
2755   rtx label;
2756
2757   /* Find an existing label at this point
2758      or make a new one if there is none.  */
2759   label = prev_nonnote_insn (insn);
2760
2761   if (label == 0 || GET_CODE (label) != CODE_LABEL)
2762     {
2763       rtx prev = PREV_INSN (insn);
2764
2765       label = gen_label_rtx ();
2766       emit_label_after (label, prev);
2767       LABEL_NUSES (label) = 0;
2768     }
2769   return label;
2770 }
2771
2772 /* Return the label after INSN, or put a new label there.  */
2773
2774 rtx
2775 get_label_after (insn)
2776      rtx insn;
2777 {
2778   rtx label;
2779
2780   /* Find an existing label at this point
2781      or make a new one if there is none.  */
2782   label = next_nonnote_insn (insn);
2783
2784   if (label == 0 || GET_CODE (label) != CODE_LABEL)
2785     {
2786       label = gen_label_rtx ();
2787       emit_label_after (label, insn);
2788       LABEL_NUSES (label) = 0;
2789     }
2790   return label;
2791 }
2792 \f
2793 /* Return 1 if INSN is a jump that jumps to right after TARGET
2794    only on the condition that TARGET itself would drop through.
2795    Assumes that TARGET is a conditional jump.  */
2796
2797 static int
2798 jump_back_p (insn, target)
2799      rtx insn, target;
2800 {
2801   rtx cinsn, ctarget;
2802   enum rtx_code codei, codet;
2803
2804   if (simplejump_p (insn) || ! condjump_p (insn)
2805       || simplejump_p (target)
2806       || target != prev_real_insn (JUMP_LABEL (insn)))
2807     return 0;
2808
2809   cinsn = XEXP (SET_SRC (PATTERN (insn)), 0);
2810   ctarget = XEXP (SET_SRC (PATTERN (target)), 0);
2811
2812   codei = GET_CODE (cinsn);
2813   codet = GET_CODE (ctarget);
2814
2815   if (XEXP (SET_SRC (PATTERN (insn)), 1) == pc_rtx)
2816     {
2817       if (! can_reverse_comparison_p (cinsn, insn))
2818         return 0;
2819       codei = reverse_condition (codei);
2820     }
2821
2822   if (XEXP (SET_SRC (PATTERN (target)), 2) == pc_rtx)
2823     {
2824       if (! can_reverse_comparison_p (ctarget, target))
2825         return 0;
2826       codet = reverse_condition (codet);
2827     }
2828
2829   return (codei == codet
2830           && rtx_renumbered_equal_p (XEXP (cinsn, 0), XEXP (ctarget, 0))
2831           && rtx_renumbered_equal_p (XEXP (cinsn, 1), XEXP (ctarget, 1)));
2832 }
2833 \f
2834 /* Given a comparison, COMPARISON, inside a conditional jump insn, INSN,
2835    return non-zero if it is safe to reverse this comparison.  It is if our
2836    floating-point is not IEEE, if this is an NE or EQ comparison, or if
2837    this is known to be an integer comparison.  */
2838
2839 int
2840 can_reverse_comparison_p (comparison, insn)
2841      rtx comparison;
2842      rtx insn;
2843 {
2844   rtx arg0;
2845
2846   /* If this is not actually a comparison, we can't reverse it.  */
2847   if (GET_RTX_CLASS (GET_CODE (comparison)) != '<')
2848     return 0;
2849
2850   if (TARGET_FLOAT_FORMAT != IEEE_FLOAT_FORMAT
2851       /* If this is an NE comparison, it is safe to reverse it to an EQ
2852          comparison and vice versa, even for floating point.  If no operands
2853          are NaNs, the reversal is valid.  If some operand is a NaN, EQ is
2854          always false and NE is always true, so the reversal is also valid.  */
2855       || flag_fast_math
2856       || GET_CODE (comparison) == NE
2857       || GET_CODE (comparison) == EQ)
2858     return 1;
2859
2860   arg0 = XEXP (comparison, 0);
2861
2862   /* Make sure ARG0 is one of the actual objects being compared.  If we
2863      can't do this, we can't be sure the comparison can be reversed. 
2864
2865      Handle cc0 and a MODE_CC register.  */
2866   if ((GET_CODE (arg0) == REG && GET_MODE_CLASS (GET_MODE (arg0)) == MODE_CC)
2867 #ifdef HAVE_cc0
2868       || arg0 == cc0_rtx
2869 #endif
2870       )
2871     {
2872       rtx prev = prev_nonnote_insn (insn);
2873       rtx set = single_set (prev);
2874
2875       if (set == 0 || SET_DEST (set) != arg0)
2876         return 0;
2877
2878       arg0 = SET_SRC (set);
2879
2880       if (GET_CODE (arg0) == COMPARE)
2881         arg0 = XEXP (arg0, 0);
2882     }
2883
2884   /* We can reverse this if ARG0 is a CONST_INT or if its mode is
2885      not VOIDmode and neither a MODE_CC nor MODE_FLOAT type.  */
2886   return (GET_CODE (arg0) == CONST_INT
2887           || (GET_MODE (arg0) != VOIDmode
2888               && GET_MODE_CLASS (GET_MODE (arg0)) != MODE_CC
2889               && GET_MODE_CLASS (GET_MODE (arg0)) != MODE_FLOAT));
2890 }
2891
2892 /* Given an rtx-code for a comparison, return the code
2893    for the negated comparison.
2894    WATCH OUT!  reverse_condition is not safe to use on a jump
2895    that might be acting on the results of an IEEE floating point comparison,
2896    because of the special treatment of non-signaling nans in comparisons.  
2897    Use can_reverse_comparison_p to be sure.  */
2898
2899 enum rtx_code
2900 reverse_condition (code)
2901      enum rtx_code code;
2902 {
2903   switch (code)
2904     {
2905     case EQ:
2906       return NE;
2907
2908     case NE:
2909       return EQ;
2910
2911     case GT:
2912       return LE;
2913
2914     case GE:
2915       return LT;
2916
2917     case LT:
2918       return GE;
2919
2920     case LE:
2921       return GT;
2922
2923     case GTU:
2924       return LEU;
2925
2926     case GEU:
2927       return LTU;
2928
2929     case LTU:
2930       return GEU;
2931
2932     case LEU:
2933       return GTU;
2934
2935     default:
2936       abort ();
2937       return UNKNOWN;
2938     }
2939 }
2940
2941 /* Similar, but return the code when two operands of a comparison are swapped.
2942    This IS safe for IEEE floating-point.  */
2943
2944 enum rtx_code
2945 swap_condition (code)
2946      enum rtx_code code;
2947 {
2948   switch (code)
2949     {
2950     case EQ:
2951     case NE:
2952       return code;
2953
2954     case GT:
2955       return LT;
2956
2957     case GE:
2958       return LE;
2959
2960     case LT:
2961       return GT;
2962
2963     case LE:
2964       return GE;
2965
2966     case GTU:
2967       return LTU;
2968
2969     case GEU:
2970       return LEU;
2971
2972     case LTU:
2973       return GTU;
2974
2975     case LEU:
2976       return GEU;
2977
2978     default:
2979       abort ();
2980       return UNKNOWN;
2981     }
2982 }
2983
2984 /* Given a comparison CODE, return the corresponding unsigned comparison.
2985    If CODE is an equality comparison or already an unsigned comparison,
2986    CODE is returned.  */
2987
2988 enum rtx_code
2989 unsigned_condition (code)
2990      enum rtx_code code;
2991 {
2992   switch (code)
2993     {
2994     case EQ:
2995     case NE:
2996     case GTU:
2997     case GEU:
2998     case LTU:
2999     case LEU:
3000       return code;
3001
3002     case GT:
3003       return GTU;
3004
3005     case GE:
3006       return GEU;
3007
3008     case LT:
3009       return LTU;
3010
3011     case LE:
3012       return LEU;
3013
3014     default:
3015       abort ();
3016     }
3017 }
3018
3019 /* Similarly, return the signed version of a comparison.  */
3020
3021 enum rtx_code
3022 signed_condition (code)
3023      enum rtx_code code;
3024 {
3025   switch (code)
3026     {
3027     case EQ:
3028     case NE:
3029     case GT:
3030     case GE:
3031     case LT:
3032     case LE:
3033       return code;
3034
3035     case GTU:
3036       return GT;
3037
3038     case GEU:
3039       return GE;
3040
3041     case LTU:
3042       return LT;
3043
3044     case LEU:
3045       return LE;
3046
3047     default:
3048       abort ();
3049     }
3050 }
3051 \f
3052 /* Return non-zero if CODE1 is more strict than CODE2, i.e., if the
3053    truth of CODE1 implies the truth of CODE2.  */
3054
3055 int
3056 comparison_dominates_p (code1, code2)
3057      enum rtx_code code1, code2;
3058 {
3059   if (code1 == code2)
3060     return 1;
3061
3062   switch (code1)
3063     {
3064     case EQ:
3065       if (code2 == LE || code2 == LEU || code2 == GE || code2 == GEU)
3066         return 1;
3067       break;
3068
3069     case LT:
3070       if (code2 == LE || code2 == NE)
3071         return 1;
3072       break;
3073
3074     case GT:
3075       if (code2 == GE || code2 == NE)
3076         return 1;
3077       break;
3078
3079     case LTU:
3080       if (code2 == LEU || code2 == NE)
3081         return 1;
3082       break;
3083
3084     case GTU:
3085       if (code2 == GEU || code2 == NE)
3086         return 1;
3087       break;
3088     }
3089
3090   return 0;
3091 }
3092 \f
3093 /* Return 1 if INSN is an unconditional jump and nothing else.  */
3094
3095 int
3096 simplejump_p (insn)
3097      rtx insn;
3098 {
3099   return (GET_CODE (insn) == JUMP_INSN
3100           && GET_CODE (PATTERN (insn)) == SET
3101           && GET_CODE (SET_DEST (PATTERN (insn))) == PC
3102           && GET_CODE (SET_SRC (PATTERN (insn))) == LABEL_REF);
3103 }
3104
3105 /* Return nonzero if INSN is a (possibly) conditional jump
3106    and nothing more.  */
3107
3108 int
3109 condjump_p (insn)
3110      rtx insn;
3111 {
3112   register rtx x = PATTERN (insn);
3113   if (GET_CODE (x) != SET)
3114     return 0;
3115   if (GET_CODE (SET_DEST (x)) != PC)
3116     return 0;
3117   if (GET_CODE (SET_SRC (x)) == LABEL_REF)
3118     return 1;
3119   if (GET_CODE (SET_SRC (x)) != IF_THEN_ELSE)
3120     return 0;
3121   if (XEXP (SET_SRC (x), 2) == pc_rtx
3122       && (GET_CODE (XEXP (SET_SRC (x), 1)) == LABEL_REF
3123           || GET_CODE (XEXP (SET_SRC (x), 1)) == RETURN))
3124     return 1;
3125   if (XEXP (SET_SRC (x), 1) == pc_rtx
3126       && (GET_CODE (XEXP (SET_SRC (x), 2)) == LABEL_REF
3127           || GET_CODE (XEXP (SET_SRC (x), 2)) == RETURN))
3128     return 1;
3129   return 0;
3130 }
3131
3132 /* Return nonzero if INSN is a (possibly) conditional jump
3133    and nothing more.  */
3134
3135 int
3136 condjump_in_parallel_p (insn)
3137      rtx insn;
3138 {
3139   register rtx x = PATTERN (insn);
3140
3141   if (GET_CODE (x) != PARALLEL)
3142     return 0;
3143   else
3144     x = XVECEXP (x, 0, 0);
3145
3146   if (GET_CODE (x) != SET)
3147     return 0;
3148   if (GET_CODE (SET_DEST (x)) != PC)
3149     return 0;
3150   if (GET_CODE (SET_SRC (x)) == LABEL_REF)
3151     return 1;
3152   if (GET_CODE (SET_SRC (x)) != IF_THEN_ELSE)
3153     return 0;
3154   if (XEXP (SET_SRC (x), 2) == pc_rtx
3155       && (GET_CODE (XEXP (SET_SRC (x), 1)) == LABEL_REF
3156           || GET_CODE (XEXP (SET_SRC (x), 1)) == RETURN))
3157     return 1;
3158   if (XEXP (SET_SRC (x), 1) == pc_rtx
3159       && (GET_CODE (XEXP (SET_SRC (x), 2)) == LABEL_REF
3160           || GET_CODE (XEXP (SET_SRC (x), 2)) == RETURN))
3161     return 1;
3162   return 0;
3163 }
3164
3165 /* Return 1 if X is an RTX that does nothing but set the condition codes
3166    and CLOBBER or USE registers.
3167    Return -1 if X does explicitly set the condition codes,
3168    but also does other things.  */
3169
3170 int
3171 sets_cc0_p (x)
3172      rtx x;
3173 {
3174 #ifdef HAVE_cc0
3175   if (GET_CODE (x) == SET && SET_DEST (x) == cc0_rtx)
3176     return 1;
3177   if (GET_CODE (x) == PARALLEL)
3178     {
3179       int i;
3180       int sets_cc0 = 0;
3181       int other_things = 0;
3182       for (i = XVECLEN (x, 0) - 1; i >= 0; i--)
3183         {
3184           if (GET_CODE (XVECEXP (x, 0, i)) == SET
3185               && SET_DEST (XVECEXP (x, 0, i)) == cc0_rtx)
3186             sets_cc0 = 1;
3187           else if (GET_CODE (XVECEXP (x, 0, i)) == SET)
3188             other_things = 1;
3189         }
3190       return ! sets_cc0 ? 0 : other_things ? -1 : 1;
3191     }
3192   return 0;
3193 #else
3194   abort ();
3195 #endif
3196 }
3197 \f
3198 /* Follow any unconditional jump at LABEL;
3199    return the ultimate label reached by any such chain of jumps.
3200    If LABEL is not followed by a jump, return LABEL.
3201    If the chain loops or we can't find end, return LABEL,
3202    since that tells caller to avoid changing the insn.
3203
3204    If RELOAD_COMPLETED is 0, we do not chain across a NOTE_INSN_LOOP_BEG or
3205    a USE or CLOBBER.  */
3206
3207 rtx
3208 follow_jumps (label)
3209      rtx label;
3210 {
3211   register rtx insn;
3212   register rtx next;
3213   register rtx value = label;
3214   register int depth;
3215
3216   for (depth = 0;
3217        (depth < 10
3218         && (insn = next_active_insn (value)) != 0
3219         && GET_CODE (insn) == JUMP_INSN
3220         && ((JUMP_LABEL (insn) != 0 && simplejump_p (insn))
3221             || GET_CODE (PATTERN (insn)) == RETURN)
3222         && (next = NEXT_INSN (insn))
3223         && GET_CODE (next) == BARRIER);
3224        depth++)
3225     {
3226       /* Don't chain through the insn that jumps into a loop
3227          from outside the loop,
3228          since that would create multiple loop entry jumps
3229          and prevent loop optimization.  */
3230       rtx tem;
3231       if (!reload_completed)
3232         for (tem = value; tem != insn; tem = NEXT_INSN (tem))
3233           if (GET_CODE (tem) == NOTE
3234               && (NOTE_LINE_NUMBER (tem) == NOTE_INSN_LOOP_BEG
3235                   /* ??? Optional.  Disables some optimizations, but makes
3236                      gcov output more accurate with -O.  */
3237                   || (flag_test_coverage && NOTE_LINE_NUMBER (tem) > 0)))
3238             return value;
3239
3240       /* If we have found a cycle, make the insn jump to itself.  */
3241       if (JUMP_LABEL (insn) == label)
3242         return label;
3243
3244       tem = next_active_insn (JUMP_LABEL (insn));
3245       if (tem && (GET_CODE (PATTERN (tem)) == ADDR_VEC
3246                   || GET_CODE (PATTERN (tem)) == ADDR_DIFF_VEC))
3247         break;
3248
3249       value = JUMP_LABEL (insn);
3250     }
3251   if (depth == 10)
3252     return label;
3253   return value;
3254 }
3255
3256 /* Assuming that field IDX of X is a vector of label_refs,
3257    replace each of them by the ultimate label reached by it.
3258    Return nonzero if a change is made.
3259    If IGNORE_LOOPS is 0, we do not chain across a NOTE_INSN_LOOP_BEG.  */
3260
3261 static int
3262 tension_vector_labels (x, idx)
3263      register rtx x;
3264      register int idx;
3265 {
3266   int changed = 0;
3267   register int i;
3268   for (i = XVECLEN (x, idx) - 1; i >= 0; i--)
3269     {
3270       register rtx olabel = XEXP (XVECEXP (x, idx, i), 0);
3271       register rtx nlabel = follow_jumps (olabel);
3272       if (nlabel && nlabel != olabel)
3273         {
3274           XEXP (XVECEXP (x, idx, i), 0) = nlabel;
3275           ++LABEL_NUSES (nlabel);
3276           if (--LABEL_NUSES (olabel) == 0)
3277             delete_insn (olabel);
3278           changed = 1;
3279         }
3280     }
3281   return changed;
3282 }
3283 \f
3284 /* Find all CODE_LABELs referred to in X, and increment their use counts.
3285    If INSN is a JUMP_INSN and there is at least one CODE_LABEL referenced
3286    in INSN, then store one of them in JUMP_LABEL (INSN).
3287    If INSN is an INSN or a CALL_INSN and there is at least one CODE_LABEL
3288    referenced in INSN, add a REG_LABEL note containing that label to INSN.
3289    Also, when there are consecutive labels, canonicalize on the last of them.
3290
3291    Note that two labels separated by a loop-beginning note
3292    must be kept distinct if we have not yet done loop-optimization,
3293    because the gap between them is where loop-optimize
3294    will want to move invariant code to.  CROSS_JUMP tells us
3295    that loop-optimization is done with.
3296
3297    Once reload has completed (CROSS_JUMP non-zero), we need not consider
3298    two labels distinct if they are separated by only USE or CLOBBER insns.  */
3299
3300 static void
3301 mark_jump_label (x, insn, cross_jump)
3302      register rtx x;
3303      rtx insn;
3304      int cross_jump;
3305 {
3306   register RTX_CODE code = GET_CODE (x);
3307   register int i;
3308   register char *fmt;
3309
3310   switch (code)
3311     {
3312     case PC:
3313     case CC0:
3314     case REG:
3315     case SUBREG:
3316     case CONST_INT:
3317     case SYMBOL_REF:
3318     case CONST_DOUBLE:
3319     case CLOBBER:
3320     case CALL:
3321       return;
3322
3323     case MEM:
3324       /* If this is a constant-pool reference, see if it is a label.  */
3325       if (GET_CODE (XEXP (x, 0)) == SYMBOL_REF
3326           && CONSTANT_POOL_ADDRESS_P (XEXP (x, 0)))
3327         mark_jump_label (get_pool_constant (XEXP (x, 0)), insn, cross_jump);
3328       break;
3329
3330     case LABEL_REF:
3331       {
3332         rtx label = XEXP (x, 0);
3333         rtx olabel = label;
3334         rtx note;
3335         rtx next;
3336
3337         if (GET_CODE (label) != CODE_LABEL)
3338           abort ();
3339
3340         /* Ignore references to labels of containing functions.  */
3341         if (LABEL_REF_NONLOCAL_P (x))
3342           break;
3343
3344         /* If there are other labels following this one,
3345            replace it with the last of the consecutive labels.  */
3346         for (next = NEXT_INSN (label); next; next = NEXT_INSN (next))
3347           {
3348             if (GET_CODE (next) == CODE_LABEL)
3349               label = next;
3350             else if (cross_jump && GET_CODE (next) == INSN
3351                      && (GET_CODE (PATTERN (next)) == USE
3352                          || GET_CODE (PATTERN (next)) == CLOBBER))
3353               continue;
3354             else if (GET_CODE (next) != NOTE)
3355               break;
3356             else if (! cross_jump
3357                      && (NOTE_LINE_NUMBER (next) == NOTE_INSN_LOOP_BEG
3358                          || NOTE_LINE_NUMBER (next) == NOTE_INSN_FUNCTION_END
3359                          /* ??? Optional.  Disables some optimizations, but
3360                             makes gcov output more accurate with -O.  */
3361                          || (flag_test_coverage && NOTE_LINE_NUMBER (next) > 0)))
3362               break;
3363           }
3364
3365         XEXP (x, 0) = label;
3366         ++LABEL_NUSES (label);
3367
3368         if (insn)
3369           {
3370             if (GET_CODE (insn) == JUMP_INSN)
3371               JUMP_LABEL (insn) = label;
3372
3373             /* If we've changed OLABEL and we had a REG_LABEL note
3374                for it, update it as well.  */
3375             else if (label != olabel
3376                      && (note = find_reg_note (insn, REG_LABEL, olabel)) != 0)
3377               XEXP (note, 0) = label;
3378
3379             /* Otherwise, add a REG_LABEL note for LABEL unless there already
3380                is one.  */
3381             else if (! find_reg_note (insn, REG_LABEL, label))
3382               {
3383                 rtx next = next_real_insn (label);
3384                 /* Don't record labels that refer to dispatch tables.
3385                    This is not necessary, since the tablejump
3386                    references the same label.
3387                    And if we did record them, flow.c would make worse code.  */
3388                 if (next == 0
3389                     || ! (GET_CODE (next) == JUMP_INSN
3390                           && (GET_CODE (PATTERN (next)) == ADDR_VEC
3391                               || GET_CODE (PATTERN (next)) == ADDR_DIFF_VEC)))
3392                   REG_NOTES (insn) = gen_rtx (EXPR_LIST, REG_LABEL, label,
3393                                               REG_NOTES (insn));
3394               }
3395           }
3396         return;
3397       }
3398
3399   /* Do walk the labels in a vector, but not the first operand of an
3400      ADDR_DIFF_VEC.  Don't set the JUMP_LABEL of a vector.  */
3401     case ADDR_VEC:
3402     case ADDR_DIFF_VEC:
3403       {
3404         int eltnum = code == ADDR_DIFF_VEC ? 1 : 0;
3405
3406         for (i = 0; i < XVECLEN (x, eltnum); i++)
3407           mark_jump_label (XVECEXP (x, eltnum, i), NULL_RTX, cross_jump);
3408         return;
3409       }
3410     }
3411
3412   fmt = GET_RTX_FORMAT (code);
3413   for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
3414     {
3415       if (fmt[i] == 'e')
3416         mark_jump_label (XEXP (x, i), insn, cross_jump);
3417       else if (fmt[i] == 'E')
3418         {
3419           register int j;
3420           for (j = 0; j < XVECLEN (x, i); j++)
3421             mark_jump_label (XVECEXP (x, i, j), insn, cross_jump);
3422         }
3423     }
3424 }
3425
3426 /* If all INSN does is set the pc, delete it,
3427    and delete the insn that set the condition codes for it
3428    if that's what the previous thing was.  */
3429
3430 void
3431 delete_jump (insn)
3432      rtx insn;
3433 {
3434   register rtx set = single_set (insn);
3435
3436   if (set && GET_CODE (SET_DEST (set)) == PC)
3437     delete_computation (insn);
3438 }
3439
3440 /* Delete INSN and recursively delete insns that compute values used only
3441    by INSN.  This uses the REG_DEAD notes computed during flow analysis.
3442    If we are running before flow.c, we need do nothing since flow.c will
3443    delete dead code.  We also can't know if the registers being used are
3444    dead or not at this point.
3445
3446    Otherwise, look at all our REG_DEAD notes.  If a previous insn does
3447    nothing other than set a register that dies in this insn, we can delete
3448    that insn as well.
3449
3450    On machines with CC0, if CC0 is used in this insn, we may be able to
3451    delete the insn that set it.  */
3452
3453 static void
3454 delete_computation (insn)
3455      rtx insn;
3456 {
3457   rtx note, next;
3458
3459 #ifdef HAVE_cc0
3460   if (reg_referenced_p (cc0_rtx, PATTERN (insn)))
3461     {
3462       rtx prev = prev_nonnote_insn (insn);
3463       /* We assume that at this stage
3464          CC's are always set explicitly
3465          and always immediately before the jump that
3466          will use them.  So if the previous insn
3467          exists to set the CC's, delete it
3468          (unless it performs auto-increments, etc.).  */
3469       if (prev && GET_CODE (prev) == INSN
3470           && sets_cc0_p (PATTERN (prev)))
3471         {
3472           if (sets_cc0_p (PATTERN (prev)) > 0
3473               && !FIND_REG_INC_NOTE (prev, NULL_RTX))
3474             delete_computation (prev);
3475           else
3476             /* Otherwise, show that cc0 won't be used.  */
3477             REG_NOTES (prev) = gen_rtx (EXPR_LIST, REG_UNUSED,
3478                                         cc0_rtx, REG_NOTES (prev));
3479         }
3480     }
3481 #endif
3482
3483   for (note = REG_NOTES (insn); note; note = next)
3484     {
3485       rtx our_prev;
3486
3487       next = XEXP (note, 1);
3488
3489       if (REG_NOTE_KIND (note) != REG_DEAD
3490           /* Verify that the REG_NOTE is legitimate.  */
3491           || GET_CODE (XEXP (note, 0)) != REG)
3492         continue;
3493
3494       for (our_prev = prev_nonnote_insn (insn);
3495            our_prev && GET_CODE (our_prev) == INSN;
3496            our_prev = prev_nonnote_insn (our_prev))
3497         {
3498           /* If we reach a SEQUENCE, it is too complex to try to
3499              do anything with it, so give up.  */
3500           if (GET_CODE (PATTERN (our_prev)) == SEQUENCE)
3501             break;
3502
3503           if (GET_CODE (PATTERN (our_prev)) == USE
3504               && GET_CODE (XEXP (PATTERN (our_prev), 0)) == INSN)
3505             /* reorg creates USEs that look like this.  We leave them
3506                alone because reorg needs them for its own purposes.  */
3507             break;
3508
3509           if (reg_set_p (XEXP (note, 0), PATTERN (our_prev)))
3510             {
3511               if (FIND_REG_INC_NOTE (our_prev, NULL_RTX))
3512                 break;
3513
3514               if (GET_CODE (PATTERN (our_prev)) == PARALLEL)
3515                 {
3516                   /* If we find a SET of something else, we can't
3517                      delete the insn.  */
3518
3519                   int i;
3520
3521                   for (i = 0; i < XVECLEN (PATTERN (our_prev), 0); i++)
3522                     {
3523                       rtx part = XVECEXP (PATTERN (our_prev), 0, i);
3524
3525                       if (GET_CODE (part) == SET
3526                           && SET_DEST (part) != XEXP (note, 0))
3527                         break;
3528                     }
3529
3530                   if (i == XVECLEN (PATTERN (our_prev), 0))
3531                     delete_computation (our_prev);
3532                 }
3533               else if (GET_CODE (PATTERN (our_prev)) == SET
3534                        && SET_DEST (PATTERN (our_prev)) == XEXP (note, 0))
3535                 delete_computation (our_prev);
3536
3537               break;
3538             }
3539
3540           /* If OUR_PREV references the register that dies here, it is an
3541              additional use.  Hence any prior SET isn't dead.  However, this
3542              insn becomes the new place for the REG_DEAD note.  */
3543           if (reg_overlap_mentioned_p (XEXP (note, 0),
3544                                        PATTERN (our_prev)))
3545             {
3546               XEXP (note, 1) = REG_NOTES (our_prev);
3547               REG_NOTES (our_prev) = note;
3548               break;
3549             }
3550         }
3551     }
3552
3553   delete_insn (insn);
3554 }
3555 \f
3556 /* Delete insn INSN from the chain of insns and update label ref counts.
3557    May delete some following insns as a consequence; may even delete
3558    a label elsewhere and insns that follow it.
3559
3560    Returns the first insn after INSN that was not deleted.  */
3561
3562 rtx
3563 delete_insn (insn)
3564      register rtx insn;
3565 {
3566   register rtx next = NEXT_INSN (insn);
3567   register rtx prev = PREV_INSN (insn);
3568   register int was_code_label = (GET_CODE (insn) == CODE_LABEL);
3569   register int dont_really_delete = 0;
3570
3571   while (next && INSN_DELETED_P (next))
3572     next = NEXT_INSN (next);
3573
3574   /* This insn is already deleted => return first following nondeleted.  */
3575   if (INSN_DELETED_P (insn))
3576     return next;
3577
3578   /* Don't delete user-declared labels.  Convert them to special NOTEs
3579      instead.  */
3580   if (was_code_label && LABEL_NAME (insn) != 0
3581       && optimize && ! dont_really_delete)
3582     {
3583       PUT_CODE (insn, NOTE);
3584       NOTE_LINE_NUMBER (insn) = NOTE_INSN_DELETED_LABEL;
3585       NOTE_SOURCE_FILE (insn) = 0;
3586       dont_really_delete = 1;
3587     }
3588   else
3589     /* Mark this insn as deleted.  */
3590     INSN_DELETED_P (insn) = 1;
3591
3592   /* If this is an unconditional jump, delete it from the jump chain.  */
3593   if (simplejump_p (insn))
3594     delete_from_jump_chain (insn);
3595
3596   /* If instruction is followed by a barrier,
3597      delete the barrier too.  */
3598
3599   if (next != 0 && GET_CODE (next) == BARRIER)
3600     {
3601       INSN_DELETED_P (next) = 1;
3602       next = NEXT_INSN (next);
3603     }
3604
3605   /* Patch out INSN (and the barrier if any) */
3606
3607   if (optimize && ! dont_really_delete)
3608     {
3609       if (prev)
3610         {
3611           NEXT_INSN (prev) = next;
3612           if (GET_CODE (prev) == INSN && GET_CODE (PATTERN (prev)) == SEQUENCE)
3613             NEXT_INSN (XVECEXP (PATTERN (prev), 0,
3614                                 XVECLEN (PATTERN (prev), 0) - 1)) = next;
3615         }
3616
3617       if (next)
3618         {
3619           PREV_INSN (next) = prev;
3620           if (GET_CODE (next) == INSN && GET_CODE (PATTERN (next)) == SEQUENCE)
3621             PREV_INSN (XVECEXP (PATTERN (next), 0, 0)) = prev;
3622         }
3623
3624       if (prev && NEXT_INSN (prev) == 0)
3625         set_last_insn (prev);
3626     }
3627
3628   /* If deleting a jump, decrement the count of the label,
3629      and delete the label if it is now unused.  */
3630
3631   if (GET_CODE (insn) == JUMP_INSN && JUMP_LABEL (insn))
3632     if (--LABEL_NUSES (JUMP_LABEL (insn)) == 0)
3633       {
3634         /* This can delete NEXT or PREV,
3635            either directly if NEXT is JUMP_LABEL (INSN),
3636            or indirectly through more levels of jumps.  */
3637         delete_insn (JUMP_LABEL (insn));
3638         /* I feel a little doubtful about this loop,
3639            but I see no clean and sure alternative way
3640            to find the first insn after INSN that is not now deleted.
3641            I hope this works.  */
3642         while (next && INSN_DELETED_P (next))
3643           next = NEXT_INSN (next);
3644         return next;
3645       }
3646
3647   /* Likewise if we're deleting a dispatch table.  */
3648
3649   if (GET_CODE (insn) == JUMP_INSN
3650       && (GET_CODE (PATTERN (insn)) == ADDR_VEC
3651           || GET_CODE (PATTERN (insn)) == ADDR_DIFF_VEC))
3652     {
3653       rtx pat = PATTERN (insn);
3654       int i, diff_vec_p = GET_CODE (pat) == ADDR_DIFF_VEC;
3655       int len = XVECLEN (pat, diff_vec_p);
3656
3657       for (i = 0; i < len; i++)
3658         if (--LABEL_NUSES (XEXP (XVECEXP (pat, diff_vec_p, i), 0)) == 0)
3659           delete_insn (XEXP (XVECEXP (pat, diff_vec_p, i), 0));
3660       while (next && INSN_DELETED_P (next))
3661         next = NEXT_INSN (next);
3662       return next;
3663     }
3664
3665   while (prev && (INSN_DELETED_P (prev) || GET_CODE (prev) == NOTE))
3666     prev = PREV_INSN (prev);
3667
3668   /* If INSN was a label and a dispatch table follows it,
3669      delete the dispatch table.  The tablejump must have gone already.
3670      It isn't useful to fall through into a table.  */
3671
3672   if (was_code_label
3673       && NEXT_INSN (insn) != 0
3674       && GET_CODE (NEXT_INSN (insn)) == JUMP_INSN
3675       && (GET_CODE (PATTERN (NEXT_INSN (insn))) == ADDR_VEC
3676           || GET_CODE (PATTERN (NEXT_INSN (insn))) == ADDR_DIFF_VEC))
3677     next = delete_insn (NEXT_INSN (insn));
3678
3679   /* If INSN was a label, delete insns following it if now unreachable.  */
3680
3681   if (was_code_label && prev && GET_CODE (prev) == BARRIER)
3682     {
3683       register RTX_CODE code;
3684       while (next != 0
3685              && (GET_RTX_CLASS (code = GET_CODE (next)) == 'i'
3686                  || code == NOTE || code == BARRIER
3687                  || (code == CODE_LABEL && INSN_DELETED_P (next))))
3688         {
3689           if (code == NOTE
3690               && NOTE_LINE_NUMBER (next) != NOTE_INSN_FUNCTION_END)
3691             next = NEXT_INSN (next);
3692           /* Keep going past other deleted labels to delete what follows.  */
3693           else if (code == CODE_LABEL && INSN_DELETED_P (next))
3694             next = NEXT_INSN (next);
3695           else
3696             /* Note: if this deletes a jump, it can cause more
3697                deletion of unreachable code, after a different label.
3698                As long as the value from this recursive call is correct,
3699                this invocation functions correctly.  */
3700             next = delete_insn (next);
3701         }
3702     }
3703
3704   return next;
3705 }
3706
3707 /* Advance from INSN till reaching something not deleted
3708    then return that.  May return INSN itself.  */
3709
3710 rtx
3711 next_nondeleted_insn (insn)
3712      rtx insn;
3713 {
3714   while (INSN_DELETED_P (insn))
3715     insn = NEXT_INSN (insn);
3716   return insn;
3717 }
3718 \f
3719 /* Delete a range of insns from FROM to TO, inclusive.
3720    This is for the sake of peephole optimization, so assume
3721    that whatever these insns do will still be done by a new
3722    peephole insn that will replace them.  */
3723
3724 void
3725 delete_for_peephole (from, to)
3726      register rtx from, to;
3727 {
3728   register rtx insn = from;
3729
3730   while (1)
3731     {
3732       register rtx next = NEXT_INSN (insn);
3733       register rtx prev = PREV_INSN (insn);
3734
3735       if (GET_CODE (insn) != NOTE)
3736         {
3737           INSN_DELETED_P (insn) = 1;
3738
3739           /* Patch this insn out of the chain.  */
3740           /* We don't do this all at once, because we
3741              must preserve all NOTEs.  */
3742           if (prev)
3743             NEXT_INSN (prev) = next;
3744
3745           if (next)
3746             PREV_INSN (next) = prev;
3747         }
3748
3749       if (insn == to)
3750         break;
3751       insn = next;
3752     }
3753
3754   /* Note that if TO is an unconditional jump
3755      we *do not* delete the BARRIER that follows,
3756      since the peephole that replaces this sequence
3757      is also an unconditional jump in that case.  */
3758 }
3759 \f
3760 /* Invert the condition of the jump JUMP, and make it jump
3761    to label NLABEL instead of where it jumps now.  */
3762
3763 int
3764 invert_jump (jump, nlabel)
3765      rtx jump, nlabel;
3766 {
3767   /* We have to either invert the condition and change the label or
3768      do neither.  Either operation could fail.  We first try to invert
3769      the jump. If that succeeds, we try changing the label.  If that fails,
3770      we invert the jump back to what it was.  */
3771
3772   if (! invert_exp (PATTERN (jump), jump))
3773     return 0;
3774
3775   if (redirect_jump (jump, nlabel))
3776     {
3777       if (flag_branch_probabilities)
3778         {
3779           rtx note = find_reg_note (jump, REG_BR_PROB, 0);
3780
3781           /* An inverted jump means that a probability taken becomes a
3782              probability not taken.  Subtract the branch probability from the
3783              probability base to convert it back to a taken probability.
3784              (We don't flip the probability on a branch that's never taken.  */
3785           if (note && XINT (XEXP (note, 0), 0) >= 0)
3786             XINT (XEXP (note, 0), 0) = REG_BR_PROB_BASE - XINT (XEXP (note, 0), 0);
3787         }
3788
3789       return 1;
3790     }
3791
3792   if (! invert_exp (PATTERN (jump), jump))
3793     /* This should just be putting it back the way it was.  */
3794     abort ();
3795
3796   return  0;
3797 }
3798
3799 /* Invert the jump condition of rtx X contained in jump insn, INSN. 
3800
3801    Return 1 if we can do so, 0 if we cannot find a way to do so that
3802    matches a pattern.  */
3803
3804 int
3805 invert_exp (x, insn)
3806      rtx x;
3807      rtx insn;
3808 {
3809   register RTX_CODE code;
3810   register int i;
3811   register char *fmt;
3812
3813   code = GET_CODE (x);
3814
3815   if (code == IF_THEN_ELSE)
3816     {
3817       register rtx comp = XEXP (x, 0);
3818       register rtx tem;
3819
3820       /* We can do this in two ways:  The preferable way, which can only
3821          be done if this is not an integer comparison, is to reverse
3822          the comparison code.  Otherwise, swap the THEN-part and ELSE-part
3823          of the IF_THEN_ELSE.  If we can't do either, fail.  */
3824
3825       if (can_reverse_comparison_p (comp, insn)
3826           && validate_change (insn, &XEXP (x, 0),
3827                               gen_rtx (reverse_condition (GET_CODE (comp)),
3828                                        GET_MODE (comp), XEXP (comp, 0),
3829                                        XEXP (comp, 1)), 0))
3830         return 1;
3831                                        
3832       tem = XEXP (x, 1);
3833       validate_change (insn, &XEXP (x, 1), XEXP (x, 2), 1);
3834       validate_change (insn, &XEXP (x, 2), tem, 1);
3835       return apply_change_group ();
3836     }
3837
3838   fmt = GET_RTX_FORMAT (code);
3839   for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
3840     {
3841       if (fmt[i] == 'e')
3842         if (! invert_exp (XEXP (x, i), insn))
3843           return 0;
3844       if (fmt[i] == 'E')
3845         {
3846           register int j;
3847           for (j = 0; j < XVECLEN (x, i); j++)
3848             if (!invert_exp (XVECEXP (x, i, j), insn))
3849               return 0;
3850         }
3851     }
3852
3853   return 1;
3854 }
3855 \f
3856 /* Make jump JUMP jump to label NLABEL instead of where it jumps now.
3857    If the old jump target label is unused as a result,
3858    it and the code following it may be deleted.
3859
3860    If NLABEL is zero, we are to turn the jump into a (possibly conditional)
3861    RETURN insn.
3862
3863    The return value will be 1 if the change was made, 0 if it wasn't (this
3864    can only occur for NLABEL == 0).  */
3865
3866 int
3867 redirect_jump (jump, nlabel)
3868      rtx jump, nlabel;
3869 {
3870   register rtx olabel = JUMP_LABEL (jump);
3871
3872   if (nlabel == olabel)
3873     return 1;
3874
3875   if (! redirect_exp (&PATTERN (jump), olabel, nlabel, jump))
3876     return 0;
3877
3878   /* If this is an unconditional branch, delete it from the jump_chain of
3879      OLABEL and add it to the jump_chain of NLABEL (assuming both labels
3880      have UID's in range and JUMP_CHAIN is valid).  */
3881   if (jump_chain && (simplejump_p (jump)
3882                      || GET_CODE (PATTERN (jump)) == RETURN))
3883     {
3884       int label_index = nlabel ? INSN_UID (nlabel) : 0;
3885
3886       delete_from_jump_chain (jump);
3887       if (label_index < max_jump_chain
3888           && INSN_UID (jump) < max_jump_chain)
3889         {
3890           jump_chain[INSN_UID (jump)] = jump_chain[label_index];
3891           jump_chain[label_index] = jump;
3892         }
3893     }
3894
3895   JUMP_LABEL (jump) = nlabel;
3896   if (nlabel)
3897     ++LABEL_NUSES (nlabel);
3898
3899   if (olabel && --LABEL_NUSES (olabel) == 0)
3900     delete_insn (olabel);
3901
3902   return 1;
3903 }
3904
3905 /* Delete the instruction JUMP from any jump chain it might be on.  */
3906
3907 static void
3908 delete_from_jump_chain (jump)
3909      rtx jump;
3910 {
3911   int index;
3912   rtx olabel = JUMP_LABEL (jump);
3913
3914   /* Handle unconditional jumps.  */
3915   if (jump_chain && olabel != 0
3916       && INSN_UID (olabel) < max_jump_chain
3917       && simplejump_p (jump))
3918     index = INSN_UID (olabel);
3919   /* Handle return insns.  */
3920   else if (jump_chain && GET_CODE (PATTERN (jump)) == RETURN)
3921     index = 0;
3922   else return;
3923
3924   if (jump_chain[index] == jump)
3925     jump_chain[index] = jump_chain[INSN_UID (jump)];
3926   else
3927     {
3928       rtx insn;
3929
3930       for (insn = jump_chain[index];
3931            insn != 0;
3932            insn = jump_chain[INSN_UID (insn)])
3933         if (jump_chain[INSN_UID (insn)] == jump)
3934           {
3935             jump_chain[INSN_UID (insn)] = jump_chain[INSN_UID (jump)];
3936             break;
3937           }
3938     }
3939 }
3940
3941 /* If NLABEL is nonzero, throughout the rtx at LOC,
3942    alter (LABEL_REF OLABEL) to (LABEL_REF NLABEL).  If OLABEL is
3943    zero, alter (RETURN) to (LABEL_REF NLABEL).
3944
3945    If NLABEL is zero, alter (LABEL_REF OLABEL) to (RETURN) and check
3946    validity with validate_change.  Convert (set (pc) (label_ref olabel))
3947    to (return).
3948
3949    Return 0 if we found a change we would like to make but it is invalid.
3950    Otherwise, return 1.  */
3951
3952 int
3953 redirect_exp (loc, olabel, nlabel, insn)
3954      rtx *loc;
3955      rtx olabel, nlabel;
3956      rtx insn;
3957 {
3958   register rtx x = *loc;
3959   register RTX_CODE code = GET_CODE (x);
3960   register int i;
3961   register char *fmt;
3962
3963   if (code == LABEL_REF)
3964     {
3965       if (XEXP (x, 0) == olabel)
3966         {
3967           if (nlabel)
3968             XEXP (x, 0) = nlabel;
3969           else
3970             return validate_change (insn, loc, gen_rtx (RETURN, VOIDmode), 0);
3971           return 1;
3972         }
3973     }
3974   else if (code == RETURN && olabel == 0)
3975     {
3976       x = gen_rtx (LABEL_REF, VOIDmode, nlabel);
3977       if (loc == &PATTERN (insn))
3978         x = gen_rtx (SET, VOIDmode, pc_rtx, x);
3979       return validate_change (insn, loc, x, 0);
3980     }
3981
3982   if (code == SET && nlabel == 0 && SET_DEST (x) == pc_rtx
3983       && GET_CODE (SET_SRC (x)) == LABEL_REF
3984       && XEXP (SET_SRC (x), 0) == olabel)
3985     return validate_change (insn, loc, gen_rtx (RETURN, VOIDmode), 0);
3986
3987   fmt = GET_RTX_FORMAT (code);
3988   for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
3989     {
3990       if (fmt[i] == 'e')
3991         if (! redirect_exp (&XEXP (x, i), olabel, nlabel, insn))
3992           return 0;
3993       if (fmt[i] == 'E')
3994         {
3995           register int j;
3996           for (j = 0; j < XVECLEN (x, i); j++)
3997             if (! redirect_exp (&XVECEXP (x, i, j), olabel, nlabel, insn))
3998               return 0;
3999         }
4000     }
4001
4002   return 1;
4003 }
4004 \f
4005 /* Make jump JUMP jump to label NLABEL, assuming it used to be a tablejump.
4006
4007    If the old jump target label (before the dispatch table) becomes unused,
4008    it and the dispatch table may be deleted.  In that case, find the insn
4009    before the jump references that label and delete it and logical successors
4010    too.  */
4011
4012 static void
4013 redirect_tablejump (jump, nlabel)
4014      rtx jump, nlabel;
4015 {
4016   register rtx olabel = JUMP_LABEL (jump);
4017
4018   /* Add this jump to the jump_chain of NLABEL.  */
4019   if (jump_chain && INSN_UID (nlabel) < max_jump_chain
4020       && INSN_UID (jump) < max_jump_chain)
4021     {
4022       jump_chain[INSN_UID (jump)] = jump_chain[INSN_UID (nlabel)];
4023       jump_chain[INSN_UID (nlabel)] = jump;
4024     }
4025
4026   PATTERN (jump) = gen_jump (nlabel);
4027   JUMP_LABEL (jump) = nlabel;
4028   ++LABEL_NUSES (nlabel);
4029   INSN_CODE (jump) = -1;
4030
4031   if (--LABEL_NUSES (olabel) == 0)
4032     {
4033       delete_labelref_insn (jump, olabel, 0);
4034       delete_insn (olabel);
4035     }
4036 }
4037
4038 /* Find the insn referencing LABEL that is a logical predecessor of INSN.
4039    If we found one, delete it and then delete this insn if DELETE_THIS is
4040    non-zero.  Return non-zero if INSN or a predecessor references LABEL.  */
4041
4042 static int
4043 delete_labelref_insn (insn, label, delete_this)
4044      rtx insn, label;
4045      int delete_this;
4046 {
4047   int deleted = 0;
4048   rtx link;
4049
4050   if (GET_CODE (insn) != NOTE
4051       && reg_mentioned_p (label, PATTERN (insn)))
4052     {
4053       if (delete_this)
4054         {
4055           delete_insn (insn);
4056           deleted = 1;
4057         }
4058       else
4059         return 1;
4060     }
4061
4062   for (link = LOG_LINKS (insn); link; link = XEXP (link, 1))
4063     if (delete_labelref_insn (XEXP (link, 0), label, 1))
4064       {
4065         if (delete_this)
4066           {
4067             delete_insn (insn);
4068             deleted = 1;
4069           }
4070         else
4071           return 1;
4072       }
4073
4074   return deleted;
4075 }
4076 \f
4077 /* Like rtx_equal_p except that it considers two REGs as equal
4078    if they renumber to the same value and considers two commutative
4079    operations to be the same if the order of the operands has been
4080    reversed.  */
4081
4082 int
4083 rtx_renumbered_equal_p (x, y)
4084      rtx x, y;
4085 {
4086   register int i;
4087   register RTX_CODE code = GET_CODE (x);
4088   register char *fmt;
4089       
4090   if (x == y)
4091     return 1;
4092
4093   if ((code == REG || (code == SUBREG && GET_CODE (SUBREG_REG (x)) == REG))
4094       && (GET_CODE (y) == REG || (GET_CODE (y) == SUBREG
4095                                   && GET_CODE (SUBREG_REG (y)) == REG)))
4096     {
4097       int reg_x = -1, reg_y = -1;
4098       int word_x = 0, word_y = 0;
4099
4100       if (GET_MODE (x) != GET_MODE (y))
4101         return 0;
4102
4103       /* If we haven't done any renumbering, don't
4104          make any assumptions.  */
4105       if (reg_renumber == 0)
4106         return rtx_equal_p (x, y);
4107
4108       if (code == SUBREG)
4109         {
4110           reg_x = REGNO (SUBREG_REG (x));
4111           word_x = SUBREG_WORD (x);
4112
4113           if (reg_renumber[reg_x] >= 0)
4114             {
4115               reg_x = reg_renumber[reg_x] + word_x;
4116               word_x = 0;
4117             }
4118         }
4119
4120       else
4121         {
4122           reg_x = REGNO (x);
4123           if (reg_renumber[reg_x] >= 0)
4124             reg_x = reg_renumber[reg_x];
4125         }
4126
4127       if (GET_CODE (y) == SUBREG)
4128         {
4129           reg_y = REGNO (SUBREG_REG (y));
4130           word_y = SUBREG_WORD (y);
4131
4132           if (reg_renumber[reg_y] >= 0)
4133             {
4134               reg_y = reg_renumber[reg_y];
4135               word_y = 0;
4136             }
4137         }
4138
4139       else
4140         {
4141           reg_y = REGNO (y);
4142           if (reg_renumber[reg_y] >= 0)
4143             reg_y = reg_renumber[reg_y];
4144         }
4145
4146       return reg_x >= 0 && reg_x == reg_y && word_x == word_y;
4147     }
4148
4149   /* Now we have disposed of all the cases 
4150      in which different rtx codes can match.  */
4151   if (code != GET_CODE (y))
4152     return 0;
4153
4154   switch (code)
4155     {
4156     case PC:
4157     case CC0:
4158     case ADDR_VEC:
4159     case ADDR_DIFF_VEC:
4160       return 0;
4161
4162     case CONST_INT:
4163       return INTVAL (x) == INTVAL (y);
4164
4165     case LABEL_REF:
4166       /* We can't assume nonlocal labels have their following insns yet.  */
4167       if (LABEL_REF_NONLOCAL_P (x) || LABEL_REF_NONLOCAL_P (y))
4168         return XEXP (x, 0) == XEXP (y, 0);
4169
4170       /* Two label-refs are equivalent if they point at labels
4171          in the same position in the instruction stream.  */
4172       return (next_real_insn (XEXP (x, 0))
4173               == next_real_insn (XEXP (y, 0)));
4174
4175     case SYMBOL_REF:
4176       return XSTR (x, 0) == XSTR (y, 0);
4177     }
4178
4179   /* (MULT:SI x y) and (MULT:HI x y) are NOT equivalent.  */
4180
4181   if (GET_MODE (x) != GET_MODE (y))
4182     return 0;
4183
4184   /* For commutative operations, the RTX match if the operand match in any
4185      order.  Also handle the simple binary and unary cases without a loop.  */
4186   if (code == EQ || code == NE || GET_RTX_CLASS (code) == 'c')
4187     return ((rtx_renumbered_equal_p (XEXP (x, 0), XEXP (y, 0))
4188              && rtx_renumbered_equal_p (XEXP (x, 1), XEXP (y, 1)))
4189             || (rtx_renumbered_equal_p (XEXP (x, 0), XEXP (y, 1))
4190                 && rtx_renumbered_equal_p (XEXP (x, 1), XEXP (y, 0))));
4191   else if (GET_RTX_CLASS (code) == '<' || GET_RTX_CLASS (code) == '2')
4192     return (rtx_renumbered_equal_p (XEXP (x, 0), XEXP (y, 0))
4193             && rtx_renumbered_equal_p (XEXP (x, 1), XEXP (y, 1)));
4194   else if (GET_RTX_CLASS (code) == '1')
4195     return rtx_renumbered_equal_p (XEXP (x, 0), XEXP (y, 0));
4196
4197   /* Compare the elements.  If any pair of corresponding elements
4198      fail to match, return 0 for the whole things.  */
4199
4200   fmt = GET_RTX_FORMAT (code);
4201   for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
4202     {
4203       register int j;
4204       switch (fmt[i])
4205         {
4206         case 'w':
4207           if (XWINT (x, i) != XWINT (y, i))
4208             return 0;
4209           break;
4210
4211         case 'i':
4212           if (XINT (x, i) != XINT (y, i))
4213             return 0;
4214           break;
4215
4216         case 's':
4217           if (strcmp (XSTR (x, i), XSTR (y, i)))
4218             return 0;
4219           break;
4220
4221         case 'e':
4222           if (! rtx_renumbered_equal_p (XEXP (x, i), XEXP (y, i)))
4223             return 0;
4224           break;
4225
4226         case 'u':
4227           if (XEXP (x, i) != XEXP (y, i))
4228             return 0;
4229           /* fall through.  */
4230         case '0':
4231           break;
4232
4233         case 'E':
4234           if (XVECLEN (x, i) != XVECLEN (y, i))
4235             return 0;
4236           for (j = XVECLEN (x, i) - 1; j >= 0; j--)
4237             if (!rtx_renumbered_equal_p (XVECEXP (x, i, j), XVECEXP (y, i, j)))
4238               return 0;
4239           break;
4240
4241         default:
4242           abort ();
4243         }
4244     }
4245   return 1;
4246 }
4247 \f
4248 /* If X is a hard register or equivalent to one or a subregister of one,
4249    return the hard register number.  If X is a pseudo register that was not
4250    assigned a hard register, return the pseudo register number.  Otherwise,
4251    return -1.  Any rtx is valid for X.  */
4252
4253 int
4254 true_regnum (x)
4255      rtx x;
4256 {
4257   if (GET_CODE (x) == REG)
4258     {
4259       if (REGNO (x) >= FIRST_PSEUDO_REGISTER && reg_renumber[REGNO (x)] >= 0)
4260         return reg_renumber[REGNO (x)];
4261       return REGNO (x);
4262     }
4263   if (GET_CODE (x) == SUBREG)
4264     {
4265       int base = true_regnum (SUBREG_REG (x));
4266       if (base >= 0 && base < FIRST_PSEUDO_REGISTER)
4267         return SUBREG_WORD (x) + base;
4268     }
4269   return -1;
4270 }
4271 \f
4272 /* Optimize code of the form:
4273
4274         for (x = a[i]; x; ...)
4275           ...
4276         for (x = a[i]; x; ...)
4277           ...
4278       foo:
4279
4280    Loop optimize will change the above code into
4281
4282         if (x = a[i])
4283           for (;;)
4284              { ...; if (! (x = ...)) break; }
4285         if (x = a[i])
4286           for (;;)
4287              { ...; if (! (x = ...)) break; }
4288       foo:
4289
4290    In general, if the first test fails, the program can branch
4291    directly to `foo' and skip the second try which is doomed to fail.
4292    We run this after loop optimization and before flow analysis.  */
4293    
4294 /* When comparing the insn patterns, we track the fact that different
4295    pseudo-register numbers may have been used in each computation.
4296    The following array stores an equivalence -- same_regs[I] == J means
4297    that pseudo register I was used in the first set of tests in a context
4298    where J was used in the second set.  We also count the number of such
4299    pending equivalences.  If nonzero, the expressions really aren't the
4300    same.  */
4301
4302 static int *same_regs;
4303
4304 static int num_same_regs;
4305
4306 /* Track any registers modified between the target of the first jump and
4307    the second jump.  They never compare equal.  */
4308
4309 static char *modified_regs;
4310
4311 /* Record if memory was modified.  */
4312
4313 static int modified_mem;
4314
4315 /* Called via note_stores on each insn between the target of the first 
4316    branch and the second branch.  It marks any changed registers.  */
4317
4318 static void
4319 mark_modified_reg (dest, x)
4320      rtx dest;
4321      rtx x;
4322 {
4323   int regno, i;
4324
4325   if (GET_CODE (dest) == SUBREG)
4326     dest = SUBREG_REG (dest);
4327
4328   if (GET_CODE (dest) == MEM)
4329     modified_mem = 1;
4330
4331   if (GET_CODE (dest) != REG)
4332     return;
4333
4334   regno = REGNO (dest);
4335   if (regno >= FIRST_PSEUDO_REGISTER)
4336     modified_regs[regno] = 1;
4337   else
4338     for (i = 0; i < HARD_REGNO_NREGS (regno, GET_MODE (dest)); i++)
4339       modified_regs[regno + i] = 1;
4340 }
4341
4342 /* F is the first insn in the chain of insns.  */
4343    
4344 void
4345 thread_jumps (f, max_reg, flag_before_loop)
4346      rtx f;
4347      int max_reg;
4348      int flag_before_loop;
4349 {
4350   /* Basic algorithm is to find a conditional branch,
4351      the label it may branch to, and the branch after
4352      that label.  If the two branches test the same condition,
4353      walk back from both branch paths until the insn patterns
4354      differ, or code labels are hit.  If we make it back to
4355      the target of the first branch, then we know that the first branch
4356      will either always succeed or always fail depending on the relative
4357      senses of the two branches.  So adjust the first branch accordingly
4358      in this case.  */
4359      
4360   rtx label, b1, b2, t1, t2;
4361   enum rtx_code code1, code2;
4362   rtx b1op0, b1op1, b2op0, b2op1;
4363   int changed = 1;
4364   int i;
4365   int *all_reset;
4366
4367   /* Allocate register tables and quick-reset table.  */
4368   modified_regs = (char *) alloca (max_reg * sizeof (char));
4369   same_regs = (int *) alloca (max_reg * sizeof (int));
4370   all_reset = (int *) alloca (max_reg * sizeof (int));
4371   for (i = 0; i < max_reg; i++)
4372     all_reset[i] = -1;
4373     
4374   while (changed)
4375     {
4376       changed = 0;
4377
4378       for (b1 = f; b1; b1 = NEXT_INSN (b1))
4379         {
4380           /* Get to a candidate branch insn.  */
4381           if (GET_CODE (b1) != JUMP_INSN
4382               || ! condjump_p (b1) || simplejump_p (b1)
4383               || JUMP_LABEL (b1) == 0)
4384             continue;
4385
4386           bzero (modified_regs, max_reg * sizeof (char));
4387           modified_mem = 0;
4388
4389           bcopy ((char *) all_reset, (char *) same_regs,
4390                  max_reg * sizeof (int));
4391           num_same_regs = 0;
4392
4393           label = JUMP_LABEL (b1);
4394
4395           /* Look for a branch after the target.  Record any registers and
4396              memory modified between the target and the branch.  Stop when we
4397              get to a label since we can't know what was changed there.  */
4398           for (b2 = NEXT_INSN (label); b2; b2 = NEXT_INSN (b2))
4399             {
4400               if (GET_CODE (b2) == CODE_LABEL)
4401                 break;
4402
4403               else if (GET_CODE (b2) == JUMP_INSN)
4404                 {
4405                   /* If this is an unconditional jump and is the only use of
4406                      its target label, we can follow it.  */
4407                   if (simplejump_p (b2)
4408                       && JUMP_LABEL (b2) != 0
4409                       && LABEL_NUSES (JUMP_LABEL (b2)) == 1)
4410                     {
4411                       b2 = JUMP_LABEL (b2);
4412                       continue;
4413                     }
4414                   else
4415                     break;
4416                 }
4417
4418               if (GET_CODE (b2) != CALL_INSN && GET_CODE (b2) != INSN)
4419                 continue;
4420
4421               if (GET_CODE (b2) == CALL_INSN)
4422                 {
4423                   modified_mem = 1;
4424                   for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
4425                     if (call_used_regs[i] && ! fixed_regs[i]
4426                         && i != STACK_POINTER_REGNUM
4427                         && i != FRAME_POINTER_REGNUM
4428                         && i != HARD_FRAME_POINTER_REGNUM
4429                         && i != ARG_POINTER_REGNUM)
4430                       modified_regs[i] = 1;
4431                 }
4432
4433               note_stores (PATTERN (b2), mark_modified_reg);
4434             }
4435
4436           /* Check the next candidate branch insn from the label
4437              of the first.  */
4438           if (b2 == 0
4439               || GET_CODE (b2) != JUMP_INSN
4440               || b2 == b1
4441               || ! condjump_p (b2)
4442               || simplejump_p (b2))
4443             continue;
4444
4445           /* Get the comparison codes and operands, reversing the
4446              codes if appropriate.  If we don't have comparison codes,
4447              we can't do anything.  */
4448           b1op0 = XEXP (XEXP (SET_SRC (PATTERN (b1)), 0), 0);
4449           b1op1 = XEXP (XEXP (SET_SRC (PATTERN (b1)), 0), 1);
4450           code1 = GET_CODE (XEXP (SET_SRC (PATTERN (b1)), 0));
4451           if (XEXP (SET_SRC (PATTERN (b1)), 1) == pc_rtx)
4452             code1 = reverse_condition (code1);
4453
4454           b2op0 = XEXP (XEXP (SET_SRC (PATTERN (b2)), 0), 0);
4455           b2op1 = XEXP (XEXP (SET_SRC (PATTERN (b2)), 0), 1);
4456           code2 = GET_CODE (XEXP (SET_SRC (PATTERN (b2)), 0));
4457           if (XEXP (SET_SRC (PATTERN (b2)), 1) == pc_rtx)
4458             code2 = reverse_condition (code2);
4459
4460           /* If they test the same things and knowing that B1 branches
4461              tells us whether or not B2 branches, check if we
4462              can thread the branch.  */
4463           if (rtx_equal_for_thread_p (b1op0, b2op0, b2)
4464               && rtx_equal_for_thread_p (b1op1, b2op1, b2)
4465               && (comparison_dominates_p (code1, code2)
4466                   || comparison_dominates_p (code1, reverse_condition (code2))))
4467             {
4468               t1 = prev_nonnote_insn (b1);
4469               t2 = prev_nonnote_insn (b2);
4470               
4471               while (t1 != 0 && t2 != 0)
4472                 {
4473                   if (t2 == label)
4474                     {
4475                       /* We have reached the target of the first branch.
4476                          If there are no pending register equivalents,
4477                          we know that this branch will either always
4478                          succeed (if the senses of the two branches are
4479                          the same) or always fail (if not).  */
4480                       rtx new_label;
4481
4482                       if (num_same_regs != 0)
4483                         break;
4484
4485                       if (comparison_dominates_p (code1, code2))
4486                         new_label = JUMP_LABEL (b2);
4487                       else
4488                         new_label = get_label_after (b2);
4489
4490                       if (JUMP_LABEL (b1) != new_label)
4491                         {
4492                           rtx prev = PREV_INSN (new_label);
4493
4494                           if (flag_before_loop
4495                               && NOTE_LINE_NUMBER (prev) == NOTE_INSN_LOOP_BEG)
4496                             {
4497                               /* Don't thread to the loop label.  If a loop
4498                                  label is reused, loop optimization will
4499                                  be disabled for that loop.  */
4500                               new_label = gen_label_rtx ();
4501                               emit_label_after (new_label, PREV_INSN (prev));
4502                             }
4503                           changed |= redirect_jump (b1, new_label);
4504                         }
4505                       break;
4506                     }
4507                     
4508                   /* If either of these is not a normal insn (it might be
4509                      a JUMP_INSN, CALL_INSN, or CODE_LABEL) we fail.  (NOTEs
4510                      have already been skipped above.)  Similarly, fail
4511                      if the insns are different.  */
4512                   if (GET_CODE (t1) != INSN || GET_CODE (t2) != INSN
4513                       || recog_memoized (t1) != recog_memoized (t2)
4514                       || ! rtx_equal_for_thread_p (PATTERN (t1),
4515                                                    PATTERN (t2), t2))
4516                     break;
4517                     
4518                   t1 = prev_nonnote_insn (t1);
4519                   t2 = prev_nonnote_insn (t2);
4520                 }
4521             }
4522         }
4523     }
4524 }
4525 \f
4526 /* This is like RTX_EQUAL_P except that it knows about our handling of
4527    possibly equivalent registers and knows to consider volatile and
4528    modified objects as not equal.
4529    
4530    YINSN is the insn containing Y.  */
4531
4532 int
4533 rtx_equal_for_thread_p (x, y, yinsn)
4534      rtx x, y;
4535      rtx yinsn;
4536 {
4537   register int i;
4538   register int j;
4539   register enum rtx_code code;
4540   register char *fmt;
4541
4542   code = GET_CODE (x);
4543   /* Rtx's of different codes cannot be equal.  */
4544   if (code != GET_CODE (y))
4545     return 0;
4546
4547   /* (MULT:SI x y) and (MULT:HI x y) are NOT equivalent.
4548      (REG:SI x) and (REG:HI x) are NOT equivalent.  */
4549
4550   if (GET_MODE (x) != GET_MODE (y))
4551     return 0;
4552
4553   /* For floating-point, consider everything unequal.  This is a bit
4554      pessimistic, but this pass would only rarely do anything for FP
4555      anyway.  */
4556   if (TARGET_FLOAT_FORMAT == IEEE_FLOAT_FORMAT
4557       && FLOAT_MODE_P (GET_MODE (x)) && ! flag_fast_math)
4558     return 0;
4559
4560   /* For commutative operations, the RTX match if the operand match in any
4561      order.  Also handle the simple binary and unary cases without a loop.  */
4562   if (code == EQ || code == NE || GET_RTX_CLASS (code) == 'c')
4563     return ((rtx_equal_for_thread_p (XEXP (x, 0), XEXP (y, 0), yinsn)
4564              && rtx_equal_for_thread_p (XEXP (x, 1), XEXP (y, 1), yinsn))
4565             || (rtx_equal_for_thread_p (XEXP (x, 0), XEXP (y, 1), yinsn)
4566                 && rtx_equal_for_thread_p (XEXP (x, 1), XEXP (y, 0), yinsn)));
4567   else if (GET_RTX_CLASS (code) == '<' || GET_RTX_CLASS (code) == '2')
4568     return (rtx_equal_for_thread_p (XEXP (x, 0), XEXP (y, 0), yinsn)
4569             && rtx_equal_for_thread_p (XEXP (x, 1), XEXP (y, 1), yinsn));
4570   else if (GET_RTX_CLASS (code) == '1')
4571     return rtx_equal_for_thread_p (XEXP (x, 0), XEXP (y, 0), yinsn);
4572
4573   /* Handle special-cases first.  */
4574   switch (code)
4575     {
4576     case REG:
4577       if (REGNO (x) == REGNO (y) && ! modified_regs[REGNO (x)])
4578         return 1;
4579
4580       /* If neither is user variable or hard register, check for possible
4581          equivalence.  */
4582       if (REG_USERVAR_P (x) || REG_USERVAR_P (y)
4583           || REGNO (x) < FIRST_PSEUDO_REGISTER
4584           || REGNO (y) < FIRST_PSEUDO_REGISTER)
4585         return 0;
4586
4587       if (same_regs[REGNO (x)] == -1)
4588         {
4589           same_regs[REGNO (x)] = REGNO (y);
4590           num_same_regs++;
4591
4592           /* If this is the first time we are seeing a register on the `Y'
4593              side, see if it is the last use.  If not, we can't thread the 
4594              jump, so mark it as not equivalent.  */
4595           if (regno_last_uid[REGNO (y)] != INSN_UID (yinsn))
4596             return 0;
4597
4598           return 1;
4599         }
4600       else
4601         return (same_regs[REGNO (x)] == REGNO (y));
4602
4603       break;
4604
4605     case MEM:
4606       /* If memory modified or either volatile, not equivalent.
4607          Else, check address.  */
4608       if (modified_mem || MEM_VOLATILE_P (x) || MEM_VOLATILE_P (y))
4609         return 0;
4610
4611       return rtx_equal_for_thread_p (XEXP (x, 0), XEXP (y, 0), yinsn);
4612
4613     case ASM_INPUT:
4614       if (MEM_VOLATILE_P (x) || MEM_VOLATILE_P (y))
4615         return 0;
4616
4617       break;
4618
4619     case SET:
4620       /* Cancel a pending `same_regs' if setting equivalenced registers.
4621          Then process source.  */
4622       if (GET_CODE (SET_DEST (x)) == REG
4623           && GET_CODE (SET_DEST (y)) == REG)
4624         {
4625           if (same_regs[REGNO (SET_DEST (x))] == REGNO (SET_DEST (y)))
4626             {
4627               same_regs[REGNO (SET_DEST (x))] = -1;
4628               num_same_regs--;
4629             }
4630           else if (REGNO (SET_DEST (x)) != REGNO (SET_DEST (y)))
4631             return 0;
4632         }
4633       else
4634         if (rtx_equal_for_thread_p (SET_DEST (x), SET_DEST (y), yinsn) == 0)
4635           return 0;
4636
4637       return rtx_equal_for_thread_p (SET_SRC (x), SET_SRC (y), yinsn);
4638
4639     case LABEL_REF:
4640       return XEXP (x, 0) == XEXP (y, 0);
4641
4642     case SYMBOL_REF:
4643       return XSTR (x, 0) == XSTR (y, 0);
4644     }
4645
4646   if (x == y)
4647     return 1;
4648
4649   fmt = GET_RTX_FORMAT (code);
4650   for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
4651     {
4652       switch (fmt[i])
4653         {
4654         case 'w':
4655           if (XWINT (x, i) != XWINT (y, i))
4656             return 0;
4657           break;
4658
4659         case 'n':
4660         case 'i':
4661           if (XINT (x, i) != XINT (y, i))
4662             return 0;
4663           break;
4664
4665         case 'V':
4666         case 'E':
4667           /* Two vectors must have the same length.  */
4668           if (XVECLEN (x, i) != XVECLEN (y, i))
4669             return 0;
4670
4671           /* And the corresponding elements must match.  */
4672           for (j = 0; j < XVECLEN (x, i); j++)
4673             if (rtx_equal_for_thread_p (XVECEXP (x, i, j),
4674                                         XVECEXP (y, i, j), yinsn) == 0)
4675               return 0;
4676           break;
4677
4678         case 'e':
4679           if (rtx_equal_for_thread_p (XEXP (x, i), XEXP (y, i), yinsn) == 0)
4680             return 0;
4681           break;
4682
4683         case 'S':
4684         case 's':
4685           if (strcmp (XSTR (x, i), XSTR (y, i)))
4686             return 0;
4687           break;
4688
4689         case 'u':
4690           /* These are just backpointers, so they don't matter.  */
4691           break;
4692
4693         case '0':
4694           break;
4695
4696           /* It is believed that rtx's at this level will never
4697              contain anything but integers and other rtx's,
4698              except for within LABEL_REFs and SYMBOL_REFs.  */
4699         default:
4700           abort ();
4701         }
4702     }
4703   return 1;
4704 }