dse.c (struct store_info): Remove alias_set member.
[platform/upstream/gcc.git] / gcc / dse.c
1 /* RTL dead store elimination.
2    Copyright (C) 2005-2016 Free Software Foundation, Inc.
3
4    Contributed by Richard Sandiford <rsandifor@codesourcery.com>
5    and Kenneth Zadeck <zadeck@naturalbridge.com>
6
7 This file is part of GCC.
8
9 GCC is free software; you can redistribute it and/or modify it under
10 the terms of the GNU General Public License as published by the Free
11 Software Foundation; either version 3, or (at your option) any later
12 version.
13
14 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
15 WARRANTY; without even the implied warranty of MERCHANTABILITY or
16 FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
17 for more details.
18
19 You should have received a copy of the GNU General Public License
20 along with GCC; see the file COPYING3.  If not see
21 <http://www.gnu.org/licenses/>.  */
22
23 #undef BASELINE
24
25 #include "config.h"
26 #include "system.h"
27 #include "coretypes.h"
28 #include "backend.h"
29 #include "target.h"
30 #include "rtl.h"
31 #include "tree.h"
32 #include "gimple.h"
33 #include "predict.h"
34 #include "df.h"
35 #include "tm_p.h"
36 #include "gimple-ssa.h"
37 #include "expmed.h"
38 #include "optabs.h"
39 #include "emit-rtl.h"
40 #include "recog.h"
41 #include "alias.h"
42 #include "stor-layout.h"
43 #include "cfgrtl.h"
44 #include "cselib.h"
45 #include "tree-pass.h"
46 #include "explow.h"
47 #include "expr.h"
48 #include "dbgcnt.h"
49 #include "params.h"
50 #include "rtl-iter.h"
51 #include "cfgcleanup.h"
52
53 /* This file contains three techniques for performing Dead Store
54    Elimination (dse).
55
56    * The first technique performs dse locally on any base address.  It
57    is based on the cselib which is a local value numbering technique.
58    This technique is local to a basic block but deals with a fairly
59    general addresses.
60
61    * The second technique performs dse globally but is restricted to
62    base addresses that are either constant or are relative to the
63    frame_pointer.
64
65    * The third technique, (which is only done after register allocation)
66    processes the spill slots.  This differs from the second
67    technique because it takes advantage of the fact that spilling is
68    completely free from the effects of aliasing.
69
70    Logically, dse is a backwards dataflow problem.  A store can be
71    deleted if it if cannot be reached in the backward direction by any
72    use of the value being stored.  However, the local technique uses a
73    forwards scan of the basic block because cselib requires that the
74    block be processed in that order.
75
76    The pass is logically broken into 7 steps:
77
78    0) Initialization.
79
80    1) The local algorithm, as well as scanning the insns for the two
81    global algorithms.
82
83    2) Analysis to see if the global algs are necessary.  In the case
84    of stores base on a constant address, there must be at least two
85    stores to that address, to make it possible to delete some of the
86    stores.  In the case of stores off of the frame or spill related
87    stores, only one store to an address is necessary because those
88    stores die at the end of the function.
89
90    3) Set up the global dataflow equations based on processing the
91    info parsed in the first step.
92
93    4) Solve the dataflow equations.
94
95    5) Delete the insns that the global analysis has indicated are
96    unnecessary.
97
98    6) Delete insns that store the same value as preceding store
99    where the earlier store couldn't be eliminated.
100
101    7) Cleanup.
102
103    This step uses cselib and canon_rtx to build the largest expression
104    possible for each address.  This pass is a forwards pass through
105    each basic block.  From the point of view of the global technique,
106    the first pass could examine a block in either direction.  The
107    forwards ordering is to accommodate cselib.
108
109    We make a simplifying assumption: addresses fall into four broad
110    categories:
111
112    1) base has rtx_varies_p == false, offset is constant.
113    2) base has rtx_varies_p == false, offset variable.
114    3) base has rtx_varies_p == true, offset constant.
115    4) base has rtx_varies_p == true, offset variable.
116
117    The local passes are able to process all 4 kinds of addresses.  The
118    global pass only handles 1).
119
120    The global problem is formulated as follows:
121
122      A store, S1, to address A, where A is not relative to the stack
123      frame, can be eliminated if all paths from S1 to the end of the
124      function contain another store to A before a read to A.
125
126      If the address A is relative to the stack frame, a store S2 to A
127      can be eliminated if there are no paths from S2 that reach the
128      end of the function that read A before another store to A.  In
129      this case S2 can be deleted if there are paths from S2 to the
130      end of the function that have no reads or writes to A.  This
131      second case allows stores to the stack frame to be deleted that
132      would otherwise die when the function returns.  This cannot be
133      done if stores_off_frame_dead_at_return is not true.  See the doc
134      for that variable for when this variable is false.
135
136      The global problem is formulated as a backwards set union
137      dataflow problem where the stores are the gens and reads are the
138      kills.  Set union problems are rare and require some special
139      handling given our representation of bitmaps.  A straightforward
140      implementation requires a lot of bitmaps filled with 1s.
141      These are expensive and cumbersome in our bitmap formulation so
142      care has been taken to avoid large vectors filled with 1s.  See
143      the comments in bb_info and in the dataflow confluence functions
144      for details.
145
146    There are two places for further enhancements to this algorithm:
147
148    1) The original dse which was embedded in a pass called flow also
149    did local address forwarding.  For example in
150
151    A <- r100
152    ... <- A
153
154    flow would replace the right hand side of the second insn with a
155    reference to r100.  Most of the information is available to add this
156    to this pass.  It has not done it because it is a lot of work in
157    the case that either r100 is assigned to between the first and
158    second insn and/or the second insn is a load of part of the value
159    stored by the first insn.
160
161    insn 5 in gcc.c-torture/compile/990203-1.c simple case.
162    insn 15 in gcc.c-torture/execute/20001017-2.c simple case.
163    insn 25 in gcc.c-torture/execute/20001026-1.c simple case.
164    insn 44 in gcc.c-torture/execute/20010910-1.c simple case.
165
166    2) The cleaning up of spill code is quite profitable.  It currently
167    depends on reading tea leaves and chicken entrails left by reload.
168    This pass depends on reload creating a singleton alias set for each
169    spill slot and telling the next dse pass which of these alias sets
170    are the singletons.  Rather than analyze the addresses of the
171    spills, dse's spill processing just does analysis of the loads and
172    stores that use those alias sets.  There are three cases where this
173    falls short:
174
175      a) Reload sometimes creates the slot for one mode of access, and
176      then inserts loads and/or stores for a smaller mode.  In this
177      case, the current code just punts on the slot.  The proper thing
178      to do is to back out and use one bit vector position for each
179      byte of the entity associated with the slot.  This depends on
180      KNOWING that reload always generates the accesses for each of the
181      bytes in some canonical (read that easy to understand several
182      passes after reload happens) way.
183
184      b) Reload sometimes decides that spill slot it allocated was not
185      large enough for the mode and goes back and allocates more slots
186      with the same mode and alias set.  The backout in this case is a
187      little more graceful than (a).  In this case the slot is unmarked
188      as being a spill slot and if final address comes out to be based
189      off the frame pointer, the global algorithm handles this slot.
190
191      c) For any pass that may prespill, there is currently no
192      mechanism to tell the dse pass that the slot being used has the
193      special properties that reload uses.  It may be that all that is
194      required is to have those passes make the same calls that reload
195      does, assuming that the alias sets can be manipulated in the same
196      way.  */
197
198 /* There are limits to the size of constant offsets we model for the
199    global problem.  There are certainly test cases, that exceed this
200    limit, however, it is unlikely that there are important programs
201    that really have constant offsets this size.  */
202 #define MAX_OFFSET (64 * 1024)
203
204 /* Obstack for the DSE dataflow bitmaps.  We don't want to put these
205    on the default obstack because these bitmaps can grow quite large
206    (~2GB for the small (!) test case of PR54146) and we'll hold on to
207    all that memory until the end of the compiler run.
208    As a bonus, delete_tree_live_info can destroy all the bitmaps by just
209    releasing the whole obstack.  */
210 static bitmap_obstack dse_bitmap_obstack;
211
212 /* Obstack for other data.  As for above: Kinda nice to be able to
213    throw it all away at the end in one big sweep.  */
214 static struct obstack dse_obstack;
215
216 /* Scratch bitmap for cselib's cselib_expand_value_rtx.  */
217 static bitmap scratch = NULL;
218
219 struct insn_info_type;
220
221 /* This structure holds information about a candidate store.  */
222 struct store_info
223 {
224
225   /* False means this is a clobber.  */
226   bool is_set;
227
228   /* False if a single HOST_WIDE_INT bitmap is used for positions_needed.  */
229   bool is_large;
230
231   /* The id of the mem group of the base address.  If rtx_varies_p is
232      true, this is -1.  Otherwise, it is the index into the group
233      table.  */
234   int group_id;
235
236   /* This is the cselib value.  */
237   cselib_val *cse_base;
238
239   /* This canonized mem.  */
240   rtx mem;
241
242   /* Canonized MEM address for use by canon_true_dependence.  */
243   rtx mem_addr;
244
245   /* The offset of the first and byte before the last byte associated
246      with the operation.  */
247   HOST_WIDE_INT begin, end;
248
249   union
250     {
251       /* A bitmask as wide as the number of bytes in the word that
252          contains a 1 if the byte may be needed.  The store is unused if
253          all of the bits are 0.  This is used if IS_LARGE is false.  */
254       unsigned HOST_WIDE_INT small_bitmask;
255
256       struct
257         {
258           /* A bitmap with one bit per byte.  Cleared bit means the position
259              is needed.  Used if IS_LARGE is false.  */
260           bitmap bmap;
261
262           /* Number of set bits (i.e. unneeded bytes) in BITMAP.  If it is
263              equal to END - BEGIN, the whole store is unused.  */
264           int count;
265         } large;
266     } positions_needed;
267
268   /* The next store info for this insn.  */
269   struct store_info *next;
270
271   /* The right hand side of the store.  This is used if there is a
272      subsequent reload of the mems address somewhere later in the
273      basic block.  */
274   rtx rhs;
275
276   /* If rhs is or holds a constant, this contains that constant,
277      otherwise NULL.  */
278   rtx const_rhs;
279
280   /* Set if this store stores the same constant value as REDUNDANT_REASON
281      insn stored.  These aren't eliminated early, because doing that
282      might prevent the earlier larger store to be eliminated.  */
283   struct insn_info_type *redundant_reason;
284 };
285
286 /* Return a bitmask with the first N low bits set.  */
287
288 static unsigned HOST_WIDE_INT
289 lowpart_bitmask (int n)
290 {
291   unsigned HOST_WIDE_INT mask = ~(unsigned HOST_WIDE_INT) 0;
292   return mask >> (HOST_BITS_PER_WIDE_INT - n);
293 }
294
295 static object_allocator<store_info> cse_store_info_pool ("cse_store_info_pool");
296
297 static object_allocator<store_info> rtx_store_info_pool ("rtx_store_info_pool");
298
299 /* This structure holds information about a load.  These are only
300    built for rtx bases.  */
301 struct read_info_type
302 {
303   /* The id of the mem group of the base address.  */
304   int group_id;
305
306   /* The offset of the first and byte after the last byte associated
307      with the operation.  If begin == end == 0, the read did not have
308      a constant offset.  */
309   int begin, end;
310
311   /* The mem being read.  */
312   rtx mem;
313
314   /* The next read_info for this insn.  */
315   struct read_info_type *next;
316 };
317 typedef struct read_info_type *read_info_t;
318
319 static object_allocator<read_info_type> read_info_type_pool ("read_info_pool");
320
321 /* One of these records is created for each insn.  */
322
323 struct insn_info_type
324 {
325   /* Set true if the insn contains a store but the insn itself cannot
326      be deleted.  This is set if the insn is a parallel and there is
327      more than one non dead output or if the insn is in some way
328      volatile.  */
329   bool cannot_delete;
330
331   /* This field is only used by the global algorithm.  It is set true
332      if the insn contains any read of mem except for a (1).  This is
333      also set if the insn is a call or has a clobber mem.  If the insn
334      contains a wild read, the use_rec will be null.  */
335   bool wild_read;
336
337   /* This is true only for CALL instructions which could potentially read
338      any non-frame memory location. This field is used by the global
339      algorithm.  */
340   bool non_frame_wild_read;
341
342   /* This field is only used for the processing of const functions.
343      These functions cannot read memory, but they can read the stack
344      because that is where they may get their parms.  We need to be
345      this conservative because, like the store motion pass, we don't
346      consider CALL_INSN_FUNCTION_USAGE when processing call insns.
347      Moreover, we need to distinguish two cases:
348      1. Before reload (register elimination), the stores related to
349         outgoing arguments are stack pointer based and thus deemed
350         of non-constant base in this pass.  This requires special
351         handling but also means that the frame pointer based stores
352         need not be killed upon encountering a const function call.
353      2. After reload, the stores related to outgoing arguments can be
354         either stack pointer or hard frame pointer based.  This means
355         that we have no other choice than also killing all the frame
356         pointer based stores upon encountering a const function call.
357      This field is set after reload for const function calls and before
358      reload for const tail function calls on targets where arg pointer
359      is the frame pointer.  Having this set is less severe than a wild
360      read, it just means that all the frame related stores are killed
361      rather than all the stores.  */
362   bool frame_read;
363
364   /* This field is only used for the processing of const functions.
365      It is set if the insn may contain a stack pointer based store.  */
366   bool stack_pointer_based;
367
368   /* This is true if any of the sets within the store contains a
369      cselib base.  Such stores can only be deleted by the local
370      algorithm.  */
371   bool contains_cselib_groups;
372
373   /* The insn. */
374   rtx_insn *insn;
375
376   /* The list of mem sets or mem clobbers that are contained in this
377      insn.  If the insn is deletable, it contains only one mem set.
378      But it could also contain clobbers.  Insns that contain more than
379      one mem set are not deletable, but each of those mems are here in
380      order to provide info to delete other insns.  */
381   store_info *store_rec;
382
383   /* The linked list of mem uses in this insn.  Only the reads from
384      rtx bases are listed here.  The reads to cselib bases are
385      completely processed during the first scan and so are never
386      created.  */
387   read_info_t read_rec;
388
389   /* The live fixed registers.  We assume only fixed registers can
390      cause trouble by being clobbered from an expanded pattern;
391      storing only the live fixed registers (rather than all registers)
392      means less memory needs to be allocated / copied for the individual
393      stores.  */
394   regset fixed_regs_live;
395
396   /* The prev insn in the basic block.  */
397   struct insn_info_type * prev_insn;
398
399   /* The linked list of insns that are in consideration for removal in
400      the forwards pass through the basic block.  This pointer may be
401      trash as it is not cleared when a wild read occurs.  The only
402      time it is guaranteed to be correct is when the traversal starts
403      at active_local_stores.  */
404   struct insn_info_type * next_local_store;
405 };
406 typedef struct insn_info_type *insn_info_t;
407
408 static object_allocator<insn_info_type> insn_info_type_pool ("insn_info_pool");
409
410 /* The linked list of stores that are under consideration in this
411    basic block.  */
412 static insn_info_t active_local_stores;
413 static int active_local_stores_len;
414
415 struct dse_bb_info_type
416 {
417   /* Pointer to the insn info for the last insn in the block.  These
418      are linked so this is how all of the insns are reached.  During
419      scanning this is the current insn being scanned.  */
420   insn_info_t last_insn;
421
422   /* The info for the global dataflow problem.  */
423
424
425   /* This is set if the transfer function should and in the wild_read
426      bitmap before applying the kill and gen sets.  That vector knocks
427      out most of the bits in the bitmap and thus speeds up the
428      operations.  */
429   bool apply_wild_read;
430
431   /* The following 4 bitvectors hold information about which positions
432      of which stores are live or dead.  They are indexed by
433      get_bitmap_index.  */
434
435   /* The set of store positions that exist in this block before a wild read.  */
436   bitmap gen;
437
438   /* The set of load positions that exist in this block above the
439      same position of a store.  */
440   bitmap kill;
441
442   /* The set of stores that reach the top of the block without being
443      killed by a read.
444
445      Do not represent the in if it is all ones.  Note that this is
446      what the bitvector should logically be initialized to for a set
447      intersection problem.  However, like the kill set, this is too
448      expensive.  So initially, the in set will only be created for the
449      exit block and any block that contains a wild read.  */
450   bitmap in;
451
452   /* The set of stores that reach the bottom of the block from it's
453      successors.
454
455      Do not represent the in if it is all ones.  Note that this is
456      what the bitvector should logically be initialized to for a set
457      intersection problem.  However, like the kill and in set, this is
458      too expensive.  So what is done is that the confluence operator
459      just initializes the vector from one of the out sets of the
460      successors of the block.  */
461   bitmap out;
462
463   /* The following bitvector is indexed by the reg number.  It
464      contains the set of regs that are live at the current instruction
465      being processed.  While it contains info for all of the
466      registers, only the hard registers are actually examined.  It is used
467      to assure that shift and/or add sequences that are inserted do not
468      accidentally clobber live hard regs.  */
469   bitmap regs_live;
470 };
471
472 typedef struct dse_bb_info_type *bb_info_t;
473
474 static object_allocator<dse_bb_info_type> dse_bb_info_type_pool
475   ("bb_info_pool");
476
477 /* Table to hold all bb_infos.  */
478 static bb_info_t *bb_table;
479
480 /* There is a group_info for each rtx base that is used to reference
481    memory.  There are also not many of the rtx bases because they are
482    very limited in scope.  */
483
484 struct group_info
485 {
486   /* The actual base of the address.  */
487   rtx rtx_base;
488
489   /* The sequential id of the base.  This allows us to have a
490      canonical ordering of these that is not based on addresses.  */
491   int id;
492
493   /* True if there are any positions that are to be processed
494      globally.  */
495   bool process_globally;
496
497   /* True if the base of this group is either the frame_pointer or
498      hard_frame_pointer.  */
499   bool frame_related;
500
501   /* A mem wrapped around the base pointer for the group in order to do
502      read dependency.  It must be given BLKmode in order to encompass all
503      the possible offsets from the base.  */
504   rtx base_mem;
505
506   /* Canonized version of base_mem's address.  */
507   rtx canon_base_addr;
508
509   /* These two sets of two bitmaps are used to keep track of how many
510      stores are actually referencing that position from this base.  We
511      only do this for rtx bases as this will be used to assign
512      positions in the bitmaps for the global problem.  Bit N is set in
513      store1 on the first store for offset N.  Bit N is set in store2
514      for the second store to offset N.  This is all we need since we
515      only care about offsets that have two or more stores for them.
516
517      The "_n" suffix is for offsets less than 0 and the "_p" suffix is
518      for 0 and greater offsets.
519
520      There is one special case here, for stores into the stack frame,
521      we will or store1 into store2 before deciding which stores look
522      at globally.  This is because stores to the stack frame that have
523      no other reads before the end of the function can also be
524      deleted.  */
525   bitmap store1_n, store1_p, store2_n, store2_p;
526
527   /* These bitmaps keep track of offsets in this group escape this function.
528      An offset escapes if it corresponds to a named variable whose
529      addressable flag is set.  */
530   bitmap escaped_n, escaped_p;
531
532   /* The positions in this bitmap have the same assignments as the in,
533      out, gen and kill bitmaps.  This bitmap is all zeros except for
534      the positions that are occupied by stores for this group.  */
535   bitmap group_kill;
536
537   /* The offset_map is used to map the offsets from this base into
538      positions in the global bitmaps.  It is only created after all of
539      the all of stores have been scanned and we know which ones we
540      care about.  */
541   int *offset_map_n, *offset_map_p;
542   int offset_map_size_n, offset_map_size_p;
543 };
544
545 static object_allocator<group_info> group_info_pool ("rtx_group_info_pool");
546
547 /* Index into the rtx_group_vec.  */
548 static int rtx_group_next_id;
549
550
551 static vec<group_info *> rtx_group_vec;
552
553
554 /* This structure holds the set of changes that are being deferred
555    when removing read operation.  See replace_read.  */
556 struct deferred_change
557 {
558
559   /* The mem that is being replaced.  */
560   rtx *loc;
561
562   /* The reg it is being replaced with.  */
563   rtx reg;
564
565   struct deferred_change *next;
566 };
567
568 static object_allocator<deferred_change> deferred_change_pool
569   ("deferred_change_pool");
570
571 static deferred_change *deferred_change_list = NULL;
572
573 /* This is true except if cfun->stdarg -- i.e. we cannot do
574    this for vararg functions because they play games with the frame.  */
575 static bool stores_off_frame_dead_at_return;
576
577 /* Counter for stats.  */
578 static int globally_deleted;
579 static int locally_deleted;
580
581 static bitmap all_blocks;
582
583 /* Locations that are killed by calls in the global phase.  */
584 static bitmap kill_on_calls;
585
586 /* The number of bits used in the global bitmaps.  */
587 static unsigned int current_position;
588 \f
589 /*----------------------------------------------------------------------------
590    Zeroth step.
591
592    Initialization.
593 ----------------------------------------------------------------------------*/
594
595
596 /* Hashtable callbacks for maintaining the "bases" field of
597    store_group_info, given that the addresses are function invariants.  */
598
599 struct invariant_group_base_hasher : nofree_ptr_hash <group_info>
600 {
601   static inline hashval_t hash (const group_info *);
602   static inline bool equal (const group_info *, const group_info *);
603 };
604
605 inline bool
606 invariant_group_base_hasher::equal (const group_info *gi1,
607                                     const group_info *gi2)
608 {
609   return rtx_equal_p (gi1->rtx_base, gi2->rtx_base);
610 }
611
612 inline hashval_t
613 invariant_group_base_hasher::hash (const group_info *gi)
614 {
615   int do_not_record;
616   return hash_rtx (gi->rtx_base, Pmode, &do_not_record, NULL, false);
617 }
618
619 /* Tables of group_info structures, hashed by base value.  */
620 static hash_table<invariant_group_base_hasher> *rtx_group_table;
621
622
623 /* Get the GROUP for BASE.  Add a new group if it is not there.  */
624
625 static group_info *
626 get_group_info (rtx base)
627 {
628   struct group_info tmp_gi;
629   group_info *gi;
630   group_info **slot;
631
632   gcc_assert (base != NULL_RTX);
633
634   /* Find the store_base_info structure for BASE, creating a new one
635      if necessary.  */
636   tmp_gi.rtx_base = base;
637   slot = rtx_group_table->find_slot (&tmp_gi, INSERT);
638   gi = *slot;
639
640   if (gi == NULL)
641     {
642       *slot = gi = group_info_pool.allocate ();
643       gi->rtx_base = base;
644       gi->id = rtx_group_next_id++;
645       gi->base_mem = gen_rtx_MEM (BLKmode, base);
646       gi->canon_base_addr = canon_rtx (base);
647       gi->store1_n = BITMAP_ALLOC (&dse_bitmap_obstack);
648       gi->store1_p = BITMAP_ALLOC (&dse_bitmap_obstack);
649       gi->store2_n = BITMAP_ALLOC (&dse_bitmap_obstack);
650       gi->store2_p = BITMAP_ALLOC (&dse_bitmap_obstack);
651       gi->escaped_p = BITMAP_ALLOC (&dse_bitmap_obstack);
652       gi->escaped_n = BITMAP_ALLOC (&dse_bitmap_obstack);
653       gi->group_kill = BITMAP_ALLOC (&dse_bitmap_obstack);
654       gi->process_globally = false;
655       gi->frame_related =
656         (base == frame_pointer_rtx) || (base == hard_frame_pointer_rtx);
657       gi->offset_map_size_n = 0;
658       gi->offset_map_size_p = 0;
659       gi->offset_map_n = NULL;
660       gi->offset_map_p = NULL;
661       rtx_group_vec.safe_push (gi);
662     }
663
664   return gi;
665 }
666
667
668 /* Initialization of data structures.  */
669
670 static void
671 dse_step0 (void)
672 {
673   locally_deleted = 0;
674   globally_deleted = 0;
675
676   bitmap_obstack_initialize (&dse_bitmap_obstack);
677   gcc_obstack_init (&dse_obstack);
678
679   scratch = BITMAP_ALLOC (&reg_obstack);
680   kill_on_calls = BITMAP_ALLOC (&dse_bitmap_obstack);
681
682
683   rtx_group_table = new hash_table<invariant_group_base_hasher> (11);
684
685   bb_table = XNEWVEC (bb_info_t, last_basic_block_for_fn (cfun));
686   rtx_group_next_id = 0;
687
688   stores_off_frame_dead_at_return = !cfun->stdarg;
689
690   init_alias_analysis ();
691 }
692
693
694 \f
695 /*----------------------------------------------------------------------------
696    First step.
697
698    Scan all of the insns.  Any random ordering of the blocks is fine.
699    Each block is scanned in forward order to accommodate cselib which
700    is used to remove stores with non-constant bases.
701 ----------------------------------------------------------------------------*/
702
703 /* Delete all of the store_info recs from INSN_INFO.  */
704
705 static void
706 free_store_info (insn_info_t insn_info)
707 {
708   store_info *cur = insn_info->store_rec;
709   while (cur)
710     {
711       store_info *next = cur->next;
712       if (cur->is_large)
713         BITMAP_FREE (cur->positions_needed.large.bmap);
714       if (cur->cse_base)
715         cse_store_info_pool.remove (cur);
716       else
717         rtx_store_info_pool.remove (cur);
718       cur = next;
719     }
720
721   insn_info->cannot_delete = true;
722   insn_info->contains_cselib_groups = false;
723   insn_info->store_rec = NULL;
724 }
725
726 struct note_add_store_info
727 {
728   rtx_insn *first, *current;
729   regset fixed_regs_live;
730   bool failure;
731 };
732
733 /* Callback for emit_inc_dec_insn_before via note_stores.
734    Check if a register is clobbered which is live afterwards.  */
735
736 static void
737 note_add_store (rtx loc, const_rtx expr ATTRIBUTE_UNUSED, void *data)
738 {
739   rtx_insn *insn;
740   note_add_store_info *info = (note_add_store_info *) data;
741
742   if (!REG_P (loc))
743     return;
744
745   /* If this register is referenced by the current or an earlier insn,
746      that's OK.  E.g. this applies to the register that is being incremented
747      with this addition.  */
748   for (insn = info->first;
749        insn != NEXT_INSN (info->current);
750        insn = NEXT_INSN (insn))
751     if (reg_referenced_p (loc, PATTERN (insn)))
752       return;
753
754   /* If we come here, we have a clobber of a register that's only OK
755      if that register is not live.  If we don't have liveness information
756      available, fail now.  */
757   if (!info->fixed_regs_live)
758     {
759       info->failure = true;
760       return;
761     }
762   /* Now check if this is a live fixed register.  */
763   unsigned int end_regno = END_REGNO (loc);
764   for (unsigned int regno = REGNO (loc); regno < end_regno; ++regno)
765     if (REGNO_REG_SET_P (info->fixed_regs_live, regno))
766       info->failure = true;
767 }
768
769 /* Callback for for_each_inc_dec that emits an INSN that sets DEST to
770    SRC + SRCOFF before insn ARG.  */
771
772 static int
773 emit_inc_dec_insn_before (rtx mem ATTRIBUTE_UNUSED,
774                           rtx op ATTRIBUTE_UNUSED,
775                           rtx dest, rtx src, rtx srcoff, void *arg)
776 {
777   insn_info_t insn_info = (insn_info_t) arg;
778   rtx_insn *insn = insn_info->insn, *new_insn, *cur;
779   note_add_store_info info;
780
781   /* We can reuse all operands without copying, because we are about
782      to delete the insn that contained it.  */
783   if (srcoff)
784     {
785       start_sequence ();
786       emit_insn (gen_add3_insn (dest, src, srcoff));
787       new_insn = get_insns ();
788       end_sequence ();
789     }
790   else
791     new_insn = gen_move_insn (dest, src);
792   info.first = new_insn;
793   info.fixed_regs_live = insn_info->fixed_regs_live;
794   info.failure = false;
795   for (cur = new_insn; cur; cur = NEXT_INSN (cur))
796     {
797       info.current = cur;
798       note_stores (PATTERN (cur), note_add_store, &info);
799     }
800
801   /* If a failure was flagged above, return 1 so that for_each_inc_dec will
802      return it immediately, communicating the failure to its caller.  */
803   if (info.failure)
804     return 1;
805
806   emit_insn_before (new_insn, insn);
807
808   return 0;
809 }
810
811 /* Before we delete INSN_INFO->INSN, make sure that the auto inc/dec, if it
812    is there, is split into a separate insn.
813    Return true on success (or if there was nothing to do), false on failure.  */
814
815 static bool
816 check_for_inc_dec_1 (insn_info_t insn_info)
817 {
818   rtx_insn *insn = insn_info->insn;
819   rtx note = find_reg_note (insn, REG_INC, NULL_RTX);
820   if (note)
821     return for_each_inc_dec (PATTERN (insn), emit_inc_dec_insn_before,
822                              insn_info) == 0;
823   return true;
824 }
825
826
827 /* Entry point for postreload.  If you work on reload_cse, or you need this
828    anywhere else, consider if you can provide register liveness information
829    and add a parameter to this function so that it can be passed down in
830    insn_info.fixed_regs_live.  */
831 bool
832 check_for_inc_dec (rtx_insn *insn)
833 {
834   insn_info_type insn_info;
835   rtx note;
836
837   insn_info.insn = insn;
838   insn_info.fixed_regs_live = NULL;
839   note = find_reg_note (insn, REG_INC, NULL_RTX);
840   if (note)
841     return for_each_inc_dec (PATTERN (insn), emit_inc_dec_insn_before,
842                              &insn_info) == 0;
843   return true;
844 }
845
846 /* Delete the insn and free all of the fields inside INSN_INFO.  */
847
848 static void
849 delete_dead_store_insn (insn_info_t insn_info)
850 {
851   read_info_t read_info;
852
853   if (!dbg_cnt (dse))
854     return;
855
856   if (!check_for_inc_dec_1 (insn_info))
857     return;
858   if (dump_file && (dump_flags & TDF_DETAILS))
859     fprintf (dump_file, "Locally deleting insn %d\n",
860              INSN_UID (insn_info->insn));
861
862   free_store_info (insn_info);
863   read_info = insn_info->read_rec;
864
865   while (read_info)
866     {
867       read_info_t next = read_info->next;
868       read_info_type_pool.remove (read_info);
869       read_info = next;
870     }
871   insn_info->read_rec = NULL;
872
873   delete_insn (insn_info->insn);
874   locally_deleted++;
875   insn_info->insn = NULL;
876
877   insn_info->wild_read = false;
878 }
879
880 /* Return whether DECL, a local variable, can possibly escape the current
881    function scope.  */
882
883 static bool
884 local_variable_can_escape (tree decl)
885 {
886   if (TREE_ADDRESSABLE (decl))
887     return true;
888
889   /* If this is a partitioned variable, we need to consider all the variables
890      in the partition.  This is necessary because a store into one of them can
891      be replaced with a store into another and this may not change the outcome
892      of the escape analysis.  */
893   if (cfun->gimple_df->decls_to_pointers != NULL)
894     {
895       tree *namep = cfun->gimple_df->decls_to_pointers->get (decl);
896       if (namep)
897         return TREE_ADDRESSABLE (*namep);
898     }
899
900   return false;
901 }
902
903 /* Return whether EXPR can possibly escape the current function scope.  */
904
905 static bool
906 can_escape (tree expr)
907 {
908   tree base;
909   if (!expr)
910     return true;
911   base = get_base_address (expr);
912   if (DECL_P (base)
913       && !may_be_aliased (base)
914       && !(TREE_CODE (base) == VAR_DECL
915            && !DECL_EXTERNAL (base)
916            && !TREE_STATIC (base)
917            && local_variable_can_escape (base)))
918     return false;
919   return true;
920 }
921
922 /* Set the store* bitmaps offset_map_size* fields in GROUP based on
923    OFFSET and WIDTH.  */
924
925 static void
926 set_usage_bits (group_info *group, HOST_WIDE_INT offset, HOST_WIDE_INT width,
927                 tree expr)
928 {
929   HOST_WIDE_INT i;
930   bool expr_escapes = can_escape (expr);
931   if (offset > -MAX_OFFSET && offset + width < MAX_OFFSET)
932     for (i=offset; i<offset+width; i++)
933       {
934         bitmap store1;
935         bitmap store2;
936         bitmap escaped;
937         int ai;
938         if (i < 0)
939           {
940             store1 = group->store1_n;
941             store2 = group->store2_n;
942             escaped = group->escaped_n;
943             ai = -i;
944           }
945         else
946           {
947             store1 = group->store1_p;
948             store2 = group->store2_p;
949             escaped = group->escaped_p;
950             ai = i;
951           }
952
953         if (!bitmap_set_bit (store1, ai))
954           bitmap_set_bit (store2, ai);
955         else
956           {
957             if (i < 0)
958               {
959                 if (group->offset_map_size_n < ai)
960                   group->offset_map_size_n = ai;
961               }
962             else
963               {
964                 if (group->offset_map_size_p < ai)
965                   group->offset_map_size_p = ai;
966               }
967           }
968         if (expr_escapes)
969           bitmap_set_bit (escaped, ai);
970       }
971 }
972
973 static void
974 reset_active_stores (void)
975 {
976   active_local_stores = NULL;
977   active_local_stores_len = 0;
978 }
979
980 /* Free all READ_REC of the LAST_INSN of BB_INFO.  */
981
982 static void
983 free_read_records (bb_info_t bb_info)
984 {
985   insn_info_t insn_info = bb_info->last_insn;
986   read_info_t *ptr = &insn_info->read_rec;
987   while (*ptr)
988     {
989       read_info_t next = (*ptr)->next;
990       read_info_type_pool.remove (*ptr);
991       *ptr = next;
992     }
993 }
994
995 /* Set the BB_INFO so that the last insn is marked as a wild read.  */
996
997 static void
998 add_wild_read (bb_info_t bb_info)
999 {
1000   insn_info_t insn_info = bb_info->last_insn;
1001   insn_info->wild_read = true;
1002   free_read_records (bb_info);
1003   reset_active_stores ();
1004 }
1005
1006 /* Set the BB_INFO so that the last insn is marked as a wild read of
1007    non-frame locations.  */
1008
1009 static void
1010 add_non_frame_wild_read (bb_info_t bb_info)
1011 {
1012   insn_info_t insn_info = bb_info->last_insn;
1013   insn_info->non_frame_wild_read = true;
1014   free_read_records (bb_info);
1015   reset_active_stores ();
1016 }
1017
1018 /* Return true if X is a constant or one of the registers that behave
1019    as a constant over the life of a function.  This is equivalent to
1020    !rtx_varies_p for memory addresses.  */
1021
1022 static bool
1023 const_or_frame_p (rtx x)
1024 {
1025   if (CONSTANT_P (x))
1026     return true;
1027
1028   if (GET_CODE (x) == REG)
1029     {
1030       /* Note that we have to test for the actual rtx used for the frame
1031          and arg pointers and not just the register number in case we have
1032          eliminated the frame and/or arg pointer and are using it
1033          for pseudos.  */
1034       if (x == frame_pointer_rtx || x == hard_frame_pointer_rtx
1035           /* The arg pointer varies if it is not a fixed register.  */
1036           || (x == arg_pointer_rtx && fixed_regs[ARG_POINTER_REGNUM])
1037           || x == pic_offset_table_rtx)
1038         return true;
1039       return false;
1040     }
1041
1042   return false;
1043 }
1044
1045 /* Take all reasonable action to put the address of MEM into the form
1046    that we can do analysis on.
1047
1048    The gold standard is to get the address into the form: address +
1049    OFFSET where address is something that rtx_varies_p considers a
1050    constant.  When we can get the address in this form, we can do
1051    global analysis on it.  Note that for constant bases, address is
1052    not actually returned, only the group_id.  The address can be
1053    obtained from that.
1054
1055    If that fails, we try cselib to get a value we can at least use
1056    locally.  If that fails we return false.
1057
1058    The GROUP_ID is set to -1 for cselib bases and the index of the
1059    group for non_varying bases.
1060
1061    FOR_READ is true if this is a mem read and false if not.  */
1062
1063 static bool
1064 canon_address (rtx mem,
1065                int *group_id,
1066                HOST_WIDE_INT *offset,
1067                cselib_val **base)
1068 {
1069   machine_mode address_mode = get_address_mode (mem);
1070   rtx mem_address = XEXP (mem, 0);
1071   rtx expanded_address, address;
1072   int expanded;
1073
1074   cselib_lookup (mem_address, address_mode, 1, GET_MODE (mem));
1075
1076   if (dump_file && (dump_flags & TDF_DETAILS))
1077     {
1078       fprintf (dump_file, "  mem: ");
1079       print_inline_rtx (dump_file, mem_address, 0);
1080       fprintf (dump_file, "\n");
1081     }
1082
1083   /* First see if just canon_rtx (mem_address) is const or frame,
1084      if not, try cselib_expand_value_rtx and call canon_rtx on that.  */
1085   address = NULL_RTX;
1086   for (expanded = 0; expanded < 2; expanded++)
1087     {
1088       if (expanded)
1089         {
1090           /* Use cselib to replace all of the reg references with the full
1091              expression.  This will take care of the case where we have
1092
1093              r_x = base + offset;
1094              val = *r_x;
1095
1096              by making it into
1097
1098              val = *(base + offset);  */
1099
1100           expanded_address = cselib_expand_value_rtx (mem_address,
1101                                                       scratch, 5);
1102
1103           /* If this fails, just go with the address from first
1104              iteration.  */
1105           if (!expanded_address)
1106             break;
1107         }
1108       else
1109         expanded_address = mem_address;
1110
1111       /* Split the address into canonical BASE + OFFSET terms.  */
1112       address = canon_rtx (expanded_address);
1113
1114       *offset = 0;
1115
1116       if (dump_file && (dump_flags & TDF_DETAILS))
1117         {
1118           if (expanded)
1119             {
1120               fprintf (dump_file, "\n   after cselib_expand address: ");
1121               print_inline_rtx (dump_file, expanded_address, 0);
1122               fprintf (dump_file, "\n");
1123             }
1124
1125           fprintf (dump_file, "\n   after canon_rtx address: ");
1126           print_inline_rtx (dump_file, address, 0);
1127           fprintf (dump_file, "\n");
1128         }
1129
1130       if (GET_CODE (address) == CONST)
1131         address = XEXP (address, 0);
1132
1133       if (GET_CODE (address) == PLUS
1134           && CONST_INT_P (XEXP (address, 1)))
1135         {
1136           *offset = INTVAL (XEXP (address, 1));
1137           address = XEXP (address, 0);
1138         }
1139
1140       if (ADDR_SPACE_GENERIC_P (MEM_ADDR_SPACE (mem))
1141           && const_or_frame_p (address))
1142         {
1143           group_info *group = get_group_info (address);
1144
1145           if (dump_file && (dump_flags & TDF_DETAILS))
1146             fprintf (dump_file, "  gid=%d offset=%d \n",
1147                      group->id, (int)*offset);
1148           *base = NULL;
1149           *group_id = group->id;
1150           return true;
1151         }
1152     }
1153
1154   *base = cselib_lookup (address, address_mode, true, GET_MODE (mem));
1155   *group_id = -1;
1156
1157   if (*base == NULL)
1158     {
1159       if (dump_file && (dump_flags & TDF_DETAILS))
1160         fprintf (dump_file, " no cselib val - should be a wild read.\n");
1161       return false;
1162     }
1163   if (dump_file && (dump_flags & TDF_DETAILS))
1164     fprintf (dump_file, "  varying cselib base=%u:%u offset = %d\n",
1165              (*base)->uid, (*base)->hash, (int)*offset);
1166   return true;
1167 }
1168
1169
1170 /* Clear the rhs field from the active_local_stores array.  */
1171
1172 static void
1173 clear_rhs_from_active_local_stores (void)
1174 {
1175   insn_info_t ptr = active_local_stores;
1176
1177   while (ptr)
1178     {
1179       store_info *store_info = ptr->store_rec;
1180       /* Skip the clobbers.  */
1181       while (!store_info->is_set)
1182         store_info = store_info->next;
1183
1184       store_info->rhs = NULL;
1185       store_info->const_rhs = NULL;
1186
1187       ptr = ptr->next_local_store;
1188     }
1189 }
1190
1191
1192 /* Mark byte POS bytes from the beginning of store S_INFO as unneeded.  */
1193
1194 static inline void
1195 set_position_unneeded (store_info *s_info, int pos)
1196 {
1197   if (__builtin_expect (s_info->is_large, false))
1198     {
1199       if (bitmap_set_bit (s_info->positions_needed.large.bmap, pos))
1200         s_info->positions_needed.large.count++;
1201     }
1202   else
1203     s_info->positions_needed.small_bitmask
1204       &= ~(((unsigned HOST_WIDE_INT) 1) << pos);
1205 }
1206
1207 /* Mark the whole store S_INFO as unneeded.  */
1208
1209 static inline void
1210 set_all_positions_unneeded (store_info *s_info)
1211 {
1212   if (__builtin_expect (s_info->is_large, false))
1213     {
1214       int pos, end = s_info->end - s_info->begin;
1215       for (pos = 0; pos < end; pos++)
1216         bitmap_set_bit (s_info->positions_needed.large.bmap, pos);
1217       s_info->positions_needed.large.count = end;
1218     }
1219   else
1220     s_info->positions_needed.small_bitmask = (unsigned HOST_WIDE_INT) 0;
1221 }
1222
1223 /* Return TRUE if any bytes from S_INFO store are needed.  */
1224
1225 static inline bool
1226 any_positions_needed_p (store_info *s_info)
1227 {
1228   if (__builtin_expect (s_info->is_large, false))
1229     return (s_info->positions_needed.large.count
1230             < s_info->end - s_info->begin);
1231   else
1232     return (s_info->positions_needed.small_bitmask
1233             != (unsigned HOST_WIDE_INT) 0);
1234 }
1235
1236 /* Return TRUE if all bytes START through START+WIDTH-1 from S_INFO
1237    store are needed.  */
1238
1239 static inline bool
1240 all_positions_needed_p (store_info *s_info, int start, int width)
1241 {
1242   if (__builtin_expect (s_info->is_large, false))
1243     {
1244       int end = start + width;
1245       while (start < end)
1246         if (bitmap_bit_p (s_info->positions_needed.large.bmap, start++))
1247           return false;
1248       return true;
1249     }
1250   else
1251     {
1252       unsigned HOST_WIDE_INT mask = lowpart_bitmask (width) << start;
1253       return (s_info->positions_needed.small_bitmask & mask) == mask;
1254     }
1255 }
1256
1257
1258 static rtx get_stored_val (store_info *, machine_mode, HOST_WIDE_INT,
1259                            HOST_WIDE_INT, basic_block, bool);
1260
1261
1262 /* BODY is an instruction pattern that belongs to INSN.  Return 1 if
1263    there is a candidate store, after adding it to the appropriate
1264    local store group if so.  */
1265
1266 static int
1267 record_store (rtx body, bb_info_t bb_info)
1268 {
1269   rtx mem, rhs, const_rhs, mem_addr;
1270   HOST_WIDE_INT offset = 0;
1271   HOST_WIDE_INT width = 0;
1272   insn_info_t insn_info = bb_info->last_insn;
1273   store_info *store_info = NULL;
1274   int group_id;
1275   cselib_val *base = NULL;
1276   insn_info_t ptr, last, redundant_reason;
1277   bool store_is_unused;
1278
1279   if (GET_CODE (body) != SET && GET_CODE (body) != CLOBBER)
1280     return 0;
1281
1282   mem = SET_DEST (body);
1283
1284   /* If this is not used, then this cannot be used to keep the insn
1285      from being deleted.  On the other hand, it does provide something
1286      that can be used to prove that another store is dead.  */
1287   store_is_unused
1288     = (find_reg_note (insn_info->insn, REG_UNUSED, mem) != NULL);
1289
1290   /* Check whether that value is a suitable memory location.  */
1291   if (!MEM_P (mem))
1292     {
1293       /* If the set or clobber is unused, then it does not effect our
1294          ability to get rid of the entire insn.  */
1295       if (!store_is_unused)
1296         insn_info->cannot_delete = true;
1297       return 0;
1298     }
1299
1300   /* At this point we know mem is a mem. */
1301   if (GET_MODE (mem) == BLKmode)
1302     {
1303       if (GET_CODE (XEXP (mem, 0)) == SCRATCH)
1304         {
1305           if (dump_file && (dump_flags & TDF_DETAILS))
1306             fprintf (dump_file, " adding wild read for (clobber (mem:BLK (scratch))\n");
1307           add_wild_read (bb_info);
1308           insn_info->cannot_delete = true;
1309           return 0;
1310         }
1311       /* Handle (set (mem:BLK (addr) [... S36 ...]) (const_int 0))
1312          as memset (addr, 0, 36);  */
1313       else if (!MEM_SIZE_KNOWN_P (mem)
1314                || MEM_SIZE (mem) <= 0
1315                || MEM_SIZE (mem) > MAX_OFFSET
1316                || GET_CODE (body) != SET
1317                || !CONST_INT_P (SET_SRC (body)))
1318         {
1319           if (!store_is_unused)
1320             {
1321               /* If the set or clobber is unused, then it does not effect our
1322                  ability to get rid of the entire insn.  */
1323               insn_info->cannot_delete = true;
1324               clear_rhs_from_active_local_stores ();
1325             }
1326           return 0;
1327         }
1328     }
1329
1330   /* We can still process a volatile mem, we just cannot delete it.  */
1331   if (MEM_VOLATILE_P (mem))
1332     insn_info->cannot_delete = true;
1333
1334   if (!canon_address (mem, &group_id, &offset, &base))
1335     {
1336       clear_rhs_from_active_local_stores ();
1337       return 0;
1338     }
1339
1340   if (GET_MODE (mem) == BLKmode)
1341     width = MEM_SIZE (mem);
1342   else
1343     width = GET_MODE_SIZE (GET_MODE (mem));
1344
1345   if (group_id >= 0)
1346     {
1347       /* In the restrictive case where the base is a constant or the
1348          frame pointer we can do global analysis.  */
1349
1350       group_info *group
1351         = rtx_group_vec[group_id];
1352       tree expr = MEM_EXPR (mem);
1353
1354       store_info = rtx_store_info_pool.allocate ();
1355       set_usage_bits (group, offset, width, expr);
1356
1357       if (dump_file && (dump_flags & TDF_DETAILS))
1358         fprintf (dump_file, " processing const base store gid=%d[%d..%d)\n",
1359                  group_id, (int)offset, (int)(offset+width));
1360     }
1361   else
1362     {
1363       if (may_be_sp_based_p (XEXP (mem, 0)))
1364         insn_info->stack_pointer_based = true;
1365       insn_info->contains_cselib_groups = true;
1366
1367       store_info = cse_store_info_pool.allocate ();
1368       group_id = -1;
1369
1370       if (dump_file && (dump_flags & TDF_DETAILS))
1371         fprintf (dump_file, " processing cselib store [%d..%d)\n",
1372                  (int)offset, (int)(offset+width));
1373     }
1374
1375   const_rhs = rhs = NULL_RTX;
1376   if (GET_CODE (body) == SET
1377       /* No place to keep the value after ra.  */
1378       && !reload_completed
1379       && (REG_P (SET_SRC (body))
1380           || GET_CODE (SET_SRC (body)) == SUBREG
1381           || CONSTANT_P (SET_SRC (body)))
1382       && !MEM_VOLATILE_P (mem)
1383       /* Sometimes the store and reload is used for truncation and
1384          rounding.  */
1385       && !(FLOAT_MODE_P (GET_MODE (mem)) && (flag_float_store)))
1386     {
1387       rhs = SET_SRC (body);
1388       if (CONSTANT_P (rhs))
1389         const_rhs = rhs;
1390       else if (body == PATTERN (insn_info->insn))
1391         {
1392           rtx tem = find_reg_note (insn_info->insn, REG_EQUAL, NULL_RTX);
1393           if (tem && CONSTANT_P (XEXP (tem, 0)))
1394             const_rhs = XEXP (tem, 0);
1395         }
1396       if (const_rhs == NULL_RTX && REG_P (rhs))
1397         {
1398           rtx tem = cselib_expand_value_rtx (rhs, scratch, 5);
1399
1400           if (tem && CONSTANT_P (tem))
1401             const_rhs = tem;
1402         }
1403     }
1404
1405   /* Check to see if this stores causes some other stores to be
1406      dead.  */
1407   ptr = active_local_stores;
1408   last = NULL;
1409   redundant_reason = NULL;
1410   mem = canon_rtx (mem);
1411
1412   if (group_id < 0)
1413     mem_addr = base->val_rtx;
1414   else
1415     {
1416       group_info *group = rtx_group_vec[group_id];
1417       mem_addr = group->canon_base_addr;
1418     }
1419   if (offset)
1420     mem_addr = plus_constant (get_address_mode (mem), mem_addr, offset);
1421
1422   while (ptr)
1423     {
1424       insn_info_t next = ptr->next_local_store;
1425       struct store_info *s_info = ptr->store_rec;
1426       bool del = true;
1427
1428       /* Skip the clobbers. We delete the active insn if this insn
1429          shadows the set.  To have been put on the active list, it
1430          has exactly on set. */
1431       while (!s_info->is_set)
1432         s_info = s_info->next;
1433
1434       if (s_info->group_id == group_id && s_info->cse_base == base)
1435         {
1436           HOST_WIDE_INT i;
1437           if (dump_file && (dump_flags & TDF_DETAILS))
1438             fprintf (dump_file, "    trying store in insn=%d gid=%d[%d..%d)\n",
1439                      INSN_UID (ptr->insn), s_info->group_id,
1440                      (int)s_info->begin, (int)s_info->end);
1441
1442           /* Even if PTR won't be eliminated as unneeded, if both
1443              PTR and this insn store the same constant value, we might
1444              eliminate this insn instead.  */
1445           if (s_info->const_rhs
1446               && const_rhs
1447               && offset >= s_info->begin
1448               && offset + width <= s_info->end
1449               && all_positions_needed_p (s_info, offset - s_info->begin,
1450                                          width))
1451             {
1452               if (GET_MODE (mem) == BLKmode)
1453                 {
1454                   if (GET_MODE (s_info->mem) == BLKmode
1455                       && s_info->const_rhs == const_rhs)
1456                     redundant_reason = ptr;
1457                 }
1458               else if (s_info->const_rhs == const0_rtx
1459                        && const_rhs == const0_rtx)
1460                 redundant_reason = ptr;
1461               else
1462                 {
1463                   rtx val;
1464                   start_sequence ();
1465                   val = get_stored_val (s_info, GET_MODE (mem),
1466                                         offset, offset + width,
1467                                         BLOCK_FOR_INSN (insn_info->insn),
1468                                         true);
1469                   if (get_insns () != NULL)
1470                     val = NULL_RTX;
1471                   end_sequence ();
1472                   if (val && rtx_equal_p (val, const_rhs))
1473                     redundant_reason = ptr;
1474                 }
1475             }
1476
1477           for (i = MAX (offset, s_info->begin);
1478                i < offset + width && i < s_info->end;
1479                i++)
1480             set_position_unneeded (s_info, i - s_info->begin);
1481         }
1482       else if (s_info->rhs)
1483         /* Need to see if it is possible for this store to overwrite
1484            the value of store_info.  If it is, set the rhs to NULL to
1485            keep it from being used to remove a load.  */
1486         {
1487           if (canon_output_dependence (s_info->mem, true,
1488                                        mem, GET_MODE (mem),
1489                                        mem_addr))
1490             {
1491               s_info->rhs = NULL;
1492               s_info->const_rhs = NULL;
1493             }
1494         }
1495
1496       /* An insn can be deleted if every position of every one of
1497          its s_infos is zero.  */
1498       if (any_positions_needed_p (s_info))
1499         del = false;
1500
1501       if (del)
1502         {
1503           insn_info_t insn_to_delete = ptr;
1504
1505           active_local_stores_len--;
1506           if (last)
1507             last->next_local_store = ptr->next_local_store;
1508           else
1509             active_local_stores = ptr->next_local_store;
1510
1511           if (!insn_to_delete->cannot_delete)
1512             delete_dead_store_insn (insn_to_delete);
1513         }
1514       else
1515         last = ptr;
1516
1517       ptr = next;
1518     }
1519
1520   /* Finish filling in the store_info.  */
1521   store_info->next = insn_info->store_rec;
1522   insn_info->store_rec = store_info;
1523   store_info->mem = mem;
1524   store_info->mem_addr = mem_addr;
1525   store_info->cse_base = base;
1526   if (width > HOST_BITS_PER_WIDE_INT)
1527     {
1528       store_info->is_large = true;
1529       store_info->positions_needed.large.count = 0;
1530       store_info->positions_needed.large.bmap = BITMAP_ALLOC (&dse_bitmap_obstack);
1531     }
1532   else
1533     {
1534       store_info->is_large = false;
1535       store_info->positions_needed.small_bitmask = lowpart_bitmask (width);
1536     }
1537   store_info->group_id = group_id;
1538   store_info->begin = offset;
1539   store_info->end = offset + width;
1540   store_info->is_set = GET_CODE (body) == SET;
1541   store_info->rhs = rhs;
1542   store_info->const_rhs = const_rhs;
1543   store_info->redundant_reason = redundant_reason;
1544
1545   /* If this is a clobber, we return 0.  We will only be able to
1546      delete this insn if there is only one store USED store, but we
1547      can use the clobber to delete other stores earlier.  */
1548   return store_info->is_set ? 1 : 0;
1549 }
1550
1551
1552 static void
1553 dump_insn_info (const char * start, insn_info_t insn_info)
1554 {
1555   fprintf (dump_file, "%s insn=%d %s\n", start,
1556            INSN_UID (insn_info->insn),
1557            insn_info->store_rec ? "has store" : "naked");
1558 }
1559
1560
1561 /* If the modes are different and the value's source and target do not
1562    line up, we need to extract the value from lower part of the rhs of
1563    the store, shift it, and then put it into a form that can be shoved
1564    into the read_insn.  This function generates a right SHIFT of a
1565    value that is at least ACCESS_SIZE bytes wide of READ_MODE.  The
1566    shift sequence is returned or NULL if we failed to find a
1567    shift.  */
1568
1569 static rtx
1570 find_shift_sequence (int access_size,
1571                      store_info *store_info,
1572                      machine_mode read_mode,
1573                      int shift, bool speed, bool require_cst)
1574 {
1575   machine_mode store_mode = GET_MODE (store_info->mem);
1576   machine_mode new_mode;
1577   rtx read_reg = NULL;
1578
1579   /* Some machines like the x86 have shift insns for each size of
1580      operand.  Other machines like the ppc or the ia-64 may only have
1581      shift insns that shift values within 32 or 64 bit registers.
1582      This loop tries to find the smallest shift insn that will right
1583      justify the value we want to read but is available in one insn on
1584      the machine.  */
1585
1586   for (new_mode = smallest_mode_for_size (access_size * BITS_PER_UNIT,
1587                                           MODE_INT);
1588        GET_MODE_BITSIZE (new_mode) <= BITS_PER_WORD;
1589        new_mode = GET_MODE_WIDER_MODE (new_mode))
1590     {
1591       rtx target, new_reg, new_lhs;
1592       rtx_insn *shift_seq, *insn;
1593       int cost;
1594
1595       /* If a constant was stored into memory, try to simplify it here,
1596          otherwise the cost of the shift might preclude this optimization
1597          e.g. at -Os, even when no actual shift will be needed.  */
1598       if (store_info->const_rhs)
1599         {
1600           unsigned int byte = subreg_lowpart_offset (new_mode, store_mode);
1601           rtx ret = simplify_subreg (new_mode, store_info->const_rhs,
1602                                      store_mode, byte);
1603           if (ret && CONSTANT_P (ret))
1604             {
1605               ret = simplify_const_binary_operation (LSHIFTRT, new_mode,
1606                                                      ret, GEN_INT (shift));
1607               if (ret && CONSTANT_P (ret))
1608                 {
1609                   byte = subreg_lowpart_offset (read_mode, new_mode);
1610                   ret = simplify_subreg (read_mode, ret, new_mode, byte);
1611                   if (ret && CONSTANT_P (ret)
1612                       && (set_src_cost (ret, read_mode, speed)
1613                           <= COSTS_N_INSNS (1)))
1614                     return ret;
1615                 }
1616             }
1617         }
1618
1619       if (require_cst)
1620         return NULL_RTX;
1621
1622       /* Try a wider mode if truncating the store mode to NEW_MODE
1623          requires a real instruction.  */
1624       if (GET_MODE_BITSIZE (new_mode) < GET_MODE_BITSIZE (store_mode)
1625           && !TRULY_NOOP_TRUNCATION_MODES_P (new_mode, store_mode))
1626         continue;
1627
1628       /* Also try a wider mode if the necessary punning is either not
1629          desirable or not possible.  */
1630       if (!CONSTANT_P (store_info->rhs)
1631           && !MODES_TIEABLE_P (new_mode, store_mode))
1632         continue;
1633
1634       new_reg = gen_reg_rtx (new_mode);
1635
1636       start_sequence ();
1637
1638       /* In theory we could also check for an ashr.  Ian Taylor knows
1639          of one dsp where the cost of these two was not the same.  But
1640          this really is a rare case anyway.  */
1641       target = expand_binop (new_mode, lshr_optab, new_reg,
1642                              GEN_INT (shift), new_reg, 1, OPTAB_DIRECT);
1643
1644       shift_seq = get_insns ();
1645       end_sequence ();
1646
1647       if (target != new_reg || shift_seq == NULL)
1648         continue;
1649
1650       cost = 0;
1651       for (insn = shift_seq; insn != NULL_RTX; insn = NEXT_INSN (insn))
1652         if (INSN_P (insn))
1653           cost += insn_rtx_cost (PATTERN (insn), speed);
1654
1655       /* The computation up to here is essentially independent
1656          of the arguments and could be precomputed.  It may
1657          not be worth doing so.  We could precompute if
1658          worthwhile or at least cache the results.  The result
1659          technically depends on both SHIFT and ACCESS_SIZE,
1660          but in practice the answer will depend only on ACCESS_SIZE.  */
1661
1662       if (cost > COSTS_N_INSNS (1))
1663         continue;
1664
1665       new_lhs = extract_low_bits (new_mode, store_mode,
1666                                   copy_rtx (store_info->rhs));
1667       if (new_lhs == NULL_RTX)
1668         continue;
1669
1670       /* We found an acceptable shift.  Generate a move to
1671          take the value from the store and put it into the
1672          shift pseudo, then shift it, then generate another
1673          move to put in into the target of the read.  */
1674       emit_move_insn (new_reg, new_lhs);
1675       emit_insn (shift_seq);
1676       read_reg = extract_low_bits (read_mode, new_mode, new_reg);
1677       break;
1678     }
1679
1680   return read_reg;
1681 }
1682
1683
1684 /* Call back for note_stores to find the hard regs set or clobbered by
1685    insn.  Data is a bitmap of the hardregs set so far.  */
1686
1687 static void
1688 look_for_hardregs (rtx x, const_rtx pat ATTRIBUTE_UNUSED, void *data)
1689 {
1690   bitmap regs_set = (bitmap) data;
1691
1692   if (REG_P (x)
1693       && HARD_REGISTER_P (x))
1694     bitmap_set_range (regs_set, REGNO (x), REG_NREGS (x));
1695 }
1696
1697 /* Helper function for replace_read and record_store.
1698    Attempt to return a value stored in STORE_INFO, from READ_BEGIN
1699    to one before READ_END bytes read in READ_MODE.  Return NULL
1700    if not successful.  If REQUIRE_CST is true, return always constant.  */
1701
1702 static rtx
1703 get_stored_val (store_info *store_info, machine_mode read_mode,
1704                 HOST_WIDE_INT read_begin, HOST_WIDE_INT read_end,
1705                 basic_block bb, bool require_cst)
1706 {
1707   machine_mode store_mode = GET_MODE (store_info->mem);
1708   int shift;
1709   int access_size; /* In bytes.  */
1710   rtx read_reg;
1711
1712   /* To get here the read is within the boundaries of the write so
1713      shift will never be negative.  Start out with the shift being in
1714      bytes.  */
1715   if (store_mode == BLKmode)
1716     shift = 0;
1717   else if (BYTES_BIG_ENDIAN)
1718     shift = store_info->end - read_end;
1719   else
1720     shift = read_begin - store_info->begin;
1721
1722   access_size = shift + GET_MODE_SIZE (read_mode);
1723
1724   /* From now on it is bits.  */
1725   shift *= BITS_PER_UNIT;
1726
1727   if (shift)
1728     read_reg = find_shift_sequence (access_size, store_info, read_mode, shift,
1729                                     optimize_bb_for_speed_p (bb),
1730                                     require_cst);
1731   else if (store_mode == BLKmode)
1732     {
1733       /* The store is a memset (addr, const_val, const_size).  */
1734       gcc_assert (CONST_INT_P (store_info->rhs));
1735       store_mode = int_mode_for_mode (read_mode);
1736       if (store_mode == BLKmode)
1737         read_reg = NULL_RTX;
1738       else if (store_info->rhs == const0_rtx)
1739         read_reg = extract_low_bits (read_mode, store_mode, const0_rtx);
1740       else if (GET_MODE_BITSIZE (store_mode) > HOST_BITS_PER_WIDE_INT
1741                || BITS_PER_UNIT >= HOST_BITS_PER_WIDE_INT)
1742         read_reg = NULL_RTX;
1743       else
1744         {
1745           unsigned HOST_WIDE_INT c
1746             = INTVAL (store_info->rhs)
1747               & (((HOST_WIDE_INT) 1 << BITS_PER_UNIT) - 1);
1748           int shift = BITS_PER_UNIT;
1749           while (shift < HOST_BITS_PER_WIDE_INT)
1750             {
1751               c |= (c << shift);
1752               shift <<= 1;
1753             }
1754           read_reg = gen_int_mode (c, store_mode);
1755           read_reg = extract_low_bits (read_mode, store_mode, read_reg);
1756         }
1757     }
1758   else if (store_info->const_rhs
1759            && (require_cst
1760                || GET_MODE_CLASS (read_mode) != GET_MODE_CLASS (store_mode)))
1761     read_reg = extract_low_bits (read_mode, store_mode,
1762                                  copy_rtx (store_info->const_rhs));
1763   else
1764     read_reg = extract_low_bits (read_mode, store_mode,
1765                                  copy_rtx (store_info->rhs));
1766   if (require_cst && read_reg && !CONSTANT_P (read_reg))
1767     read_reg = NULL_RTX;
1768   return read_reg;
1769 }
1770
1771 /* Take a sequence of:
1772      A <- r1
1773      ...
1774      ... <- A
1775
1776    and change it into
1777    r2 <- r1
1778    A <- r1
1779    ...
1780    ... <- r2
1781
1782    or
1783
1784    r3 <- extract (r1)
1785    r3 <- r3 >> shift
1786    r2 <- extract (r3)
1787    ... <- r2
1788
1789    or
1790
1791    r2 <- extract (r1)
1792    ... <- r2
1793
1794    Depending on the alignment and the mode of the store and
1795    subsequent load.
1796
1797
1798    The STORE_INFO and STORE_INSN are for the store and READ_INFO
1799    and READ_INSN are for the read.  Return true if the replacement
1800    went ok.  */
1801
1802 static bool
1803 replace_read (store_info *store_info, insn_info_t store_insn,
1804               read_info_t read_info, insn_info_t read_insn, rtx *loc,
1805               bitmap regs_live)
1806 {
1807   machine_mode store_mode = GET_MODE (store_info->mem);
1808   machine_mode read_mode = GET_MODE (read_info->mem);
1809   rtx_insn *insns, *this_insn;
1810   rtx read_reg;
1811   basic_block bb;
1812
1813   if (!dbg_cnt (dse))
1814     return false;
1815
1816   /* Create a sequence of instructions to set up the read register.
1817      This sequence goes immediately before the store and its result
1818      is read by the load.
1819
1820      We need to keep this in perspective.  We are replacing a read
1821      with a sequence of insns, but the read will almost certainly be
1822      in cache, so it is not going to be an expensive one.  Thus, we
1823      are not willing to do a multi insn shift or worse a subroutine
1824      call to get rid of the read.  */
1825   if (dump_file && (dump_flags & TDF_DETAILS))
1826     fprintf (dump_file, "trying to replace %smode load in insn %d"
1827              " from %smode store in insn %d\n",
1828              GET_MODE_NAME (read_mode), INSN_UID (read_insn->insn),
1829              GET_MODE_NAME (store_mode), INSN_UID (store_insn->insn));
1830   start_sequence ();
1831   bb = BLOCK_FOR_INSN (read_insn->insn);
1832   read_reg = get_stored_val (store_info,
1833                              read_mode, read_info->begin, read_info->end,
1834                              bb, false);
1835   if (read_reg == NULL_RTX)
1836     {
1837       end_sequence ();
1838       if (dump_file && (dump_flags & TDF_DETAILS))
1839         fprintf (dump_file, " -- could not extract bits of stored value\n");
1840       return false;
1841     }
1842   /* Force the value into a new register so that it won't be clobbered
1843      between the store and the load.  */
1844   read_reg = copy_to_mode_reg (read_mode, read_reg);
1845   insns = get_insns ();
1846   end_sequence ();
1847
1848   if (insns != NULL_RTX)
1849     {
1850       /* Now we have to scan the set of new instructions to see if the
1851          sequence contains and sets of hardregs that happened to be
1852          live at this point.  For instance, this can happen if one of
1853          the insns sets the CC and the CC happened to be live at that
1854          point.  This does occasionally happen, see PR 37922.  */
1855       bitmap regs_set = BITMAP_ALLOC (&reg_obstack);
1856
1857       for (this_insn = insns; this_insn != NULL_RTX; this_insn = NEXT_INSN (this_insn))
1858         note_stores (PATTERN (this_insn), look_for_hardregs, regs_set);
1859
1860       bitmap_and_into (regs_set, regs_live);
1861       if (!bitmap_empty_p (regs_set))
1862         {
1863           if (dump_file && (dump_flags & TDF_DETAILS))
1864             {
1865               fprintf (dump_file,
1866                        "abandoning replacement because sequence clobbers live hardregs:");
1867               df_print_regset (dump_file, regs_set);
1868             }
1869
1870           BITMAP_FREE (regs_set);
1871           return false;
1872         }
1873       BITMAP_FREE (regs_set);
1874     }
1875
1876   if (validate_change (read_insn->insn, loc, read_reg, 0))
1877     {
1878       deferred_change *change = deferred_change_pool.allocate ();
1879
1880       /* Insert this right before the store insn where it will be safe
1881          from later insns that might change it before the read.  */
1882       emit_insn_before (insns, store_insn->insn);
1883
1884       /* And now for the kludge part: cselib croaks if you just
1885          return at this point.  There are two reasons for this:
1886
1887          1) Cselib has an idea of how many pseudos there are and
1888          that does not include the new ones we just added.
1889
1890          2) Cselib does not know about the move insn we added
1891          above the store_info, and there is no way to tell it
1892          about it, because it has "moved on".
1893
1894          Problem (1) is fixable with a certain amount of engineering.
1895          Problem (2) is requires starting the bb from scratch.  This
1896          could be expensive.
1897
1898          So we are just going to have to lie.  The move/extraction
1899          insns are not really an issue, cselib did not see them.  But
1900          the use of the new pseudo read_insn is a real problem because
1901          cselib has not scanned this insn.  The way that we solve this
1902          problem is that we are just going to put the mem back for now
1903          and when we are finished with the block, we undo this.  We
1904          keep a table of mems to get rid of.  At the end of the basic
1905          block we can put them back.  */
1906
1907       *loc = read_info->mem;
1908       change->next = deferred_change_list;
1909       deferred_change_list = change;
1910       change->loc = loc;
1911       change->reg = read_reg;
1912
1913       /* Get rid of the read_info, from the point of view of the
1914          rest of dse, play like this read never happened.  */
1915       read_insn->read_rec = read_info->next;
1916       read_info_type_pool.remove (read_info);
1917       if (dump_file && (dump_flags & TDF_DETAILS))
1918         {
1919           fprintf (dump_file, " -- replaced the loaded MEM with ");
1920           print_simple_rtl (dump_file, read_reg);
1921           fprintf (dump_file, "\n");
1922         }
1923       return true;
1924     }
1925   else
1926     {
1927       if (dump_file && (dump_flags & TDF_DETAILS))
1928         {
1929           fprintf (dump_file, " -- replacing the loaded MEM with ");
1930           print_simple_rtl (dump_file, read_reg);
1931           fprintf (dump_file, " led to an invalid instruction\n");
1932         }
1933       return false;
1934     }
1935 }
1936
1937 /* Check the address of MEM *LOC and kill any appropriate stores that may
1938    be active.  */
1939
1940 static void
1941 check_mem_read_rtx (rtx *loc, bb_info_t bb_info)
1942 {
1943   rtx mem = *loc, mem_addr;
1944   insn_info_t insn_info;
1945   HOST_WIDE_INT offset = 0;
1946   HOST_WIDE_INT width = 0;
1947   cselib_val *base = NULL;
1948   int group_id;
1949   read_info_t read_info;
1950
1951   insn_info = bb_info->last_insn;
1952
1953   if ((MEM_ALIAS_SET (mem) == ALIAS_SET_MEMORY_BARRIER)
1954       || (MEM_VOLATILE_P (mem)))
1955     {
1956       if (dump_file && (dump_flags & TDF_DETAILS))
1957         fprintf (dump_file, " adding wild read, volatile or barrier.\n");
1958       add_wild_read (bb_info);
1959       insn_info->cannot_delete = true;
1960       return;
1961     }
1962
1963   /* If it is reading readonly mem, then there can be no conflict with
1964      another write. */
1965   if (MEM_READONLY_P (mem))
1966     return;
1967
1968   if (!canon_address (mem, &group_id, &offset, &base))
1969     {
1970       if (dump_file && (dump_flags & TDF_DETAILS))
1971         fprintf (dump_file, " adding wild read, canon_address failure.\n");
1972       add_wild_read (bb_info);
1973       return;
1974     }
1975
1976   if (GET_MODE (mem) == BLKmode)
1977     width = -1;
1978   else
1979     width = GET_MODE_SIZE (GET_MODE (mem));
1980
1981   read_info = read_info_type_pool.allocate ();
1982   read_info->group_id = group_id;
1983   read_info->mem = mem;
1984   read_info->begin = offset;
1985   read_info->end = offset + width;
1986   read_info->next = insn_info->read_rec;
1987   insn_info->read_rec = read_info;
1988   if (group_id < 0)
1989     mem_addr = base->val_rtx;
1990   else
1991     {
1992       group_info *group = rtx_group_vec[group_id];
1993       mem_addr = group->canon_base_addr;
1994     }
1995   if (offset)
1996     mem_addr = plus_constant (get_address_mode (mem), mem_addr, offset);
1997
1998   if (group_id >= 0)
1999     {
2000       /* This is the restricted case where the base is a constant or
2001          the frame pointer and offset is a constant.  */
2002       insn_info_t i_ptr = active_local_stores;
2003       insn_info_t last = NULL;
2004
2005       if (dump_file && (dump_flags & TDF_DETAILS))
2006         {
2007           if (width == -1)
2008             fprintf (dump_file, " processing const load gid=%d[BLK]\n",
2009                      group_id);
2010           else
2011             fprintf (dump_file, " processing const load gid=%d[%d..%d)\n",
2012                      group_id, (int)offset, (int)(offset+width));
2013         }
2014
2015       while (i_ptr)
2016         {
2017           bool remove = false;
2018           store_info *store_info = i_ptr->store_rec;
2019
2020           /* Skip the clobbers.  */
2021           while (!store_info->is_set)
2022             store_info = store_info->next;
2023
2024           /* There are three cases here.  */
2025           if (store_info->group_id < 0)
2026             /* We have a cselib store followed by a read from a
2027                const base. */
2028             remove
2029               = canon_true_dependence (store_info->mem,
2030                                        GET_MODE (store_info->mem),
2031                                        store_info->mem_addr,
2032                                        mem, mem_addr);
2033
2034           else if (group_id == store_info->group_id)
2035             {
2036               /* This is a block mode load.  We may get lucky and
2037                  canon_true_dependence may save the day.  */
2038               if (width == -1)
2039                 remove
2040                   = canon_true_dependence (store_info->mem,
2041                                            GET_MODE (store_info->mem),
2042                                            store_info->mem_addr,
2043                                            mem, mem_addr);
2044
2045               /* If this read is just reading back something that we just
2046                  stored, rewrite the read.  */
2047               else
2048                 {
2049                   if (store_info->rhs
2050                       && offset >= store_info->begin
2051                       && offset + width <= store_info->end
2052                       && all_positions_needed_p (store_info,
2053                                                  offset - store_info->begin,
2054                                                  width)
2055                       && replace_read (store_info, i_ptr, read_info,
2056                                        insn_info, loc, bb_info->regs_live))
2057                     return;
2058
2059                   /* The bases are the same, just see if the offsets
2060                      overlap.  */
2061                   if ((offset < store_info->end)
2062                       && (offset + width > store_info->begin))
2063                     remove = true;
2064                 }
2065             }
2066
2067           /* else
2068              The else case that is missing here is that the
2069              bases are constant but different.  There is nothing
2070              to do here because there is no overlap.  */
2071
2072           if (remove)
2073             {
2074               if (dump_file && (dump_flags & TDF_DETAILS))
2075                 dump_insn_info ("removing from active", i_ptr);
2076
2077               active_local_stores_len--;
2078               if (last)
2079                 last->next_local_store = i_ptr->next_local_store;
2080               else
2081                 active_local_stores = i_ptr->next_local_store;
2082             }
2083           else
2084             last = i_ptr;
2085           i_ptr = i_ptr->next_local_store;
2086         }
2087     }
2088   else
2089     {
2090       insn_info_t i_ptr = active_local_stores;
2091       insn_info_t last = NULL;
2092       if (dump_file && (dump_flags & TDF_DETAILS))
2093         {
2094           fprintf (dump_file, " processing cselib load mem:");
2095           print_inline_rtx (dump_file, mem, 0);
2096           fprintf (dump_file, "\n");
2097         }
2098
2099       while (i_ptr)
2100         {
2101           bool remove = false;
2102           store_info *store_info = i_ptr->store_rec;
2103
2104           if (dump_file && (dump_flags & TDF_DETAILS))
2105             fprintf (dump_file, " processing cselib load against insn %d\n",
2106                      INSN_UID (i_ptr->insn));
2107
2108           /* Skip the clobbers.  */
2109           while (!store_info->is_set)
2110             store_info = store_info->next;
2111
2112           /* If this read is just reading back something that we just
2113              stored, rewrite the read.  */
2114           if (store_info->rhs
2115               && store_info->group_id == -1
2116               && store_info->cse_base == base
2117               && width != -1
2118               && offset >= store_info->begin
2119               && offset + width <= store_info->end
2120               && all_positions_needed_p (store_info,
2121                                          offset - store_info->begin, width)
2122               && replace_read (store_info, i_ptr,  read_info, insn_info, loc,
2123                                bb_info->regs_live))
2124             return;
2125
2126           remove = canon_true_dependence (store_info->mem,
2127                                           GET_MODE (store_info->mem),
2128                                           store_info->mem_addr,
2129                                           mem, mem_addr);
2130
2131           if (remove)
2132             {
2133               if (dump_file && (dump_flags & TDF_DETAILS))
2134                 dump_insn_info ("removing from active", i_ptr);
2135
2136               active_local_stores_len--;
2137               if (last)
2138                 last->next_local_store = i_ptr->next_local_store;
2139               else
2140                 active_local_stores = i_ptr->next_local_store;
2141             }
2142           else
2143             last = i_ptr;
2144           i_ptr = i_ptr->next_local_store;
2145         }
2146     }
2147 }
2148
2149 /* A note_uses callback in which DATA points the INSN_INFO for
2150    as check_mem_read_rtx.  Nullify the pointer if i_m_r_m_r returns
2151    true for any part of *LOC.  */
2152
2153 static void
2154 check_mem_read_use (rtx *loc, void *data)
2155 {
2156   subrtx_ptr_iterator::array_type array;
2157   FOR_EACH_SUBRTX_PTR (iter, array, loc, NONCONST)
2158     {
2159       rtx *loc = *iter;
2160       if (MEM_P (*loc))
2161         check_mem_read_rtx (loc, (bb_info_t) data);
2162     }
2163 }
2164
2165
2166 /* Get arguments passed to CALL_INSN.  Return TRUE if successful.
2167    So far it only handles arguments passed in registers.  */
2168
2169 static bool
2170 get_call_args (rtx call_insn, tree fn, rtx *args, int nargs)
2171 {
2172   CUMULATIVE_ARGS args_so_far_v;
2173   cumulative_args_t args_so_far;
2174   tree arg;
2175   int idx;
2176
2177   INIT_CUMULATIVE_ARGS (args_so_far_v, TREE_TYPE (fn), NULL_RTX, 0, 3);
2178   args_so_far = pack_cumulative_args (&args_so_far_v);
2179
2180   arg = TYPE_ARG_TYPES (TREE_TYPE (fn));
2181   for (idx = 0;
2182        arg != void_list_node && idx < nargs;
2183        arg = TREE_CHAIN (arg), idx++)
2184     {
2185       machine_mode mode = TYPE_MODE (TREE_VALUE (arg));
2186       rtx reg, link, tmp;
2187       reg = targetm.calls.function_arg (args_so_far, mode, NULL_TREE, true);
2188       if (!reg || !REG_P (reg) || GET_MODE (reg) != mode
2189           || GET_MODE_CLASS (mode) != MODE_INT)
2190         return false;
2191
2192       for (link = CALL_INSN_FUNCTION_USAGE (call_insn);
2193            link;
2194            link = XEXP (link, 1))
2195         if (GET_CODE (XEXP (link, 0)) == USE)
2196           {
2197             args[idx] = XEXP (XEXP (link, 0), 0);
2198             if (REG_P (args[idx])
2199                 && REGNO (args[idx]) == REGNO (reg)
2200                 && (GET_MODE (args[idx]) == mode
2201                     || (GET_MODE_CLASS (GET_MODE (args[idx])) == MODE_INT
2202                         && (GET_MODE_SIZE (GET_MODE (args[idx]))
2203                             <= UNITS_PER_WORD)
2204                         && (GET_MODE_SIZE (GET_MODE (args[idx]))
2205                             > GET_MODE_SIZE (mode)))))
2206               break;
2207           }
2208       if (!link)
2209         return false;
2210
2211       tmp = cselib_expand_value_rtx (args[idx], scratch, 5);
2212       if (GET_MODE (args[idx]) != mode)
2213         {
2214           if (!tmp || !CONST_INT_P (tmp))
2215             return false;
2216           tmp = gen_int_mode (INTVAL (tmp), mode);
2217         }
2218       if (tmp)
2219         args[idx] = tmp;
2220
2221       targetm.calls.function_arg_advance (args_so_far, mode, NULL_TREE, true);
2222     }
2223   if (arg != void_list_node || idx != nargs)
2224     return false;
2225   return true;
2226 }
2227
2228 /* Return a bitmap of the fixed registers contained in IN.  */
2229
2230 static bitmap
2231 copy_fixed_regs (const_bitmap in)
2232 {
2233   bitmap ret;
2234
2235   ret = ALLOC_REG_SET (NULL);
2236   bitmap_and (ret, in, fixed_reg_set_regset);
2237   return ret;
2238 }
2239
2240 /* Apply record_store to all candidate stores in INSN.  Mark INSN
2241    if some part of it is not a candidate store and assigns to a
2242    non-register target.  */
2243
2244 static void
2245 scan_insn (bb_info_t bb_info, rtx_insn *insn)
2246 {
2247   rtx body;
2248   insn_info_type *insn_info = insn_info_type_pool.allocate ();
2249   int mems_found = 0;
2250   memset (insn_info, 0, sizeof (struct insn_info_type));
2251
2252   if (dump_file && (dump_flags & TDF_DETAILS))
2253     fprintf (dump_file, "\n**scanning insn=%d\n",
2254              INSN_UID (insn));
2255
2256   insn_info->prev_insn = bb_info->last_insn;
2257   insn_info->insn = insn;
2258   bb_info->last_insn = insn_info;
2259
2260   if (DEBUG_INSN_P (insn))
2261     {
2262       insn_info->cannot_delete = true;
2263       return;
2264     }
2265
2266   /* Look at all of the uses in the insn.  */
2267   note_uses (&PATTERN (insn), check_mem_read_use, bb_info);
2268
2269   if (CALL_P (insn))
2270     {
2271       bool const_call;
2272       tree memset_call = NULL_TREE;
2273
2274       insn_info->cannot_delete = true;
2275
2276       /* Const functions cannot do anything bad i.e. read memory,
2277          however, they can read their parameters which may have
2278          been pushed onto the stack.
2279          memset and bzero don't read memory either.  */
2280       const_call = RTL_CONST_CALL_P (insn);
2281       if (!const_call)
2282         {
2283           rtx call = get_call_rtx_from (insn);
2284           if (call && GET_CODE (XEXP (XEXP (call, 0), 0)) == SYMBOL_REF)
2285             {
2286               rtx symbol = XEXP (XEXP (call, 0), 0);
2287               if (SYMBOL_REF_DECL (symbol)
2288                   && TREE_CODE (SYMBOL_REF_DECL (symbol)) == FUNCTION_DECL)
2289                 {
2290                   if ((DECL_BUILT_IN_CLASS (SYMBOL_REF_DECL (symbol))
2291                        == BUILT_IN_NORMAL
2292                        && (DECL_FUNCTION_CODE (SYMBOL_REF_DECL (symbol))
2293                            == BUILT_IN_MEMSET))
2294                       || SYMBOL_REF_DECL (symbol) == block_clear_fn)
2295                     memset_call = SYMBOL_REF_DECL (symbol);
2296                 }
2297             }
2298         }
2299       if (const_call || memset_call)
2300         {
2301           insn_info_t i_ptr = active_local_stores;
2302           insn_info_t last = NULL;
2303
2304           if (dump_file && (dump_flags & TDF_DETAILS))
2305             fprintf (dump_file, "%s call %d\n",
2306                      const_call ? "const" : "memset", INSN_UID (insn));
2307
2308           /* See the head comment of the frame_read field.  */
2309           if (reload_completed
2310               /* Tail calls are storing their arguments using
2311                  arg pointer.  If it is a frame pointer on the target,
2312                  even before reload we need to kill frame pointer based
2313                  stores.  */
2314               || (SIBLING_CALL_P (insn)
2315                   && HARD_FRAME_POINTER_IS_ARG_POINTER))
2316             insn_info->frame_read = true;
2317
2318           /* Loop over the active stores and remove those which are
2319              killed by the const function call.  */
2320           while (i_ptr)
2321             {
2322               bool remove_store = false;
2323
2324               /* The stack pointer based stores are always killed.  */
2325               if (i_ptr->stack_pointer_based)
2326                 remove_store = true;
2327
2328               /* If the frame is read, the frame related stores are killed.  */
2329               else if (insn_info->frame_read)
2330                 {
2331                   store_info *store_info = i_ptr->store_rec;
2332
2333                   /* Skip the clobbers.  */
2334                   while (!store_info->is_set)
2335                     store_info = store_info->next;
2336
2337                   if (store_info->group_id >= 0
2338                       && rtx_group_vec[store_info->group_id]->frame_related)
2339                     remove_store = true;
2340                 }
2341
2342               if (remove_store)
2343                 {
2344                   if (dump_file && (dump_flags & TDF_DETAILS))
2345                     dump_insn_info ("removing from active", i_ptr);
2346
2347                   active_local_stores_len--;
2348                   if (last)
2349                     last->next_local_store = i_ptr->next_local_store;
2350                   else
2351                     active_local_stores = i_ptr->next_local_store;
2352                 }
2353               else
2354                 last = i_ptr;
2355
2356               i_ptr = i_ptr->next_local_store;
2357             }
2358
2359           if (memset_call)
2360             {
2361               rtx args[3];
2362               if (get_call_args (insn, memset_call, args, 3)
2363                   && CONST_INT_P (args[1])
2364                   && CONST_INT_P (args[2])
2365                   && INTVAL (args[2]) > 0)
2366                 {
2367                   rtx mem = gen_rtx_MEM (BLKmode, args[0]);
2368                   set_mem_size (mem, INTVAL (args[2]));
2369                   body = gen_rtx_SET (mem, args[1]);
2370                   mems_found += record_store (body, bb_info);
2371                   if (dump_file && (dump_flags & TDF_DETAILS))
2372                     fprintf (dump_file, "handling memset as BLKmode store\n");
2373                   if (mems_found == 1)
2374                     {
2375                       if (active_local_stores_len++
2376                           >= PARAM_VALUE (PARAM_MAX_DSE_ACTIVE_LOCAL_STORES))
2377                         {
2378                           active_local_stores_len = 1;
2379                           active_local_stores = NULL;
2380                         }
2381                       insn_info->fixed_regs_live
2382                         = copy_fixed_regs (bb_info->regs_live);
2383                       insn_info->next_local_store = active_local_stores;
2384                       active_local_stores = insn_info;
2385                     }
2386                 }
2387               else
2388                 clear_rhs_from_active_local_stores ();
2389             }
2390         }
2391       else if (SIBLING_CALL_P (insn) && reload_completed)
2392         /* Arguments for a sibling call that are pushed to memory are passed
2393            using the incoming argument pointer of the current function.  After
2394            reload that might be (and likely is) frame pointer based.  */
2395         add_wild_read (bb_info);
2396       else
2397         /* Every other call, including pure functions, may read any memory
2398            that is not relative to the frame.  */
2399         add_non_frame_wild_read (bb_info);
2400
2401       return;
2402     }
2403
2404   /* Assuming that there are sets in these insns, we cannot delete
2405      them.  */
2406   if ((GET_CODE (PATTERN (insn)) == CLOBBER)
2407       || volatile_refs_p (PATTERN (insn))
2408       || (!cfun->can_delete_dead_exceptions && !insn_nothrow_p (insn))
2409       || (RTX_FRAME_RELATED_P (insn))
2410       || find_reg_note (insn, REG_FRAME_RELATED_EXPR, NULL_RTX))
2411     insn_info->cannot_delete = true;
2412
2413   body = PATTERN (insn);
2414   if (GET_CODE (body) == PARALLEL)
2415     {
2416       int i;
2417       for (i = 0; i < XVECLEN (body, 0); i++)
2418         mems_found += record_store (XVECEXP (body, 0, i), bb_info);
2419     }
2420   else
2421     mems_found += record_store (body, bb_info);
2422
2423   if (dump_file && (dump_flags & TDF_DETAILS))
2424     fprintf (dump_file, "mems_found = %d, cannot_delete = %s\n",
2425              mems_found, insn_info->cannot_delete ? "true" : "false");
2426
2427   /* If we found some sets of mems, add it into the active_local_stores so
2428      that it can be locally deleted if found dead or used for
2429      replace_read and redundant constant store elimination.  Otherwise mark
2430      it as cannot delete.  This simplifies the processing later.  */
2431   if (mems_found == 1)
2432     {
2433       if (active_local_stores_len++
2434           >= PARAM_VALUE (PARAM_MAX_DSE_ACTIVE_LOCAL_STORES))
2435         {
2436           active_local_stores_len = 1;
2437           active_local_stores = NULL;
2438         }
2439       insn_info->fixed_regs_live = copy_fixed_regs (bb_info->regs_live);
2440       insn_info->next_local_store = active_local_stores;
2441       active_local_stores = insn_info;
2442     }
2443   else
2444     insn_info->cannot_delete = true;
2445 }
2446
2447
2448 /* Remove BASE from the set of active_local_stores.  This is a
2449    callback from cselib that is used to get rid of the stores in
2450    active_local_stores.  */
2451
2452 static void
2453 remove_useless_values (cselib_val *base)
2454 {
2455   insn_info_t insn_info = active_local_stores;
2456   insn_info_t last = NULL;
2457
2458   while (insn_info)
2459     {
2460       store_info *store_info = insn_info->store_rec;
2461       bool del = false;
2462
2463       /* If ANY of the store_infos match the cselib group that is
2464          being deleted, then the insn can not be deleted.  */
2465       while (store_info)
2466         {
2467           if ((store_info->group_id == -1)
2468               && (store_info->cse_base == base))
2469             {
2470               del = true;
2471               break;
2472             }
2473           store_info = store_info->next;
2474         }
2475
2476       if (del)
2477         {
2478           active_local_stores_len--;
2479           if (last)
2480             last->next_local_store = insn_info->next_local_store;
2481           else
2482             active_local_stores = insn_info->next_local_store;
2483           free_store_info (insn_info);
2484         }
2485       else
2486         last = insn_info;
2487
2488       insn_info = insn_info->next_local_store;
2489     }
2490 }
2491
2492
2493 /* Do all of step 1.  */
2494
2495 static void
2496 dse_step1 (void)
2497 {
2498   basic_block bb;
2499   bitmap regs_live = BITMAP_ALLOC (&reg_obstack);
2500
2501   cselib_init (0);
2502   all_blocks = BITMAP_ALLOC (NULL);
2503   bitmap_set_bit (all_blocks, ENTRY_BLOCK);
2504   bitmap_set_bit (all_blocks, EXIT_BLOCK);
2505
2506   FOR_ALL_BB_FN (bb, cfun)
2507     {
2508       insn_info_t ptr;
2509       bb_info_t bb_info = dse_bb_info_type_pool.allocate ();
2510
2511       memset (bb_info, 0, sizeof (dse_bb_info_type));
2512       bitmap_set_bit (all_blocks, bb->index);
2513       bb_info->regs_live = regs_live;
2514
2515       bitmap_copy (regs_live, DF_LR_IN (bb));
2516       df_simulate_initialize_forwards (bb, regs_live);
2517
2518       bb_table[bb->index] = bb_info;
2519       cselib_discard_hook = remove_useless_values;
2520
2521       if (bb->index >= NUM_FIXED_BLOCKS)
2522         {
2523           rtx_insn *insn;
2524
2525           active_local_stores = NULL;
2526           active_local_stores_len = 0;
2527           cselib_clear_table ();
2528
2529           /* Scan the insns.  */
2530           FOR_BB_INSNS (bb, insn)
2531             {
2532               if (INSN_P (insn))
2533                 scan_insn (bb_info, insn);
2534               cselib_process_insn (insn);
2535               if (INSN_P (insn))
2536                 df_simulate_one_insn_forwards (bb, insn, regs_live);
2537             }
2538
2539           /* This is something of a hack, because the global algorithm
2540              is supposed to take care of the case where stores go dead
2541              at the end of the function.  However, the global
2542              algorithm must take a more conservative view of block
2543              mode reads than the local alg does.  So to get the case
2544              where you have a store to the frame followed by a non
2545              overlapping block more read, we look at the active local
2546              stores at the end of the function and delete all of the
2547              frame and spill based ones.  */
2548           if (stores_off_frame_dead_at_return
2549               && (EDGE_COUNT (bb->succs) == 0
2550                   || (single_succ_p (bb)
2551                       && single_succ (bb) == EXIT_BLOCK_PTR_FOR_FN (cfun)
2552                       && ! crtl->calls_eh_return)))
2553             {
2554               insn_info_t i_ptr = active_local_stores;
2555               while (i_ptr)
2556                 {
2557                   store_info *store_info = i_ptr->store_rec;
2558
2559                   /* Skip the clobbers.  */
2560                   while (!store_info->is_set)
2561                     store_info = store_info->next;
2562                   if (store_info->group_id >= 0)
2563                     {
2564                       group_info *group = rtx_group_vec[store_info->group_id];
2565                       if (group->frame_related && !i_ptr->cannot_delete)
2566                         delete_dead_store_insn (i_ptr);
2567                     }
2568
2569                   i_ptr = i_ptr->next_local_store;
2570                 }
2571             }
2572
2573           /* Get rid of the loads that were discovered in
2574              replace_read.  Cselib is finished with this block.  */
2575           while (deferred_change_list)
2576             {
2577               deferred_change *next = deferred_change_list->next;
2578
2579               /* There is no reason to validate this change.  That was
2580                  done earlier.  */
2581               *deferred_change_list->loc = deferred_change_list->reg;
2582               deferred_change_pool.remove (deferred_change_list);
2583               deferred_change_list = next;
2584             }
2585
2586           /* Get rid of all of the cselib based store_infos in this
2587              block and mark the containing insns as not being
2588              deletable.  */
2589           ptr = bb_info->last_insn;
2590           while (ptr)
2591             {
2592               if (ptr->contains_cselib_groups)
2593                 {
2594                   store_info *s_info = ptr->store_rec;
2595                   while (s_info && !s_info->is_set)
2596                     s_info = s_info->next;
2597                   if (s_info
2598                       && s_info->redundant_reason
2599                       && s_info->redundant_reason->insn
2600                       && !ptr->cannot_delete)
2601                     {
2602                       if (dump_file && (dump_flags & TDF_DETAILS))
2603                         fprintf (dump_file, "Locally deleting insn %d "
2604                                             "because insn %d stores the "
2605                                             "same value and couldn't be "
2606                                             "eliminated\n",
2607                                  INSN_UID (ptr->insn),
2608                                  INSN_UID (s_info->redundant_reason->insn));
2609                       delete_dead_store_insn (ptr);
2610                     }
2611                   free_store_info (ptr);
2612                 }
2613               else
2614                 {
2615                   store_info *s_info;
2616
2617                   /* Free at least positions_needed bitmaps.  */
2618                   for (s_info = ptr->store_rec; s_info; s_info = s_info->next)
2619                     if (s_info->is_large)
2620                       {
2621                         BITMAP_FREE (s_info->positions_needed.large.bmap);
2622                         s_info->is_large = false;
2623                       }
2624                 }
2625               ptr = ptr->prev_insn;
2626             }
2627
2628           cse_store_info_pool.release ();
2629         }
2630       bb_info->regs_live = NULL;
2631     }
2632
2633   BITMAP_FREE (regs_live);
2634   cselib_finish ();
2635   rtx_group_table->empty ();
2636 }
2637
2638 \f
2639 /*----------------------------------------------------------------------------
2640    Second step.
2641
2642    Assign each byte position in the stores that we are going to
2643    analyze globally to a position in the bitmaps.  Returns true if
2644    there are any bit positions assigned.
2645 ----------------------------------------------------------------------------*/
2646
2647 static void
2648 dse_step2_init (void)
2649 {
2650   unsigned int i;
2651   group_info *group;
2652
2653   FOR_EACH_VEC_ELT (rtx_group_vec, i, group)
2654     {
2655       /* For all non stack related bases, we only consider a store to
2656          be deletable if there are two or more stores for that
2657          position.  This is because it takes one store to make the
2658          other store redundant.  However, for the stores that are
2659          stack related, we consider them if there is only one store
2660          for the position.  We do this because the stack related
2661          stores can be deleted if their is no read between them and
2662          the end of the function.
2663
2664          To make this work in the current framework, we take the stack
2665          related bases add all of the bits from store1 into store2.
2666          This has the effect of making the eligible even if there is
2667          only one store.   */
2668
2669       if (stores_off_frame_dead_at_return && group->frame_related)
2670         {
2671           bitmap_ior_into (group->store2_n, group->store1_n);
2672           bitmap_ior_into (group->store2_p, group->store1_p);
2673           if (dump_file && (dump_flags & TDF_DETAILS))
2674             fprintf (dump_file, "group %d is frame related ", i);
2675         }
2676
2677       group->offset_map_size_n++;
2678       group->offset_map_n = XOBNEWVEC (&dse_obstack, int,
2679                                        group->offset_map_size_n);
2680       group->offset_map_size_p++;
2681       group->offset_map_p = XOBNEWVEC (&dse_obstack, int,
2682                                        group->offset_map_size_p);
2683       group->process_globally = false;
2684       if (dump_file && (dump_flags & TDF_DETAILS))
2685         {
2686           fprintf (dump_file, "group %d(%d+%d): ", i,
2687                    (int)bitmap_count_bits (group->store2_n),
2688                    (int)bitmap_count_bits (group->store2_p));
2689           bitmap_print (dump_file, group->store2_n, "n ", " ");
2690           bitmap_print (dump_file, group->store2_p, "p ", "\n");
2691         }
2692     }
2693 }
2694
2695
2696 /* Init the offset tables.  */
2697
2698 static bool
2699 dse_step2 (void)
2700 {
2701   unsigned int i;
2702   group_info *group;
2703   /* Position 0 is unused because 0 is used in the maps to mean
2704      unused.  */
2705   current_position = 1;
2706   FOR_EACH_VEC_ELT (rtx_group_vec, i, group)
2707     {
2708       bitmap_iterator bi;
2709       unsigned int j;
2710
2711       memset (group->offset_map_n, 0, sizeof (int) * group->offset_map_size_n);
2712       memset (group->offset_map_p, 0, sizeof (int) * group->offset_map_size_p);
2713       bitmap_clear (group->group_kill);
2714
2715       EXECUTE_IF_SET_IN_BITMAP (group->store2_n, 0, j, bi)
2716         {
2717           bitmap_set_bit (group->group_kill, current_position);
2718           if (bitmap_bit_p (group->escaped_n, j))
2719             bitmap_set_bit (kill_on_calls, current_position);
2720           group->offset_map_n[j] = current_position++;
2721           group->process_globally = true;
2722         }
2723       EXECUTE_IF_SET_IN_BITMAP (group->store2_p, 0, j, bi)
2724         {
2725           bitmap_set_bit (group->group_kill, current_position);
2726           if (bitmap_bit_p (group->escaped_p, j))
2727             bitmap_set_bit (kill_on_calls, current_position);
2728           group->offset_map_p[j] = current_position++;
2729           group->process_globally = true;
2730         }
2731     }
2732   return current_position != 1;
2733 }
2734
2735
2736 \f
2737 /*----------------------------------------------------------------------------
2738   Third step.
2739
2740   Build the bit vectors for the transfer functions.
2741 ----------------------------------------------------------------------------*/
2742
2743
2744 /* Look up the bitmap index for OFFSET in GROUP_INFO.  If it is not
2745    there, return 0.  */
2746
2747 static int
2748 get_bitmap_index (group_info *group_info, HOST_WIDE_INT offset)
2749 {
2750   if (offset < 0)
2751     {
2752       HOST_WIDE_INT offset_p = -offset;
2753       if (offset_p >= group_info->offset_map_size_n)
2754         return 0;
2755       return group_info->offset_map_n[offset_p];
2756     }
2757   else
2758     {
2759       if (offset >= group_info->offset_map_size_p)
2760         return 0;
2761       return group_info->offset_map_p[offset];
2762     }
2763 }
2764
2765
2766 /* Process the STORE_INFOs into the bitmaps into GEN and KILL.  KILL
2767    may be NULL. */
2768
2769 static void
2770 scan_stores (store_info *store_info, bitmap gen, bitmap kill)
2771 {
2772   while (store_info)
2773     {
2774       HOST_WIDE_INT i;
2775       group_info *group_info
2776         = rtx_group_vec[store_info->group_id];
2777       if (group_info->process_globally)
2778         for (i = store_info->begin; i < store_info->end; i++)
2779           {
2780             int index = get_bitmap_index (group_info, i);
2781             if (index != 0)
2782               {
2783                 bitmap_set_bit (gen, index);
2784                 if (kill)
2785                   bitmap_clear_bit (kill, index);
2786               }
2787           }
2788       store_info = store_info->next;
2789     }
2790 }
2791
2792
2793 /* Process the READ_INFOs into the bitmaps into GEN and KILL.  KILL
2794    may be NULL.  */
2795
2796 static void
2797 scan_reads (insn_info_t insn_info, bitmap gen, bitmap kill)
2798 {
2799   read_info_t read_info = insn_info->read_rec;
2800   int i;
2801   group_info *group;
2802
2803   /* If this insn reads the frame, kill all the frame related stores.  */
2804   if (insn_info->frame_read)
2805     {
2806       FOR_EACH_VEC_ELT (rtx_group_vec, i, group)
2807         if (group->process_globally && group->frame_related)
2808           {
2809             if (kill)
2810               bitmap_ior_into (kill, group->group_kill);
2811             bitmap_and_compl_into (gen, group->group_kill);
2812           }
2813     }
2814   if (insn_info->non_frame_wild_read)
2815     {
2816       /* Kill all non-frame related stores.  Kill all stores of variables that
2817          escape.  */
2818       if (kill)
2819         bitmap_ior_into (kill, kill_on_calls);
2820       bitmap_and_compl_into (gen, kill_on_calls);
2821       FOR_EACH_VEC_ELT (rtx_group_vec, i, group)
2822         if (group->process_globally && !group->frame_related)
2823           {
2824             if (kill)
2825               bitmap_ior_into (kill, group->group_kill);
2826             bitmap_and_compl_into (gen, group->group_kill);
2827           }
2828     }
2829   while (read_info)
2830     {
2831       FOR_EACH_VEC_ELT (rtx_group_vec, i, group)
2832         {
2833           if (group->process_globally)
2834             {
2835               if (i == read_info->group_id)
2836                 {
2837                   if (read_info->begin > read_info->end)
2838                     {
2839                       /* Begin > end for block mode reads.  */
2840                       if (kill)
2841                         bitmap_ior_into (kill, group->group_kill);
2842                       bitmap_and_compl_into (gen, group->group_kill);
2843                     }
2844                   else
2845                     {
2846                       /* The groups are the same, just process the
2847                          offsets.  */
2848                       HOST_WIDE_INT j;
2849                       for (j = read_info->begin; j < read_info->end; j++)
2850                         {
2851                           int index = get_bitmap_index (group, j);
2852                           if (index != 0)
2853                             {
2854                               if (kill)
2855                                 bitmap_set_bit (kill, index);
2856                               bitmap_clear_bit (gen, index);
2857                             }
2858                         }
2859                     }
2860                 }
2861               else
2862                 {
2863                   /* The groups are different, if the alias sets
2864                      conflict, clear the entire group.  We only need
2865                      to apply this test if the read_info is a cselib
2866                      read.  Anything with a constant base cannot alias
2867                      something else with a different constant
2868                      base.  */
2869                   if ((read_info->group_id < 0)
2870                       && canon_true_dependence (group->base_mem,
2871                                                 GET_MODE (group->base_mem),
2872                                                 group->canon_base_addr,
2873                                                 read_info->mem, NULL_RTX))
2874                     {
2875                       if (kill)
2876                         bitmap_ior_into (kill, group->group_kill);
2877                       bitmap_and_compl_into (gen, group->group_kill);
2878                     }
2879                 }
2880             }
2881         }
2882
2883       read_info = read_info->next;
2884     }
2885 }
2886
2887
2888 /* Return the insn in BB_INFO before the first wild read or if there
2889    are no wild reads in the block, return the last insn.  */
2890
2891 static insn_info_t
2892 find_insn_before_first_wild_read (bb_info_t bb_info)
2893 {
2894   insn_info_t insn_info = bb_info->last_insn;
2895   insn_info_t last_wild_read = NULL;
2896
2897   while (insn_info)
2898     {
2899       if (insn_info->wild_read)
2900         {
2901           last_wild_read = insn_info->prev_insn;
2902           /* Block starts with wild read.  */
2903           if (!last_wild_read)
2904             return NULL;
2905         }
2906
2907       insn_info = insn_info->prev_insn;
2908     }
2909
2910   if (last_wild_read)
2911     return last_wild_read;
2912   else
2913     return bb_info->last_insn;
2914 }
2915
2916
2917 /* Scan the insns in BB_INFO starting at PTR and going to the top of
2918    the block in order to build the gen and kill sets for the block.
2919    We start at ptr which may be the last insn in the block or may be
2920    the first insn with a wild read.  In the latter case we are able to
2921    skip the rest of the block because it just does not matter:
2922    anything that happens is hidden by the wild read.  */
2923
2924 static void
2925 dse_step3_scan (basic_block bb)
2926 {
2927   bb_info_t bb_info = bb_table[bb->index];
2928   insn_info_t insn_info;
2929
2930   insn_info = find_insn_before_first_wild_read (bb_info);
2931
2932   /* In the spill case or in the no_spill case if there is no wild
2933      read in the block, we will need a kill set.  */
2934   if (insn_info == bb_info->last_insn)
2935     {
2936       if (bb_info->kill)
2937         bitmap_clear (bb_info->kill);
2938       else
2939         bb_info->kill = BITMAP_ALLOC (&dse_bitmap_obstack);
2940     }
2941   else
2942     if (bb_info->kill)
2943       BITMAP_FREE (bb_info->kill);
2944
2945   while (insn_info)
2946     {
2947       /* There may have been code deleted by the dce pass run before
2948          this phase.  */
2949       if (insn_info->insn && INSN_P (insn_info->insn))
2950         {
2951           scan_stores (insn_info->store_rec, bb_info->gen, bb_info->kill);
2952           scan_reads (insn_info, bb_info->gen, bb_info->kill);
2953         }
2954
2955       insn_info = insn_info->prev_insn;
2956     }
2957 }
2958
2959
2960 /* Set the gen set of the exit block, and also any block with no
2961    successors that does not have a wild read.  */
2962
2963 static void
2964 dse_step3_exit_block_scan (bb_info_t bb_info)
2965 {
2966   /* The gen set is all 0's for the exit block except for the
2967      frame_pointer_group.  */
2968
2969   if (stores_off_frame_dead_at_return)
2970     {
2971       unsigned int i;
2972       group_info *group;
2973
2974       FOR_EACH_VEC_ELT (rtx_group_vec, i, group)
2975         {
2976           if (group->process_globally && group->frame_related)
2977             bitmap_ior_into (bb_info->gen, group->group_kill);
2978         }
2979     }
2980 }
2981
2982
2983 /* Find all of the blocks that are not backwards reachable from the
2984    exit block or any block with no successors (BB).  These are the
2985    infinite loops or infinite self loops.  These blocks will still
2986    have their bits set in UNREACHABLE_BLOCKS.  */
2987
2988 static void
2989 mark_reachable_blocks (sbitmap unreachable_blocks, basic_block bb)
2990 {
2991   edge e;
2992   edge_iterator ei;
2993
2994   if (bitmap_bit_p (unreachable_blocks, bb->index))
2995     {
2996       bitmap_clear_bit (unreachable_blocks, bb->index);
2997       FOR_EACH_EDGE (e, ei, bb->preds)
2998         {
2999           mark_reachable_blocks (unreachable_blocks, e->src);
3000         }
3001     }
3002 }
3003
3004 /* Build the transfer functions for the function.  */
3005
3006 static void
3007 dse_step3 ()
3008 {
3009   basic_block bb;
3010   sbitmap unreachable_blocks = sbitmap_alloc (last_basic_block_for_fn (cfun));
3011   sbitmap_iterator sbi;
3012   bitmap all_ones = NULL;
3013   unsigned int i;
3014
3015   bitmap_ones (unreachable_blocks);
3016
3017   FOR_ALL_BB_FN (bb, cfun)
3018     {
3019       bb_info_t bb_info = bb_table[bb->index];
3020       if (bb_info->gen)
3021         bitmap_clear (bb_info->gen);
3022       else
3023         bb_info->gen = BITMAP_ALLOC (&dse_bitmap_obstack);
3024
3025       if (bb->index == ENTRY_BLOCK)
3026         ;
3027       else if (bb->index == EXIT_BLOCK)
3028         dse_step3_exit_block_scan (bb_info);
3029       else
3030         dse_step3_scan (bb);
3031       if (EDGE_COUNT (bb->succs) == 0)
3032         mark_reachable_blocks (unreachable_blocks, bb);
3033
3034       /* If this is the second time dataflow is run, delete the old
3035          sets.  */
3036       if (bb_info->in)
3037         BITMAP_FREE (bb_info->in);
3038       if (bb_info->out)
3039         BITMAP_FREE (bb_info->out);
3040     }
3041
3042   /* For any block in an infinite loop, we must initialize the out set
3043      to all ones.  This could be expensive, but almost never occurs in
3044      practice. However, it is common in regression tests.  */
3045   EXECUTE_IF_SET_IN_BITMAP (unreachable_blocks, 0, i, sbi)
3046     {
3047       if (bitmap_bit_p (all_blocks, i))
3048         {
3049           bb_info_t bb_info = bb_table[i];
3050           if (!all_ones)
3051             {
3052               unsigned int j;
3053               group_info *group;
3054
3055               all_ones = BITMAP_ALLOC (&dse_bitmap_obstack);
3056               FOR_EACH_VEC_ELT (rtx_group_vec, j, group)
3057                 bitmap_ior_into (all_ones, group->group_kill);
3058             }
3059           if (!bb_info->out)
3060             {
3061               bb_info->out = BITMAP_ALLOC (&dse_bitmap_obstack);
3062               bitmap_copy (bb_info->out, all_ones);
3063             }
3064         }
3065     }
3066
3067   if (all_ones)
3068     BITMAP_FREE (all_ones);
3069   sbitmap_free (unreachable_blocks);
3070 }
3071
3072
3073 \f
3074 /*----------------------------------------------------------------------------
3075    Fourth step.
3076
3077    Solve the bitvector equations.
3078 ----------------------------------------------------------------------------*/
3079
3080
3081 /* Confluence function for blocks with no successors.  Create an out
3082    set from the gen set of the exit block.  This block logically has
3083    the exit block as a successor.  */
3084
3085
3086
3087 static void
3088 dse_confluence_0 (basic_block bb)
3089 {
3090   bb_info_t bb_info = bb_table[bb->index];
3091
3092   if (bb->index == EXIT_BLOCK)
3093     return;
3094
3095   if (!bb_info->out)
3096     {
3097       bb_info->out = BITMAP_ALLOC (&dse_bitmap_obstack);
3098       bitmap_copy (bb_info->out, bb_table[EXIT_BLOCK]->gen);
3099     }
3100 }
3101
3102 /* Propagate the information from the in set of the dest of E to the
3103    out set of the src of E.  If the various in or out sets are not
3104    there, that means they are all ones.  */
3105
3106 static bool
3107 dse_confluence_n (edge e)
3108 {
3109   bb_info_t src_info = bb_table[e->src->index];
3110   bb_info_t dest_info = bb_table[e->dest->index];
3111
3112   if (dest_info->in)
3113     {
3114       if (src_info->out)
3115         bitmap_and_into (src_info->out, dest_info->in);
3116       else
3117         {
3118           src_info->out = BITMAP_ALLOC (&dse_bitmap_obstack);
3119           bitmap_copy (src_info->out, dest_info->in);
3120         }
3121     }
3122   return true;
3123 }
3124
3125
3126 /* Propagate the info from the out to the in set of BB_INDEX's basic
3127    block.  There are three cases:
3128
3129    1) The block has no kill set.  In this case the kill set is all
3130    ones.  It does not matter what the out set of the block is, none of
3131    the info can reach the top.  The only thing that reaches the top is
3132    the gen set and we just copy the set.
3133
3134    2) There is a kill set but no out set and bb has successors.  In
3135    this case we just return. Eventually an out set will be created and
3136    it is better to wait than to create a set of ones.
3137
3138    3) There is both a kill and out set.  We apply the obvious transfer
3139    function.
3140 */
3141
3142 static bool
3143 dse_transfer_function (int bb_index)
3144 {
3145   bb_info_t bb_info = bb_table[bb_index];
3146
3147   if (bb_info->kill)
3148     {
3149       if (bb_info->out)
3150         {
3151           /* Case 3 above.  */
3152           if (bb_info->in)
3153             return bitmap_ior_and_compl (bb_info->in, bb_info->gen,
3154                                          bb_info->out, bb_info->kill);
3155           else
3156             {
3157               bb_info->in = BITMAP_ALLOC (&dse_bitmap_obstack);
3158               bitmap_ior_and_compl (bb_info->in, bb_info->gen,
3159                                     bb_info->out, bb_info->kill);
3160               return true;
3161             }
3162         }
3163       else
3164         /* Case 2 above.  */
3165         return false;
3166     }
3167   else
3168     {
3169       /* Case 1 above.  If there is already an in set, nothing
3170          happens.  */
3171       if (bb_info->in)
3172         return false;
3173       else
3174         {
3175           bb_info->in = BITMAP_ALLOC (&dse_bitmap_obstack);
3176           bitmap_copy (bb_info->in, bb_info->gen);
3177           return true;
3178         }
3179     }
3180 }
3181
3182 /* Solve the dataflow equations.  */
3183
3184 static void
3185 dse_step4 (void)
3186 {
3187   df_simple_dataflow (DF_BACKWARD, NULL, dse_confluence_0,
3188                       dse_confluence_n, dse_transfer_function,
3189                       all_blocks, df_get_postorder (DF_BACKWARD),
3190                       df_get_n_blocks (DF_BACKWARD));
3191   if (dump_file && (dump_flags & TDF_DETAILS))
3192     {
3193       basic_block bb;
3194
3195       fprintf (dump_file, "\n\n*** Global dataflow info after analysis.\n");
3196       FOR_ALL_BB_FN (bb, cfun)
3197         {
3198           bb_info_t bb_info = bb_table[bb->index];
3199
3200           df_print_bb_index (bb, dump_file);
3201           if (bb_info->in)
3202             bitmap_print (dump_file, bb_info->in, "  in:   ", "\n");
3203           else
3204             fprintf (dump_file, "  in:   *MISSING*\n");
3205           if (bb_info->gen)
3206             bitmap_print (dump_file, bb_info->gen, "  gen:  ", "\n");
3207           else
3208             fprintf (dump_file, "  gen:  *MISSING*\n");
3209           if (bb_info->kill)
3210             bitmap_print (dump_file, bb_info->kill, "  kill: ", "\n");
3211           else
3212             fprintf (dump_file, "  kill: *MISSING*\n");
3213           if (bb_info->out)
3214             bitmap_print (dump_file, bb_info->out, "  out:  ", "\n");
3215           else
3216             fprintf (dump_file, "  out:  *MISSING*\n\n");
3217         }
3218     }
3219 }
3220
3221
3222 \f
3223 /*----------------------------------------------------------------------------
3224    Fifth step.
3225
3226    Delete the stores that can only be deleted using the global information.
3227 ----------------------------------------------------------------------------*/
3228
3229
3230 static void
3231 dse_step5 (void)
3232 {
3233   basic_block bb;
3234   FOR_EACH_BB_FN (bb, cfun)
3235     {
3236       bb_info_t bb_info = bb_table[bb->index];
3237       insn_info_t insn_info = bb_info->last_insn;
3238       bitmap v = bb_info->out;
3239
3240       while (insn_info)
3241         {
3242           bool deleted = false;
3243           if (dump_file && insn_info->insn)
3244             {
3245               fprintf (dump_file, "starting to process insn %d\n",
3246                        INSN_UID (insn_info->insn));
3247               bitmap_print (dump_file, v, "  v:  ", "\n");
3248             }
3249
3250           /* There may have been code deleted by the dce pass run before
3251              this phase.  */
3252           if (insn_info->insn
3253               && INSN_P (insn_info->insn)
3254               && (!insn_info->cannot_delete)
3255               && (!bitmap_empty_p (v)))
3256             {
3257               store_info *store_info = insn_info->store_rec;
3258
3259               /* Try to delete the current insn.  */
3260               deleted = true;
3261
3262               /* Skip the clobbers.  */
3263               while (!store_info->is_set)
3264                 store_info = store_info->next;
3265
3266               HOST_WIDE_INT i;
3267               group_info *group_info = rtx_group_vec[store_info->group_id];
3268
3269               for (i = store_info->begin; i < store_info->end; i++)
3270                 {
3271                   int index = get_bitmap_index (group_info, i);
3272
3273                   if (dump_file && (dump_flags & TDF_DETAILS))
3274                     fprintf (dump_file, "i = %d, index = %d\n", (int)i, index);
3275                   if (index == 0 || !bitmap_bit_p (v, index))
3276                     {
3277                       if (dump_file && (dump_flags & TDF_DETAILS))
3278                         fprintf (dump_file, "failing at i = %d\n", (int)i);
3279                       deleted = false;
3280                       break;
3281                     }
3282                 }
3283               if (deleted)
3284                 {
3285                   if (dbg_cnt (dse)
3286                       && check_for_inc_dec_1 (insn_info))
3287                     {
3288                       delete_insn (insn_info->insn);
3289                       insn_info->insn = NULL;
3290                       globally_deleted++;
3291                     }
3292                 }
3293             }
3294           /* We do want to process the local info if the insn was
3295              deleted.  For instance, if the insn did a wild read, we
3296              no longer need to trash the info.  */
3297           if (insn_info->insn
3298               && INSN_P (insn_info->insn)
3299               && (!deleted))
3300             {
3301               scan_stores (insn_info->store_rec, v, NULL);
3302               if (insn_info->wild_read)
3303                 {
3304                   if (dump_file && (dump_flags & TDF_DETAILS))
3305                     fprintf (dump_file, "wild read\n");
3306                   bitmap_clear (v);
3307                 }
3308               else if (insn_info->read_rec
3309                        || insn_info->non_frame_wild_read)
3310                 {
3311                   if (dump_file && !insn_info->non_frame_wild_read)
3312                     fprintf (dump_file, "regular read\n");
3313                   else if (dump_file && (dump_flags & TDF_DETAILS))
3314                     fprintf (dump_file, "non-frame wild read\n");
3315                   scan_reads (insn_info, v, NULL);
3316                 }
3317             }
3318
3319           insn_info = insn_info->prev_insn;
3320         }
3321     }
3322 }
3323
3324
3325 \f
3326 /*----------------------------------------------------------------------------
3327    Sixth step.
3328
3329    Delete stores made redundant by earlier stores (which store the same
3330    value) that couldn't be eliminated.
3331 ----------------------------------------------------------------------------*/
3332
3333 static void
3334 dse_step6 (void)
3335 {
3336   basic_block bb;
3337
3338   FOR_ALL_BB_FN (bb, cfun)
3339     {
3340       bb_info_t bb_info = bb_table[bb->index];
3341       insn_info_t insn_info = bb_info->last_insn;
3342
3343       while (insn_info)
3344         {
3345           /* There may have been code deleted by the dce pass run before
3346              this phase.  */
3347           if (insn_info->insn
3348               && INSN_P (insn_info->insn)
3349               && !insn_info->cannot_delete)
3350             {
3351               store_info *s_info = insn_info->store_rec;
3352
3353               while (s_info && !s_info->is_set)
3354                 s_info = s_info->next;
3355               if (s_info
3356                   && s_info->redundant_reason
3357                   && s_info->redundant_reason->insn
3358                   && INSN_P (s_info->redundant_reason->insn))
3359                 {
3360                   rtx_insn *rinsn = s_info->redundant_reason->insn;
3361                   if (dump_file && (dump_flags & TDF_DETAILS))
3362                     fprintf (dump_file, "Locally deleting insn %d "
3363                                         "because insn %d stores the "
3364                                         "same value and couldn't be "
3365                                         "eliminated\n",
3366                                         INSN_UID (insn_info->insn),
3367                                         INSN_UID (rinsn));
3368                   delete_dead_store_insn (insn_info);
3369                 }
3370             }
3371           insn_info = insn_info->prev_insn;
3372         }
3373     }
3374 }
3375 \f
3376 /*----------------------------------------------------------------------------
3377    Seventh step.
3378
3379    Destroy everything left standing.
3380 ----------------------------------------------------------------------------*/
3381
3382 static void
3383 dse_step7 (void)
3384 {
3385   bitmap_obstack_release (&dse_bitmap_obstack);
3386   obstack_free (&dse_obstack, NULL);
3387
3388   end_alias_analysis ();
3389   free (bb_table);
3390   delete rtx_group_table;
3391   rtx_group_table = NULL;
3392   rtx_group_vec.release ();
3393   BITMAP_FREE (all_blocks);
3394   BITMAP_FREE (scratch);
3395
3396   rtx_store_info_pool.release ();
3397   read_info_type_pool.release ();
3398   insn_info_type_pool.release ();
3399   dse_bb_info_type_pool.release ();
3400   group_info_pool.release ();
3401   deferred_change_pool.release ();
3402 }
3403
3404
3405 /* -------------------------------------------------------------------------
3406    DSE
3407    ------------------------------------------------------------------------- */
3408
3409 /* Callback for running pass_rtl_dse.  */
3410
3411 static unsigned int
3412 rest_of_handle_dse (void)
3413 {
3414   df_set_flags (DF_DEFER_INSN_RESCAN);
3415
3416   /* Need the notes since we must track live hardregs in the forwards
3417      direction.  */
3418   df_note_add_problem ();
3419   df_analyze ();
3420
3421   dse_step0 ();
3422   dse_step1 ();
3423   dse_step2_init ();
3424   if (dse_step2 ())
3425     {
3426       df_set_flags (DF_LR_RUN_DCE);
3427       df_analyze ();
3428       if (dump_file && (dump_flags & TDF_DETAILS))
3429         fprintf (dump_file, "doing global processing\n");
3430       dse_step3 ();
3431       dse_step4 ();
3432       dse_step5 ();
3433     }
3434
3435   dse_step6 ();
3436   dse_step7 ();
3437
3438   if (dump_file)
3439     fprintf (dump_file, "dse: local deletions = %d, global deletions = %d\n",
3440              locally_deleted, globally_deleted);
3441
3442   /* DSE can eliminate potentially-trapping MEMs.
3443      Remove any EH edges associated with them.  */
3444   if ((locally_deleted || globally_deleted)
3445       && cfun->can_throw_non_call_exceptions
3446       && purge_all_dead_edges ())
3447     cleanup_cfg (0);
3448
3449   return 0;
3450 }
3451
3452 namespace {
3453
3454 const pass_data pass_data_rtl_dse1 =
3455 {
3456   RTL_PASS, /* type */
3457   "dse1", /* name */
3458   OPTGROUP_NONE, /* optinfo_flags */
3459   TV_DSE1, /* tv_id */
3460   0, /* properties_required */
3461   0, /* properties_provided */
3462   0, /* properties_destroyed */
3463   0, /* todo_flags_start */
3464   TODO_df_finish, /* todo_flags_finish */
3465 };
3466
3467 class pass_rtl_dse1 : public rtl_opt_pass
3468 {
3469 public:
3470   pass_rtl_dse1 (gcc::context *ctxt)
3471     : rtl_opt_pass (pass_data_rtl_dse1, ctxt)
3472   {}
3473
3474   /* opt_pass methods: */
3475   virtual bool gate (function *)
3476     {
3477       return optimize > 0 && flag_dse && dbg_cnt (dse1);
3478     }
3479
3480   virtual unsigned int execute (function *) { return rest_of_handle_dse (); }
3481
3482 }; // class pass_rtl_dse1
3483
3484 } // anon namespace
3485
3486 rtl_opt_pass *
3487 make_pass_rtl_dse1 (gcc::context *ctxt)
3488 {
3489   return new pass_rtl_dse1 (ctxt);
3490 }
3491
3492 namespace {
3493
3494 const pass_data pass_data_rtl_dse2 =
3495 {
3496   RTL_PASS, /* type */
3497   "dse2", /* name */
3498   OPTGROUP_NONE, /* optinfo_flags */
3499   TV_DSE2, /* tv_id */
3500   0, /* properties_required */
3501   0, /* properties_provided */
3502   0, /* properties_destroyed */
3503   0, /* todo_flags_start */
3504   TODO_df_finish, /* todo_flags_finish */
3505 };
3506
3507 class pass_rtl_dse2 : public rtl_opt_pass
3508 {
3509 public:
3510   pass_rtl_dse2 (gcc::context *ctxt)
3511     : rtl_opt_pass (pass_data_rtl_dse2, ctxt)
3512   {}
3513
3514   /* opt_pass methods: */
3515   virtual bool gate (function *)
3516     {
3517       return optimize > 0 && flag_dse && dbg_cnt (dse2);
3518     }
3519
3520   virtual unsigned int execute (function *) { return rest_of_handle_dse (); }
3521
3522 }; // class pass_rtl_dse2
3523
3524 } // anon namespace
3525
3526 rtl_opt_pass *
3527 make_pass_rtl_dse2 (gcc::context *ctxt)
3528 {
3529   return new pass_rtl_dse2 (ctxt);
3530 }