]> git.ipfire.org Git - thirdparty/gcc.git/blame - gcc/tree-ssa-structalias.c
switch from gimple to gimple*
[thirdparty/gcc.git] / gcc / tree-ssa-structalias.c
CommitLineData
910fdc79 1/* Tree based points-to analysis
5624e564 2 Copyright (C) 2005-2015 Free Software Foundation, Inc.
910fdc79
DB
3 Contributed by Daniel Berlin <dberlin@dberlin.org>
4
9dcd6f09 5 This file is part of GCC.
910fdc79 6
9dcd6f09
NC
7 GCC is free software; you can redistribute it and/or modify
8 under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3 of the License, or
10 (at your option) any later version.
910fdc79 11
9dcd6f09
NC
12 GCC is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
910fdc79 16
9dcd6f09
NC
17 You should have received a copy of the GNU General Public License
18 along with GCC; see the file COPYING3. If not see
19 <http://www.gnu.org/licenses/>. */
910fdc79
DB
20
21#include "config.h"
22#include "system.h"
23#include "coretypes.h"
c7131fb2
AM
24#include "backend.h"
25#include "tree.h"
26#include "gimple.h"
27#include "rtl.h"
28#include "ssa.h"
910fdc79 29#include "flags.h"
40e23961 30#include "alias.h"
40e23961 31#include "fold-const.h"
d8a2d370
DN
32#include "stor-layout.h"
33#include "stmt.h"
2fb9a547 34#include "internal-fn.h"
5be5c238 35#include "gimple-iterator.h"
442b4905 36#include "cgraph.h"
442b4905 37#include "tree-into-ssa.h"
36566b39
PK
38#include "insn-config.h"
39#include "expmed.h"
40#include "dojump.h"
41#include "explow.h"
42#include "calls.h"
43#include "emit-rtl.h"
44#include "varasm.h"
d8a2d370 45#include "expr.h"
442b4905 46#include "tree-dfa.h"
910fdc79 47#include "tree-inline.h"
718f9c0f 48#include "diagnostic-core.h"
910fdc79 49#include "tree-pass.h"
910fdc79
DB
50#include "alloc-pool.h"
51#include "splay-tree.h"
a916f21d 52#include "params.h"
aa098165
RB
53#include "tree-pretty-print.h"
54#include "gimple-walk.h"
910fdc79
DB
55
56/* The idea behind this analyzer is to generate set constraints from the
57 program, then solve the resulting constraints in order to generate the
c58936b6 58 points-to sets.
910fdc79
DB
59
60 Set constraints are a way of modeling program analysis problems that
61 involve sets. They consist of an inclusion constraint language,
62 describing the variables (each variable is a set) and operations that
63 are involved on the variables, and a set of rules that derive facts
64 from these operations. To solve a system of set constraints, you derive
65 all possible facts under the rules, which gives you the correct sets
66 as a consequence.
67
68 See "Efficient Field-sensitive pointer analysis for C" by "David
69 J. Pearce and Paul H. J. Kelly and Chris Hankin, at
70 http://citeseer.ist.psu.edu/pearce04efficient.html
71
72 Also see "Ultra-fast Aliasing Analysis using CLA: A Million Lines
73 of C Code in a Second" by ""Nevin Heintze and Olivier Tardieu" at
c58936b6
DB
74 http://citeseer.ist.psu.edu/heintze01ultrafast.html
75
76 There are three types of real constraint expressions, DEREF,
3e5937d7 77 ADDRESSOF, and SCALAR. Each constraint expression consists
c58936b6 78 of a constraint type, a variable, and an offset.
910fdc79 79
910fdc79
DB
80 SCALAR is a constraint expression type used to represent x, whether
81 it appears on the LHS or the RHS of a statement.
82 DEREF is a constraint expression type used to represent *x, whether
c58936b6 83 it appears on the LHS or the RHS of a statement.
910fdc79 84 ADDRESSOF is a constraint expression used to represent &x, whether
607fb860 85 it appears on the LHS or the RHS of a statement.
c58936b6 86
910fdc79
DB
87 Each pointer variable in the program is assigned an integer id, and
88 each field of a structure variable is assigned an integer id as well.
c58936b6 89
910fdc79
DB
90 Structure variables are linked to their list of fields through a "next
91 field" in each variable that points to the next field in offset
c58936b6
DB
92 order.
93 Each variable for a structure field has
910fdc79
DB
94
95 1. "size", that tells the size in bits of that field.
96 2. "fullsize, that tells the size in bits of the entire structure.
97 3. "offset", that tells the offset in bits from the beginning of the
98 structure to this field.
99
c58936b6 100 Thus,
910fdc79
DB
101 struct f
102 {
103 int a;
104 int b;
105 } foo;
106 int *bar;
107
108 looks like
109
110 foo.a -> id 1, size 32, offset 0, fullsize 64, next foo.b
111 foo.b -> id 2, size 32, offset 32, fullsize 64, next NULL
112 bar -> id 3, size 32, offset 0, fullsize 32, next NULL
113
c58936b6 114
910fdc79
DB
115 In order to solve the system of set constraints, the following is
116 done:
117
118 1. Each constraint variable x has a solution set associated with it,
119 Sol(x).
c58936b6 120
910fdc79
DB
121 2. Constraints are separated into direct, copy, and complex.
122 Direct constraints are ADDRESSOF constraints that require no extra
123 processing, such as P = &Q
124 Copy constraints are those of the form P = Q.
2941f691
DB
125 Complex constraints are all the constraints involving dereferences
126 and offsets (including offsetted copies).
c58936b6 127
910fdc79 128 3. All direct constraints of the form P = &Q are processed, such
c58936b6 129 that Q is added to Sol(P)
910fdc79
DB
130
131 4. All complex constraints for a given constraint variable are stored in a
c58936b6 132 linked list attached to that variable's node.
910fdc79
DB
133
134 5. A directed graph is built out of the copy constraints. Each
c58936b6 135 constraint variable is a node in the graph, and an edge from
910fdc79 136 Q to P is added for each copy constraint of the form P = Q
c58936b6 137
910fdc79
DB
138 6. The graph is then walked, and solution sets are
139 propagated along the copy edges, such that an edge from Q to P
140 causes Sol(P) <- Sol(P) union Sol(Q).
c58936b6 141
910fdc79 142 7. As we visit each node, all complex constraints associated with
607fb860 143 that node are processed by adding appropriate copy edges to the graph, or the
c58936b6 144 appropriate variables to the solution set.
910fdc79
DB
145
146 8. The process of walking the graph is iterated until no solution
147 sets change.
148
149 Prior to walking the graph in steps 6 and 7, We perform static
c58936b6 150 cycle elimination on the constraint graph, as well
910fdc79 151 as off-line variable substitution.
c58936b6 152
910fdc79
DB
153 TODO: Adding offsets to pointer-to-structures can be handled (IE not punted
154 on and turned into anything), but isn't. You can just see what offset
155 inside the pointed-to struct it's going to access.
c58936b6 156
910fdc79 157 TODO: Constant bounded arrays can be handled as if they were structs of the
c58936b6 158 same number of elements.
910fdc79
DB
159
160 TODO: Modeling heap and incoming pointers becomes much better if we
161 add fields to them as we discover them, which we could do.
162
163 TODO: We could handle unions, but to be honest, it's probably not
164 worth the pain or slowdown. */
165
25a6a873
RG
166/* IPA-PTA optimizations possible.
167
168 When the indirect function called is ANYTHING we can add disambiguation
169 based on the function signatures (or simply the parameter count which
170 is the varinfo size). We also do not need to consider functions that
171 do not have their address taken.
172
173 The is_global_var bit which marks escape points is overly conservative
174 in IPA mode. Split it to is_escape_point and is_global_var - only
175 externally visible globals are escape points in IPA mode. This is
176 also needed to fix the pt_solution_includes_global predicate
177 (and thus ptr_deref_may_alias_global_p).
178
179 The way we introduce DECL_PT_UID to avoid fixing up all points-to
180 sets in the translation unit when we copy a DECL during inlining
181 pessimizes precision. The advantage is that the DECL_PT_UID keeps
182 compile-time and memory usage overhead low - the points-to sets
183 do not grow or get unshared as they would during a fixup phase.
184 An alternative solution is to delay IPA PTA until after all
185 inlining transformations have been applied.
186
187 The way we propagate clobber/use information isn't optimized.
188 It should use a new complex constraint that properly filters
189 out local variables of the callee (though that would make
190 the sets invalid after inlining). OTOH we might as well
191 admit defeat to WHOPR and simply do all the clobber/use analysis
192 and propagation after PTA finished but before we threw away
193 points-to information for memory variables. WHOPR and PTA
194 do not play along well anyway - the whole constraint solving
195 would need to be done in WPA phase and it will be very interesting
196 to apply the results to local SSA names during LTRANS phase.
197
198 We probably should compute a per-function unit-ESCAPE solution
199 propagating it simply like the clobber / uses solutions. The
200 solution can go alongside the non-IPA espaced solution and be
201 used to query which vars escape the unit through a function.
202
203 We never put function decls in points-to sets so we do not
204 keep the set of called functions for indirect calls.
205
206 And probably more. */
21392f19 207
910fdc79 208static bool use_field_sensitive = true;
4ee00913 209static int in_ipa_mode = 0;
3e5937d7
DB
210
211/* Used for predecessor bitmaps. */
4ee00913 212static bitmap_obstack predbitmap_obstack;
3e5937d7
DB
213
214/* Used for points-to sets. */
215static bitmap_obstack pta_obstack;
216
217/* Used for oldsolution members of variables. */
218static bitmap_obstack oldpta_obstack;
219
220/* Used for per-solver-iteration bitmaps. */
4ee00913
DB
221static bitmap_obstack iteration_obstack;
222
910fdc79 223static unsigned int create_variable_info_for (tree, const char *);
3e5937d7
DB
224typedef struct constraint_graph *constraint_graph_t;
225static void unify_nodes (constraint_graph_t, unsigned int, unsigned int, bool);
910fdc79 226
5006671f
RG
227struct constraint;
228typedef struct constraint *constraint_t;
229
910fdc79 230
4ee00913
DB
231#define EXECUTE_IF_IN_NONNULL_BITMAP(a, b, c, d) \
232 if (a) \
233 EXECUTE_IF_SET_IN_BITMAP (a, b, c, d)
234
910fdc79
DB
235static struct constraint_stats
236{
237 unsigned int total_vars;
3e5937d7 238 unsigned int nonpointer_vars;
910fdc79
DB
239 unsigned int unified_vars_static;
240 unsigned int unified_vars_dynamic;
241 unsigned int iterations;
4ee00913 242 unsigned int num_edges;
3e5937d7
DB
243 unsigned int num_implicit_edges;
244 unsigned int points_to_sets_created;
910fdc79
DB
245} stats;
246
247struct variable_info
248{
249 /* ID of this variable */
250 unsigned int id;
251
910fdc79
DB
252 /* True if this is a variable created by the constraint analysis, such as
253 heap variables and constraints we had to break up. */
74d27244 254 unsigned int is_artificial_var : 1;
c58936b6 255
13c2c08b
DB
256 /* True if this is a special variable whose solution set should not be
257 changed. */
74d27244 258 unsigned int is_special_var : 1;
910fdc79
DB
259
260 /* True for variables whose size is not known or variable. */
74d27244 261 unsigned int is_unknown_size_var : 1;
910fdc79 262
e5bae89b
RG
263 /* True for (sub-)fields that represent a whole variable. */
264 unsigned int is_full_var : 1;
265
e8ca4159 266 /* True if this is a heap variable. */
74d27244
RG
267 unsigned int is_heap_var : 1;
268
9e39dba6
RG
269 /* True if this field may contain pointers. */
270 unsigned int may_have_pointers : 1;
271
18abb35e
RG
272 /* True if this field has only restrict qualified pointers. */
273 unsigned int only_restrict_pointers : 1;
274
aa098165
RB
275 /* True if this represents a heap var created for a restrict qualified
276 pointer. */
277 unsigned int is_restrict_var : 1;
278
0bbf2ffa
RG
279 /* True if this represents a global variable. */
280 unsigned int is_global_var : 1;
281
25a6a873
RG
282 /* True if this represents a IPA function info. */
283 unsigned int is_fn_info : 1;
284
aa098165
RB
285 /* ??? Store somewhere better. */
286 unsigned short ruid;
287
d6d305fe
RB
288 /* The ID of the variable for the next field in this structure
289 or zero for the last field in this structure. */
290 unsigned next;
291
292 /* The ID of the variable for the first field in this structure. */
293 unsigned head;
795a337a
RG
294
295 /* Offset of this variable, in bits, from the base variable */
296 unsigned HOST_WIDE_INT offset;
297
298 /* Size of the variable, in bits. */
299 unsigned HOST_WIDE_INT size;
300
301 /* Full size of the base variable, in bits. */
302 unsigned HOST_WIDE_INT fullsize;
303
304 /* Name of this variable */
305 const char *name;
306
307 /* Tree that this variable is associated with. */
308 tree decl;
309
910fdc79
DB
310 /* Points-to set for this variable. */
311 bitmap solution;
312
3e5937d7
DB
313 /* Old points-to set for this variable. */
314 bitmap oldsolution;
910fdc79
DB
315};
316typedef struct variable_info *varinfo_t;
317
318static varinfo_t first_vi_for_offset (varinfo_t, unsigned HOST_WIDE_INT);
5006671f
RG
319static varinfo_t first_or_preceding_vi_for_offset (varinfo_t,
320 unsigned HOST_WIDE_INT);
0e1f4c6b 321static varinfo_t lookup_vi_for_tree (tree);
b4cf8c9d 322static inline bool type_can_have_subvars (const_tree);
910fdc79
DB
323
324/* Pool of variable info structures. */
fb0b2914 325static object_allocator<variable_info> variable_info_pool
fcb87c50 326 ("Variable info pool");
910fdc79 327
d394a308 328/* Map varinfo to final pt_solution. */
b787e7a2 329static hash_map<varinfo_t, pt_solution *> *final_solutions;
d394a308 330struct obstack final_solutions_obstack;
910fdc79 331
38635499
DN
332/* Table of variable info structures for constraint variables.
333 Indexed directly by variable info id. */
9771b263 334static vec<varinfo_t> varmap;
13c2c08b
DB
335
336/* Return the varmap element N */
337
338static inline varinfo_t
03190594 339get_varinfo (unsigned int n)
13c2c08b 340{
9771b263 341 return varmap[n];
13c2c08b 342}
910fdc79 343
d6d305fe
RB
344/* Return the next variable in the list of sub-variables of VI
345 or NULL if VI is the last sub-variable. */
346
347static inline varinfo_t
348vi_next (varinfo_t vi)
349{
350 return get_varinfo (vi->next);
351}
352
353/* Static IDs for the special variables. Variable ID zero is unused
354 and used as terminator for the sub-variable chain. */
ebd7d910 355enum { nothing_id = 1, anything_id = 2, string_id = 3,
d6d305fe
RB
356 escaped_id = 4, nonlocal_id = 5,
357 storedanything_id = 6, integer_id = 7 };
b7091901 358
910fdc79 359/* Return a new variable info structure consisting for a variable
0bbf2ffa
RG
360 named NAME, and using constraint graph node NODE. Append it
361 to the vector of variable info structures. */
910fdc79
DB
362
363static varinfo_t
0bbf2ffa 364new_var_info (tree t, const char *name)
910fdc79 365{
9771b263 366 unsigned index = varmap.length ();
dc5667a3 367 varinfo_t ret = variable_info_pool.allocate ();
910fdc79 368
0bbf2ffa 369 ret->id = index;
910fdc79
DB
370 ret->name = name;
371 ret->decl = t;
0bbf2ffa
RG
372 /* Vars without decl are artificial and do not have sub-variables. */
373 ret->is_artificial_var = (t == NULL_TREE);
13c2c08b 374 ret->is_special_var = false;
910fdc79 375 ret->is_unknown_size_var = false;
02583d3c
RG
376 ret->is_full_var = (t == NULL_TREE);
377 ret->is_heap_var = false;
9e39dba6 378 ret->may_have_pointers = true;
18abb35e 379 ret->only_restrict_pointers = false;
aa098165 380 ret->is_restrict_var = false;
b1512ea0 381 ret->ruid = 0;
74d27244 382 ret->is_global_var = (t == NULL_TREE);
25a6a873 383 ret->is_fn_info = false;
0bbf2ffa 384 if (t && DECL_P (t))
6c0c92e6
RG
385 ret->is_global_var = (is_global_var (t)
386 /* We have to treat even local register variables
387 as escape points. */
9a6c9288
RG
388 || (TREE_CODE (t) == VAR_DECL
389 && DECL_HARD_REGISTER (t)));
3e5937d7 390 ret->solution = BITMAP_ALLOC (&pta_obstack);
74d8fa44 391 ret->oldsolution = NULL;
d6d305fe
RB
392 ret->next = 0;
393 ret->head = ret->id;
0bbf2ffa 394
18abb35e
RG
395 stats.total_vars++;
396
9771b263 397 varmap.safe_push (ret);
0bbf2ffa 398
910fdc79
DB
399 return ret;
400}
401
3e8542ca
RG
402
403/* A map mapping call statements to per-stmt variables for uses
404 and clobbers specific to the call. */
355fe088 405static hash_map<gimple *, varinfo_t> *call_stmt_vars;
3e8542ca
RG
406
407/* Lookup or create the variable for the call statement CALL. */
408
409static varinfo_t
538dd0b7 410get_call_vi (gcall *call)
3e8542ca 411{
3e8542ca
RG
412 varinfo_t vi, vi2;
413
b787e7a2
TS
414 bool existed;
415 varinfo_t *slot_p = &call_stmt_vars->get_or_insert (call, &existed);
416 if (existed)
417 return *slot_p;
3e8542ca
RG
418
419 vi = new_var_info (NULL_TREE, "CALLUSED");
420 vi->offset = 0;
421 vi->size = 1;
422 vi->fullsize = 2;
423 vi->is_full_var = true;
424
d6d305fe 425 vi2 = new_var_info (NULL_TREE, "CALLCLOBBERED");
3e8542ca
RG
426 vi2->offset = 1;
427 vi2->size = 1;
428 vi2->fullsize = 2;
429 vi2->is_full_var = true;
430
d6d305fe
RB
431 vi->next = vi2->id;
432
b787e7a2 433 *slot_p = vi;
3e8542ca
RG
434 return vi;
435}
436
437/* Lookup the variable for the call statement CALL representing
438 the uses. Returns NULL if there is nothing special about this call. */
439
440static varinfo_t
538dd0b7 441lookup_call_use_vi (gcall *call)
3e8542ca 442{
b787e7a2 443 varinfo_t *slot_p = call_stmt_vars->get (call);
3e8542ca 444 if (slot_p)
b787e7a2 445 return *slot_p;
3e8542ca
RG
446
447 return NULL;
448}
449
450/* Lookup the variable for the call statement CALL representing
451 the clobbers. Returns NULL if there is nothing special about this call. */
452
453static varinfo_t
538dd0b7 454lookup_call_clobber_vi (gcall *call)
3e8542ca
RG
455{
456 varinfo_t uses = lookup_call_use_vi (call);
457 if (!uses)
458 return NULL;
459
d6d305fe 460 return vi_next (uses);
3e8542ca
RG
461}
462
463/* Lookup or create the variable for the call statement CALL representing
464 the uses. */
465
466static varinfo_t
538dd0b7 467get_call_use_vi (gcall *call)
3e8542ca
RG
468{
469 return get_call_vi (call);
470}
471
472/* Lookup or create the variable for the call statement CALL representing
473 the clobbers. */
474
475static varinfo_t ATTRIBUTE_UNUSED
538dd0b7 476get_call_clobber_vi (gcall *call)
3e8542ca 477{
d6d305fe 478 return vi_next (get_call_vi (call));
3e8542ca
RG
479}
480
481
a79683d5 482enum constraint_expr_type {SCALAR, DEREF, ADDRESSOF};
910fdc79
DB
483
484/* An expression that appears in a constraint. */
485
c58936b6 486struct constraint_expr
910fdc79
DB
487{
488 /* Constraint type. */
489 constraint_expr_type type;
490
491 /* Variable we are referring to in the constraint. */
492 unsigned int var;
493
494 /* Offset, in bits, of this constraint from the beginning of
495 variables it ends up referring to.
496
497 IOW, in a deref constraint, we would deref, get the result set,
498 then add OFFSET to each member. */
5006671f 499 HOST_WIDE_INT offset;
910fdc79
DB
500};
501
5006671f 502/* Use 0x8000... as special unknown offset. */
0cadbfaa 503#define UNKNOWN_OFFSET HOST_WIDE_INT_MIN
5006671f 504
4ee00913 505typedef struct constraint_expr ce_s;
9771b263
DN
506static void get_constraint_for_1 (tree, vec<ce_s> *, bool, bool);
507static void get_constraint_for (tree, vec<ce_s> *);
508static void get_constraint_for_rhs (tree, vec<ce_s> *);
509static void do_deref (vec<ce_s> *);
910fdc79
DB
510
511/* Our set constraints are made up of two constraint expressions, one
c58936b6 512 LHS, and one RHS.
910fdc79
DB
513
514 As described in the introduction, our set constraints each represent an
515 operation between set valued variables.
516*/
517struct constraint
518{
519 struct constraint_expr lhs;
520 struct constraint_expr rhs;
521};
522
523/* List of constraints that we use to build the constraint graph from. */
524
9771b263 525static vec<constraint_t> constraints;
fcb87c50 526static object_allocator<constraint> constraint_pool ("Constraint pool");
910fdc79 527
57250223
DB
528/* The constraint graph is represented as an array of bitmaps
529 containing successor nodes. */
910fdc79
DB
530
531struct constraint_graph
532{
3e5937d7
DB
533 /* Size of this graph, which may be different than the number of
534 nodes in the variable map. */
535 unsigned int size;
536
537 /* Explicit successors of each node. */
57250223 538 bitmap *succs;
3e5937d7
DB
539
540 /* Implicit predecessors of each node (Used for variable
541 substitution). */
542 bitmap *implicit_preds;
543
544 /* Explicit predecessors of each node (Used for variable substitution). */
57250223 545 bitmap *preds;
910fdc79 546
3e5937d7
DB
547 /* Indirect cycle representatives, or -1 if the node has no indirect
548 cycles. */
549 int *indirect_cycles;
550
551 /* Representative node for a node. rep[a] == a unless the node has
552 been unified. */
553 unsigned int *rep;
554
7b765bed 555 /* Equivalence class representative for a label. This is used for
3e5937d7
DB
556 variable substitution. */
557 int *eq_rep;
558
aa46c8a3
DB
559 /* Pointer equivalence label for a node. All nodes with the same
560 pointer equivalence label can be unified together at some point
561 (either during constraint optimization or after the constraint
562 graph is built). */
7b765bed
DB
563 unsigned int *pe;
564
565 /* Pointer equivalence representative for a label. This is used to
566 handle nodes that are pointer equivalent but not location
567 equivalent. We can unite these once the addressof constraints
568 are transformed into initial points-to sets. */
569 int *pe_rep;
570
571 /* Pointer equivalence label for each node, used during variable
572 substitution. */
573 unsigned int *pointer_label;
574
575 /* Location equivalence label for each node, used during location
576 equivalence finding. */
577 unsigned int *loc_label;
578
579 /* Pointed-by set for each node, used during location equivalence
580 finding. This is pointed-by rather than pointed-to, because it
581 is constructed using the predecessor graph. */
582 bitmap *pointed_by;
583
584 /* Points to sets for pointer equivalence. This is *not* the actual
585 points-to sets for nodes. */
586 bitmap *points_to;
3e5937d7
DB
587
588 /* Bitmap of nodes where the bit is set if the node is a direct
589 node. Used for variable substitution. */
590 sbitmap direct_nodes;
591
7b765bed
DB
592 /* Bitmap of nodes where the bit is set if the node is address
593 taken. Used for variable substitution. */
594 bitmap address_taken;
595
3e5937d7
DB
596 /* Vector of complex constraints for each graph node. Complex
597 constraints are those involving dereferences or offsets that are
598 not 0. */
9771b263 599 vec<constraint_t> *complex;
3e5937d7 600};
910fdc79
DB
601
602static constraint_graph_t graph;
603
3e5937d7
DB
604/* During variable substitution and the offline version of indirect
605 cycle finding, we create nodes to represent dereferences and
606 address taken constraints. These represent where these start and
607 end. */
9771b263 608#define FIRST_REF_NODE (varmap).length ()
3e5937d7 609#define LAST_REF_NODE (FIRST_REF_NODE + (FIRST_REF_NODE - 1))
3e5937d7
DB
610
611/* Return the representative node for NODE, if NODE has been unioned
612 with another NODE.
613 This function performs path compression along the way to finding
614 the representative. */
615
616static unsigned int
617find (unsigned int node)
618{
6e55eda7 619 gcc_checking_assert (node < graph->size);
3e5937d7
DB
620 if (graph->rep[node] != node)
621 return graph->rep[node] = find (graph->rep[node]);
622 return node;
623}
624
625/* Union the TO and FROM nodes to the TO nodes.
626 Note that at some point in the future, we may want to do
627 union-by-rank, in which case we are going to have to return the
628 node we unified to. */
629
630static bool
631unite (unsigned int to, unsigned int from)
632{
6e55eda7 633 gcc_checking_assert (to < graph->size && from < graph->size);
3e5937d7
DB
634 if (to != from && graph->rep[from] != to)
635 {
636 graph->rep[from] = to;
637 return true;
638 }
639 return false;
640}
641
910fdc79
DB
642/* Create a new constraint consisting of LHS and RHS expressions. */
643
c58936b6 644static constraint_t
910fdc79
DB
645new_constraint (const struct constraint_expr lhs,
646 const struct constraint_expr rhs)
647{
dc5667a3 648 constraint_t ret = constraint_pool.allocate ();
910fdc79
DB
649 ret->lhs = lhs;
650 ret->rhs = rhs;
651 return ret;
652}
653
654/* Print out constraint C to FILE. */
655
5006671f 656static void
910fdc79
DB
657dump_constraint (FILE *file, constraint_t c)
658{
659 if (c->lhs.type == ADDRESSOF)
660 fprintf (file, "&");
661 else if (c->lhs.type == DEREF)
c58936b6 662 fprintf (file, "*");
5006671f
RG
663 fprintf (file, "%s", get_varinfo (c->lhs.var)->name);
664 if (c->lhs.offset == UNKNOWN_OFFSET)
665 fprintf (file, " + UNKNOWN");
666 else if (c->lhs.offset != 0)
910fdc79
DB
667 fprintf (file, " + " HOST_WIDE_INT_PRINT_DEC, c->lhs.offset);
668 fprintf (file, " = ");
669 if (c->rhs.type == ADDRESSOF)
670 fprintf (file, "&");
671 else if (c->rhs.type == DEREF)
672 fprintf (file, "*");
5006671f
RG
673 fprintf (file, "%s", get_varinfo (c->rhs.var)->name);
674 if (c->rhs.offset == UNKNOWN_OFFSET)
675 fprintf (file, " + UNKNOWN");
676 else if (c->rhs.offset != 0)
910fdc79 677 fprintf (file, " + " HOST_WIDE_INT_PRINT_DEC, c->rhs.offset);
910fdc79
DB
678}
679
5006671f
RG
680
681void debug_constraint (constraint_t);
682void debug_constraints (void);
683void debug_constraint_graph (void);
684void debug_solution_for_var (unsigned int);
685void debug_sa_points_to_info (void);
686
910fdc79
DB
687/* Print out constraint C to stderr. */
688
24e47c76 689DEBUG_FUNCTION void
910fdc79
DB
690debug_constraint (constraint_t c)
691{
692 dump_constraint (stderr, c);
8576f20a 693 fprintf (stderr, "\n");
910fdc79
DB
694}
695
696/* Print out all constraints to FILE */
697
5006671f 698static void
25a6a873 699dump_constraints (FILE *file, int from)
910fdc79
DB
700{
701 int i;
702 constraint_t c;
9771b263 703 for (i = from; constraints.iterate (i, &c); i++)
8576f20a
RG
704 if (c)
705 {
706 dump_constraint (file, c);
707 fprintf (file, "\n");
708 }
910fdc79
DB
709}
710
711/* Print out all constraints to stderr. */
712
24e47c76 713DEBUG_FUNCTION void
910fdc79
DB
714debug_constraints (void)
715{
25a6a873 716 dump_constraints (stderr, 0);
910fdc79
DB
717}
718
fc93bcb6
FP
719/* Print the constraint graph in dot format. */
720
5006671f 721static void
fc93bcb6
FP
722dump_constraint_graph (FILE *file)
723{
8576f20a 724 unsigned int i;
fc93bcb6
FP
725
726 /* Only print the graph if it has already been initialized: */
727 if (!graph)
728 return;
729
fc93bcb6 730 /* Prints the header of the dot file: */
fc93bcb6
FP
731 fprintf (file, "strict digraph {\n");
732 fprintf (file, " node [\n shape = box\n ]\n");
733 fprintf (file, " edge [\n fontsize = \"12\"\n ]\n");
8576f20a
RG
734 fprintf (file, "\n // List of nodes and complex constraints in "
735 "the constraint graph:\n");
736
737 /* The next lines print the nodes in the graph together with the
738 complex constraints attached to them. */
d6d305fe 739 for (i = 1; i < graph->size; i++)
fc93bcb6 740 {
d6d305fe
RB
741 if (i == FIRST_REF_NODE)
742 continue;
8576f20a
RG
743 if (find (i) != i)
744 continue;
745 if (i < FIRST_REF_NODE)
746 fprintf (file, "\"%s\"", get_varinfo (i)->name);
747 else
748 fprintf (file, "\"*%s\"", get_varinfo (i - FIRST_REF_NODE)->name);
9771b263 749 if (graph->complex[i].exists ())
8576f20a
RG
750 {
751 unsigned j;
752 constraint_t c;
753 fprintf (file, " [label=\"\\N\\n");
9771b263 754 for (j = 0; graph->complex[i].iterate (j, &c); ++j)
8576f20a
RG
755 {
756 dump_constraint (file, c);
757 fprintf (file, "\\l");
758 }
759 fprintf (file, "\"]");
760 }
761 fprintf (file, ";\n");
fc93bcb6
FP
762 }
763
8576f20a
RG
764 /* Go over the edges. */
765 fprintf (file, "\n // Edges in the constraint graph:\n");
d6d305fe 766 for (i = 1; i < graph->size; i++)
8576f20a
RG
767 {
768 unsigned j;
769 bitmap_iterator bi;
770 if (find (i) != i)
771 continue;
772 EXECUTE_IF_IN_NONNULL_BITMAP (graph->succs[i], 0, j, bi)
773 {
774 unsigned to = find (j);
775 if (i == to)
776 continue;
777 if (i < FIRST_REF_NODE)
778 fprintf (file, "\"%s\"", get_varinfo (i)->name);
779 else
780 fprintf (file, "\"*%s\"", get_varinfo (i - FIRST_REF_NODE)->name);
781 fprintf (file, " -> ");
782 if (to < FIRST_REF_NODE)
783 fprintf (file, "\"%s\"", get_varinfo (to)->name);
784 else
785 fprintf (file, "\"*%s\"", get_varinfo (to - FIRST_REF_NODE)->name);
786 fprintf (file, ";\n");
787 }
788 }
fc93bcb6 789
8576f20a
RG
790 /* Prints the tail of the dot file. */
791 fprintf (file, "}\n");
fc93bcb6
FP
792}
793
794/* Print out the constraint graph to stderr. */
795
24e47c76 796DEBUG_FUNCTION void
fc93bcb6
FP
797debug_constraint_graph (void)
798{
799 dump_constraint_graph (stderr);
800}
801
c58936b6 802/* SOLVER FUNCTIONS
910fdc79
DB
803
804 The solver is a simple worklist solver, that works on the following
805 algorithm:
c58936b6 806
3e5937d7
DB
807 sbitmap changed_nodes = all zeroes;
808 changed_count = 0;
809 For each node that is not already collapsed:
810 changed_count++;
811 set bit in changed nodes
910fdc79 812
910fdc79
DB
813 while (changed_count > 0)
814 {
815 compute topological ordering for constraint graph
c58936b6 816
910fdc79
DB
817 find and collapse cycles in the constraint graph (updating
818 changed if necessary)
c58936b6 819
910fdc79
DB
820 for each node (n) in the graph in topological order:
821 changed_count--;
822
823 Process each complex constraint associated with the node,
824 updating changed if necessary.
825
826 For each outgoing edge from n, propagate the solution from n to
827 the destination of the edge, updating changed as necessary.
828
829 } */
830
831/* Return true if two constraint expressions A and B are equal. */
832
833static bool
834constraint_expr_equal (struct constraint_expr a, struct constraint_expr b)
835{
4ee00913 836 return a.type == b.type && a.var == b.var && a.offset == b.offset;
910fdc79
DB
837}
838
839/* Return true if constraint expression A is less than constraint expression
840 B. This is just arbitrary, but consistent, in order to give them an
841 ordering. */
842
843static bool
844constraint_expr_less (struct constraint_expr a, struct constraint_expr b)
845{
846 if (a.type == b.type)
847 {
848 if (a.var == b.var)
849 return a.offset < b.offset;
850 else
851 return a.var < b.var;
852 }
853 else
854 return a.type < b.type;
855}
856
857/* Return true if constraint A is less than constraint B. This is just
858 arbitrary, but consistent, in order to give them an ordering. */
859
860static bool
f32682ca 861constraint_less (const constraint_t &a, const constraint_t &b)
910fdc79
DB
862{
863 if (constraint_expr_less (a->lhs, b->lhs))
864 return true;
865 else if (constraint_expr_less (b->lhs, a->lhs))
866 return false;
867 else
868 return constraint_expr_less (a->rhs, b->rhs);
869}
870
871/* Return true if two constraints A and B are equal. */
c58936b6 872
910fdc79
DB
873static bool
874constraint_equal (struct constraint a, struct constraint b)
875{
c58936b6 876 return constraint_expr_equal (a.lhs, b.lhs)
910fdc79
DB
877 && constraint_expr_equal (a.rhs, b.rhs);
878}
879
880
881/* Find a constraint LOOKFOR in the sorted constraint vector VEC */
882
883static constraint_t
9771b263 884constraint_vec_find (vec<constraint_t> vec,
910fdc79
DB
885 struct constraint lookfor)
886{
c58936b6 887 unsigned int place;
910fdc79
DB
888 constraint_t found;
889
9771b263 890 if (!vec.exists ())
910fdc79
DB
891 return NULL;
892
9771b263
DN
893 place = vec.lower_bound (&lookfor, constraint_less);
894 if (place >= vec.length ())
910fdc79 895 return NULL;
9771b263 896 found = vec[place];
910fdc79
DB
897 if (!constraint_equal (*found, lookfor))
898 return NULL;
899 return found;
900}
901
4f6843aa
XDL
902/* Union two constraint vectors, TO and FROM. Put the result in TO.
903 Returns true of TO set is changed. */
910fdc79 904
4f6843aa 905static bool
9771b263
DN
906constraint_set_union (vec<constraint_t> *to,
907 vec<constraint_t> *from)
910fdc79
DB
908{
909 int i;
910 constraint_t c;
4f6843aa 911 bool any_change = false;
910fdc79 912
9771b263 913 FOR_EACH_VEC_ELT (*from, i, c)
910fdc79
DB
914 {
915 if (constraint_vec_find (*to, *c) == NULL)
916 {
9771b263
DN
917 unsigned int place = to->lower_bound (c, constraint_less);
918 to->safe_insert (place, c);
4f6843aa 919 any_change = true;
910fdc79
DB
920 }
921 }
4f6843aa 922 return any_change;
910fdc79
DB
923}
924
d6d305fe 925/* Expands the solution in SET to all sub-fields of variables included. */
5006671f 926
6489e318
RB
927static bitmap
928solution_set_expand (bitmap set, bitmap *expanded)
5006671f
RG
929{
930 bitmap_iterator bi;
5006671f
RG
931 unsigned j;
932
6489e318
RB
933 if (*expanded)
934 return *expanded;
935
936 *expanded = BITMAP_ALLOC (&iteration_obstack);
937
d6d305fe
RB
938 /* In a first pass expand to the head of the variables we need to
939 add all sub-fields off. This avoids quadratic behavior. */
5006671f
RG
940 EXECUTE_IF_SET_IN_BITMAP (set, 0, j, bi)
941 {
942 varinfo_t v = get_varinfo (j);
943 if (v->is_artificial_var
944 || v->is_full_var)
945 continue;
6489e318 946 bitmap_set_bit (*expanded, v->head);
5006671f
RG
947 }
948
d6d305fe 949 /* In the second pass now expand all head variables with subfields. */
6489e318 950 EXECUTE_IF_SET_IN_BITMAP (*expanded, 0, j, bi)
5006671f 951 {
d6d305fe 952 varinfo_t v = get_varinfo (j);
6489e318 953 if (v->head != j)
d6d305fe
RB
954 continue;
955 for (v = vi_next (v); v != NULL; v = vi_next (v))
6489e318 956 bitmap_set_bit (*expanded, v->id);
5006671f 957 }
6489e318
RB
958
959 /* And finally set the rest of the bits from SET. */
960 bitmap_ior_into (*expanded, set);
961
962 return *expanded;
5006671f
RG
963}
964
6489e318 965/* Union solution sets TO and DELTA, and add INC to each member of DELTA in the
d6d305fe 966 process. */
910fdc79 967
d6d305fe 968static bool
6489e318
RB
969set_union_with_increment (bitmap to, bitmap delta, HOST_WIDE_INT inc,
970 bitmap *expanded_delta)
910fdc79 971{
d6d305fe 972 bool changed = false;
910fdc79 973 bitmap_iterator bi;
d6d305fe
RB
974 unsigned int i;
975
6489e318 976 /* If the solution of DELTA contains anything it is good enough to transfer
d6d305fe 977 this to TO. */
6489e318 978 if (bitmap_bit_p (delta, anything_id))
d6d305fe
RB
979 return bitmap_set_bit (to, anything_id);
980
5006671f
RG
981 /* If the offset is unknown we have to expand the solution to
982 all subfields. */
d6d305fe 983 if (inc == UNKNOWN_OFFSET)
5006671f 984 {
6489e318
RB
985 delta = solution_set_expand (delta, expanded_delta);
986 changed |= bitmap_ior_into (to, delta);
d6d305fe 987 return changed;
5006671f
RG
988 }
989
d6d305fe 990 /* For non-zero offset union the offsetted solution into the destination. */
6489e318 991 EXECUTE_IF_SET_IN_BITMAP (delta, 0, i, bi)
910fdc79 992 {
e5bae89b 993 varinfo_t vi = get_varinfo (i);
c58936b6 994
e5bae89b
RG
995 /* If this is a variable with just one field just set its bit
996 in the result. */
997 if (vi->is_artificial_var
998 || vi->is_unknown_size_var
999 || vi->is_full_var)
d6d305fe 1000 changed |= bitmap_set_bit (to, i);
e5bae89b 1001 else
910fdc79 1002 {
af1ab449
RB
1003 HOST_WIDE_INT fieldoffset = vi->offset + inc;
1004 unsigned HOST_WIDE_INT size = vi->size;
5006671f
RG
1005
1006 /* If the offset makes the pointer point to before the
1007 variable use offset zero for the field lookup. */
af1ab449
RB
1008 if (fieldoffset < 0)
1009 vi = get_varinfo (vi->head);
1010 else
1011 vi = first_or_preceding_vi_for_offset (vi, fieldoffset);
1012
1013 do
1014 {
1015 changed |= bitmap_set_bit (to, vi->id);
1016 if (vi->is_full_var
1017 || vi->next == 0)
1018 break;
1019
1020 /* We have to include all fields that overlap the current field
1021 shifted by inc. */
1022 vi = vi_next (vi);
1023 }
1024 while (vi->offset < fieldoffset + size);
910fdc79
DB
1025 }
1026 }
c58936b6 1027
d6d305fe 1028 return changed;
910fdc79
DB
1029}
1030
3e5937d7
DB
1031/* Insert constraint C into the list of complex constraints for graph
1032 node VAR. */
910fdc79
DB
1033
1034static void
3e5937d7
DB
1035insert_into_complex (constraint_graph_t graph,
1036 unsigned int var, constraint_t c)
910fdc79 1037{
9771b263
DN
1038 vec<constraint_t> complex = graph->complex[var];
1039 unsigned int place = complex.lower_bound (c, constraint_less);
3e5937d7
DB
1040
1041 /* Only insert constraints that do not already exist. */
9771b263
DN
1042 if (place >= complex.length ()
1043 || !constraint_equal (*c, *complex[place]))
1044 graph->complex[var].safe_insert (place, c);
910fdc79
DB
1045}
1046
1047
910fdc79 1048/* Condense two variable nodes into a single variable node, by moving
4f6843aa
XDL
1049 all associated info from FROM to TO. Returns true if TO node's
1050 constraint set changes after the merge. */
910fdc79 1051
4f6843aa 1052static bool
3e5937d7
DB
1053merge_node_constraints (constraint_graph_t graph, unsigned int to,
1054 unsigned int from)
910fdc79 1055{
910fdc79
DB
1056 unsigned int i;
1057 constraint_t c;
4f6843aa 1058 bool any_change = false;
c58936b6 1059
6e55eda7 1060 gcc_checking_assert (find (from) == to);
c58936b6 1061
910fdc79 1062 /* Move all complex constraints from src node into to node */
9771b263 1063 FOR_EACH_VEC_ELT (graph->complex[from], i, c)
910fdc79 1064 {
4f6843aa
XDL
1065 /* In complex constraints for node FROM, we may have either
1066 a = *FROM, and *FROM = a, or an offseted constraint which are
3e5937d7 1067 always added to the rhs node's constraints. */
c58936b6 1068
910fdc79
DB
1069 if (c->rhs.type == DEREF)
1070 c->rhs.var = to;
3e5937d7 1071 else if (c->lhs.type == DEREF)
910fdc79 1072 c->lhs.var = to;
3e5937d7
DB
1073 else
1074 c->rhs.var = to;
4f6843aa 1075
910fdc79 1076 }
4f6843aa
XDL
1077 any_change = constraint_set_union (&graph->complex[to],
1078 &graph->complex[from]);
9771b263 1079 graph->complex[from].release ();
4f6843aa 1080 return any_change;
910fdc79
DB
1081}
1082
910fdc79
DB
1083
1084/* Remove edges involving NODE from GRAPH. */
1085
1086static void
1087clear_edges_for_node (constraint_graph_t graph, unsigned int node)
1088{
57250223 1089 if (graph->succs[node])
3e5937d7 1090 BITMAP_FREE (graph->succs[node]);
f71ef09d
DB
1091}
1092
910fdc79
DB
1093/* Merge GRAPH nodes FROM and TO into node TO. */
1094
1095static void
c58936b6 1096merge_graph_nodes (constraint_graph_t graph, unsigned int to,
910fdc79
DB
1097 unsigned int from)
1098{
3e5937d7 1099 if (graph->indirect_cycles[from] != -1)
4ee00913 1100 {
3e5937d7
DB
1101 /* If we have indirect cycles with the from node, and we have
1102 none on the to node, the to node has indirect cycles from the
1103 from node now that they are unified.
1104 If indirect cycles exist on both, unify the nodes that they
1105 are in a cycle with, since we know they are in a cycle with
1106 each other. */
1107 if (graph->indirect_cycles[to] == -1)
7b765bed 1108 graph->indirect_cycles[to] = graph->indirect_cycles[from];
4ee00913 1109 }
910fdc79 1110
57250223
DB
1111 /* Merge all the successor edges. */
1112 if (graph->succs[from])
4ee00913 1113 {
57250223 1114 if (!graph->succs[to])
3e5937d7 1115 graph->succs[to] = BITMAP_ALLOC (&pta_obstack);
c58936b6 1116 bitmap_ior_into (graph->succs[to],
57250223 1117 graph->succs[from]);
4ee00913 1118 }
4ee00913 1119
910fdc79
DB
1120 clear_edges_for_node (graph, from);
1121}
1122
3e5937d7
DB
1123
1124/* Add an indirect graph edge to GRAPH, going from TO to FROM if
1125 it doesn't exist in the graph already. */
1126
1127static void
1128add_implicit_graph_edge (constraint_graph_t graph, unsigned int to,
1129 unsigned int from)
1130{
1131 if (to == from)
1132 return;
1133
1134 if (!graph->implicit_preds[to])
1135 graph->implicit_preds[to] = BITMAP_ALLOC (&predbitmap_obstack);
1136
5f0d975b
RG
1137 if (bitmap_set_bit (graph->implicit_preds[to], from))
1138 stats.num_implicit_edges++;
3e5937d7
DB
1139}
1140
1141/* Add a predecessor graph edge to GRAPH, going from TO to FROM if
1142 it doesn't exist in the graph already.
1143 Return false if the edge already existed, true otherwise. */
1144
1145static void
1146add_pred_graph_edge (constraint_graph_t graph, unsigned int to,
1147 unsigned int from)
1148{
1149 if (!graph->preds[to])
1150 graph->preds[to] = BITMAP_ALLOC (&predbitmap_obstack);
5f0d975b 1151 bitmap_set_bit (graph->preds[to], from);
3e5937d7
DB
1152}
1153
1154/* Add a graph edge to GRAPH, going from FROM to TO if
910fdc79
DB
1155 it doesn't exist in the graph already.
1156 Return false if the edge already existed, true otherwise. */
1157
1158static bool
57250223
DB
1159add_graph_edge (constraint_graph_t graph, unsigned int to,
1160 unsigned int from)
910fdc79 1161{
57250223 1162 if (to == from)
910fdc79
DB
1163 {
1164 return false;
1165 }
1166 else
1167 {
4ee00913 1168 bool r = false;
c58936b6 1169
57250223 1170 if (!graph->succs[from])
3e5937d7 1171 graph->succs[from] = BITMAP_ALLOC (&pta_obstack);
5f0d975b 1172 if (bitmap_set_bit (graph->succs[from], to))
f71ef09d 1173 {
57250223 1174 r = true;
3e5937d7
DB
1175 if (to < FIRST_REF_NODE && from < FIRST_REF_NODE)
1176 stats.num_edges++;
f71ef09d 1177 }
910fdc79
DB
1178 return r;
1179 }
1180}
1181
1182
7b765bed
DB
1183/* Initialize the constraint graph structure to contain SIZE nodes. */
1184
1185static void
1186init_graph (unsigned int size)
1187{
1188 unsigned int j;
1189
1190 graph = XCNEW (struct constraint_graph);
1191 graph->size = size;
1192 graph->succs = XCNEWVEC (bitmap, graph->size);
1193 graph->indirect_cycles = XNEWVEC (int, graph->size);
1194 graph->rep = XNEWVEC (unsigned int, graph->size);
9771b263
DN
1195 /* ??? Macros do not support template types with multiple arguments,
1196 so we use a typedef to work around it. */
1197 typedef vec<constraint_t> vec_constraint_t_heap;
1198 graph->complex = XCNEWVEC (vec_constraint_t_heap, size);
aa46c8a3 1199 graph->pe = XCNEWVEC (unsigned int, graph->size);
7b765bed
DB
1200 graph->pe_rep = XNEWVEC (int, graph->size);
1201
1202 for (j = 0; j < graph->size; j++)
1203 {
1204 graph->rep[j] = j;
7b765bed
DB
1205 graph->pe_rep[j] = -1;
1206 graph->indirect_cycles[j] = -1;
1207 }
1208}
1209
3e5937d7 1210/* Build the constraint graph, adding only predecessor edges right now. */
910fdc79
DB
1211
1212static void
3e5937d7 1213build_pred_graph (void)
910fdc79 1214{
3e5937d7 1215 int i;
910fdc79 1216 constraint_t c;
3e5937d7 1217 unsigned int j;
910fdc79 1218
3e5937d7
DB
1219 graph->implicit_preds = XCNEWVEC (bitmap, graph->size);
1220 graph->preds = XCNEWVEC (bitmap, graph->size);
7b765bed
DB
1221 graph->pointer_label = XCNEWVEC (unsigned int, graph->size);
1222 graph->loc_label = XCNEWVEC (unsigned int, graph->size);
1223 graph->pointed_by = XCNEWVEC (bitmap, graph->size);
1224 graph->points_to = XCNEWVEC (bitmap, graph->size);
3e5937d7 1225 graph->eq_rep = XNEWVEC (int, graph->size);
3e5937d7 1226 graph->direct_nodes = sbitmap_alloc (graph->size);
7b765bed 1227 graph->address_taken = BITMAP_ALLOC (&predbitmap_obstack);
f61e445a 1228 bitmap_clear (graph->direct_nodes);
3e5937d7 1229
d6d305fe 1230 for (j = 1; j < FIRST_REF_NODE; j++)
3e5937d7
DB
1231 {
1232 if (!get_varinfo (j)->is_special_var)
d7c028c0 1233 bitmap_set_bit (graph->direct_nodes, j);
3e5937d7
DB
1234 }
1235
1236 for (j = 0; j < graph->size; j++)
7b765bed 1237 graph->eq_rep[j] = -1;
3e5937d7 1238
9771b263 1239 for (j = 0; j < varmap.length (); j++)
3e5937d7 1240 graph->indirect_cycles[j] = -1;
e8ca4159 1241
9771b263 1242 FOR_EACH_VEC_ELT (constraints, i, c)
910fdc79
DB
1243 {
1244 struct constraint_expr lhs = c->lhs;
1245 struct constraint_expr rhs = c->rhs;
5006671f
RG
1246 unsigned int lhsvar = lhs.var;
1247 unsigned int rhsvar = rhs.var;
03190594 1248
910fdc79
DB
1249 if (lhs.type == DEREF)
1250 {
3e5937d7
DB
1251 /* *x = y. */
1252 if (rhs.offset == 0 && lhs.offset == 0 && rhs.type == SCALAR)
1253 add_pred_graph_edge (graph, FIRST_REF_NODE + lhsvar, rhsvar);
910fdc79
DB
1254 }
1255 else if (rhs.type == DEREF)
1256 {
3e5937d7
DB
1257 /* x = *y */
1258 if (rhs.offset == 0 && lhs.offset == 0 && lhs.type == SCALAR)
1259 add_pred_graph_edge (graph, lhsvar, FIRST_REF_NODE + rhsvar);
1260 else
d7c028c0 1261 bitmap_clear_bit (graph->direct_nodes, lhsvar);
910fdc79 1262 }
3e5937d7 1263 else if (rhs.type == ADDRESSOF)
910fdc79 1264 {
10bd6c5c
RG
1265 varinfo_t v;
1266
910fdc79 1267 /* x = &y */
7b765bed
DB
1268 if (graph->points_to[lhsvar] == NULL)
1269 graph->points_to[lhsvar] = BITMAP_ALLOC (&predbitmap_obstack);
1270 bitmap_set_bit (graph->points_to[lhsvar], rhsvar);
1271
1272 if (graph->pointed_by[rhsvar] == NULL)
1273 graph->pointed_by[rhsvar] = BITMAP_ALLOC (&predbitmap_obstack);
1274 bitmap_set_bit (graph->pointed_by[rhsvar], lhsvar);
1275
3e5937d7
DB
1276 /* Implicitly, *x = y */
1277 add_implicit_graph_edge (graph, FIRST_REF_NODE + lhsvar, rhsvar);
1278
10bd6c5c 1279 /* All related variables are no longer direct nodes. */
d7c028c0 1280 bitmap_clear_bit (graph->direct_nodes, rhsvar);
5006671f
RG
1281 v = get_varinfo (rhsvar);
1282 if (!v->is_full_var)
1283 {
d6d305fe 1284 v = get_varinfo (v->head);
5006671f
RG
1285 do
1286 {
d7c028c0 1287 bitmap_clear_bit (graph->direct_nodes, v->id);
d6d305fe 1288 v = vi_next (v);
5006671f
RG
1289 }
1290 while (v != NULL);
1291 }
7b765bed 1292 bitmap_set_bit (graph->address_taken, rhsvar);
910fdc79 1293 }
3e5937d7
DB
1294 else if (lhsvar > anything_id
1295 && lhsvar != rhsvar && lhs.offset == 0 && rhs.offset == 0)
910fdc79 1296 {
3e5937d7
DB
1297 /* x = y */
1298 add_pred_graph_edge (graph, lhsvar, rhsvar);
1299 /* Implicitly, *x = *y */
1300 add_implicit_graph_edge (graph, FIRST_REF_NODE + lhsvar,
1301 FIRST_REF_NODE + rhsvar);
1302 }
1303 else if (lhs.offset != 0 || rhs.offset != 0)
1304 {
1305 if (rhs.offset != 0)
d7c028c0 1306 bitmap_clear_bit (graph->direct_nodes, lhs.var);
7b765bed 1307 else if (lhs.offset != 0)
d7c028c0 1308 bitmap_clear_bit (graph->direct_nodes, rhs.var);
3e5937d7
DB
1309 }
1310 }
1311}
1312
1313/* Build the constraint graph, adding successor edges. */
1314
1315static void
1316build_succ_graph (void)
1317{
9e39dba6 1318 unsigned i, t;
3e5937d7
DB
1319 constraint_t c;
1320
9771b263 1321 FOR_EACH_VEC_ELT (constraints, i, c)
3e5937d7
DB
1322 {
1323 struct constraint_expr lhs;
1324 struct constraint_expr rhs;
1325 unsigned int lhsvar;
1326 unsigned int rhsvar;
1327
1328 if (!c)
1329 continue;
c58936b6 1330
3e5937d7
DB
1331 lhs = c->lhs;
1332 rhs = c->rhs;
5006671f
RG
1333 lhsvar = find (lhs.var);
1334 rhsvar = find (rhs.var);
3e5937d7
DB
1335
1336 if (lhs.type == DEREF)
1337 {
1338 if (rhs.offset == 0 && lhs.offset == 0 && rhs.type == SCALAR)
1339 add_graph_edge (graph, FIRST_REF_NODE + lhsvar, rhsvar);
1340 }
1341 else if (rhs.type == DEREF)
1342 {
1343 if (rhs.offset == 0 && lhs.offset == 0 && lhs.type == SCALAR)
1344 add_graph_edge (graph, lhsvar, FIRST_REF_NODE + rhsvar);
1345 }
1346 else if (rhs.type == ADDRESSOF)
1347 {
1348 /* x = &y */
6e55eda7 1349 gcc_checking_assert (find (rhs.var) == rhs.var);
3e5937d7
DB
1350 bitmap_set_bit (get_varinfo (lhsvar)->solution, rhsvar);
1351 }
1352 else if (lhsvar > anything_id
1353 && lhsvar != rhsvar && lhs.offset == 0 && rhs.offset == 0)
1354 {
1355 add_graph_edge (graph, lhsvar, rhsvar);
910fdc79
DB
1356 }
1357 }
9e39dba6 1358
de925a03
RG
1359 /* Add edges from STOREDANYTHING to all non-direct nodes that can
1360 receive pointers. */
9e39dba6
RG
1361 t = find (storedanything_id);
1362 for (i = integer_id + 1; i < FIRST_REF_NODE; ++i)
1363 {
d7c028c0 1364 if (!bitmap_bit_p (graph->direct_nodes, i)
de925a03 1365 && get_varinfo (i)->may_have_pointers)
9e39dba6
RG
1366 add_graph_edge (graph, find (i), t);
1367 }
379c6f48
RG
1368
1369 /* Everything stored to ANYTHING also potentially escapes. */
1370 add_graph_edge (graph, find (escaped_id), t);
910fdc79 1371}
e8ca4159
DN
1372
1373
910fdc79 1374/* Changed variables on the last iteration. */
648b5f85 1375static bitmap changed;
910fdc79 1376
910fdc79
DB
1377/* Strongly Connected Component visitation info. */
1378
1379struct scc_info
1380{
1381 sbitmap visited;
7b765bed 1382 sbitmap deleted;
3e5937d7
DB
1383 unsigned int *dfs;
1384 unsigned int *node_mapping;
910fdc79 1385 int current_index;
9771b263 1386 vec<unsigned> scc_stack;
910fdc79
DB
1387};
1388
1389
1390/* Recursive routine to find strongly connected components in GRAPH.
1391 SI is the SCC info to store the information in, and N is the id of current
1392 graph node we are processing.
c58936b6 1393
910fdc79 1394 This is Tarjan's strongly connected component finding algorithm, as
c58936b6 1395 modified by Nuutila to keep only non-root nodes on the stack.
910fdc79
DB
1396 The algorithm can be found in "On finding the strongly connected
1397 connected components in a directed graph" by Esko Nuutila and Eljas
1398 Soisalon-Soininen, in Information Processing Letters volume 49,
1399 number 1, pages 9-14. */
1400
1401static void
1402scc_visit (constraint_graph_t graph, struct scc_info *si, unsigned int n)
1403{
4ee00913
DB
1404 unsigned int i;
1405 bitmap_iterator bi;
3e5937d7 1406 unsigned int my_dfs;
910fdc79 1407
d7c028c0 1408 bitmap_set_bit (si->visited, n);
3e5937d7
DB
1409 si->dfs[n] = si->current_index ++;
1410 my_dfs = si->dfs[n];
c58936b6 1411
910fdc79 1412 /* Visit all the successors. */
57250223 1413 EXECUTE_IF_IN_NONNULL_BITMAP (graph->succs[n], 0, i, bi)
910fdc79 1414 {
3e5937d7
DB
1415 unsigned int w;
1416
1417 if (i > LAST_REF_NODE)
1418 break;
1419
1420 w = find (i);
d7c028c0 1421 if (bitmap_bit_p (si->deleted, w))
3e5937d7
DB
1422 continue;
1423
d7c028c0 1424 if (!bitmap_bit_p (si->visited, w))
4ee00913 1425 scc_visit (graph, si, w);
3e5937d7 1426
6e55eda7
RB
1427 unsigned int t = find (w);
1428 gcc_checking_assert (find (n) == n);
1429 if (si->dfs[t] < si->dfs[n])
1430 si->dfs[n] = si->dfs[t];
910fdc79 1431 }
c58936b6 1432
910fdc79 1433 /* See if any components have been identified. */
3e5937d7 1434 if (si->dfs[n] == my_dfs)
910fdc79 1435 {
9771b263
DN
1436 if (si->scc_stack.length () > 0
1437 && si->dfs[si->scc_stack.last ()] >= my_dfs)
910fdc79 1438 {
3e5937d7 1439 bitmap scc = BITMAP_ALLOC (NULL);
3e5937d7
DB
1440 unsigned int lowest_node;
1441 bitmap_iterator bi;
910fdc79 1442
3e5937d7 1443 bitmap_set_bit (scc, n);
910fdc79 1444
9771b263
DN
1445 while (si->scc_stack.length () != 0
1446 && si->dfs[si->scc_stack.last ()] >= my_dfs)
3e5937d7 1447 {
9771b263 1448 unsigned int w = si->scc_stack.pop ();
910fdc79 1449
3e5937d7 1450 bitmap_set_bit (scc, w);
3e5937d7 1451 }
4ee00913 1452
3e5937d7
DB
1453 lowest_node = bitmap_first_set_bit (scc);
1454 gcc_assert (lowest_node < FIRST_REF_NODE);
7b765bed
DB
1455
1456 /* Collapse the SCC nodes into a single node, and mark the
1457 indirect cycles. */
3e5937d7
DB
1458 EXECUTE_IF_SET_IN_BITMAP (scc, 0, i, bi)
1459 {
1460 if (i < FIRST_REF_NODE)
1461 {
3e5937d7
DB
1462 if (unite (lowest_node, i))
1463 unify_nodes (graph, lowest_node, i, false);
1464 }
1465 else
1466 {
1467 unite (lowest_node, i);
1468 graph->indirect_cycles[i - FIRST_REF_NODE] = lowest_node;
1469 }
1470 }
4ee00913 1471 }
d7c028c0 1472 bitmap_set_bit (si->deleted, n);
910fdc79 1473 }
3e5937d7 1474 else
9771b263 1475 si->scc_stack.safe_push (n);
910fdc79
DB
1476}
1477
3e5937d7
DB
1478/* Unify node FROM into node TO, updating the changed count if
1479 necessary when UPDATE_CHANGED is true. */
910fdc79
DB
1480
1481static void
3e5937d7
DB
1482unify_nodes (constraint_graph_t graph, unsigned int to, unsigned int from,
1483 bool update_changed)
910fdc79 1484{
6e55eda7 1485 gcc_checking_assert (to != from && find (to) == to);
910fdc79 1486
3e5937d7
DB
1487 if (dump_file && (dump_flags & TDF_DETAILS))
1488 fprintf (dump_file, "Unifying %s to %s\n",
1489 get_varinfo (from)->name,
1490 get_varinfo (to)->name);
910fdc79 1491
3e5937d7
DB
1492 if (update_changed)
1493 stats.unified_vars_dynamic++;
1494 else
1495 stats.unified_vars_static++;
910fdc79 1496
3e5937d7 1497 merge_graph_nodes (graph, to, from);
4f6843aa
XDL
1498 if (merge_node_constraints (graph, to, from))
1499 {
1500 if (update_changed)
1501 bitmap_set_bit (changed, to);
1502 }
c58936b6 1503
7b765bed
DB
1504 /* Mark TO as changed if FROM was changed. If TO was already marked
1505 as changed, decrease the changed count. */
1506
648b5f85 1507 if (update_changed
6e55eda7
RB
1508 && bitmap_clear_bit (changed, from))
1509 bitmap_set_bit (changed, to);
1510 varinfo_t fromvi = get_varinfo (from);
1511 if (fromvi->solution)
3e5937d7 1512 {
aa46c8a3
DB
1513 /* If the solution changes because of the merging, we need to mark
1514 the variable as changed. */
6e55eda7
RB
1515 varinfo_t tovi = get_varinfo (to);
1516 if (bitmap_ior_into (tovi->solution, fromvi->solution))
910fdc79 1517 {
648b5f85
RG
1518 if (update_changed)
1519 bitmap_set_bit (changed, to);
aa46c8a3 1520 }
b8698a0f 1521
6e55eda7
RB
1522 BITMAP_FREE (fromvi->solution);
1523 if (fromvi->oldsolution)
1524 BITMAP_FREE (fromvi->oldsolution);
b8698a0f 1525
74d8fa44 1526 if (stats.iterations > 0
6e55eda7
RB
1527 && tovi->oldsolution)
1528 BITMAP_FREE (tovi->oldsolution);
910fdc79 1529 }
6e55eda7
RB
1530 if (graph->succs[to])
1531 bitmap_clear_bit (graph->succs[to], to);
910fdc79
DB
1532}
1533
910fdc79
DB
1534/* Information needed to compute the topological ordering of a graph. */
1535
1536struct topo_info
1537{
1538 /* sbitmap of visited nodes. */
1539 sbitmap visited;
1540 /* Array that stores the topological order of the graph, *in
1541 reverse*. */
9771b263 1542 vec<unsigned> topo_order;
910fdc79
DB
1543};
1544
1545
1546/* Initialize and return a topological info structure. */
1547
1548static struct topo_info *
1549init_topo_info (void)
1550{
7b765bed 1551 size_t size = graph->size;
5ed6ace5 1552 struct topo_info *ti = XNEW (struct topo_info);
910fdc79 1553 ti->visited = sbitmap_alloc (size);
f61e445a 1554 bitmap_clear (ti->visited);
9771b263 1555 ti->topo_order.create (1);
910fdc79
DB
1556 return ti;
1557}
1558
1559
1560/* Free the topological sort info pointed to by TI. */
1561
1562static void
1563free_topo_info (struct topo_info *ti)
1564{
1565 sbitmap_free (ti->visited);
9771b263 1566 ti->topo_order.release ();
910fdc79
DB
1567 free (ti);
1568}
1569
1570/* Visit the graph in topological order, and store the order in the
1571 topo_info structure. */
1572
1573static void
1574topo_visit (constraint_graph_t graph, struct topo_info *ti,
1575 unsigned int n)
1576{
4ee00913 1577 bitmap_iterator bi;
4ee00913
DB
1578 unsigned int j;
1579
d7c028c0 1580 bitmap_set_bit (ti->visited, n);
4ee00913 1581
3e5937d7
DB
1582 if (graph->succs[n])
1583 EXECUTE_IF_SET_IN_BITMAP (graph->succs[n], 0, j, bi)
4ee00913 1584 {
d7c028c0 1585 if (!bitmap_bit_p (ti->visited, j))
4ee00913
DB
1586 topo_visit (graph, ti, j);
1587 }
3e5937d7 1588
9771b263 1589 ti->topo_order.safe_push (n);
910fdc79
DB
1590}
1591
5006671f
RG
1592/* Process a constraint C that represents x = *(y + off), using DELTA as the
1593 starting solution for y. */
910fdc79
DB
1594
1595static void
1596do_sd_constraint (constraint_graph_t graph, constraint_t c,
6489e318 1597 bitmap delta, bitmap *expanded_delta)
910fdc79 1598{
7b765bed 1599 unsigned int lhs = c->lhs.var;
910fdc79
DB
1600 bool flag = false;
1601 bitmap sol = get_varinfo (lhs)->solution;
1602 unsigned int j;
1603 bitmap_iterator bi;
5006671f 1604 HOST_WIDE_INT roffset = c->rhs.offset;
4ee00913 1605
5006671f 1606 /* Our IL does not allow this. */
6e55eda7 1607 gcc_checking_assert (c->lhs.offset == 0);
0e1f4c6b 1608
5006671f
RG
1609 /* If the solution of Y contains anything it is good enough to transfer
1610 this to the LHS. */
14c28276
RG
1611 if (bitmap_bit_p (delta, anything_id))
1612 {
1613 flag |= bitmap_set_bit (sol, anything_id);
1614 goto done;
1615 }
1616
5006671f
RG
1617 /* If we do not know at with offset the rhs is dereferenced compute
1618 the reachability set of DELTA, conservatively assuming it is
1619 dereferenced at all valid offsets. */
1620 if (roffset == UNKNOWN_OFFSET)
1621 {
6489e318 1622 delta = solution_set_expand (delta, expanded_delta);
5006671f
RG
1623 /* No further offset processing is necessary. */
1624 roffset = 0;
1625 }
1626
c58936b6 1627 /* For each variable j in delta (Sol(y)), add
910fdc79
DB
1628 an edge in the graph from j to x, and union Sol(j) into Sol(x). */
1629 EXECUTE_IF_SET_IN_BITMAP (delta, 0, j, bi)
1630 {
5006671f
RG
1631 varinfo_t v = get_varinfo (j);
1632 HOST_WIDE_INT fieldoffset = v->offset + roffset;
af1ab449 1633 unsigned HOST_WIDE_INT size = v->size;
5006671f
RG
1634 unsigned int t;
1635
1636 if (v->is_full_var)
af1ab449 1637 ;
5006671f 1638 else if (roffset != 0)
af1ab449
RB
1639 {
1640 if (fieldoffset < 0)
1641 v = get_varinfo (v->head);
1642 else
1643 v = first_or_preceding_vi_for_offset (v, fieldoffset);
1644 }
910fdc79 1645
af1ab449
RB
1646 /* We have to include all fields that overlap the current field
1647 shifted by roffset. */
5006671f
RG
1648 do
1649 {
3e5937d7 1650 t = find (v->id);
4ee00913
DB
1651
1652 /* Adding edges from the special vars is pointless.
1653 They don't have sets that can change. */
b7091901 1654 if (get_varinfo (t)->is_special_var)
4ee00913 1655 flag |= bitmap_ior_into (sol, get_varinfo (t)->solution);
b7091901 1656 /* Merging the solution from ESCAPED needlessly increases
472c7fbd 1657 the set. Use ESCAPED as representative instead. */
5006671f 1658 else if (v->id == escaped_id)
6a66f28e 1659 flag |= bitmap_set_bit (sol, escaped_id);
3c323b52
RG
1660 else if (v->may_have_pointers
1661 && add_graph_edge (graph, lhs, t))
4ee00913 1662 flag |= bitmap_ior_into (sol, get_varinfo (t)->solution);
5006671f 1663
af1ab449 1664 if (v->is_full_var
d6d305fe 1665 || v->next == 0)
5006671f
RG
1666 break;
1667
d6d305fe 1668 v = vi_next (v);
910fdc79 1669 }
af1ab449 1670 while (v->offset < fieldoffset + size);
910fdc79 1671 }
4cf4d6a3 1672
4ee00913 1673done:
910fdc79
DB
1674 /* If the LHS solution changed, mark the var as changed. */
1675 if (flag)
1676 {
1677 get_varinfo (lhs)->solution = sol;
648b5f85 1678 bitmap_set_bit (changed, lhs);
c58936b6 1679 }
910fdc79
DB
1680}
1681
5006671f
RG
1682/* Process a constraint C that represents *(x + off) = y using DELTA
1683 as the starting solution for x. */
910fdc79
DB
1684
1685static void
6489e318 1686do_ds_constraint (constraint_t c, bitmap delta, bitmap *expanded_delta)
910fdc79 1687{
7b765bed 1688 unsigned int rhs = c->rhs.var;
910fdc79
DB
1689 bitmap sol = get_varinfo (rhs)->solution;
1690 unsigned int j;
1691 bitmap_iterator bi;
5006671f 1692 HOST_WIDE_INT loff = c->lhs.offset;
11152c95 1693 bool escaped_p = false;
910fdc79 1694
9e39dba6 1695 /* Our IL does not allow this. */
6e55eda7 1696 gcc_checking_assert (c->rhs.offset == 0);
9e39dba6
RG
1697
1698 /* If the solution of y contains ANYTHING simply use the ANYTHING
1699 solution. This avoids needlessly increasing the points-to sets. */
1700 if (bitmap_bit_p (sol, anything_id))
1701 sol = get_varinfo (find (anything_id))->solution;
1702
1703 /* If the solution for x contains ANYTHING we have to merge the
1704 solution of y into all pointer variables which we do via
1705 STOREDANYTHING. */
1706 if (bitmap_bit_p (delta, anything_id))
1707 {
1708 unsigned t = find (storedanything_id);
1709 if (add_graph_edge (graph, t, rhs))
1710 {
1711 if (bitmap_ior_into (get_varinfo (t)->solution, sol))
648b5f85 1712 bitmap_set_bit (changed, t);
9e39dba6
RG
1713 }
1714 return;
1715 }
4ee00913 1716
5006671f
RG
1717 /* If we do not know at with offset the rhs is dereferenced compute
1718 the reachability set of DELTA, conservatively assuming it is
1719 dereferenced at all valid offsets. */
1720 if (loff == UNKNOWN_OFFSET)
1721 {
6489e318 1722 delta = solution_set_expand (delta, expanded_delta);
5006671f
RG
1723 loff = 0;
1724 }
1725
910fdc79
DB
1726 /* For each member j of delta (Sol(x)), add an edge from y to j and
1727 union Sol(y) into Sol(j) */
1728 EXECUTE_IF_SET_IN_BITMAP (delta, 0, j, bi)
1729 {
5006671f
RG
1730 varinfo_t v = get_varinfo (j);
1731 unsigned int t;
1732 HOST_WIDE_INT fieldoffset = v->offset + loff;
af1ab449 1733 unsigned HOST_WIDE_INT size = v->size;
c58936b6 1734
5006671f 1735 if (v->is_full_var)
af1ab449 1736 ;
5006671f 1737 else if (loff != 0)
af1ab449
RB
1738 {
1739 if (fieldoffset < 0)
1740 v = get_varinfo (v->head);
1741 else
1742 v = first_or_preceding_vi_for_offset (v, fieldoffset);
1743 }
57250223 1744
af1ab449
RB
1745 /* We have to include all fields that overlap the current field
1746 shifted by loff. */
5006671f
RG
1747 do
1748 {
9e39dba6 1749 if (v->may_have_pointers)
910fdc79 1750 {
11152c95
RG
1751 /* If v is a global variable then this is an escape point. */
1752 if (v->is_global_var
1753 && !escaped_p)
1754 {
1755 t = find (escaped_id);
1756 if (add_graph_edge (graph, t, rhs)
648b5f85
RG
1757 && bitmap_ior_into (get_varinfo (t)->solution, sol))
1758 bitmap_set_bit (changed, t);
11152c95
RG
1759 /* Enough to let rhs escape once. */
1760 escaped_p = true;
1761 }
1762
1763 if (v->is_special_var)
1764 break;
1765
9e39dba6 1766 t = find (v->id);
de70bb20 1767 if (add_graph_edge (graph, t, rhs)
648b5f85
RG
1768 && bitmap_ior_into (get_varinfo (t)->solution, sol))
1769 bitmap_set_bit (changed, t);
de70bb20 1770 }
5006671f 1771
af1ab449 1772 if (v->is_full_var
d6d305fe 1773 || v->next == 0)
5006671f
RG
1774 break;
1775
d6d305fe 1776 v = vi_next (v);
57250223 1777 }
af1ab449 1778 while (v->offset < fieldoffset + size);
910fdc79
DB
1779 }
1780}
1781
3e5937d7
DB
1782/* Handle a non-simple (simple meaning requires no iteration),
1783 constraint (IE *x = &y, x = *y, *x = y, and x = y with offsets involved). */
c58936b6 1784
910fdc79 1785static void
6489e318
RB
1786do_complex_constraint (constraint_graph_t graph, constraint_t c, bitmap delta,
1787 bitmap *expanded_delta)
910fdc79
DB
1788{
1789 if (c->lhs.type == DEREF)
1790 {
1791 if (c->rhs.type == ADDRESSOF)
1792 {
c3284718 1793 gcc_unreachable ();
910fdc79
DB
1794 }
1795 else
1796 {
1797 /* *x = y */
6489e318 1798 do_ds_constraint (c, delta, expanded_delta);
910fdc79
DB
1799 }
1800 }
57250223 1801 else if (c->rhs.type == DEREF)
910fdc79
DB
1802 {
1803 /* x = *y */
13c2c08b 1804 if (!(get_varinfo (c->lhs.var)->is_special_var))
6489e318 1805 do_sd_constraint (graph, c, delta, expanded_delta);
910fdc79 1806 }
c58936b6 1807 else
57250223 1808 {
c58936b6 1809 bitmap tmp;
57250223 1810 bool flag = false;
57250223 1811
8cfaeac7
RB
1812 gcc_checking_assert (c->rhs.type == SCALAR && c->lhs.type == SCALAR
1813 && c->rhs.offset != 0 && c->lhs.offset == 0);
7b765bed 1814 tmp = get_varinfo (c->lhs.var)->solution;
57250223 1815
6489e318
RB
1816 flag = set_union_with_increment (tmp, delta, c->rhs.offset,
1817 expanded_delta);
c58936b6 1818
57250223 1819 if (flag)
d6d305fe 1820 bitmap_set_bit (changed, c->lhs.var);
57250223 1821 }
910fdc79
DB
1822}
1823
1824/* Initialize and return a new SCC info structure. */
1825
1826static struct scc_info *
3e5937d7 1827init_scc_info (size_t size)
910fdc79 1828{
5ed6ace5 1829 struct scc_info *si = XNEW (struct scc_info);
3e5937d7 1830 size_t i;
910fdc79
DB
1831
1832 si->current_index = 0;
1833 si->visited = sbitmap_alloc (size);
f61e445a 1834 bitmap_clear (si->visited);
7b765bed 1835 si->deleted = sbitmap_alloc (size);
f61e445a 1836 bitmap_clear (si->deleted);
3e5937d7
DB
1837 si->node_mapping = XNEWVEC (unsigned int, size);
1838 si->dfs = XCNEWVEC (unsigned int, size);
1839
1840 for (i = 0; i < size; i++)
1841 si->node_mapping[i] = i;
1842
9771b263 1843 si->scc_stack.create (1);
910fdc79
DB
1844 return si;
1845}
1846
1847/* Free an SCC info structure pointed to by SI */
1848
1849static void
1850free_scc_info (struct scc_info *si)
c58936b6 1851{
910fdc79 1852 sbitmap_free (si->visited);
7b765bed 1853 sbitmap_free (si->deleted);
3e5937d7
DB
1854 free (si->node_mapping);
1855 free (si->dfs);
9771b263 1856 si->scc_stack.release ();
3e5937d7 1857 free (si);
910fdc79
DB
1858}
1859
1860
3e5937d7
DB
1861/* Find indirect cycles in GRAPH that occur, using strongly connected
1862 components, and note them in the indirect cycles map.
1863
1864 This technique comes from Ben Hardekopf and Calvin Lin,
1865 "It Pays to be Lazy: Fast and Accurate Pointer Analysis for Millions of
1866 Lines of Code", submitted to PLDI 2007. */
910fdc79
DB
1867
1868static void
3e5937d7 1869find_indirect_cycles (constraint_graph_t graph)
910fdc79
DB
1870{
1871 unsigned int i;
3e5937d7
DB
1872 unsigned int size = graph->size;
1873 struct scc_info *si = init_scc_info (size);
910fdc79 1874
3e5937d7 1875 for (i = 0; i < MIN (LAST_REF_NODE, size); i ++ )
d7c028c0 1876 if (!bitmap_bit_p (si->visited, i) && find (i) == i)
910fdc79 1877 scc_visit (graph, si, i);
c58936b6 1878
910fdc79
DB
1879 free_scc_info (si);
1880}
1881
1882/* Compute a topological ordering for GRAPH, and store the result in the
1883 topo_info structure TI. */
1884
c58936b6 1885static void
910fdc79
DB
1886compute_topo_order (constraint_graph_t graph,
1887 struct topo_info *ti)
1888{
1889 unsigned int i;
7b765bed 1890 unsigned int size = graph->size;
c58936b6 1891
910fdc79 1892 for (i = 0; i != size; ++i)
d7c028c0 1893 if (!bitmap_bit_p (ti->visited, i) && find (i) == i)
910fdc79
DB
1894 topo_visit (graph, ti, i);
1895}
1896
7b765bed
DB
1897/* Structure used to for hash value numbering of pointer equivalence
1898 classes. */
1899
1900typedef struct equiv_class_label
1901{
3691626c 1902 hashval_t hashcode;
7b765bed
DB
1903 unsigned int equivalence_class;
1904 bitmap labels;
7b765bed 1905} *equiv_class_label_t;
586de218 1906typedef const struct equiv_class_label *const_equiv_class_label_t;
7b765bed 1907
bf190e8d 1908/* Equiv_class_label hashtable helpers. */
7b765bed 1909
95fbe13e 1910struct equiv_class_hasher : free_ptr_hash <equiv_class_label>
bf190e8d 1911{
67f58944
TS
1912 static inline hashval_t hash (const equiv_class_label *);
1913 static inline bool equal (const equiv_class_label *,
1914 const equiv_class_label *);
bf190e8d 1915};
7b765bed
DB
1916
1917/* Hash function for a equiv_class_label_t */
1918
bf190e8d 1919inline hashval_t
67f58944 1920equiv_class_hasher::hash (const equiv_class_label *ecl)
7b765bed 1921{
7b765bed
DB
1922 return ecl->hashcode;
1923}
1924
1925/* Equality function for two equiv_class_label_t's. */
1926
bf190e8d 1927inline bool
67f58944
TS
1928equiv_class_hasher::equal (const equiv_class_label *eql1,
1929 const equiv_class_label *eql2)
7b765bed 1930{
821bb7f8
RG
1931 return (eql1->hashcode == eql2->hashcode
1932 && bitmap_equal_p (eql1->labels, eql2->labels));
7b765bed
DB
1933}
1934
bf190e8d
LC
1935/* A hashtable for mapping a bitmap of labels->pointer equivalence
1936 classes. */
c203e8a7 1937static hash_table<equiv_class_hasher> *pointer_equiv_class_table;
bf190e8d
LC
1938
1939/* A hashtable for mapping a bitmap of labels->location equivalence
1940 classes. */
c203e8a7 1941static hash_table<equiv_class_hasher> *location_equiv_class_table;
bf190e8d 1942
139a0707
RB
1943/* Lookup a equivalence class in TABLE by the bitmap of LABELS with
1944 hash HAS it contains. Sets *REF_LABELS to the bitmap LABELS
1945 is equivalent to. */
7b765bed 1946
139a0707 1947static equiv_class_label *
c203e8a7
TS
1948equiv_class_lookup_or_add (hash_table<equiv_class_hasher> *table,
1949 bitmap labels)
7b765bed 1950{
139a0707
RB
1951 equiv_class_label **slot;
1952 equiv_class_label ecl;
7b765bed
DB
1953
1954 ecl.labels = labels;
1955 ecl.hashcode = bitmap_hash (labels);
c203e8a7 1956 slot = table->find_slot (&ecl, INSERT);
139a0707 1957 if (!*slot)
78d087bc 1958 {
139a0707
RB
1959 *slot = XNEW (struct equiv_class_label);
1960 (*slot)->labels = labels;
1961 (*slot)->hashcode = ecl.hashcode;
1962 (*slot)->equivalence_class = 0;
78d087bc 1963 }
7b765bed 1964
139a0707 1965 return *slot;
7b765bed
DB
1966}
1967
1968/* Perform offline variable substitution.
910fdc79 1969
7b765bed
DB
1970 This is a worst case quadratic time way of identifying variables
1971 that must have equivalent points-to sets, including those caused by
1972 static cycles, and single entry subgraphs, in the constraint graph.
3e5937d7 1973
7b765bed
DB
1974 The technique is described in "Exploiting Pointer and Location
1975 Equivalence to Optimize Pointer Analysis. In the 14th International
1976 Static Analysis Symposium (SAS), August 2007." It is known as the
1977 "HU" algorithm, and is equivalent to value numbering the collapsed
1978 constraint graph including evaluating unions.
3e5937d7
DB
1979
1980 The general method of finding equivalence classes is as follows:
1981 Add fake nodes (REF nodes) and edges for *a = b and a = *b constraints.
7b765bed
DB
1982 Initialize all non-REF nodes to be direct nodes.
1983 For each constraint a = a U {b}, we set pts(a) = pts(a) u {fresh
1984 variable}
1985 For each constraint containing the dereference, we also do the same
1986 thing.
1987
1988 We then compute SCC's in the graph and unify nodes in the same SCC,
1989 including pts sets.
1990
1991 For each non-collapsed node x:
1992 Visit all unvisited explicit incoming edges.
1993 Ignoring all non-pointers, set pts(x) = Union of pts(a) for y
1994 where y->x.
1995 Lookup the equivalence class for pts(x).
1996 If we found one, equivalence_class(x) = found class.
1997 Otherwise, equivalence_class(x) = new class, and new_class is
1998 added to the lookup table.
3e5937d7
DB
1999
2000 All direct nodes with the same equivalence class can be replaced
2001 with a single representative node.
2002 All unlabeled nodes (label == 0) are not pointers and all edges
2003 involving them can be eliminated.
7b765bed
DB
2004 We perform these optimizations during rewrite_constraints
2005
2006 In addition to pointer equivalence class finding, we also perform
2007 location equivalence class finding. This is the set of variables
2008 that always appear together in points-to sets. We use this to
2009 compress the size of the points-to sets. */
2010
2011/* Current maximum pointer equivalence class id. */
2012static int pointer_equiv_class;
3e5937d7 2013
7b765bed
DB
2014/* Current maximum location equivalence class id. */
2015static int location_equiv_class;
3e5937d7
DB
2016
2017/* Recursive routine to find strongly connected components in GRAPH,
7b765bed 2018 and label it's nodes with DFS numbers. */
910fdc79
DB
2019
2020static void
7b765bed 2021condense_visit (constraint_graph_t graph, struct scc_info *si, unsigned int n)
910fdc79 2022{
3e5937d7
DB
2023 unsigned int i;
2024 bitmap_iterator bi;
2025 unsigned int my_dfs;
c58936b6 2026
6e55eda7 2027 gcc_checking_assert (si->node_mapping[n] == n);
d7c028c0 2028 bitmap_set_bit (si->visited, n);
3e5937d7
DB
2029 si->dfs[n] = si->current_index ++;
2030 my_dfs = si->dfs[n];
c58936b6 2031
3e5937d7
DB
2032 /* Visit all the successors. */
2033 EXECUTE_IF_IN_NONNULL_BITMAP (graph->preds[n], 0, i, bi)
910fdc79 2034 {
3e5937d7 2035 unsigned int w = si->node_mapping[i];
910fdc79 2036
d7c028c0 2037 if (bitmap_bit_p (si->deleted, w))
910fdc79
DB
2038 continue;
2039
d7c028c0 2040 if (!bitmap_bit_p (si->visited, w))
7b765bed 2041 condense_visit (graph, si, w);
910fdc79 2042
6e55eda7
RB
2043 unsigned int t = si->node_mapping[w];
2044 gcc_checking_assert (si->node_mapping[n] == n);
2045 if (si->dfs[t] < si->dfs[n])
2046 si->dfs[n] = si->dfs[t];
3e5937d7 2047 }
910fdc79 2048
3e5937d7
DB
2049 /* Visit all the implicit predecessors. */
2050 EXECUTE_IF_IN_NONNULL_BITMAP (graph->implicit_preds[n], 0, i, bi)
2051 {
2052 unsigned int w = si->node_mapping[i];
2053
d7c028c0 2054 if (bitmap_bit_p (si->deleted, w))
3e5937d7
DB
2055 continue;
2056
d7c028c0 2057 if (!bitmap_bit_p (si->visited, w))
7b765bed 2058 condense_visit (graph, si, w);
3e5937d7 2059
6e55eda7
RB
2060 unsigned int t = si->node_mapping[w];
2061 gcc_assert (si->node_mapping[n] == n);
2062 if (si->dfs[t] < si->dfs[n])
2063 si->dfs[n] = si->dfs[t];
3e5937d7 2064 }
4ee00913 2065
3e5937d7
DB
2066 /* See if any components have been identified. */
2067 if (si->dfs[n] == my_dfs)
2068 {
9771b263
DN
2069 while (si->scc_stack.length () != 0
2070 && si->dfs[si->scc_stack.last ()] >= my_dfs)
910fdc79 2071 {
9771b263 2072 unsigned int w = si->scc_stack.pop ();
3e5937d7
DB
2073 si->node_mapping[w] = n;
2074
d7c028c0
LC
2075 if (!bitmap_bit_p (graph->direct_nodes, w))
2076 bitmap_clear_bit (graph->direct_nodes, n);
3e5937d7 2077
7b765bed
DB
2078 /* Unify our nodes. */
2079 if (graph->preds[w])
2080 {
2081 if (!graph->preds[n])
2082 graph->preds[n] = BITMAP_ALLOC (&predbitmap_obstack);
2083 bitmap_ior_into (graph->preds[n], graph->preds[w]);
2084 }
2085 if (graph->implicit_preds[w])
2086 {
2087 if (!graph->implicit_preds[n])
2088 graph->implicit_preds[n] = BITMAP_ALLOC (&predbitmap_obstack);
2089 bitmap_ior_into (graph->implicit_preds[n],
2090 graph->implicit_preds[w]);
2091 }
2092 if (graph->points_to[w])
2093 {
2094 if (!graph->points_to[n])
2095 graph->points_to[n] = BITMAP_ALLOC (&predbitmap_obstack);
2096 bitmap_ior_into (graph->points_to[n],
2097 graph->points_to[w]);
2098 }
3e5937d7 2099 }
d7c028c0 2100 bitmap_set_bit (si->deleted, n);
3e5937d7
DB
2101 }
2102 else
9771b263 2103 si->scc_stack.safe_push (n);
3e5937d7
DB
2104}
2105
11924f8b
RB
2106/* Label pointer equivalences.
2107
2108 This performs a value numbering of the constraint graph to
2109 discover which variables will always have the same points-to sets
2110 under the current set of constraints.
2111
2112 The way it value numbers is to store the set of points-to bits
2113 generated by the constraints and graph edges. This is just used as a
2114 hash and equality comparison. The *actual set of points-to bits* is
2115 completely irrelevant, in that we don't care about being able to
2116 extract them later.
2117
2118 The equality values (currently bitmaps) just have to satisfy a few
2119 constraints, the main ones being:
2120 1. The combining operation must be order independent.
2121 2. The end result of a given set of operations must be unique iff the
2122 combination of input values is unique
2123 3. Hashable. */
7b765bed
DB
2124
2125static void
2126label_visit (constraint_graph_t graph, struct scc_info *si, unsigned int n)
2127{
8c7ca45c 2128 unsigned int i, first_pred;
7b765bed 2129 bitmap_iterator bi;
7b765bed 2130
8c7ca45c 2131 bitmap_set_bit (si->visited, n);
7b765bed
DB
2132
2133 /* Label and union our incoming edges's points to sets. */
8c7ca45c 2134 first_pred = -1U;
7b765bed
DB
2135 EXECUTE_IF_IN_NONNULL_BITMAP (graph->preds[n], 0, i, bi)
2136 {
2137 unsigned int w = si->node_mapping[i];
d7c028c0 2138 if (!bitmap_bit_p (si->visited, w))
7b765bed
DB
2139 label_visit (graph, si, w);
2140
2141 /* Skip unused edges */
2142 if (w == n || graph->pointer_label[w] == 0)
3dc21182
DB
2143 continue;
2144
7b765bed 2145 if (graph->points_to[w])
8c7ca45c 2146 {
14597080 2147 if (!graph->points_to[n])
8c7ca45c 2148 {
14597080
RB
2149 if (first_pred == -1U)
2150 first_pred = w;
2151 else
2152 {
2153 graph->points_to[n] = BITMAP_ALLOC (&predbitmap_obstack);
2154 bitmap_ior (graph->points_to[n],
2155 graph->points_to[first_pred],
2156 graph->points_to[w]);
2157 }
8c7ca45c
RB
2158 }
2159 else
c3284718 2160 bitmap_ior_into (graph->points_to[n], graph->points_to[w]);
8c7ca45c 2161 }
7b765bed 2162 }
8c7ca45c
RB
2163
2164 /* Indirect nodes get fresh variables and a new pointer equiv class. */
d7c028c0 2165 if (!bitmap_bit_p (graph->direct_nodes, n))
8c7ca45c
RB
2166 {
2167 if (!graph->points_to[n])
2168 {
2169 graph->points_to[n] = BITMAP_ALLOC (&predbitmap_obstack);
2170 if (first_pred != -1U)
2171 bitmap_copy (graph->points_to[n], graph->points_to[first_pred]);
2172 }
2173 bitmap_set_bit (graph->points_to[n], FIRST_REF_NODE + n);
2174 graph->pointer_label[n] = pointer_equiv_class++;
139a0707
RB
2175 equiv_class_label_t ecl;
2176 ecl = equiv_class_lookup_or_add (pointer_equiv_class_table,
2177 graph->points_to[n]);
2178 ecl->equivalence_class = graph->pointer_label[n];
8c7ca45c
RB
2179 return;
2180 }
2181
2182 /* If there was only a single non-empty predecessor the pointer equiv
2183 class is the same. */
2184 if (!graph->points_to[n])
2185 {
2186 if (first_pred != -1U)
2187 {
2188 graph->pointer_label[n] = graph->pointer_label[first_pred];
2189 graph->points_to[n] = graph->points_to[first_pred];
2190 }
2191 return;
2192 }
7b765bed
DB
2193
2194 if (!bitmap_empty_p (graph->points_to[n]))
2195 {
139a0707
RB
2196 equiv_class_label_t ecl;
2197 ecl = equiv_class_lookup_or_add (pointer_equiv_class_table,
2198 graph->points_to[n]);
2199 if (ecl->equivalence_class == 0)
2200 ecl->equivalence_class = pointer_equiv_class++;
78d087bc
RB
2201 else
2202 {
2203 BITMAP_FREE (graph->points_to[n]);
139a0707 2204 graph->points_to[n] = ecl->labels;
78d087bc 2205 }
139a0707 2206 graph->pointer_label[n] = ecl->equivalence_class;
7b765bed
DB
2207 }
2208}
2209
6e55eda7
RB
2210/* Print the pred graph in dot format. */
2211
2212static void
2213dump_pred_graph (struct scc_info *si, FILE *file)
2214{
2215 unsigned int i;
2216
2217 /* Only print the graph if it has already been initialized: */
2218 if (!graph)
2219 return;
2220
2221 /* Prints the header of the dot file: */
2222 fprintf (file, "strict digraph {\n");
2223 fprintf (file, " node [\n shape = box\n ]\n");
2224 fprintf (file, " edge [\n fontsize = \"12\"\n ]\n");
2225 fprintf (file, "\n // List of nodes and complex constraints in "
2226 "the constraint graph:\n");
2227
2228 /* The next lines print the nodes in the graph together with the
2229 complex constraints attached to them. */
d6d305fe 2230 for (i = 1; i < graph->size; i++)
6e55eda7 2231 {
d6d305fe
RB
2232 if (i == FIRST_REF_NODE)
2233 continue;
6e55eda7
RB
2234 if (si->node_mapping[i] != i)
2235 continue;
2236 if (i < FIRST_REF_NODE)
2237 fprintf (file, "\"%s\"", get_varinfo (i)->name);
2238 else
2239 fprintf (file, "\"*%s\"", get_varinfo (i - FIRST_REF_NODE)->name);
2240 if (graph->points_to[i]
2241 && !bitmap_empty_p (graph->points_to[i]))
2242 {
2243 fprintf (file, "[label=\"%s = {", get_varinfo (i)->name);
2244 unsigned j;
2245 bitmap_iterator bi;
2246 EXECUTE_IF_SET_IN_BITMAP (graph->points_to[i], 0, j, bi)
2247 fprintf (file, " %d", j);
2248 fprintf (file, " }\"]");
2249 }
2250 fprintf (file, ";\n");
2251 }
2252
2253 /* Go over the edges. */
2254 fprintf (file, "\n // Edges in the constraint graph:\n");
d6d305fe 2255 for (i = 1; i < graph->size; i++)
6e55eda7
RB
2256 {
2257 unsigned j;
2258 bitmap_iterator bi;
2259 if (si->node_mapping[i] != i)
2260 continue;
2261 EXECUTE_IF_IN_NONNULL_BITMAP (graph->preds[i], 0, j, bi)
2262 {
2263 unsigned from = si->node_mapping[j];
2264 if (from < FIRST_REF_NODE)
2265 fprintf (file, "\"%s\"", get_varinfo (from)->name);
2266 else
2267 fprintf (file, "\"*%s\"", get_varinfo (from - FIRST_REF_NODE)->name);
2268 fprintf (file, " -> ");
2269 if (i < FIRST_REF_NODE)
2270 fprintf (file, "\"%s\"", get_varinfo (i)->name);
2271 else
2272 fprintf (file, "\"*%s\"", get_varinfo (i - FIRST_REF_NODE)->name);
2273 fprintf (file, ";\n");
2274 }
2275 }
2276
2277 /* Prints the tail of the dot file. */
2278 fprintf (file, "}\n");
2279}
2280
3e5937d7
DB
2281/* Perform offline variable substitution, discovering equivalence
2282 classes, and eliminating non-pointer variables. */
2283
2284static struct scc_info *
2285perform_var_substitution (constraint_graph_t graph)
2286{
2287 unsigned int i;
2288 unsigned int size = graph->size;
2289 struct scc_info *si = init_scc_info (size);
2290
2291 bitmap_obstack_initialize (&iteration_obstack);
c203e8a7
TS
2292 pointer_equiv_class_table = new hash_table<equiv_class_hasher> (511);
2293 location_equiv_class_table
2294 = new hash_table<equiv_class_hasher> (511);
7b765bed
DB
2295 pointer_equiv_class = 1;
2296 location_equiv_class = 1;
2297
2298 /* Condense the nodes, which means to find SCC's, count incoming
2299 predecessors, and unite nodes in SCC's. */
d6d305fe 2300 for (i = 1; i < FIRST_REF_NODE; i++)
d7c028c0 2301 if (!bitmap_bit_p (si->visited, si->node_mapping[i]))
7b765bed 2302 condense_visit (graph, si, si->node_mapping[i]);
3e5937d7 2303
6e55eda7
RB
2304 if (dump_file && (dump_flags & TDF_GRAPH))
2305 {
2306 fprintf (dump_file, "\n\n// The constraint graph before var-substitution "
2307 "in dot format:\n");
2308 dump_pred_graph (si, dump_file);
2309 fprintf (dump_file, "\n\n");
2310 }
2311
f61e445a 2312 bitmap_clear (si->visited);
7b765bed 2313 /* Actually the label the nodes for pointer equivalences */
d6d305fe 2314 for (i = 1; i < FIRST_REF_NODE; i++)
d7c028c0 2315 if (!bitmap_bit_p (si->visited, si->node_mapping[i]))
3e5937d7
DB
2316 label_visit (graph, si, si->node_mapping[i]);
2317
7b765bed 2318 /* Calculate location equivalence labels. */
d6d305fe 2319 for (i = 1; i < FIRST_REF_NODE; i++)
7b765bed
DB
2320 {
2321 bitmap pointed_by;
2322 bitmap_iterator bi;
2323 unsigned int j;
7b765bed
DB
2324
2325 if (!graph->pointed_by[i])
2326 continue;
2327 pointed_by = BITMAP_ALLOC (&iteration_obstack);
2328
2329 /* Translate the pointed-by mapping for pointer equivalence
2330 labels. */
2331 EXECUTE_IF_SET_IN_BITMAP (graph->pointed_by[i], 0, j, bi)
2332 {
2333 bitmap_set_bit (pointed_by,
2334 graph->pointer_label[si->node_mapping[j]]);
2335 }
2336 /* The original pointed_by is now dead. */
2337 BITMAP_FREE (graph->pointed_by[i]);
2338
2339 /* Look up the location equivalence label if one exists, or make
2340 one otherwise. */
139a0707
RB
2341 equiv_class_label_t ecl;
2342 ecl = equiv_class_lookup_or_add (location_equiv_class_table, pointed_by);
2343 if (ecl->equivalence_class == 0)
2344 ecl->equivalence_class = location_equiv_class++;
7b765bed
DB
2345 else
2346 {
2347 if (dump_file && (dump_flags & TDF_DETAILS))
2348 fprintf (dump_file, "Found location equivalence for node %s\n",
2349 get_varinfo (i)->name);
2350 BITMAP_FREE (pointed_by);
2351 }
139a0707 2352 graph->loc_label[i] = ecl->equivalence_class;
7b765bed
DB
2353
2354 }
2355
3e5937d7 2356 if (dump_file && (dump_flags & TDF_DETAILS))
d6d305fe 2357 for (i = 1; i < FIRST_REF_NODE; i++)
3e5937d7 2358 {
14597080
RB
2359 unsigned j = si->node_mapping[i];
2360 if (j != i)
f49b33cb
RB
2361 {
2362 fprintf (dump_file, "%s node id %d ",
2363 bitmap_bit_p (graph->direct_nodes, i)
2364 ? "Direct" : "Indirect", i);
2365 if (i < FIRST_REF_NODE)
2366 fprintf (dump_file, "\"%s\"", get_varinfo (i)->name);
2367 else
2368 fprintf (dump_file, "\"*%s\"",
2369 get_varinfo (i - FIRST_REF_NODE)->name);
2370 fprintf (dump_file, " mapped to SCC leader node id %d ", j);
2371 if (j < FIRST_REF_NODE)
2372 fprintf (dump_file, "\"%s\"\n", get_varinfo (j)->name);
2373 else
2374 fprintf (dump_file, "\"*%s\"\n",
2375 get_varinfo (j - FIRST_REF_NODE)->name);
2376 }
14597080 2377 else
f49b33cb
RB
2378 {
2379 fprintf (dump_file,
2380 "Equivalence classes for %s node id %d ",
2381 bitmap_bit_p (graph->direct_nodes, i)
2382 ? "direct" : "indirect", i);
2383 if (i < FIRST_REF_NODE)
2384 fprintf (dump_file, "\"%s\"", get_varinfo (i)->name);
2385 else
2386 fprintf (dump_file, "\"*%s\"",
2387 get_varinfo (i - FIRST_REF_NODE)->name);
2388 fprintf (dump_file,
2389 ": pointer %d, location %d\n",
2390 graph->pointer_label[i], graph->loc_label[i]);
2391 }
3e5937d7
DB
2392 }
2393
2394 /* Quickly eliminate our non-pointer variables. */
2395
d6d305fe 2396 for (i = 1; i < FIRST_REF_NODE; i++)
3e5937d7
DB
2397 {
2398 unsigned int node = si->node_mapping[i];
2399
aa46c8a3 2400 if (graph->pointer_label[node] == 0)
3e5937d7 2401 {
23e73993 2402 if (dump_file && (dump_flags & TDF_DETAILS))
3e5937d7
DB
2403 fprintf (dump_file,
2404 "%s is a non-pointer variable, eliminating edges.\n",
2405 get_varinfo (node)->name);
2406 stats.nonpointer_vars++;
2407 clear_edges_for_node (graph, node);
910fdc79
DB
2408 }
2409 }
7b765bed 2410
3e5937d7
DB
2411 return si;
2412}
2413
2414/* Free information that was only necessary for variable
2415 substitution. */
910fdc79 2416
3e5937d7
DB
2417static void
2418free_var_substitution_info (struct scc_info *si)
2419{
2420 free_scc_info (si);
7b765bed
DB
2421 free (graph->pointer_label);
2422 free (graph->loc_label);
2423 free (graph->pointed_by);
2424 free (graph->points_to);
3e5937d7
DB
2425 free (graph->eq_rep);
2426 sbitmap_free (graph->direct_nodes);
c203e8a7
TS
2427 delete pointer_equiv_class_table;
2428 pointer_equiv_class_table = NULL;
2429 delete location_equiv_class_table;
2430 location_equiv_class_table = NULL;
4ee00913 2431 bitmap_obstack_release (&iteration_obstack);
3e5937d7
DB
2432}
2433
2434/* Return an existing node that is equivalent to NODE, which has
2435 equivalence class LABEL, if one exists. Return NODE otherwise. */
2436
2437static unsigned int
2438find_equivalent_node (constraint_graph_t graph,
2439 unsigned int node, unsigned int label)
2440{
2441 /* If the address version of this variable is unused, we can
2442 substitute it for anything else with the same label.
2443 Otherwise, we know the pointers are equivalent, but not the
7b765bed 2444 locations, and we can unite them later. */
3e5937d7 2445
7b765bed 2446 if (!bitmap_bit_p (graph->address_taken, node))
3e5937d7 2447 {
6e55eda7 2448 gcc_checking_assert (label < graph->size);
3e5937d7
DB
2449
2450 if (graph->eq_rep[label] != -1)
2451 {
2452 /* Unify the two variables since we know they are equivalent. */
2453 if (unite (graph->eq_rep[label], node))
2454 unify_nodes (graph, graph->eq_rep[label], node, false);
2455 return graph->eq_rep[label];
2456 }
2457 else
2458 {
2459 graph->eq_rep[label] = node;
7b765bed 2460 graph->pe_rep[label] = node;
3e5937d7
DB
2461 }
2462 }
7b765bed
DB
2463 else
2464 {
6e55eda7 2465 gcc_checking_assert (label < graph->size);
7b765bed
DB
2466 graph->pe[node] = label;
2467 if (graph->pe_rep[label] == -1)
2468 graph->pe_rep[label] = node;
2469 }
2470
3e5937d7
DB
2471 return node;
2472}
2473
7b765bed
DB
2474/* Unite pointer equivalent but not location equivalent nodes in
2475 GRAPH. This may only be performed once variable substitution is
2476 finished. */
2477
2478static void
2479unite_pointer_equivalences (constraint_graph_t graph)
2480{
2481 unsigned int i;
2482
2483 /* Go through the pointer equivalences and unite them to their
2484 representative, if they aren't already. */
d6d305fe 2485 for (i = 1; i < FIRST_REF_NODE; i++)
7b765bed
DB
2486 {
2487 unsigned int label = graph->pe[i];
aa46c8a3
DB
2488 if (label)
2489 {
2490 int label_rep = graph->pe_rep[label];
b8698a0f 2491
aa46c8a3
DB
2492 if (label_rep == -1)
2493 continue;
b8698a0f 2494
aa46c8a3
DB
2495 label_rep = find (label_rep);
2496 if (label_rep >= 0 && unite (label_rep, find (i)))
2497 unify_nodes (graph, label_rep, i, false);
2498 }
7b765bed
DB
2499 }
2500}
2501
2502/* Move complex constraints to the GRAPH nodes they belong to. */
3e5937d7
DB
2503
2504static void
7b765bed
DB
2505move_complex_constraints (constraint_graph_t graph)
2506{
2507 int i;
2508 constraint_t c;
2509
9771b263 2510 FOR_EACH_VEC_ELT (constraints, i, c)
7b765bed
DB
2511 {
2512 if (c)
2513 {
2514 struct constraint_expr lhs = c->lhs;
2515 struct constraint_expr rhs = c->rhs;
2516
2517 if (lhs.type == DEREF)
2518 {
2519 insert_into_complex (graph, lhs.var, c);
2520 }
2521 else if (rhs.type == DEREF)
2522 {
2523 if (!(get_varinfo (lhs.var)->is_special_var))
2524 insert_into_complex (graph, rhs.var, c);
2525 }
2526 else if (rhs.type != ADDRESSOF && lhs.var > anything_id
2527 && (lhs.offset != 0 || rhs.offset != 0))
2528 {
2529 insert_into_complex (graph, rhs.var, c);
2530 }
2531 }
2532 }
2533}
2534
2535
2536/* Optimize and rewrite complex constraints while performing
2537 collapsing of equivalent nodes. SI is the SCC_INFO that is the
2538 result of perform_variable_substitution. */
2539
2540static void
2541rewrite_constraints (constraint_graph_t graph,
2542 struct scc_info *si)
3e5937d7
DB
2543{
2544 int i;
3e5937d7
DB
2545 constraint_t c;
2546
6e55eda7
RB
2547#ifdef ENABLE_CHECKING
2548 for (unsigned int j = 0; j < graph->size; j++)
3e5937d7 2549 gcc_assert (find (j) == j);
6e55eda7 2550#endif
3e5937d7 2551
9771b263 2552 FOR_EACH_VEC_ELT (constraints, i, c)
3e5937d7
DB
2553 {
2554 struct constraint_expr lhs = c->lhs;
2555 struct constraint_expr rhs = c->rhs;
5006671f
RG
2556 unsigned int lhsvar = find (lhs.var);
2557 unsigned int rhsvar = find (rhs.var);
3e5937d7
DB
2558 unsigned int lhsnode, rhsnode;
2559 unsigned int lhslabel, rhslabel;
2560
2561 lhsnode = si->node_mapping[lhsvar];
2562 rhsnode = si->node_mapping[rhsvar];
7b765bed
DB
2563 lhslabel = graph->pointer_label[lhsnode];
2564 rhslabel = graph->pointer_label[rhsnode];
3e5937d7
DB
2565
2566 /* See if it is really a non-pointer variable, and if so, ignore
2567 the constraint. */
2568 if (lhslabel == 0)
2569 {
aa46c8a3 2570 if (dump_file && (dump_flags & TDF_DETAILS))
3e5937d7 2571 {
b8698a0f 2572
aa46c8a3
DB
2573 fprintf (dump_file, "%s is a non-pointer variable,"
2574 "ignoring constraint:",
2575 get_varinfo (lhs.var)->name);
2576 dump_constraint (dump_file, c);
8576f20a 2577 fprintf (dump_file, "\n");
3e5937d7 2578 }
9771b263 2579 constraints[i] = NULL;
aa46c8a3 2580 continue;
3e5937d7
DB
2581 }
2582
2583 if (rhslabel == 0)
2584 {
aa46c8a3 2585 if (dump_file && (dump_flags & TDF_DETAILS))
3e5937d7 2586 {
b8698a0f 2587
aa46c8a3
DB
2588 fprintf (dump_file, "%s is a non-pointer variable,"
2589 "ignoring constraint:",
2590 get_varinfo (rhs.var)->name);
2591 dump_constraint (dump_file, c);
8576f20a 2592 fprintf (dump_file, "\n");
3e5937d7 2593 }
9771b263 2594 constraints[i] = NULL;
aa46c8a3 2595 continue;
3e5937d7
DB
2596 }
2597
2598 lhsvar = find_equivalent_node (graph, lhsvar, lhslabel);
2599 rhsvar = find_equivalent_node (graph, rhsvar, rhslabel);
2600 c->lhs.var = lhsvar;
2601 c->rhs.var = rhsvar;
3e5937d7
DB
2602 }
2603}
2604
2605/* Eliminate indirect cycles involving NODE. Return true if NODE was
2606 part of an SCC, false otherwise. */
2607
2608static bool
2609eliminate_indirect_cycles (unsigned int node)
2610{
2611 if (graph->indirect_cycles[node] != -1
2612 && !bitmap_empty_p (get_varinfo (node)->solution))
2613 {
2614 unsigned int i;
ef062b13 2615 auto_vec<unsigned> queue;
3e5937d7
DB
2616 int queuepos;
2617 unsigned int to = find (graph->indirect_cycles[node]);
2618 bitmap_iterator bi;
2619
2620 /* We can't touch the solution set and call unify_nodes
2621 at the same time, because unify_nodes is going to do
2622 bitmap unions into it. */
2623
2624 EXECUTE_IF_SET_IN_BITMAP (get_varinfo (node)->solution, 0, i, bi)
2625 {
2626 if (find (i) == i && i != to)
2627 {
2628 if (unite (to, i))
9771b263 2629 queue.safe_push (i);
3e5937d7
DB
2630 }
2631 }
2632
2633 for (queuepos = 0;
9771b263 2634 queue.iterate (queuepos, &i);
3e5937d7
DB
2635 queuepos++)
2636 {
2637 unify_nodes (graph, to, i, true);
2638 }
3e5937d7
DB
2639 return true;
2640 }
2641 return false;
910fdc79
DB
2642}
2643
910fdc79
DB
2644/* Solve the constraint graph GRAPH using our worklist solver.
2645 This is based on the PW* family of solvers from the "Efficient Field
2646 Sensitive Pointer Analysis for C" paper.
2647 It works by iterating over all the graph nodes, processing the complex
2648 constraints and propagating the copy constraints, until everything stops
2649 changed. This corresponds to steps 6-8 in the solving list given above. */
2650
2651static void
2652solve_graph (constraint_graph_t graph)
2653{
7b765bed 2654 unsigned int size = graph->size;
910fdc79 2655 unsigned int i;
3e5937d7 2656 bitmap pts;
910fdc79 2657
648b5f85 2658 changed = BITMAP_ALLOC (NULL);
c58936b6 2659
3e5937d7 2660 /* Mark all initial non-collapsed nodes as changed. */
d6d305fe 2661 for (i = 1; i < size; i++)
3e5937d7
DB
2662 {
2663 varinfo_t ivi = get_varinfo (i);
2664 if (find (i) == i && !bitmap_empty_p (ivi->solution)
2665 && ((graph->succs[i] && !bitmap_empty_p (graph->succs[i]))
9771b263 2666 || graph->complex[i].length () > 0))
648b5f85 2667 bitmap_set_bit (changed, i);
3e5937d7
DB
2668 }
2669
2670 /* Allocate a bitmap to be used to store the changed bits. */
2671 pts = BITMAP_ALLOC (&pta_obstack);
c58936b6 2672
648b5f85 2673 while (!bitmap_empty_p (changed))
910fdc79
DB
2674 {
2675 unsigned int i;
2676 struct topo_info *ti = init_topo_info ();
2677 stats.iterations++;
4ee00913 2678
910fdc79 2679 bitmap_obstack_initialize (&iteration_obstack);
c58936b6 2680
910fdc79
DB
2681 compute_topo_order (graph, ti);
2682
9771b263 2683 while (ti->topo_order.length () != 0)
910fdc79 2684 {
3e5937d7 2685
9771b263 2686 i = ti->topo_order.pop ();
3e5937d7
DB
2687
2688 /* If this variable is not a representative, skip it. */
2689 if (find (i) != i)
2690 continue;
2691
d3c36974
DB
2692 /* In certain indirect cycle cases, we may merge this
2693 variable to another. */
62e5bf5d 2694 if (eliminate_indirect_cycles (i) && find (i) != i)
d3c36974 2695 continue;
910fdc79
DB
2696
2697 /* If the node has changed, we need to process the
2698 complex constraints and outgoing edges again. */
648b5f85 2699 if (bitmap_clear_bit (changed, i))
910fdc79
DB
2700 {
2701 unsigned int j;
2702 constraint_t c;
910fdc79 2703 bitmap solution;
9771b263 2704 vec<constraint_t> complex = graph->complex[i];
74d8fa44 2705 varinfo_t vi = get_varinfo (i);
21392f19 2706 bool solution_empty;
48e540b0 2707
d6d305fe
RB
2708 /* Compute the changed set of solution bits. If anything
2709 is in the solution just propagate that. */
2710 if (bitmap_bit_p (vi->solution, anything_id))
2711 {
2712 /* If anything is also in the old solution there is
2713 nothing to do.
2714 ??? But we shouldn't ended up with "changed" set ... */
2715 if (vi->oldsolution
2716 && bitmap_bit_p (vi->oldsolution, anything_id))
2717 continue;
2718 bitmap_copy (pts, get_varinfo (find (anything_id))->solution);
2719 }
2720 else if (vi->oldsolution)
74d8fa44
RG
2721 bitmap_and_compl (pts, vi->solution, vi->oldsolution);
2722 else
2723 bitmap_copy (pts, vi->solution);
3e5937d7
DB
2724
2725 if (bitmap_empty_p (pts))
2726 continue;
2727
74d8fa44
RG
2728 if (vi->oldsolution)
2729 bitmap_ior_into (vi->oldsolution, pts);
2730 else
2731 {
2732 vi->oldsolution = BITMAP_ALLOC (&oldpta_obstack);
2733 bitmap_copy (vi->oldsolution, pts);
2734 }
3e5937d7 2735
74d8fa44 2736 solution = vi->solution;
21392f19
DB
2737 solution_empty = bitmap_empty_p (solution);
2738
2739 /* Process the complex constraints */
6489e318 2740 bitmap expanded_pts = NULL;
9771b263 2741 FOR_EACH_VEC_ELT (complex, j, c)
21392f19 2742 {
7b765bed
DB
2743 /* XXX: This is going to unsort the constraints in
2744 some cases, which will occasionally add duplicate
2745 constraints during unification. This does not
2746 affect correctness. */
2747 c->lhs.var = find (c->lhs.var);
2748 c->rhs.var = find (c->rhs.var);
2749
21392f19
DB
2750 /* The only complex constraint that can change our
2751 solution to non-empty, given an empty solution,
2752 is a constraint where the lhs side is receiving
2753 some set from elsewhere. */
2754 if (!solution_empty || c->lhs.type != DEREF)
6489e318 2755 do_complex_constraint (graph, c, pts, &expanded_pts);
21392f19 2756 }
6489e318 2757 BITMAP_FREE (expanded_pts);
910fdc79 2758
21392f19
DB
2759 solution_empty = bitmap_empty_p (solution);
2760
5006671f 2761 if (!solution_empty)
4ee00913 2762 {
3e5937d7 2763 bitmap_iterator bi;
5006671f 2764 unsigned eff_escaped_id = find (escaped_id);
3e5937d7 2765
21392f19 2766 /* Propagate solution to all successors. */
c58936b6 2767 EXECUTE_IF_IN_NONNULL_BITMAP (graph->succs[i],
21392f19 2768 0, j, bi)
4ee00913 2769 {
3e5937d7
DB
2770 bitmap tmp;
2771 bool flag;
2772
2773 unsigned int to = find (j);
2774 tmp = get_varinfo (to)->solution;
2775 flag = false;
c58936b6 2776
3e5937d7
DB
2777 /* Don't try to propagate to ourselves. */
2778 if (to == i)
2779 continue;
c58936b6 2780
5006671f
RG
2781 /* If we propagate from ESCAPED use ESCAPED as
2782 placeholder. */
2783 if (i == eff_escaped_id)
2784 flag = bitmap_set_bit (tmp, escaped_id);
2785 else
d6d305fe 2786 flag = bitmap_ior_into (tmp, pts);
c58936b6 2787
21392f19 2788 if (flag)
d6d305fe 2789 bitmap_set_bit (changed, to);
4ee00913 2790 }
910fdc79
DB
2791 }
2792 }
2793 }
2794 free_topo_info (ti);
2795 bitmap_obstack_release (&iteration_obstack);
2796 }
c58936b6 2797
3e5937d7 2798 BITMAP_FREE (pts);
648b5f85 2799 BITMAP_FREE (changed);
3e5937d7 2800 bitmap_obstack_release (&oldpta_obstack);
910fdc79
DB
2801}
2802
3e5937d7 2803/* Map from trees to variable infos. */
b787e7a2 2804static hash_map<tree, varinfo_t> *vi_for_tree;
910fdc79 2805
910fdc79 2806
15814ba0 2807/* Insert ID as the variable id for tree T in the vi_for_tree map. */
910fdc79 2808
c58936b6 2809static void
3e5937d7 2810insert_vi_for_tree (tree t, varinfo_t vi)
910fdc79 2811{
15814ba0 2812 gcc_assert (vi);
b787e7a2 2813 gcc_assert (!vi_for_tree->put (t, vi));
910fdc79
DB
2814}
2815
3e5937d7 2816/* Find the variable info for tree T in VI_FOR_TREE. If T does not
15814ba0 2817 exist in the map, return NULL, otherwise, return the varinfo we found. */
910fdc79 2818
15814ba0
PB
2819static varinfo_t
2820lookup_vi_for_tree (tree t)
910fdc79 2821{
b787e7a2 2822 varinfo_t *slot = vi_for_tree->get (t);
15814ba0
PB
2823 if (slot == NULL)
2824 return NULL;
910fdc79 2825
b787e7a2 2826 return *slot;
910fdc79
DB
2827}
2828
2829/* Return a printable name for DECL */
2830
2831static const char *
2832alias_get_name (tree decl)
2833{
70b5e7dc 2834 const char *res = NULL;
910fdc79
DB
2835 char *temp;
2836 int num_printed = 0;
2837
4f6c9110 2838 if (!dump_file)
70b5e7dc 2839 return "NULL";
4f6c9110 2840
910fdc79
DB
2841 if (TREE_CODE (decl) == SSA_NAME)
2842 {
70b5e7dc
RG
2843 res = get_name (decl);
2844 if (res)
2845 num_printed = asprintf (&temp, "%s_%u", res, SSA_NAME_VERSION (decl));
2846 else
2847 num_printed = asprintf (&temp, "_%u", SSA_NAME_VERSION (decl));
2848 if (num_printed > 0)
2849 {
2850 res = ggc_strdup (temp);
2851 free (temp);
2852 }
910fdc79
DB
2853 }
2854 else if (DECL_P (decl))
2855 {
70b5e7dc
RG
2856 if (DECL_ASSEMBLER_NAME_SET_P (decl))
2857 res = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl));
2858 else
2859 {
2860 res = get_name (decl);
2861 if (!res)
2862 {
2863 num_printed = asprintf (&temp, "D.%u", DECL_UID (decl));
2864 if (num_printed > 0)
2865 {
2866 res = ggc_strdup (temp);
2867 free (temp);
2868 }
2869 }
2870 }
910fdc79 2871 }
70b5e7dc
RG
2872 if (res != NULL)
2873 return res;
2874
2875 return "NULL";
910fdc79
DB
2876}
2877
15814ba0
PB
2878/* Find the variable id for tree T in the map.
2879 If T doesn't exist in the map, create an entry for it and return it. */
910fdc79 2880
3e5937d7
DB
2881static varinfo_t
2882get_vi_for_tree (tree t)
910fdc79 2883{
b787e7a2 2884 varinfo_t *slot = vi_for_tree->get (t);
15814ba0 2885 if (slot == NULL)
3e5937d7 2886 return get_varinfo (create_variable_info_for (t, alias_get_name (t)));
c58936b6 2887
b787e7a2 2888 return *slot;
910fdc79
DB
2889}
2890
b14e9388 2891/* Get a scalar constraint expression for a new temporary variable. */
910fdc79
DB
2892
2893static struct constraint_expr
b14e9388 2894new_scalar_tmp_constraint_exp (const char *name)
910fdc79 2895{
b14e9388 2896 struct constraint_expr tmp;
b14e9388 2897 varinfo_t vi;
910fdc79 2898
0bbf2ffa 2899 vi = new_var_info (NULL_TREE, name);
b14e9388
RG
2900 vi->offset = 0;
2901 vi->size = -1;
2902 vi->fullsize = -1;
2903 vi->is_full_var = 1;
c0d459f0 2904
b14e9388
RG
2905 tmp.var = vi->id;
2906 tmp.type = SCALAR;
2907 tmp.offset = 0;
c0d459f0 2908
b14e9388 2909 return tmp;
c0d459f0
RG
2910}
2911
2912/* Get a constraint expression vector from an SSA_VAR_P node.
2913 If address_p is true, the result will be taken its address of. */
2914
2915static void
9771b263 2916get_constraint_for_ssa_var (tree t, vec<ce_s> *results, bool address_p)
c0d459f0
RG
2917{
2918 struct constraint_expr cexpr;
2919 varinfo_t vi;
2920
2921 /* We allow FUNCTION_DECLs here even though it doesn't make much sense. */
b2ec94d4 2922 gcc_assert (TREE_CODE (t) == SSA_NAME || DECL_P (t));
910fdc79
DB
2923
2924 /* For parameters, get at the points-to set for the actual parm
2925 decl. */
c58936b6 2926 if (TREE_CODE (t) == SSA_NAME
b2ec94d4 2927 && SSA_NAME_IS_DEFAULT_DEF (t)
6938f93f 2928 && (TREE_CODE (SSA_NAME_VAR (t)) == PARM_DECL
b2ec94d4 2929 || TREE_CODE (SSA_NAME_VAR (t)) == RESULT_DECL))
c0d459f0
RG
2930 {
2931 get_constraint_for_ssa_var (SSA_NAME_VAR (t), results, address_p);
2932 return;
2933 }
910fdc79 2934
9c7c9f10
RG
2935 /* For global variables resort to the alias target. */
2936 if (TREE_CODE (t) == VAR_DECL
2937 && (TREE_STATIC (t) || DECL_EXTERNAL (t)))
2938 {
9041d2e6 2939 varpool_node *node = varpool_node::get (t);
67348ccc 2940 if (node && node->alias && node->analyzed)
9c7c9f10 2941 {
9041d2e6 2942 node = node->ultimate_alias_target ();
67348ccc 2943 t = node->decl;
9c7c9f10
RG
2944 }
2945 }
2946
c0d459f0
RG
2947 vi = get_vi_for_tree (t);
2948 cexpr.var = vi->id;
910fdc79 2949 cexpr.type = SCALAR;
c0d459f0 2950 cexpr.offset = 0;
c58936b6 2951
c0d459f0
RG
2952 /* If we are not taking the address of the constraint expr, add all
2953 sub-fiels of the variable as well. */
de925a03
RG
2954 if (!address_p
2955 && !vi->is_full_var)
c0d459f0 2956 {
d6d305fe 2957 for (; vi; vi = vi_next (vi))
c0d459f0
RG
2958 {
2959 cexpr.var = vi->id;
9771b263 2960 results->safe_push (cexpr);
c0d459f0
RG
2961 }
2962 return;
2963 }
2964
9771b263 2965 results->safe_push (cexpr);
910fdc79
DB
2966}
2967
faf2ecc5
RG
2968/* Process constraint T, performing various simplifications and then
2969 adding it to our list of overall constraints. */
910fdc79
DB
2970
2971static void
faf2ecc5 2972process_constraint (constraint_t t)
910fdc79
DB
2973{
2974 struct constraint_expr rhs = t->rhs;
2975 struct constraint_expr lhs = t->lhs;
c58936b6 2976
9771b263
DN
2977 gcc_assert (rhs.var < varmap.length ());
2978 gcc_assert (lhs.var < varmap.length ());
910fdc79 2979
5006671f
RG
2980 /* If we didn't get any useful constraint from the lhs we get
2981 &ANYTHING as fallback from get_constraint_for. Deal with
2982 it here by turning it into *ANYTHING. */
2983 if (lhs.type == ADDRESSOF
2984 && lhs.var == anything_id)
2985 lhs.type = DEREF;
2986
2987 /* ADDRESSOF on the lhs is invalid. */
2988 gcc_assert (lhs.type != ADDRESSOF);
910fdc79 2989
3c323b52
RG
2990 /* We shouldn't add constraints from things that cannot have pointers.
2991 It's not completely trivial to avoid in the callers, so do it here. */
2992 if (rhs.type != ADDRESSOF
2993 && !get_varinfo (rhs.var)->may_have_pointers)
2994 return;
2995
2996 /* Likewise adding to the solution of a non-pointer var isn't useful. */
2997 if (!get_varinfo (lhs.var)->may_have_pointers)
2998 return;
2999
910fdc79 3000 /* This can happen in our IR with things like n->a = *p */
5006671f 3001 if (rhs.type == DEREF && lhs.type == DEREF && rhs.var != anything_id)
910fdc79
DB
3002 {
3003 /* Split into tmp = *rhs, *lhs = tmp */
b14e9388
RG
3004 struct constraint_expr tmplhs;
3005 tmplhs = new_scalar_tmp_constraint_exp ("doubledereftmp");
faf2ecc5
RG
3006 process_constraint (new_constraint (tmplhs, rhs));
3007 process_constraint (new_constraint (lhs, tmplhs));
7b765bed
DB
3008 }
3009 else if (rhs.type == ADDRESSOF && lhs.type == DEREF)
3010 {
3011 /* Split into tmp = &rhs, *lhs = tmp */
b14e9388
RG
3012 struct constraint_expr tmplhs;
3013 tmplhs = new_scalar_tmp_constraint_exp ("derefaddrtmp");
faf2ecc5
RG
3014 process_constraint (new_constraint (tmplhs, rhs));
3015 process_constraint (new_constraint (lhs, tmplhs));
910fdc79 3016 }
910fdc79
DB
3017 else
3018 {
3e5937d7 3019 gcc_assert (rhs.type != ADDRESSOF || rhs.offset == 0);
9771b263 3020 constraints.safe_push (t);
910fdc79
DB
3021 }
3022}
3023
3024
3025/* Return the position, in bits, of FIELD_DECL from the beginning of its
3026 structure. */
3027
ee7d4b57 3028static HOST_WIDE_INT
910fdc79
DB
3029bitpos_of_field (const tree fdecl)
3030{
9541ffee
RS
3031 if (!tree_fits_shwi_p (DECL_FIELD_OFFSET (fdecl))
3032 || !tree_fits_shwi_p (DECL_FIELD_BIT_OFFSET (fdecl)))
910fdc79 3033 return -1;
c58936b6 3034
eb1ce453
KZ
3035 return (tree_to_shwi (DECL_FIELD_OFFSET (fdecl)) * BITS_PER_UNIT
3036 + tree_to_shwi (DECL_FIELD_BIT_OFFSET (fdecl)));
910fdc79
DB
3037}
3038
3039
e5bae89b
RG
3040/* Get constraint expressions for offsetting PTR by OFFSET. Stores the
3041 resulting constraint expressions in *RESULTS. */
3042
3043static void
3044get_constraint_for_ptr_offset (tree ptr, tree offset,
9771b263 3045 vec<ce_s> *results)
e5bae89b 3046{
bd02b3a0 3047 struct constraint_expr c;
e5bae89b 3048 unsigned int j, n;
97919ae7 3049 HOST_WIDE_INT rhsoffset;
e5bae89b
RG
3050
3051 /* If we do not do field-sensitive PTA adding offsets to pointers
3052 does not change the points-to solution. */
3053 if (!use_field_sensitive)
3054 {
ed6c4831 3055 get_constraint_for_rhs (ptr, results);
e5bae89b
RG
3056 return;
3057 }
3058
3059 /* If the offset is not a non-negative integer constant that fits
3060 in a HOST_WIDE_INT, we have to fall back to a conservative
3061 solution which includes all sub-fields of all pointed-to
5006671f 3062 variables of ptr. */
779704e7 3063 if (offset == NULL_TREE
97919ae7 3064 || TREE_CODE (offset) != INTEGER_CST)
5006671f
RG
3065 rhsoffset = UNKNOWN_OFFSET;
3066 else
e5bae89b 3067 {
97919ae7 3068 /* Sign-extend the offset. */
807e902e
KZ
3069 offset_int soffset = offset_int::from (offset, SIGNED);
3070 if (!wi::fits_shwi_p (soffset))
5006671f 3071 rhsoffset = UNKNOWN_OFFSET;
97919ae7
RG
3072 else
3073 {
3074 /* Make sure the bit-offset also fits. */
807e902e 3075 HOST_WIDE_INT rhsunitoffset = soffset.to_shwi ();
97919ae7
RG
3076 rhsoffset = rhsunitoffset * BITS_PER_UNIT;
3077 if (rhsunitoffset != rhsoffset / BITS_PER_UNIT)
3078 rhsoffset = UNKNOWN_OFFSET;
3079 }
e5bae89b
RG
3080 }
3081
ed6c4831 3082 get_constraint_for_rhs (ptr, results);
e5bae89b
RG
3083 if (rhsoffset == 0)
3084 return;
3085
3086 /* As we are eventually appending to the solution do not use
9771b263
DN
3087 vec::iterate here. */
3088 n = results->length ();
e5bae89b
RG
3089 for (j = 0; j < n; j++)
3090 {
3091 varinfo_t curr;
9771b263 3092 c = (*results)[j];
bd02b3a0 3093 curr = get_varinfo (c.var);
e5bae89b 3094
bd02b3a0 3095 if (c.type == ADDRESSOF
5006671f
RG
3096 /* If this varinfo represents a full variable just use it. */
3097 && curr->is_full_var)
dfd7d2d6 3098 ;
bd02b3a0 3099 else if (c.type == ADDRESSOF
5006671f
RG
3100 /* If we do not know the offset add all subfields. */
3101 && rhsoffset == UNKNOWN_OFFSET)
3102 {
d6d305fe 3103 varinfo_t temp = get_varinfo (curr->head);
5006671f
RG
3104 do
3105 {
3106 struct constraint_expr c2;
3107 c2.var = temp->id;
3108 c2.type = ADDRESSOF;
3109 c2.offset = 0;
bd02b3a0 3110 if (c2.var != c.var)
9771b263 3111 results->safe_push (c2);
d6d305fe 3112 temp = vi_next (temp);
5006671f
RG
3113 }
3114 while (temp);
3115 }
bd02b3a0 3116 else if (c.type == ADDRESSOF)
e5bae89b 3117 {
5006671f
RG
3118 varinfo_t temp;
3119 unsigned HOST_WIDE_INT offset = curr->offset + rhsoffset;
e5bae89b 3120
af1ab449 3121 /* If curr->offset + rhsoffset is less than zero adjust it. */
5006671f
RG
3122 if (rhsoffset < 0
3123 && curr->offset < offset)
3124 offset = 0;
e5bae89b 3125
af1ab449
RB
3126 /* We have to include all fields that overlap the current
3127 field shifted by rhsoffset. And we include at least
3128 the last or the first field of the variable to represent
3129 reachability of off-bound addresses, in particular &object + 1,
3130 conservatively correct. */
3131 temp = first_or_preceding_vi_for_offset (curr, offset);
3132 c.var = temp->id;
3133 c.offset = 0;
3134 temp = vi_next (temp);
3135 while (temp
3136 && temp->offset < offset + curr->size)
e5bae89b
RG
3137 {
3138 struct constraint_expr c2;
af1ab449 3139 c2.var = temp->id;
e5bae89b
RG
3140 c2.type = ADDRESSOF;
3141 c2.offset = 0;
9771b263 3142 results->safe_push (c2);
af1ab449 3143 temp = vi_next (temp);
e5bae89b 3144 }
e5bae89b 3145 }
dfd7d2d6
RB
3146 else if (c.type == SCALAR)
3147 {
3148 gcc_assert (c.offset == 0);
3149 c.offset = rhsoffset;
3150 }
e5bae89b 3151 else
dfd7d2d6
RB
3152 /* We shouldn't get any DEREFs here. */
3153 gcc_unreachable ();
bd02b3a0 3154
9771b263 3155 (*results)[j] = c;
e5bae89b
RG
3156 }
3157}
3158
3159
c0d459f0 3160/* Given a COMPONENT_REF T, return the constraint_expr vector for it.
ed6c4831
RG
3161 If address_p is true the result will be taken its address of.
3162 If lhs_p is true then the constraint expression is assumed to be used
3163 as the lhs. */
910fdc79 3164
4ee00913 3165static void
9771b263 3166get_constraint_for_component_ref (tree t, vec<ce_s> *results,
ed6c4831 3167 bool address_p, bool lhs_p)
910fdc79 3168{
4ee00913 3169 tree orig_t = t;
b1347638 3170 HOST_WIDE_INT bitsize = -1;
6bec9271 3171 HOST_WIDE_INT bitmaxsize = -1;
910fdc79 3172 HOST_WIDE_INT bitpos;
910fdc79 3173 tree forzero;
910fdc79
DB
3174
3175 /* Some people like to do cute things like take the address of
3176 &0->a.b */
3177 forzero = t;
2ea9dc64 3178 while (handled_component_p (forzero)
70f34814
RG
3179 || INDIRECT_REF_P (forzero)
3180 || TREE_CODE (forzero) == MEM_REF)
4ee00913 3181 forzero = TREE_OPERAND (forzero, 0);
910fdc79 3182
c58936b6 3183 if (CONSTANT_CLASS_P (forzero) && integer_zerop (forzero))
910fdc79 3184 {
4ee00913 3185 struct constraint_expr temp;
c58936b6 3186
4ee00913
DB
3187 temp.offset = 0;
3188 temp.var = integer_id;
3189 temp.type = SCALAR;
9771b263 3190 results->safe_push (temp);
4ee00913 3191 return;
910fdc79 3192 }
c58936b6 3193
6bec9271 3194 t = get_ref_base_and_extent (t, &bitpos, &bitsize, &bitmaxsize);
21392f19 3195
c0d459f0
RG
3196 /* Pretend to take the address of the base, we'll take care of
3197 adding the required subset of sub-fields below. */
ed6c4831 3198 get_constraint_for_1 (t, results, true, lhs_p);
9771b263
DN
3199 gcc_assert (results->length () == 1);
3200 struct constraint_expr &result = results->last ();
910fdc79 3201
9771b263
DN
3202 if (result.type == SCALAR
3203 && get_varinfo (result.var)->is_full_var)
e5bae89b 3204 /* For single-field vars do not bother about the offset. */
9771b263
DN
3205 result.offset = 0;
3206 else if (result.type == SCALAR)
910fdc79
DB
3207 {
3208 /* In languages like C, you can access one past the end of an
3209 array. You aren't allowed to dereference it, so we can
3210 ignore this constraint. When we handle pointer subtraction,
3211 we may have to do something cute here. */
c58936b6 3212
9771b263 3213 if ((unsigned HOST_WIDE_INT)bitpos < get_varinfo (result.var)->fullsize
18455d17 3214 && bitmaxsize != 0)
dd68d988
DB
3215 {
3216 /* It's also not true that the constraint will actually start at the
3217 right offset, it may start in some padding. We only care about
3218 setting the constraint to the first actual field it touches, so
c58936b6 3219 walk to find it. */
9771b263 3220 struct constraint_expr cexpr = result;
dd68d988 3221 varinfo_t curr;
9771b263 3222 results->pop ();
c0d459f0 3223 cexpr.offset = 0;
d6d305fe 3224 for (curr = get_varinfo (cexpr.var); curr; curr = vi_next (curr))
dd68d988 3225 {
63d195d5 3226 if (ranges_overlap_p (curr->offset, curr->size,
c0d459f0 3227 bitpos, bitmaxsize))
dd68d988 3228 {
c0d459f0 3229 cexpr.var = curr->id;
9771b263 3230 results->safe_push (cexpr);
c0d459f0
RG
3231 if (address_p)
3232 break;
dd68d988
DB
3233 }
3234 }
e5bae89b
RG
3235 /* If we are going to take the address of this field then
3236 to be able to compute reachability correctly add at least
3237 the last field of the variable. */
9771b263 3238 if (address_p && results->length () == 0)
e5bae89b
RG
3239 {
3240 curr = get_varinfo (cexpr.var);
d6d305fe
RB
3241 while (curr->next != 0)
3242 curr = vi_next (curr);
e5bae89b 3243 cexpr.var = curr->id;
9771b263 3244 results->safe_push (cexpr);
e5bae89b 3245 }
9771b263 3246 else if (results->length () == 0)
e5bae89b
RG
3247 /* Assert that we found *some* field there. The user couldn't be
3248 accessing *only* padding. */
3249 /* Still the user could access one past the end of an array
3250 embedded in a struct resulting in accessing *only* padding. */
0ba0772b
RB
3251 /* Or accessing only padding via type-punning to a type
3252 that has a filed just in padding space. */
3253 {
3254 cexpr.type = SCALAR;
3255 cexpr.var = anything_id;
3256 cexpr.offset = 0;
9771b263 3257 results->safe_push (cexpr);
0ba0772b 3258 }
dd68d988 3259 }
18455d17
RG
3260 else if (bitmaxsize == 0)
3261 {
3262 if (dump_file && (dump_flags & TDF_DETAILS))
3263 fprintf (dump_file, "Access to zero-sized part of variable,"
3264 "ignoring\n");
3265 }
910fdc79
DB
3266 else
3267 if (dump_file && (dump_flags & TDF_DETAILS))
3268 fprintf (dump_file, "Access to past the end of variable, ignoring\n");
910fdc79 3269 }
9771b263 3270 else if (result.type == DEREF)
7b765bed 3271 {
5006671f
RG
3272 /* If we do not know exactly where the access goes say so. Note
3273 that only for non-structure accesses we know that we access
3274 at most one subfiled of any variable. */
3275 if (bitpos == -1
3276 || bitsize != bitmaxsize
1c09321c 3277 || AGGREGATE_TYPE_P (TREE_TYPE (orig_t))
9771b263
DN
3278 || result.offset == UNKNOWN_OFFSET)
3279 result.offset = UNKNOWN_OFFSET;
5006671f 3280 else
9771b263 3281 result.offset += bitpos;
7b765bed 3282 }
9771b263 3283 else if (result.type == ADDRESSOF)
b51605c4
RG
3284 {
3285 /* We can end up here for component references on a
3286 VIEW_CONVERT_EXPR <>(&foobar). */
9771b263
DN
3287 result.type = SCALAR;
3288 result.var = anything_id;
3289 result.offset = 0;
b51605c4 3290 }
c0d459f0 3291 else
5006671f 3292 gcc_unreachable ();
910fdc79
DB
3293}
3294
3295
3296/* Dereference the constraint expression CONS, and return the result.
3297 DEREF (ADDRESSOF) = SCALAR
3298 DEREF (SCALAR) = DEREF
3299 DEREF (DEREF) = (temp = DEREF1; result = DEREF(temp))
3300 This is needed so that we can handle dereferencing DEREF constraints. */
3301
4ee00913 3302static void
9771b263 3303do_deref (vec<ce_s> *constraints)
910fdc79 3304{
4ee00913
DB
3305 struct constraint_expr *c;
3306 unsigned int i = 0;
c58936b6 3307
9771b263 3308 FOR_EACH_VEC_ELT (*constraints, i, c)
910fdc79 3309 {
4ee00913
DB
3310 if (c->type == SCALAR)
3311 c->type = DEREF;
3312 else if (c->type == ADDRESSOF)
3313 c->type = SCALAR;
3314 else if (c->type == DEREF)
3315 {
b14e9388
RG
3316 struct constraint_expr tmplhs;
3317 tmplhs = new_scalar_tmp_constraint_exp ("dereftmp");
4ee00913
DB
3318 process_constraint (new_constraint (tmplhs, *c));
3319 c->var = tmplhs.var;
3320 }
3321 else
3322 gcc_unreachable ();
910fdc79 3323 }
910fdc79
DB
3324}
3325
1d24fdd9
RG
3326/* Given a tree T, return the constraint expression for taking the
3327 address of it. */
3328
3329static void
9771b263 3330get_constraint_for_address_of (tree t, vec<ce_s> *results)
1d24fdd9
RG
3331{
3332 struct constraint_expr *c;
3333 unsigned int i;
3334
ed6c4831 3335 get_constraint_for_1 (t, results, true, true);
1d24fdd9 3336
9771b263 3337 FOR_EACH_VEC_ELT (*results, i, c)
1d24fdd9
RG
3338 {
3339 if (c->type == DEREF)
3340 c->type = SCALAR;
3341 else
3342 c->type = ADDRESSOF;
3343 }
3344}
3345
910fdc79
DB
3346/* Given a tree T, return the constraint expression for it. */
3347
4ee00913 3348static void
9771b263 3349get_constraint_for_1 (tree t, vec<ce_s> *results, bool address_p,
ed6c4831 3350 bool lhs_p)
910fdc79
DB
3351{
3352 struct constraint_expr temp;
3353
3354 /* x = integer is all glommed to a single variable, which doesn't
3355 point to anything by itself. That is, of course, unless it is an
3356 integer constant being treated as a pointer, in which case, we
3357 will return that this is really the addressof anything. This
3358 happens below, since it will fall into the default case. The only
3359 case we know something about an integer treated like a pointer is
3360 when it is the NULL pointer, and then we just say it points to
89ebafc6
PB
3361 NULL.
3362
3363 Do not do that if -fno-delete-null-pointer-checks though, because
3364 in that case *NULL does not fail, so it _should_ alias *anything.
3365 It is not worth adding a new option or renaming the existing one,
3366 since this case is relatively obscure. */
8eb7bc3c
RG
3367 if ((TREE_CODE (t) == INTEGER_CST
3368 && integer_zerop (t))
3369 /* The only valid CONSTRUCTORs in gimple with pointer typed
3370 elements are zero-initializer. But in IPA mode we also
3371 process global initializers, so verify at least. */
3372 || (TREE_CODE (t) == CONSTRUCTOR
3373 && CONSTRUCTOR_NELTS (t) == 0))
3374 {
3375 if (flag_delete_null_pointer_checks)
3376 temp.var = nothing_id;
3377 else
1f181fde 3378 temp.var = nonlocal_id;
910fdc79
DB
3379 temp.type = ADDRESSOF;
3380 temp.offset = 0;
9771b263 3381 results->safe_push (temp);
4ee00913 3382 return;
910fdc79
DB
3383 }
3384
ebd7d910
RB
3385 /* String constants are read-only, ideally we'd have a CONST_DECL
3386 for those. */
bd1f29d9
EB
3387 if (TREE_CODE (t) == STRING_CST)
3388 {
ebd7d910 3389 temp.var = string_id;
bd1f29d9
EB
3390 temp.type = SCALAR;
3391 temp.offset = 0;
9771b263 3392 results->safe_push (temp);
bd1f29d9
EB
3393 return;
3394 }
3395
910fdc79
DB
3396 switch (TREE_CODE_CLASS (TREE_CODE (t)))
3397 {
3398 case tcc_expression:
3399 {
3400 switch (TREE_CODE (t))
3401 {
3402 case ADDR_EXPR:
1d24fdd9
RG
3403 get_constraint_for_address_of (TREE_OPERAND (t, 0), results);
3404 return;
e5bae89b 3405 default:;
910fdc79 3406 }
e5bae89b 3407 break;
910fdc79
DB
3408 }
3409 case tcc_reference:
3410 {
3411 switch (TREE_CODE (t))
3412 {
70f34814 3413 case MEM_REF:
910fdc79 3414 {
de2184c0 3415 struct constraint_expr cs;
343b2efc 3416 varinfo_t vi, curr;
97919ae7
RG
3417 get_constraint_for_ptr_offset (TREE_OPERAND (t, 0),
3418 TREE_OPERAND (t, 1), results);
4ee00913 3419 do_deref (results);
343b2efc
RG
3420
3421 /* If we are not taking the address then make sure to process
3422 all subvariables we might access. */
1a5d20a4
RG
3423 if (address_p)
3424 return;
3425
9771b263 3426 cs = results->last ();
b4cf8c9d
RG
3427 if (cs.type == DEREF
3428 && type_can_have_subvars (TREE_TYPE (t)))
1a5d20a4
RG
3429 {
3430 /* For dereferences this means we have to defer it
3431 to solving time. */
9771b263 3432 results->last ().offset = UNKNOWN_OFFSET;
1a5d20a4
RG
3433 return;
3434 }
3435 if (cs.type != SCALAR)
343b2efc
RG
3436 return;
3437
de2184c0 3438 vi = get_varinfo (cs.var);
d6d305fe 3439 curr = vi_next (vi);
343b2efc
RG
3440 if (!vi->is_full_var
3441 && curr)
3442 {
3443 unsigned HOST_WIDE_INT size;
cc269bb6 3444 if (tree_fits_uhwi_p (TYPE_SIZE (TREE_TYPE (t))))
eb1ce453 3445 size = tree_to_uhwi (TYPE_SIZE (TREE_TYPE (t)));
343b2efc
RG
3446 else
3447 size = -1;
d6d305fe 3448 for (; curr; curr = vi_next (curr))
343b2efc
RG
3449 {
3450 if (curr->offset - vi->offset < size)
3451 {
343b2efc 3452 cs.var = curr->id;
9771b263 3453 results->safe_push (cs);
343b2efc
RG
3454 }
3455 else
3456 break;
3457 }
3458 }
4ee00913 3459 return;
910fdc79
DB
3460 }
3461 case ARRAY_REF:
32961db5 3462 case ARRAY_RANGE_REF:
910fdc79 3463 case COMPONENT_REF:
7b909872
RB
3464 case IMAGPART_EXPR:
3465 case REALPART_EXPR:
3466 case BIT_FIELD_REF:
ed6c4831 3467 get_constraint_for_component_ref (t, results, address_p, lhs_p);
4ee00913 3468 return;
5006671f 3469 case VIEW_CONVERT_EXPR:
ed6c4831
RG
3470 get_constraint_for_1 (TREE_OPERAND (t, 0), results, address_p,
3471 lhs_p);
5006671f
RG
3472 return;
3473 /* We are missing handling for TARGET_MEM_REF here. */
e5bae89b 3474 default:;
910fdc79 3475 }
e5bae89b 3476 break;
910fdc79 3477 }
910fdc79
DB
3478 case tcc_exceptional:
3479 {
3480 switch (TREE_CODE (t))
3481 {
910fdc79 3482 case SSA_NAME:
4ee00913 3483 {
c0d459f0 3484 get_constraint_for_ssa_var (t, results, address_p);
4ee00913
DB
3485 return;
3486 }
47d8a903
RG
3487 case CONSTRUCTOR:
3488 {
3489 unsigned int i;
3490 tree val;
ef062b13 3491 auto_vec<ce_s> tmp;
47d8a903
RG
3492 FOR_EACH_CONSTRUCTOR_VALUE (CONSTRUCTOR_ELTS (t), i, val)
3493 {
3494 struct constraint_expr *rhsp;
3495 unsigned j;
ed6c4831 3496 get_constraint_for_1 (val, &tmp, address_p, lhs_p);
9771b263
DN
3497 FOR_EACH_VEC_ELT (tmp, j, rhsp)
3498 results->safe_push (*rhsp);
3499 tmp.truncate (0);
47d8a903 3500 }
47d8a903
RG
3501 /* We do not know whether the constructor was complete,
3502 so technically we have to add &NOTHING or &ANYTHING
3503 like we do for an empty constructor as well. */
3504 return;
3505 }
e5bae89b 3506 default:;
910fdc79 3507 }
e5bae89b 3508 break;
910fdc79
DB
3509 }
3510 case tcc_declaration:
4ee00913 3511 {
c0d459f0 3512 get_constraint_for_ssa_var (t, results, address_p);
4ee00913
DB
3513 return;
3514 }
1f181fde
RG
3515 case tcc_constant:
3516 {
3517 /* We cannot refer to automatic variables through constants. */
3518 temp.type = ADDRESSOF;
3519 temp.var = nonlocal_id;
3520 temp.offset = 0;
9771b263 3521 results->safe_push (temp);
1f181fde
RG
3522 return;
3523 }
e5bae89b 3524 default:;
910fdc79 3525 }
e5bae89b
RG
3526
3527 /* The default fallback is a constraint from anything. */
3528 temp.type = ADDRESSOF;
3529 temp.var = anything_id;
3530 temp.offset = 0;
9771b263 3531 results->safe_push (temp);
910fdc79
DB
3532}
3533
c0d459f0
RG
3534/* Given a gimple tree T, return the constraint expression vector for it. */
3535
3536static void
9771b263 3537get_constraint_for (tree t, vec<ce_s> *results)
c0d459f0 3538{
9771b263 3539 gcc_assert (results->length () == 0);
c0d459f0 3540
ed6c4831
RG
3541 get_constraint_for_1 (t, results, false, true);
3542}
3543
3544/* Given a gimple tree T, return the constraint expression vector for it
3545 to be used as the rhs of a constraint. */
3546
3547static void
9771b263 3548get_constraint_for_rhs (tree t, vec<ce_s> *results)
ed6c4831 3549{
9771b263 3550 gcc_assert (results->length () == 0);
ed6c4831
RG
3551
3552 get_constraint_for_1 (t, results, false, false);
c0d459f0 3553}
910fdc79 3554
779704e7
RG
3555
3556/* Efficiently generates constraints from all entries in *RHSC to all
3557 entries in *LHSC. */
3558
3559static void
9771b263
DN
3560process_all_all_constraints (vec<ce_s> lhsc,
3561 vec<ce_s> rhsc)
779704e7
RG
3562{
3563 struct constraint_expr *lhsp, *rhsp;
3564 unsigned i, j;
3565
9771b263 3566 if (lhsc.length () <= 1 || rhsc.length () <= 1)
779704e7 3567 {
9771b263
DN
3568 FOR_EACH_VEC_ELT (lhsc, i, lhsp)
3569 FOR_EACH_VEC_ELT (rhsc, j, rhsp)
779704e7
RG
3570 process_constraint (new_constraint (*lhsp, *rhsp));
3571 }
3572 else
3573 {
3574 struct constraint_expr tmp;
b14e9388 3575 tmp = new_scalar_tmp_constraint_exp ("allalltmp");
9771b263 3576 FOR_EACH_VEC_ELT (rhsc, i, rhsp)
779704e7 3577 process_constraint (new_constraint (tmp, *rhsp));
9771b263 3578 FOR_EACH_VEC_ELT (lhsc, i, lhsp)
779704e7
RG
3579 process_constraint (new_constraint (*lhsp, tmp));
3580 }
3581}
3582
910fdc79
DB
3583/* Handle aggregate copies by expanding into copies of the respective
3584 fields of the structures. */
3585
3586static void
3587do_structure_copy (tree lhsop, tree rhsop)
3588{
5006671f 3589 struct constraint_expr *lhsp, *rhsp;
ef062b13
TS
3590 auto_vec<ce_s> lhsc;
3591 auto_vec<ce_s> rhsc;
5006671f
RG
3592 unsigned j;
3593
3594 get_constraint_for (lhsop, &lhsc);
ed6c4831 3595 get_constraint_for_rhs (rhsop, &rhsc);
9771b263
DN
3596 lhsp = &lhsc[0];
3597 rhsp = &rhsc[0];
5006671f
RG
3598 if (lhsp->type == DEREF
3599 || (lhsp->type == ADDRESSOF && lhsp->var == anything_id)
3600 || rhsp->type == DEREF)
b28ae58f
RG
3601 {
3602 if (lhsp->type == DEREF)
3603 {
9771b263 3604 gcc_assert (lhsc.length () == 1);
b28ae58f
RG
3605 lhsp->offset = UNKNOWN_OFFSET;
3606 }
3607 if (rhsp->type == DEREF)
3608 {
9771b263 3609 gcc_assert (rhsc.length () == 1);
b28ae58f
RG
3610 rhsp->offset = UNKNOWN_OFFSET;
3611 }
3612 process_all_all_constraints (lhsc, rhsc);
3613 }
5006671f
RG
3614 else if (lhsp->type == SCALAR
3615 && (rhsp->type == SCALAR
3616 || rhsp->type == ADDRESSOF))
910fdc79 3617 {
5006671f
RG
3618 HOST_WIDE_INT lhssize, lhsmaxsize, lhsoffset;
3619 HOST_WIDE_INT rhssize, rhsmaxsize, rhsoffset;
3620 unsigned k = 0;
0f900dfa
JJ
3621 get_ref_base_and_extent (lhsop, &lhsoffset, &lhssize, &lhsmaxsize);
3622 get_ref_base_and_extent (rhsop, &rhsoffset, &rhssize, &rhsmaxsize);
9771b263 3623 for (j = 0; lhsc.iterate (j, &lhsp);)
910fdc79 3624 {
5006671f 3625 varinfo_t lhsv, rhsv;
9771b263 3626 rhsp = &rhsc[k];
5006671f
RG
3627 lhsv = get_varinfo (lhsp->var);
3628 rhsv = get_varinfo (rhsp->var);
3629 if (lhsv->may_have_pointers
c636a4fb
RG
3630 && (lhsv->is_full_var
3631 || rhsv->is_full_var
3632 || ranges_overlap_p (lhsv->offset + rhsoffset, lhsv->size,
3633 rhsv->offset + lhsoffset, rhsv->size)))
5006671f 3634 process_constraint (new_constraint (*lhsp, *rhsp));
c636a4fb
RG
3635 if (!rhsv->is_full_var
3636 && (lhsv->is_full_var
3637 || (lhsv->offset + rhsoffset + lhsv->size
3638 > rhsv->offset + lhsoffset + rhsv->size)))
5006671f
RG
3639 {
3640 ++k;
9771b263 3641 if (k >= rhsc.length ())
5006671f
RG
3642 break;
3643 }
910fdc79 3644 else
5006671f 3645 ++j;
910fdc79
DB
3646 }
3647 }
3648 else
5006671f 3649 gcc_unreachable ();
910fdc79
DB
3650}
3651
cb89b4b0 3652/* Create constraints ID = { rhsc }. */
b7091901
RG
3653
3654static void
9771b263 3655make_constraints_to (unsigned id, vec<ce_s> rhsc)
b7091901 3656{
b7091901
RG
3657 struct constraint_expr *c;
3658 struct constraint_expr includes;
3659 unsigned int j;
3660
3661 includes.var = id;
3662 includes.offset = 0;
3663 includes.type = SCALAR;
3664
9771b263 3665 FOR_EACH_VEC_ELT (rhsc, j, c)
faf2ecc5 3666 process_constraint (new_constraint (includes, *c));
cb89b4b0
RG
3667}
3668
3669/* Create a constraint ID = OP. */
3670
3671static void
3672make_constraint_to (unsigned id, tree op)
3673{
ef062b13 3674 auto_vec<ce_s> rhsc;
cb89b4b0
RG
3675 get_constraint_for_rhs (op, &rhsc);
3676 make_constraints_to (id, rhsc);
b7091901
RG
3677}
3678
74d27244
RG
3679/* Create a constraint ID = &FROM. */
3680
3681static void
3682make_constraint_from (varinfo_t vi, int from)
3683{
3684 struct constraint_expr lhs, rhs;
3685
3686 lhs.var = vi->id;
3687 lhs.offset = 0;
3688 lhs.type = SCALAR;
3689
3690 rhs.var = from;
3691 rhs.offset = 0;
3692 rhs.type = ADDRESSOF;
3693 process_constraint (new_constraint (lhs, rhs));
3694}
3695
3696/* Create a constraint ID = FROM. */
3697
3698static void
3699make_copy_constraint (varinfo_t vi, int from)
3700{
3701 struct constraint_expr lhs, rhs;
3702
3703 lhs.var = vi->id;
3704 lhs.offset = 0;
3705 lhs.type = SCALAR;
3706
3707 rhs.var = from;
3708 rhs.offset = 0;
3709 rhs.type = SCALAR;
3710 process_constraint (new_constraint (lhs, rhs));
3711}
3712
b7091901
RG
3713/* Make constraints necessary to make OP escape. */
3714
3715static void
3716make_escape_constraint (tree op)
3717{
3718 make_constraint_to (escaped_id, op);
3719}
3720
3e8542ca
RG
3721/* Add constraints to that the solution of VI is transitively closed. */
3722
3723static void
3724make_transitive_closure_constraints (varinfo_t vi)
3725{
3726 struct constraint_expr lhs, rhs;
3727
3728 /* VAR = *VAR; */
3729 lhs.type = SCALAR;
3730 lhs.var = vi->id;
3731 lhs.offset = 0;
3732 rhs.type = DEREF;
3733 rhs.var = vi->id;
3e8542ca
RG
3734 rhs.offset = UNKNOWN_OFFSET;
3735 process_constraint (new_constraint (lhs, rhs));
3736}
3737
7d6e2521
RG
3738/* Temporary storage for fake var decls. */
3739struct obstack fake_var_decl_obstack;
3740
3741/* Build a fake VAR_DECL acting as referrer to a DECL_UID. */
3742
3743static tree
3744build_fake_var_decl (tree type)
3745{
3746 tree decl = (tree) XOBNEW (&fake_var_decl_obstack, struct tree_var_decl);
3747 memset (decl, 0, sizeof (struct tree_var_decl));
3748 TREE_SET_CODE (decl, VAR_DECL);
3749 TREE_TYPE (decl) = type;
3750 DECL_UID (decl) = allocate_decl_uid ();
3751 SET_DECL_PT_UID (decl, -1);
3752 layout_decl (decl, 0);
3753 return decl;
3754}
3755
0b7b376d
RG
3756/* Create a new artificial heap variable with NAME.
3757 Return the created variable. */
74d27244
RG
3758
3759static varinfo_t
7d6e2521 3760make_heapvar (const char *name)
74d27244
RG
3761{
3762 varinfo_t vi;
7d6e2521
RG
3763 tree heapvar;
3764
3765 heapvar = build_fake_var_decl (ptr_type_node);
3766 DECL_EXTERNAL (heapvar) = 1;
74d27244
RG
3767
3768 vi = new_var_info (heapvar, name);
3769 vi->is_artificial_var = true;
3770 vi->is_heap_var = true;
3771 vi->is_unknown_size_var = true;
b41e33fe 3772 vi->offset = 0;
74d27244
RG
3773 vi->fullsize = ~0;
3774 vi->size = ~0;
3775 vi->is_full_var = true;
3776 insert_vi_for_tree (heapvar, vi);
3777
0b7b376d
RG
3778 return vi;
3779}
3780
3781/* Create a new artificial heap variable with NAME and make a
d3553615
RG
3782 constraint from it to LHS. Set flags according to a tag used
3783 for tracking restrict pointers. */
0b7b376d
RG
3784
3785static varinfo_t
d3553615 3786make_constraint_from_restrict (varinfo_t lhs, const char *name)
0b7b376d 3787{
7d6e2521 3788 varinfo_t vi = make_heapvar (name);
aa098165 3789 vi->is_restrict_var = 1;
d3553615
RG
3790 vi->is_global_var = 1;
3791 vi->may_have_pointers = 1;
74d27244 3792 make_constraint_from (lhs, vi->id);
74d27244
RG
3793 return vi;
3794}
3795
3796/* Create a new artificial heap variable with NAME and make a
3797 constraint from it to LHS. Set flags according to a tag used
d3553615
RG
3798 for tracking restrict pointers and make the artificial heap
3799 point to global memory. */
74d27244 3800
d3553615
RG
3801static varinfo_t
3802make_constraint_from_global_restrict (varinfo_t lhs, const char *name)
74d27244 3803{
d3553615
RG
3804 varinfo_t vi = make_constraint_from_restrict (lhs, name);
3805 make_copy_constraint (vi, nonlocal_id);
3806 return vi;
74d27244
RG
3807}
3808
25a6a873
RG
3809/* In IPA mode there are varinfos for different aspects of reach
3810 function designator. One for the points-to set of the return
3811 value, one for the variables that are clobbered by the function,
3812 one for its uses and one for each parameter (including a single
3813 glob for remaining variadic arguments). */
3814
3815enum { fi_clobbers = 1, fi_uses = 2,
3816 fi_static_chain = 3, fi_result = 4, fi_parm_base = 5 };
3817
3818/* Get a constraint for the requested part of a function designator FI
3819 when operating in IPA mode. */
3820
3821static struct constraint_expr
3822get_function_part_constraint (varinfo_t fi, unsigned part)
3823{
3824 struct constraint_expr c;
3825
3826 gcc_assert (in_ipa_mode);
3827
3828 if (fi->id == anything_id)
3829 {
3830 /* ??? We probably should have a ANYFN special variable. */
3831 c.var = anything_id;
3832 c.offset = 0;
3833 c.type = SCALAR;
3834 }
3835 else if (TREE_CODE (fi->decl) == FUNCTION_DECL)
3836 {
3837 varinfo_t ai = first_vi_for_offset (fi, part);
18abb35e
RG
3838 if (ai)
3839 c.var = ai->id;
3840 else
3841 c.var = anything_id;
25a6a873
RG
3842 c.offset = 0;
3843 c.type = SCALAR;
3844 }
3845 else
3846 {
3847 c.var = fi->id;
3848 c.offset = part;
3849 c.type = DEREF;
3850 }
3851
3852 return c;
3853}
3854
7b765bed
DB
3855/* For non-IPA mode, generate constraints necessary for a call on the
3856 RHS. */
3857
3858static void
538dd0b7 3859handle_rhs_call (gcall *stmt, vec<ce_s> *results)
7b765bed 3860{
472c7fbd 3861 struct constraint_expr rhsc;
726a989a 3862 unsigned i;
0b7b376d 3863 bool returns_uses = false;
7b765bed 3864
726a989a
RB
3865 for (i = 0; i < gimple_call_num_args (stmt); ++i)
3866 {
3867 tree arg = gimple_call_arg (stmt, i);
0b7b376d 3868 int flags = gimple_call_arg_flags (stmt, i);
726a989a 3869
0f8d6231
RG
3870 /* If the argument is not used we can ignore it. */
3871 if (flags & EAF_UNUSED)
0b7b376d
RG
3872 continue;
3873
3874 /* As we compute ESCAPED context-insensitive we do not gain
3875 any precision with just EAF_NOCLOBBER but not EAF_NOESCAPE
3876 set. The argument would still get clobbered through the
81ab7312 3877 escape solution. */
0b7b376d
RG
3878 if ((flags & EAF_NOCLOBBER)
3879 && (flags & EAF_NOESCAPE))
3880 {
3881 varinfo_t uses = get_call_use_vi (stmt);
3882 if (!(flags & EAF_DIRECT))
81ab7312
RG
3883 {
3884 varinfo_t tem = new_var_info (NULL_TREE, "callarg");
3885 make_constraint_to (tem->id, arg);
3886 make_transitive_closure_constraints (tem);
3887 make_copy_constraint (uses, tem->id);
3888 }
3889 else
3890 make_constraint_to (uses->id, arg);
0b7b376d
RG
3891 returns_uses = true;
3892 }
3893 else if (flags & EAF_NOESCAPE)
3894 {
81ab7312 3895 struct constraint_expr lhs, rhs;
0b7b376d
RG
3896 varinfo_t uses = get_call_use_vi (stmt);
3897 varinfo_t clobbers = get_call_clobber_vi (stmt);
81ab7312
RG
3898 varinfo_t tem = new_var_info (NULL_TREE, "callarg");
3899 make_constraint_to (tem->id, arg);
0b7b376d 3900 if (!(flags & EAF_DIRECT))
81ab7312
RG
3901 make_transitive_closure_constraints (tem);
3902 make_copy_constraint (uses, tem->id);
3903 make_copy_constraint (clobbers, tem->id);
3904 /* Add *tem = nonlocal, do not add *tem = callused as
3905 EAF_NOESCAPE parameters do not escape to other parameters
3906 and all other uses appear in NONLOCAL as well. */
3907 lhs.type = DEREF;
3908 lhs.var = tem->id;
3909 lhs.offset = 0;
3910 rhs.type = SCALAR;
3911 rhs.var = nonlocal_id;
3912 rhs.offset = 0;
3913 process_constraint (new_constraint (lhs, rhs));
0b7b376d
RG
3914 returns_uses = true;
3915 }
3916 else
726a989a
RB
3917 make_escape_constraint (arg);
3918 }
b7091901 3919
0b7b376d
RG
3920 /* If we added to the calls uses solution make sure we account for
3921 pointers to it to be returned. */
3922 if (returns_uses)
3923 {
3924 rhsc.var = get_call_use_vi (stmt)->id;
3925 rhsc.offset = 0;
3926 rhsc.type = SCALAR;
9771b263 3927 results->safe_push (rhsc);
0b7b376d
RG
3928 }
3929
b7091901 3930 /* The static chain escapes as well. */
726a989a
RB
3931 if (gimple_call_chain (stmt))
3932 make_escape_constraint (gimple_call_chain (stmt));
472c7fbd 3933
1d24fdd9
RG
3934 /* And if we applied NRV the address of the return slot escapes as well. */
3935 if (gimple_call_return_slot_opt_p (stmt)
3936 && gimple_call_lhs (stmt) != NULL_TREE
4d61856d 3937 && TREE_ADDRESSABLE (TREE_TYPE (gimple_call_lhs (stmt))))
1d24fdd9 3938 {
ef062b13 3939 auto_vec<ce_s> tmpc;
1d24fdd9
RG
3940 struct constraint_expr lhsc, *c;
3941 get_constraint_for_address_of (gimple_call_lhs (stmt), &tmpc);
3942 lhsc.var = escaped_id;
3943 lhsc.offset = 0;
3944 lhsc.type = SCALAR;
9771b263 3945 FOR_EACH_VEC_ELT (tmpc, i, c)
1d24fdd9 3946 process_constraint (new_constraint (lhsc, *c));
1d24fdd9
RG
3947 }
3948
5006671f
RG
3949 /* Regular functions return nonlocal memory. */
3950 rhsc.var = nonlocal_id;
472c7fbd 3951 rhsc.offset = 0;
5006671f 3952 rhsc.type = SCALAR;
9771b263 3953 results->safe_push (rhsc);
7b765bed 3954}
e8ca4159 3955
af947da7
RG
3956/* For non-IPA mode, generate constraints necessary for a call
3957 that returns a pointer and assigns it to LHS. This simply makes
b7091901 3958 the LHS point to global and escaped variables. */
af947da7
RG
3959
3960static void
538dd0b7 3961handle_lhs_call (gcall *stmt, tree lhs, int flags, vec<ce_s> rhsc,
0b7b376d 3962 tree fndecl)
af947da7 3963{
ef062b13 3964 auto_vec<ce_s> lhsc;
af947da7 3965
b7091901 3966 get_constraint_for (lhs, &lhsc);
0b7b376d
RG
3967 /* If the store is to a global decl make sure to
3968 add proper escape constraints. */
3969 lhs = get_base_address (lhs);
3970 if (lhs
3971 && DECL_P (lhs)
3972 && is_global_var (lhs))
3973 {
3974 struct constraint_expr tmpc;
3975 tmpc.var = escaped_id;
3976 tmpc.offset = 0;
3977 tmpc.type = SCALAR;
9771b263 3978 lhsc.safe_push (tmpc);
0b7b376d 3979 }
183ae595 3980
0b7b376d
RG
3981 /* If the call returns an argument unmodified override the rhs
3982 constraints. */
0b7b376d
RG
3983 if (flags & ERF_RETURNS_ARG
3984 && (flags & ERF_RETURN_ARG_MASK) < gimple_call_num_args (stmt))
3985 {
3986 tree arg;
9771b263 3987 rhsc.create (0);
0b7b376d
RG
3988 arg = gimple_call_arg (stmt, flags & ERF_RETURN_ARG_MASK);
3989 get_constraint_for (arg, &rhsc);
3990 process_all_all_constraints (lhsc, rhsc);
9771b263 3991 rhsc.release ();
0b7b376d
RG
3992 }
3993 else if (flags & ERF_NOALIAS)
183ae595 3994 {
183ae595 3995 varinfo_t vi;
0b7b376d 3996 struct constraint_expr tmpc;
9771b263 3997 rhsc.create (0);
7d6e2521 3998 vi = make_heapvar ("HEAP");
32cab212 3999 /* We are marking allocated storage local, we deal with it becoming
11924f8b 4000 global by escaping and setting of vars_contains_escaped_heap. */
91deb937 4001 DECL_EXTERNAL (vi->decl) = 0;
14c41b9b 4002 vi->is_global_var = 0;
72d182d3 4003 /* If this is not a real malloc call assume the memory was
0b7b376d 4004 initialized and thus may point to global memory. All
72d182d3
RG
4005 builtin functions with the malloc attribute behave in a sane way. */
4006 if (!fndecl
4007 || DECL_BUILT_IN_CLASS (fndecl) != BUILT_IN_NORMAL)
4008 make_constraint_from (vi, nonlocal_id);
0b7b376d
RG
4009 tmpc.var = vi->id;
4010 tmpc.offset = 0;
4011 tmpc.type = ADDRESSOF;
9771b263 4012 rhsc.safe_push (tmpc);
f5843d08 4013 process_all_all_constraints (lhsc, rhsc);
9771b263 4014 rhsc.release ();
183ae595 4015 }
f5843d08
RG
4016 else
4017 process_all_all_constraints (lhsc, rhsc);
b7091901
RG
4018}
4019
4020/* For non-IPA mode, generate constraints necessary for a call of a
4021 const function that returns a pointer in the statement STMT. */
4022
4023static void
538dd0b7 4024handle_const_call (gcall *stmt, vec<ce_s> *results)
b7091901 4025{
b14e9388 4026 struct constraint_expr rhsc;
472c7fbd 4027 unsigned int k;
b7091901 4028
472c7fbd
RG
4029 /* Treat nested const functions the same as pure functions as far
4030 as the static chain is concerned. */
726a989a 4031 if (gimple_call_chain (stmt))
b7091901 4032 {
3e8542ca
RG
4033 varinfo_t uses = get_call_use_vi (stmt);
4034 make_transitive_closure_constraints (uses);
4035 make_constraint_to (uses->id, gimple_call_chain (stmt));
4036 rhsc.var = uses->id;
b7091901 4037 rhsc.offset = 0;
472c7fbd 4038 rhsc.type = SCALAR;
9771b263 4039 results->safe_push (rhsc);
b7091901
RG
4040 }
4041
b7091901 4042 /* May return arguments. */
726a989a
RB
4043 for (k = 0; k < gimple_call_num_args (stmt); ++k)
4044 {
4045 tree arg = gimple_call_arg (stmt, k);
ef062b13 4046 auto_vec<ce_s> argc;
0f8d6231
RG
4047 unsigned i;
4048 struct constraint_expr *argp;
4049 get_constraint_for_rhs (arg, &argc);
9771b263
DN
4050 FOR_EACH_VEC_ELT (argc, i, argp)
4051 results->safe_push (*argp);
726a989a 4052 }
b7091901 4053
472c7fbd
RG
4054 /* May return addresses of globals. */
4055 rhsc.var = nonlocal_id;
4056 rhsc.offset = 0;
4057 rhsc.type = ADDRESSOF;
9771b263 4058 results->safe_push (rhsc);
af947da7
RG
4059}
4060
15c15196
RG
4061/* For non-IPA mode, generate constraints necessary for a call to a
4062 pure function in statement STMT. */
4063
4064static void
538dd0b7 4065handle_pure_call (gcall *stmt, vec<ce_s> *results)
15c15196 4066{
472c7fbd 4067 struct constraint_expr rhsc;
726a989a 4068 unsigned i;
3e8542ca 4069 varinfo_t uses = NULL;
15c15196
RG
4070
4071 /* Memory reached from pointer arguments is call-used. */
726a989a
RB
4072 for (i = 0; i < gimple_call_num_args (stmt); ++i)
4073 {
4074 tree arg = gimple_call_arg (stmt, i);
0f8d6231 4075 if (!uses)
472c7fbd 4076 {
0f8d6231
RG
4077 uses = get_call_use_vi (stmt);
4078 make_transitive_closure_constraints (uses);
472c7fbd 4079 }
0f8d6231 4080 make_constraint_to (uses->id, arg);
726a989a 4081 }
15c15196
RG
4082
4083 /* The static chain is used as well. */
726a989a 4084 if (gimple_call_chain (stmt))
15c15196 4085 {
3e8542ca
RG
4086 if (!uses)
4087 {
4088 uses = get_call_use_vi (stmt);
4089 make_transitive_closure_constraints (uses);
4090 }
4091 make_constraint_to (uses->id, gimple_call_chain (stmt));
472c7fbd 4092 }
15c15196 4093
3e8542ca
RG
4094 /* Pure functions may return call-used and nonlocal memory. */
4095 if (uses)
472c7fbd 4096 {
3e8542ca 4097 rhsc.var = uses->id;
15c15196 4098 rhsc.offset = 0;
472c7fbd 4099 rhsc.type = SCALAR;
9771b263 4100 results->safe_push (rhsc);
15c15196 4101 }
5006671f 4102 rhsc.var = nonlocal_id;
472c7fbd 4103 rhsc.offset = 0;
5006671f 4104 rhsc.type = SCALAR;
9771b263 4105 results->safe_push (rhsc);
15c15196
RG
4106}
4107
25a6a873
RG
4108
4109/* Return the varinfo for the callee of CALL. */
4110
4111static varinfo_t
538dd0b7 4112get_fi_for_callee (gcall *call)
25a6a873 4113{
5c04e9f4 4114 tree decl, fn = gimple_call_fn (call);
25a6a873 4115
5c04e9f4
RG
4116 if (fn && TREE_CODE (fn) == OBJ_TYPE_REF)
4117 fn = OBJ_TYPE_REF_EXPR (fn);
25583c4f 4118
25a6a873
RG
4119 /* If we can directly resolve the function being called, do so.
4120 Otherwise, it must be some sort of indirect expression that
4121 we should still be able to handle. */
5c04e9f4 4122 decl = gimple_call_addr_fndecl (fn);
25a6a873
RG
4123 if (decl)
4124 return get_vi_for_tree (decl);
4125
5c04e9f4 4126 /* If the function is anything other than a SSA name pointer we have no
25a6a873 4127 clue and should be getting ANYFN (well, ANYTHING for now). */
5c04e9f4 4128 if (!fn || TREE_CODE (fn) != SSA_NAME)
25a6a873 4129 return get_varinfo (anything_id);
5c04e9f4 4130
67386041
RG
4131 if (SSA_NAME_IS_DEFAULT_DEF (fn)
4132 && (TREE_CODE (SSA_NAME_VAR (fn)) == PARM_DECL
4133 || TREE_CODE (SSA_NAME_VAR (fn)) == RESULT_DECL))
5c04e9f4
RG
4134 fn = SSA_NAME_VAR (fn);
4135
4136 return get_vi_for_tree (fn);
25a6a873
RG
4137}
4138
e38811ce
RG
4139/* Create constraints for the builtin call T. Return true if the call
4140 was handled, otherwise false. */
910fdc79 4141
e38811ce 4142static bool
538dd0b7 4143find_func_aliases_for_builtin_call (struct function *fn, gcall *t)
910fdc79 4144{
e38811ce 4145 tree fndecl = gimple_call_fndecl (t);
a0791dcc
RB
4146 auto_vec<ce_s, 2> lhsc;
4147 auto_vec<ce_s, 4> rhsc;
25a6a873 4148 varinfo_t fi;
910fdc79 4149
3626621a 4150 if (gimple_call_builtin_p (t, BUILT_IN_NORMAL))
e38811ce
RG
4151 /* ??? All builtins that are handled here need to be handled
4152 in the alias-oracle query functions explicitly! */
4153 switch (DECL_FUNCTION_CODE (fndecl))
4154 {
4155 /* All the following functions return a pointer to the same object
4156 as their first argument points to. The functions do not add
4157 to the ESCAPED solution. The functions make the first argument
4158 pointed to memory point to what the second argument pointed to
4159 memory points to. */
4160 case BUILT_IN_STRCPY:
4161 case BUILT_IN_STRNCPY:
4162 case BUILT_IN_BCOPY:
4163 case BUILT_IN_MEMCPY:
4164 case BUILT_IN_MEMMOVE:
4165 case BUILT_IN_MEMPCPY:
4166 case BUILT_IN_STPCPY:
4167 case BUILT_IN_STPNCPY:
4168 case BUILT_IN_STRCAT:
4169 case BUILT_IN_STRNCAT:
36dc1a88
JJ
4170 case BUILT_IN_STRCPY_CHK:
4171 case BUILT_IN_STRNCPY_CHK:
4172 case BUILT_IN_MEMCPY_CHK:
4173 case BUILT_IN_MEMMOVE_CHK:
4174 case BUILT_IN_MEMPCPY_CHK:
4175 case BUILT_IN_STPCPY_CHK:
f3fc9b80 4176 case BUILT_IN_STPNCPY_CHK:
36dc1a88
JJ
4177 case BUILT_IN_STRCAT_CHK:
4178 case BUILT_IN_STRNCAT_CHK:
0a35513e
AH
4179 case BUILT_IN_TM_MEMCPY:
4180 case BUILT_IN_TM_MEMMOVE:
e8ca4159 4181 {
e38811ce
RG
4182 tree res = gimple_call_lhs (t);
4183 tree dest = gimple_call_arg (t, (DECL_FUNCTION_CODE (fndecl)
4184 == BUILT_IN_BCOPY ? 1 : 0));
4185 tree src = gimple_call_arg (t, (DECL_FUNCTION_CODE (fndecl)
4186 == BUILT_IN_BCOPY ? 0 : 1));
4187 if (res != NULL_TREE)
0f8d6231 4188 {
e38811ce
RG
4189 get_constraint_for (res, &lhsc);
4190 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_MEMPCPY
4191 || DECL_FUNCTION_CODE (fndecl) == BUILT_IN_STPCPY
ce7e54ff
JJ
4192 || DECL_FUNCTION_CODE (fndecl) == BUILT_IN_STPNCPY
4193 || DECL_FUNCTION_CODE (fndecl) == BUILT_IN_MEMPCPY_CHK
f3fc9b80
RG
4194 || DECL_FUNCTION_CODE (fndecl) == BUILT_IN_STPCPY_CHK
4195 || DECL_FUNCTION_CODE (fndecl) == BUILT_IN_STPNCPY_CHK)
e38811ce
RG
4196 get_constraint_for_ptr_offset (dest, NULL_TREE, &rhsc);
4197 else
4198 get_constraint_for (dest, &rhsc);
4199 process_all_all_constraints (lhsc, rhsc);
a0791dcc
RB
4200 lhsc.truncate (0);
4201 rhsc.truncate (0);
c58936b6 4202 }
e38811ce
RG
4203 get_constraint_for_ptr_offset (dest, NULL_TREE, &lhsc);
4204 get_constraint_for_ptr_offset (src, NULL_TREE, &rhsc);
4205 do_deref (&lhsc);
4206 do_deref (&rhsc);
4207 process_all_all_constraints (lhsc, rhsc);
e38811ce 4208 return true;
4ee00913 4209 }
e38811ce 4210 case BUILT_IN_MEMSET:
36dc1a88 4211 case BUILT_IN_MEMSET_CHK:
0a35513e 4212 case BUILT_IN_TM_MEMSET:
e38811ce
RG
4213 {
4214 tree res = gimple_call_lhs (t);
4215 tree dest = gimple_call_arg (t, 0);
4216 unsigned i;
4217 ce_s *lhsp;
4218 struct constraint_expr ac;
4219 if (res != NULL_TREE)
779704e7 4220 {
e38811ce
RG
4221 get_constraint_for (res, &lhsc);
4222 get_constraint_for (dest, &rhsc);
779704e7 4223 process_all_all_constraints (lhsc, rhsc);
a0791dcc 4224 lhsc.truncate (0);
779704e7 4225 }
e38811ce
RG
4226 get_constraint_for_ptr_offset (dest, NULL_TREE, &lhsc);
4227 do_deref (&lhsc);
4228 if (flag_delete_null_pointer_checks
4229 && integer_zerop (gimple_call_arg (t, 1)))
779704e7 4230 {
e38811ce
RG
4231 ac.type = ADDRESSOF;
4232 ac.var = nothing_id;
779704e7 4233 }
e38811ce 4234 else
25a6a873 4235 {
e38811ce
RG
4236 ac.type = SCALAR;
4237 ac.var = integer_id;
25a6a873 4238 }
e38811ce 4239 ac.offset = 0;
9771b263 4240 FOR_EACH_VEC_ELT (lhsc, i, lhsp)
e38811ce 4241 process_constraint (new_constraint (*lhsp, ac));
e38811ce
RG
4242 return true;
4243 }
32cab212
RB
4244 case BUILT_IN_POSIX_MEMALIGN:
4245 {
4246 tree ptrptr = gimple_call_arg (t, 0);
4247 get_constraint_for (ptrptr, &lhsc);
4248 do_deref (&lhsc);
4249 varinfo_t vi = make_heapvar ("HEAP");
4250 /* We are marking allocated storage local, we deal with it becoming
4251 global by escaping and setting of vars_contains_escaped_heap. */
4252 DECL_EXTERNAL (vi->decl) = 0;
4253 vi->is_global_var = 0;
4254 struct constraint_expr tmpc;
4255 tmpc.var = vi->id;
4256 tmpc.offset = 0;
4257 tmpc.type = ADDRESSOF;
4258 rhsc.safe_push (tmpc);
4259 process_all_all_constraints (lhsc, rhsc);
32cab212
RB
4260 return true;
4261 }
d9048d16
JJ
4262 case BUILT_IN_ASSUME_ALIGNED:
4263 {
4264 tree res = gimple_call_lhs (t);
4265 tree dest = gimple_call_arg (t, 0);
4266 if (res != NULL_TREE)
4267 {
4268 get_constraint_for (res, &lhsc);
4269 get_constraint_for (dest, &rhsc);
4270 process_all_all_constraints (lhsc, rhsc);
d9048d16
JJ
4271 }
4272 return true;
4273 }
e38811ce
RG
4274 /* All the following functions do not return pointers, do not
4275 modify the points-to sets of memory reachable from their
4276 arguments and do not add to the ESCAPED solution. */
4277 case BUILT_IN_SINCOS:
4278 case BUILT_IN_SINCOSF:
4279 case BUILT_IN_SINCOSL:
4280 case BUILT_IN_FREXP:
4281 case BUILT_IN_FREXPF:
4282 case BUILT_IN_FREXPL:
4283 case BUILT_IN_GAMMA_R:
4284 case BUILT_IN_GAMMAF_R:
4285 case BUILT_IN_GAMMAL_R:
4286 case BUILT_IN_LGAMMA_R:
4287 case BUILT_IN_LGAMMAF_R:
4288 case BUILT_IN_LGAMMAL_R:
4289 case BUILT_IN_MODF:
4290 case BUILT_IN_MODFF:
4291 case BUILT_IN_MODFL:
4292 case BUILT_IN_REMQUO:
4293 case BUILT_IN_REMQUOF:
4294 case BUILT_IN_REMQUOL:
4295 case BUILT_IN_FREE:
4296 return true;
915afed6
JJ
4297 case BUILT_IN_STRDUP:
4298 case BUILT_IN_STRNDUP:
c8f49949 4299 case BUILT_IN_REALLOC:
915afed6
JJ
4300 if (gimple_call_lhs (t))
4301 {
c8f49949
RB
4302 handle_lhs_call (t, gimple_call_lhs (t),
4303 gimple_call_return_flags (t) | ERF_NOALIAS,
6e1aa848 4304 vNULL, fndecl);
915afed6
JJ
4305 get_constraint_for_ptr_offset (gimple_call_lhs (t),
4306 NULL_TREE, &lhsc);
4307 get_constraint_for_ptr_offset (gimple_call_arg (t, 0),
4308 NULL_TREE, &rhsc);
4309 do_deref (&lhsc);
4310 do_deref (&rhsc);
4311 process_all_all_constraints (lhsc, rhsc);
a0791dcc
RB
4312 lhsc.truncate (0);
4313 rhsc.truncate (0);
c8f49949
RB
4314 /* For realloc the resulting pointer can be equal to the
4315 argument as well. But only doing this wouldn't be
4316 correct because with ptr == 0 realloc behaves like malloc. */
4317 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_REALLOC)
4318 {
4319 get_constraint_for (gimple_call_lhs (t), &lhsc);
4320 get_constraint_for (gimple_call_arg (t, 0), &rhsc);
4321 process_all_all_constraints (lhsc, rhsc);
c8f49949 4322 }
915afed6
JJ
4323 return true;
4324 }
4325 break;
92608d0e
RB
4326 /* String / character search functions return a pointer into the
4327 source string or NULL. */
4328 case BUILT_IN_INDEX:
4329 case BUILT_IN_STRCHR:
4330 case BUILT_IN_STRRCHR:
4331 case BUILT_IN_MEMCHR:
4332 case BUILT_IN_STRSTR:
4333 case BUILT_IN_STRPBRK:
4334 if (gimple_call_lhs (t))
4335 {
4336 tree src = gimple_call_arg (t, 0);
4337 get_constraint_for_ptr_offset (src, NULL_TREE, &rhsc);
4338 constraint_expr nul;
4339 nul.var = nothing_id;
4340 nul.offset = 0;
4341 nul.type = ADDRESSOF;
4342 rhsc.safe_push (nul);
4343 get_constraint_for (gimple_call_lhs (t), &lhsc);
4344 process_all_all_constraints (lhsc, rhsc);
92608d0e
RB
4345 }
4346 return true;
e38811ce
RG
4347 /* Trampolines are special - they set up passing the static
4348 frame. */
4349 case BUILT_IN_INIT_TRAMPOLINE:
4350 {
4351 tree tramp = gimple_call_arg (t, 0);
4352 tree nfunc = gimple_call_arg (t, 1);
4353 tree frame = gimple_call_arg (t, 2);
4354 unsigned i;
4355 struct constraint_expr lhs, *rhsp;
4356 if (in_ipa_mode)
25a6a873 4357 {
e38811ce
RG
4358 varinfo_t nfi = NULL;
4359 gcc_assert (TREE_CODE (nfunc) == ADDR_EXPR);
4360 nfi = lookup_vi_for_tree (TREE_OPERAND (nfunc, 0));
4361 if (nfi)
25a6a873 4362 {
e38811ce
RG
4363 lhs = get_function_part_constraint (nfi, fi_static_chain);
4364 get_constraint_for (frame, &rhsc);
9771b263 4365 FOR_EACH_VEC_ELT (rhsc, i, rhsp)
a0791dcc
RB
4366 process_constraint (new_constraint (lhs, *rhsp));
4367 rhsc.truncate (0);
e38811ce
RG
4368
4369 /* Make the frame point to the function for
4370 the trampoline adjustment call. */
4371 get_constraint_for (tramp, &lhsc);
4372 do_deref (&lhsc);
4373 get_constraint_for (nfunc, &rhsc);
25a6a873 4374 process_all_all_constraints (lhsc, rhsc);
e38811ce
RG
4375
4376 return true;
25a6a873 4377 }
25a6a873 4378 }
e38811ce
RG
4379 /* Else fallthru to generic handling which will let
4380 the frame escape. */
4381 break;
4382 }
4383 case BUILT_IN_ADJUST_TRAMPOLINE:
4384 {
4385 tree tramp = gimple_call_arg (t, 0);
4386 tree res = gimple_call_lhs (t);
4387 if (in_ipa_mode && res)
25a6a873 4388 {
e38811ce
RG
4389 get_constraint_for (res, &lhsc);
4390 get_constraint_for (tramp, &rhsc);
4391 do_deref (&rhsc);
4392 process_all_all_constraints (lhsc, rhsc);
25a6a873 4393 }
e38811ce
RG
4394 return true;
4395 }
0a35513e
AH
4396 CASE_BUILT_IN_TM_STORE (1):
4397 CASE_BUILT_IN_TM_STORE (2):
4398 CASE_BUILT_IN_TM_STORE (4):
4399 CASE_BUILT_IN_TM_STORE (8):
4400 CASE_BUILT_IN_TM_STORE (FLOAT):
4401 CASE_BUILT_IN_TM_STORE (DOUBLE):
4402 CASE_BUILT_IN_TM_STORE (LDOUBLE):
4403 CASE_BUILT_IN_TM_STORE (M64):
4404 CASE_BUILT_IN_TM_STORE (M128):
4405 CASE_BUILT_IN_TM_STORE (M256):
4406 {
4407 tree addr = gimple_call_arg (t, 0);
4408 tree src = gimple_call_arg (t, 1);
4409
4410 get_constraint_for (addr, &lhsc);
4411 do_deref (&lhsc);
4412 get_constraint_for (src, &rhsc);
4413 process_all_all_constraints (lhsc, rhsc);
0a35513e
AH
4414 return true;
4415 }
4416 CASE_BUILT_IN_TM_LOAD (1):
4417 CASE_BUILT_IN_TM_LOAD (2):
4418 CASE_BUILT_IN_TM_LOAD (4):
4419 CASE_BUILT_IN_TM_LOAD (8):
4420 CASE_BUILT_IN_TM_LOAD (FLOAT):
4421 CASE_BUILT_IN_TM_LOAD (DOUBLE):
4422 CASE_BUILT_IN_TM_LOAD (LDOUBLE):
4423 CASE_BUILT_IN_TM_LOAD (M64):
4424 CASE_BUILT_IN_TM_LOAD (M128):
4425 CASE_BUILT_IN_TM_LOAD (M256):
4426 {
4427 tree dest = gimple_call_lhs (t);
4428 tree addr = gimple_call_arg (t, 0);
4429
4430 get_constraint_for (dest, &lhsc);
4431 get_constraint_for (addr, &rhsc);
4432 do_deref (&rhsc);
4433 process_all_all_constraints (lhsc, rhsc);
0a35513e
AH
4434 return true;
4435 }
e38811ce
RG
4436 /* Variadic argument handling needs to be handled in IPA
4437 mode as well. */
4438 case BUILT_IN_VA_START:
4439 {
df2f6100
RG
4440 tree valist = gimple_call_arg (t, 0);
4441 struct constraint_expr rhs, *lhsp;
4442 unsigned i;
4443 get_constraint_for (valist, &lhsc);
4444 do_deref (&lhsc);
4445 /* The va_list gets access to pointers in variadic
4446 arguments. Which we know in the case of IPA analysis
4447 and otherwise are just all nonlocal variables. */
e38811ce 4448 if (in_ipa_mode)
a4c9bc15 4449 {
628169e0 4450 fi = lookup_vi_for_tree (fn->decl);
e38811ce
RG
4451 rhs = get_function_part_constraint (fi, ~0);
4452 rhs.type = ADDRESSOF;
a4c9bc15 4453 }
df2f6100
RG
4454 else
4455 {
4456 rhs.var = nonlocal_id;
4457 rhs.type = ADDRESSOF;
4458 rhs.offset = 0;
4459 }
9771b263 4460 FOR_EACH_VEC_ELT (lhsc, i, lhsp)
df2f6100 4461 process_constraint (new_constraint (*lhsp, rhs));
df2f6100
RG
4462 /* va_list is clobbered. */
4463 make_constraint_to (get_call_clobber_vi (t)->id, valist);
4464 return true;
e38811ce
RG
4465 }
4466 /* va_end doesn't have any effect that matters. */
4467 case BUILT_IN_VA_END:
4468 return true;
4469 /* Alternate return. Simply give up for now. */
4470 case BUILT_IN_RETURN:
4ee00913 4471 {
e38811ce
RG
4472 fi = NULL;
4473 if (!in_ipa_mode
628169e0 4474 || !(fi = get_vi_for_tree (fn->decl)))
e38811ce
RG
4475 make_constraint_from (get_varinfo (escaped_id), anything_id);
4476 else if (in_ipa_mode
4477 && fi != NULL)
b7091901 4478 {
e38811ce
RG
4479 struct constraint_expr lhs, rhs;
4480 lhs = get_function_part_constraint (fi, fi_result);
4481 rhs.var = anything_id;
4482 rhs.offset = 0;
4483 rhs.type = SCALAR;
4484 process_constraint (new_constraint (lhs, rhs));
b7091901 4485 }
e38811ce
RG
4486 return true;
4487 }
4488 /* printf-style functions may have hooks to set pointers to
4489 point to somewhere into the generated string. Leave them
c0d18c6c 4490 for a later exercise... */
e38811ce
RG
4491 default:
4492 /* Fallthru to general call handling. */;
4493 }
4494
4495 return false;
4496}
4497
4498/* Create constraints for the call T. */
4499
4500static void
538dd0b7 4501find_func_aliases_for_call (struct function *fn, gcall *t)
e38811ce
RG
4502{
4503 tree fndecl = gimple_call_fndecl (t);
e38811ce
RG
4504 varinfo_t fi;
4505
4506 if (fndecl != NULL_TREE
4507 && DECL_BUILT_IN (fndecl)
628169e0 4508 && find_func_aliases_for_builtin_call (fn, t))
e38811ce
RG
4509 return;
4510
5c04e9f4 4511 fi = get_fi_for_callee (t);
e38811ce 4512 if (!in_ipa_mode
5c04e9f4 4513 || (fndecl && !fi->is_fn_info))
e38811ce 4514 {
a0791dcc 4515 auto_vec<ce_s, 16> rhsc;
e38811ce
RG
4516 int flags = gimple_call_flags (t);
4517
4518 /* Const functions can return their arguments and addresses
4519 of global memory but not of escaped memory. */
4520 if (flags & (ECF_CONST|ECF_NOVOPS))
4521 {
cb89b4b0 4522 if (gimple_call_lhs (t))
e38811ce 4523 handle_const_call (t, &rhsc);
4ee00913 4524 }
e38811ce
RG
4525 /* Pure functions can return addresses in and of memory
4526 reachable from their arguments, but they are not an escape
4527 point for reachable memory of their arguments. */
4528 else if (flags & (ECF_PURE|ECF_LOOPING_CONST_OR_PURE))
4529 handle_pure_call (t, &rhsc);
4ee00913 4530 else
e38811ce
RG
4531 handle_rhs_call (t, &rhsc);
4532 if (gimple_call_lhs (t))
c8f49949
RB
4533 handle_lhs_call (t, gimple_call_lhs (t),
4534 gimple_call_return_flags (t), rhsc, fndecl);
e38811ce
RG
4535 }
4536 else
4537 {
a0791dcc 4538 auto_vec<ce_s, 2> rhsc;
e38811ce
RG
4539 tree lhsop;
4540 unsigned j;
6e7e772d 4541
e38811ce
RG
4542 /* Assign all the passed arguments to the appropriate incoming
4543 parameters of the function. */
4544 for (j = 0; j < gimple_call_num_args (t); j++)
4545 {
4546 struct constraint_expr lhs ;
4547 struct constraint_expr *rhsp;
4548 tree arg = gimple_call_arg (t, j);
7b765bed 4549
e38811ce
RG
4550 get_constraint_for_rhs (arg, &rhsc);
4551 lhs = get_function_part_constraint (fi, fi_parm_base + j);
9771b263 4552 while (rhsc.length () != 0)
4ee00913 4553 {
9771b263 4554 rhsp = &rhsc.last ();
e38811ce 4555 process_constraint (new_constraint (lhs, *rhsp));
9771b263 4556 rhsc.pop ();
4ee00913 4557 }
e38811ce
RG
4558 }
4559
4560 /* If we are returning a value, assign it to the result. */
4561 lhsop = gimple_call_lhs (t);
4562 if (lhsop)
4563 {
a0791dcc 4564 auto_vec<ce_s, 2> lhsc;
e38811ce
RG
4565 struct constraint_expr rhs;
4566 struct constraint_expr *lhsp;
25a6a873 4567
e38811ce
RG
4568 get_constraint_for (lhsop, &lhsc);
4569 rhs = get_function_part_constraint (fi, fi_result);
4570 if (fndecl
25a6a873
RG
4571 && DECL_RESULT (fndecl)
4572 && DECL_BY_REFERENCE (DECL_RESULT (fndecl)))
4573 {
a0791dcc
RB
4574 auto_vec<ce_s, 2> tem;
4575 tem.quick_push (rhs);
e38811ce 4576 do_deref (&tem);
a0791dcc 4577 gcc_checking_assert (tem.length () == 1);
9771b263 4578 rhs = tem[0];
25a6a873 4579 }
9771b263 4580 FOR_EACH_VEC_ELT (lhsc, j, lhsp)
5c04e9f4 4581 process_constraint (new_constraint (*lhsp, rhs));
e38811ce 4582 }
25a6a873 4583
e38811ce
RG
4584 /* If we pass the result decl by reference, honor that. */
4585 if (lhsop
4586 && fndecl
4587 && DECL_RESULT (fndecl)
4588 && DECL_BY_REFERENCE (DECL_RESULT (fndecl)))
4589 {
4590 struct constraint_expr lhs;
4591 struct constraint_expr *rhsp;
4592
4593 get_constraint_for_address_of (lhsop, &rhsc);
4594 lhs = get_function_part_constraint (fi, fi_result);
9771b263 4595 FOR_EACH_VEC_ELT (rhsc, j, rhsp)
5c04e9f4 4596 process_constraint (new_constraint (lhs, *rhsp));
a0791dcc 4597 rhsc.truncate (0);
e38811ce 4598 }
25a6a873 4599
e38811ce
RG
4600 /* If we use a static chain, pass it along. */
4601 if (gimple_call_chain (t))
4602 {
4603 struct constraint_expr lhs;
4604 struct constraint_expr *rhsp;
4605
4606 get_constraint_for (gimple_call_chain (t), &rhsc);
4607 lhs = get_function_part_constraint (fi, fi_static_chain);
9771b263 4608 FOR_EACH_VEC_ELT (rhsc, j, rhsp)
5c04e9f4 4609 process_constraint (new_constraint (lhs, *rhsp));
e38811ce
RG
4610 }
4611 }
4612}
4613
4614/* Walk statement T setting up aliasing constraints according to the
4615 references found in T. This function is the main part of the
4616 constraint builder. AI points to auxiliary alias information used
4617 when building alias sets and computing alias grouping heuristics. */
4618
4619static void
355fe088 4620find_func_aliases (struct function *fn, gimple *origt)
e38811ce 4621{
355fe088 4622 gimple *t = origt;
a0791dcc
RB
4623 auto_vec<ce_s, 16> lhsc;
4624 auto_vec<ce_s, 16> rhsc;
e38811ce
RG
4625 struct constraint_expr *c;
4626 varinfo_t fi;
4627
4628 /* Now build constraints expressions. */
4629 if (gimple_code (t) == GIMPLE_PHI)
4630 {
4631 size_t i;
4632 unsigned int j;
4633
4634 /* For a phi node, assign all the arguments to
4635 the result. */
4636 get_constraint_for (gimple_phi_result (t), &lhsc);
4637 for (i = 0; i < gimple_phi_num_args (t); i++)
4638 {
4639 tree strippedrhs = PHI_ARG_DEF (t, i);
4640
4641 STRIP_NOPS (strippedrhs);
4642 get_constraint_for_rhs (gimple_phi_arg_def (t, i), &rhsc);
4643
9771b263 4644 FOR_EACH_VEC_ELT (lhsc, j, c)
e38811ce
RG
4645 {
4646 struct constraint_expr *c2;
9771b263 4647 while (rhsc.length () > 0)
e38811ce 4648 {
9771b263 4649 c2 = &rhsc.last ();
e38811ce 4650 process_constraint (new_constraint (*c, *c2));
9771b263 4651 rhsc.pop ();
e38811ce 4652 }
25a6a873 4653 }
c58936b6 4654 }
e8ca4159 4655 }
e38811ce
RG
4656 /* In IPA mode, we need to generate constraints to pass call
4657 arguments through their calls. There are two cases,
4658 either a GIMPLE_CALL returning a value, or just a plain
4659 GIMPLE_CALL when we are not.
4660
4661 In non-ipa mode, we need to generate constraints for each
4662 pointer passed by address. */
4663 else if (is_gimple_call (t))
538dd0b7 4664 find_func_aliases_for_call (fn, as_a <gcall *> (t));
e38811ce 4665
e5bae89b
RG
4666 /* Otherwise, just a regular assignment statement. Only care about
4667 operations with pointer result, others are dealt with as escape
4668 points if they have pointer operands. */
0f8d6231 4669 else if (is_gimple_assign (t))
e8ca4159 4670 {
726a989a
RB
4671 /* Otherwise, just a regular assignment statement. */
4672 tree lhsop = gimple_assign_lhs (t);
4673 tree rhsop = (gimple_num_ops (t) == 2) ? gimple_assign_rhs1 (t) : NULL;
e8ca4159 4674
47598145
MM
4675 if (rhsop && TREE_CLOBBER_P (rhsop))
4676 /* Ignore clobbers, they don't actually store anything into
4677 the LHS. */
4678 ;
4679 else if (rhsop && AGGREGATE_TYPE_P (TREE_TYPE (lhsop)))
e5bae89b 4680 do_structure_copy (lhsop, rhsop);
e8ca4159
DN
4681 else
4682 {
194313e2
RG
4683 enum tree_code code = gimple_assign_rhs_code (t);
4684
e5bae89b 4685 get_constraint_for (lhsop, &lhsc);
726a989a 4686
7b909872 4687 if (code == POINTER_PLUS_EXPR)
726a989a
RB
4688 get_constraint_for_ptr_offset (gimple_assign_rhs1 (t),
4689 gimple_assign_rhs2 (t), &rhsc);
194313e2 4690 else if (code == BIT_AND_EXPR
fca821b5
RG
4691 && TREE_CODE (gimple_assign_rhs2 (t)) == INTEGER_CST)
4692 {
4693 /* Aligning a pointer via a BIT_AND_EXPR is offsetting
4694 the pointer. Handle it by offsetting it by UNKNOWN. */
4695 get_constraint_for_ptr_offset (gimple_assign_rhs1 (t),
4696 NULL_TREE, &rhsc);
4697 }
194313e2 4698 else if ((CONVERT_EXPR_CODE_P (code)
1961418e
RG
4699 && !(POINTER_TYPE_P (gimple_expr_type (t))
4700 && !POINTER_TYPE_P (TREE_TYPE (rhsop))))
4701 || gimple_assign_single_p (t))
ed6c4831 4702 get_constraint_for_rhs (rhsop, &rhsc);
6cadda8b
RB
4703 else if (code == COND_EXPR)
4704 {
4705 /* The result is a merge of both COND_EXPR arms. */
a0791dcc 4706 auto_vec<ce_s, 2> tmp;
6cadda8b
RB
4707 struct constraint_expr *rhsp;
4708 unsigned i;
4709 get_constraint_for_rhs (gimple_assign_rhs2 (t), &rhsc);
4710 get_constraint_for_rhs (gimple_assign_rhs3 (t), &tmp);
9771b263
DN
4711 FOR_EACH_VEC_ELT (tmp, i, rhsp)
4712 rhsc.safe_push (*rhsp);
6cadda8b 4713 }
194313e2
RG
4714 else if (truth_value_p (code))
4715 /* Truth value results are not pointer (parts). Or at least
026c3cfd 4716 very unreasonable obfuscation of a part. */
194313e2 4717 ;
726a989a
RB
4718 else
4719 {
0f8d6231 4720 /* All other operations are merges. */
a0791dcc 4721 auto_vec<ce_s, 4> tmp;
0f8d6231
RG
4722 struct constraint_expr *rhsp;
4723 unsigned i, j;
4724 get_constraint_for_rhs (gimple_assign_rhs1 (t), &rhsc);
4725 for (i = 2; i < gimple_num_ops (t); ++i)
4726 {
4727 get_constraint_for_rhs (gimple_op (t, i), &tmp);
9771b263
DN
4728 FOR_EACH_VEC_ELT (tmp, j, rhsp)
4729 rhsc.safe_push (*rhsp);
4730 tmp.truncate (0);
0f8d6231 4731 }
726a989a 4732 }
779704e7 4733 process_all_all_constraints (lhsc, rhsc);
e8ca4159 4734 }
de70bb20
RG
4735 /* If there is a store to a global variable the rhs escapes. */
4736 if ((lhsop = get_base_address (lhsop)) != NULL_TREE
4737 && DECL_P (lhsop)
25a6a873
RG
4738 && is_global_var (lhsop)
4739 && (!in_ipa_mode
4740 || DECL_EXTERNAL (lhsop) || TREE_PUBLIC (lhsop)))
de70bb20 4741 make_escape_constraint (rhsop);
910fdc79 4742 }
14c41b9b
RG
4743 /* Handle escapes through return. */
4744 else if (gimple_code (t) == GIMPLE_RETURN
538dd0b7 4745 && gimple_return_retval (as_a <greturn *> (t)) != NULL_TREE)
14c41b9b 4746 {
538dd0b7 4747 greturn *return_stmt = as_a <greturn *> (t);
25a6a873
RG
4748 fi = NULL;
4749 if (!in_ipa_mode
628169e0 4750 || !(fi = get_vi_for_tree (fn->decl)))
538dd0b7 4751 make_escape_constraint (gimple_return_retval (return_stmt));
25a6a873
RG
4752 else if (in_ipa_mode
4753 && fi != NULL)
4754 {
4755 struct constraint_expr lhs ;
4756 struct constraint_expr *rhsp;
4757 unsigned i;
4758
4759 lhs = get_function_part_constraint (fi, fi_result);
538dd0b7 4760 get_constraint_for_rhs (gimple_return_retval (return_stmt), &rhsc);
9771b263 4761 FOR_EACH_VEC_ELT (rhsc, i, rhsp)
25a6a873
RG
4762 process_constraint (new_constraint (lhs, *rhsp));
4763 }
14c41b9b 4764 }
2e407842 4765 /* Handle asms conservatively by adding escape constraints to everything. */
538dd0b7 4766 else if (gasm *asm_stmt = dyn_cast <gasm *> (t))
b7091901 4767 {
5006671f
RG
4768 unsigned i, noutputs;
4769 const char **oconstraints;
4770 const char *constraint;
4771 bool allows_mem, allows_reg, is_inout;
4772
538dd0b7 4773 noutputs = gimple_asm_noutputs (asm_stmt);
5006671f
RG
4774 oconstraints = XALLOCAVEC (const char *, noutputs);
4775
4776 for (i = 0; i < noutputs; ++i)
b7091901 4777 {
538dd0b7 4778 tree link = gimple_asm_output_op (asm_stmt, i);
5006671f
RG
4779 tree op = TREE_VALUE (link);
4780
4781 constraint = TREE_STRING_POINTER (TREE_VALUE (TREE_PURPOSE (link)));
4782 oconstraints[i] = constraint;
4783 parse_output_constraint (&constraint, i, 0, 0, &allows_mem,
4784 &allows_reg, &is_inout);
4785
4786 /* A memory constraint makes the address of the operand escape. */
4787 if (!allows_reg && allows_mem)
4788 make_escape_constraint (build_fold_addr_expr (op));
4789
4790 /* The asm may read global memory, so outputs may point to
4791 any global memory. */
0f8d6231 4792 if (op)
5006671f 4793 {
a0791dcc 4794 auto_vec<ce_s, 2> lhsc;
5006671f
RG
4795 struct constraint_expr rhsc, *lhsp;
4796 unsigned j;
4797 get_constraint_for (op, &lhsc);
4798 rhsc.var = nonlocal_id;
4799 rhsc.offset = 0;
4800 rhsc.type = SCALAR;
9771b263 4801 FOR_EACH_VEC_ELT (lhsc, j, lhsp)
5006671f 4802 process_constraint (new_constraint (*lhsp, rhsc));
5006671f 4803 }
b7091901 4804 }
538dd0b7 4805 for (i = 0; i < gimple_asm_ninputs (asm_stmt); ++i)
b7091901 4806 {
538dd0b7 4807 tree link = gimple_asm_input_op (asm_stmt, i);
5006671f
RG
4808 tree op = TREE_VALUE (link);
4809
4810 constraint = TREE_STRING_POINTER (TREE_VALUE (TREE_PURPOSE (link)));
4811
4812 parse_input_constraint (&constraint, 0, 0, noutputs, 0, oconstraints,
4813 &allows_mem, &allows_reg);
4814
4815 /* A memory constraint makes the address of the operand escape. */
4816 if (!allows_reg && allows_mem)
4817 make_escape_constraint (build_fold_addr_expr (op));
4818 /* Strictly we'd only need the constraint to ESCAPED if
3e8542ca
RG
4819 the asm clobbers memory, otherwise using something
4820 along the lines of per-call clobbers/uses would be enough. */
0f8d6231 4821 else if (op)
b7091901
RG
4822 make_escape_constraint (op);
4823 }
4824 }
910fdc79
DB
4825}
4826
4827
25a6a873
RG
4828/* Create a constraint adding to the clobber set of FI the memory
4829 pointed to by PTR. */
4830
4831static void
4832process_ipa_clobber (varinfo_t fi, tree ptr)
4833{
6e1aa848 4834 vec<ce_s> ptrc = vNULL;
25a6a873
RG
4835 struct constraint_expr *c, lhs;
4836 unsigned i;
ed6c4831 4837 get_constraint_for_rhs (ptr, &ptrc);
25a6a873 4838 lhs = get_function_part_constraint (fi, fi_clobbers);
9771b263 4839 FOR_EACH_VEC_ELT (ptrc, i, c)
25a6a873 4840 process_constraint (new_constraint (lhs, *c));
9771b263 4841 ptrc.release ();
25a6a873
RG
4842}
4843
4844/* Walk statement T setting up clobber and use constraints according to the
4845 references found in T. This function is a main part of the
4846 IPA constraint builder. */
4847
4848static void
355fe088 4849find_func_clobbers (struct function *fn, gimple *origt)
25a6a873 4850{
355fe088 4851 gimple *t = origt;
a0791dcc
RB
4852 auto_vec<ce_s, 16> lhsc;
4853 auto_vec<ce_s, 16> rhsc;
25a6a873
RG
4854 varinfo_t fi;
4855
4856 /* Add constraints for clobbered/used in IPA mode.
4857 We are not interested in what automatic variables are clobbered
4858 or used as we only use the information in the caller to which
4859 they do not escape. */
4860 gcc_assert (in_ipa_mode);
4861
4862 /* If the stmt refers to memory in any way it better had a VUSE. */
4863 if (gimple_vuse (t) == NULL_TREE)
4864 return;
4865
4866 /* We'd better have function information for the current function. */
628169e0 4867 fi = lookup_vi_for_tree (fn->decl);
25a6a873
RG
4868 gcc_assert (fi != NULL);
4869
4870 /* Account for stores in assignments and calls. */
4871 if (gimple_vdef (t) != NULL_TREE
4872 && gimple_has_lhs (t))
4873 {
4874 tree lhs = gimple_get_lhs (t);
4875 tree tem = lhs;
4876 while (handled_component_p (tem))
4877 tem = TREE_OPERAND (tem, 0);
4878 if ((DECL_P (tem)
628169e0 4879 && !auto_var_in_fn_p (tem, fn->decl))
70f34814
RG
4880 || INDIRECT_REF_P (tem)
4881 || (TREE_CODE (tem) == MEM_REF
4882 && !(TREE_CODE (TREE_OPERAND (tem, 0)) == ADDR_EXPR
4883 && auto_var_in_fn_p
628169e0 4884 (TREE_OPERAND (TREE_OPERAND (tem, 0), 0), fn->decl))))
25a6a873
RG
4885 {
4886 struct constraint_expr lhsc, *rhsp;
4887 unsigned i;
4888 lhsc = get_function_part_constraint (fi, fi_clobbers);
4889 get_constraint_for_address_of (lhs, &rhsc);
9771b263 4890 FOR_EACH_VEC_ELT (rhsc, i, rhsp)
25a6a873 4891 process_constraint (new_constraint (lhsc, *rhsp));
a0791dcc 4892 rhsc.truncate (0);
25a6a873
RG
4893 }
4894 }
4895
4896 /* Account for uses in assigments and returns. */
4897 if (gimple_assign_single_p (t)
4898 || (gimple_code (t) == GIMPLE_RETURN
538dd0b7 4899 && gimple_return_retval (as_a <greturn *> (t)) != NULL_TREE))
25a6a873
RG
4900 {
4901 tree rhs = (gimple_assign_single_p (t)
538dd0b7
DM
4902 ? gimple_assign_rhs1 (t)
4903 : gimple_return_retval (as_a <greturn *> (t)));
25a6a873
RG
4904 tree tem = rhs;
4905 while (handled_component_p (tem))
4906 tem = TREE_OPERAND (tem, 0);
4907 if ((DECL_P (tem)
628169e0 4908 && !auto_var_in_fn_p (tem, fn->decl))
70f34814
RG
4909 || INDIRECT_REF_P (tem)
4910 || (TREE_CODE (tem) == MEM_REF
4911 && !(TREE_CODE (TREE_OPERAND (tem, 0)) == ADDR_EXPR
4912 && auto_var_in_fn_p
628169e0 4913 (TREE_OPERAND (TREE_OPERAND (tem, 0), 0), fn->decl))))
25a6a873
RG
4914 {
4915 struct constraint_expr lhs, *rhsp;
4916 unsigned i;
4917 lhs = get_function_part_constraint (fi, fi_uses);
4918 get_constraint_for_address_of (rhs, &rhsc);
9771b263 4919 FOR_EACH_VEC_ELT (rhsc, i, rhsp)
25a6a873 4920 process_constraint (new_constraint (lhs, *rhsp));
a0791dcc 4921 rhsc.truncate (0);
25a6a873
RG
4922 }
4923 }
4924
538dd0b7 4925 if (gcall *call_stmt = dyn_cast <gcall *> (t))
25a6a873
RG
4926 {
4927 varinfo_t cfi = NULL;
4928 tree decl = gimple_call_fndecl (t);
4929 struct constraint_expr lhs, rhs;
4930 unsigned i, j;
4931
4932 /* For builtins we do not have separate function info. For those
4933 we do not generate escapes for we have to generate clobbers/uses. */
3626621a 4934 if (gimple_call_builtin_p (t, BUILT_IN_NORMAL))
25a6a873
RG
4935 switch (DECL_FUNCTION_CODE (decl))
4936 {
4937 /* The following functions use and clobber memory pointed to
4938 by their arguments. */
4939 case BUILT_IN_STRCPY:
4940 case BUILT_IN_STRNCPY:
4941 case BUILT_IN_BCOPY:
4942 case BUILT_IN_MEMCPY:
4943 case BUILT_IN_MEMMOVE:
4944 case BUILT_IN_MEMPCPY:
4945 case BUILT_IN_STPCPY:
4946 case BUILT_IN_STPNCPY:
4947 case BUILT_IN_STRCAT:
4948 case BUILT_IN_STRNCAT:
36dc1a88
JJ
4949 case BUILT_IN_STRCPY_CHK:
4950 case BUILT_IN_STRNCPY_CHK:
4951 case BUILT_IN_MEMCPY_CHK:
4952 case BUILT_IN_MEMMOVE_CHK:
4953 case BUILT_IN_MEMPCPY_CHK:
4954 case BUILT_IN_STPCPY_CHK:
f3fc9b80 4955 case BUILT_IN_STPNCPY_CHK:
36dc1a88
JJ
4956 case BUILT_IN_STRCAT_CHK:
4957 case BUILT_IN_STRNCAT_CHK:
25a6a873
RG
4958 {
4959 tree dest = gimple_call_arg (t, (DECL_FUNCTION_CODE (decl)
4960 == BUILT_IN_BCOPY ? 1 : 0));
4961 tree src = gimple_call_arg (t, (DECL_FUNCTION_CODE (decl)
4962 == BUILT_IN_BCOPY ? 0 : 1));
4963 unsigned i;
4964 struct constraint_expr *rhsp, *lhsp;
4965 get_constraint_for_ptr_offset (dest, NULL_TREE, &lhsc);
4966 lhs = get_function_part_constraint (fi, fi_clobbers);
9771b263 4967 FOR_EACH_VEC_ELT (lhsc, i, lhsp)
25a6a873 4968 process_constraint (new_constraint (lhs, *lhsp));
25a6a873
RG
4969 get_constraint_for_ptr_offset (src, NULL_TREE, &rhsc);
4970 lhs = get_function_part_constraint (fi, fi_uses);
9771b263 4971 FOR_EACH_VEC_ELT (rhsc, i, rhsp)
25a6a873 4972 process_constraint (new_constraint (lhs, *rhsp));
25a6a873
RG
4973 return;
4974 }
4975 /* The following function clobbers memory pointed to by
4976 its argument. */
4977 case BUILT_IN_MEMSET:
36dc1a88 4978 case BUILT_IN_MEMSET_CHK:
32cab212 4979 case BUILT_IN_POSIX_MEMALIGN:
25a6a873
RG
4980 {
4981 tree dest = gimple_call_arg (t, 0);
4982 unsigned i;
4983 ce_s *lhsp;
4984 get_constraint_for_ptr_offset (dest, NULL_TREE, &lhsc);
4985 lhs = get_function_part_constraint (fi, fi_clobbers);
9771b263 4986 FOR_EACH_VEC_ELT (lhsc, i, lhsp)
25a6a873 4987 process_constraint (new_constraint (lhs, *lhsp));
25a6a873
RG
4988 return;
4989 }
4990 /* The following functions clobber their second and third
4991 arguments. */
4992 case BUILT_IN_SINCOS:
4993 case BUILT_IN_SINCOSF:
4994 case BUILT_IN_SINCOSL:
4995 {
4996 process_ipa_clobber (fi, gimple_call_arg (t, 1));
4997 process_ipa_clobber (fi, gimple_call_arg (t, 2));
4998 return;
4999 }
5000 /* The following functions clobber their second argument. */
5001 case BUILT_IN_FREXP:
5002 case BUILT_IN_FREXPF:
5003 case BUILT_IN_FREXPL:
5004 case BUILT_IN_LGAMMA_R:
5005 case BUILT_IN_LGAMMAF_R:
5006 case BUILT_IN_LGAMMAL_R:
5007 case BUILT_IN_GAMMA_R:
5008 case BUILT_IN_GAMMAF_R:
5009 case BUILT_IN_GAMMAL_R:
5010 case BUILT_IN_MODF:
5011 case BUILT_IN_MODFF:
5012 case BUILT_IN_MODFL:
5013 {
5014 process_ipa_clobber (fi, gimple_call_arg (t, 1));
5015 return;
5016 }
5017 /* The following functions clobber their third argument. */
5018 case BUILT_IN_REMQUO:
5019 case BUILT_IN_REMQUOF:
5020 case BUILT_IN_REMQUOL:
5021 {
5022 process_ipa_clobber (fi, gimple_call_arg (t, 2));
5023 return;
5024 }
5025 /* The following functions neither read nor clobber memory. */
45d439ac 5026 case BUILT_IN_ASSUME_ALIGNED:
25a6a873
RG
5027 case BUILT_IN_FREE:
5028 return;
5029 /* Trampolines are of no interest to us. */
5030 case BUILT_IN_INIT_TRAMPOLINE:
5031 case BUILT_IN_ADJUST_TRAMPOLINE:
5032 return;
5033 case BUILT_IN_VA_START:
5034 case BUILT_IN_VA_END:
5035 return;
5036 /* printf-style functions may have hooks to set pointers to
5037 point to somewhere into the generated string. Leave them
c0d18c6c 5038 for a later exercise... */
25a6a873
RG
5039 default:
5040 /* Fallthru to general call handling. */;
5041 }
5042
5043 /* Parameters passed by value are used. */
5044 lhs = get_function_part_constraint (fi, fi_uses);
5045 for (i = 0; i < gimple_call_num_args (t); i++)
5046 {
5047 struct constraint_expr *rhsp;
5048 tree arg = gimple_call_arg (t, i);
5049
5050 if (TREE_CODE (arg) == SSA_NAME
5051 || is_gimple_min_invariant (arg))
5052 continue;
5053
5054 get_constraint_for_address_of (arg, &rhsc);
9771b263 5055 FOR_EACH_VEC_ELT (rhsc, j, rhsp)
25a6a873 5056 process_constraint (new_constraint (lhs, *rhsp));
3f734f66 5057 rhsc.truncate (0);
25a6a873
RG
5058 }
5059
5060 /* Build constraints for propagating clobbers/uses along the
5061 callgraph edges. */
538dd0b7 5062 cfi = get_fi_for_callee (call_stmt);
25a6a873
RG
5063 if (cfi->id == anything_id)
5064 {
5065 if (gimple_vdef (t))
5066 make_constraint_from (first_vi_for_offset (fi, fi_clobbers),
5067 anything_id);
5068 make_constraint_from (first_vi_for_offset (fi, fi_uses),
5069 anything_id);
5070 return;
5071 }
5072
5073 /* For callees without function info (that's external functions),
5074 ESCAPED is clobbered and used. */
5075 if (gimple_call_fndecl (t)
5076 && !cfi->is_fn_info)
5077 {
5078 varinfo_t vi;
5079
5080 if (gimple_vdef (t))
5081 make_copy_constraint (first_vi_for_offset (fi, fi_clobbers),
5082 escaped_id);
5083 make_copy_constraint (first_vi_for_offset (fi, fi_uses), escaped_id);
5084
5085 /* Also honor the call statement use/clobber info. */
538dd0b7 5086 if ((vi = lookup_call_clobber_vi (call_stmt)) != NULL)
25a6a873
RG
5087 make_copy_constraint (first_vi_for_offset (fi, fi_clobbers),
5088 vi->id);
538dd0b7 5089 if ((vi = lookup_call_use_vi (call_stmt)) != NULL)
25a6a873
RG
5090 make_copy_constraint (first_vi_for_offset (fi, fi_uses),
5091 vi->id);
5092 return;
5093 }
5094
5095 /* Otherwise the caller clobbers and uses what the callee does.
5096 ??? This should use a new complex constraint that filters
5097 local variables of the callee. */
5098 if (gimple_vdef (t))
5099 {
5100 lhs = get_function_part_constraint (fi, fi_clobbers);
5101 rhs = get_function_part_constraint (cfi, fi_clobbers);
5102 process_constraint (new_constraint (lhs, rhs));
5103 }
5104 lhs = get_function_part_constraint (fi, fi_uses);
5105 rhs = get_function_part_constraint (cfi, fi_uses);
5106 process_constraint (new_constraint (lhs, rhs));
5107 }
5108 else if (gimple_code (t) == GIMPLE_ASM)
5109 {
5110 /* ??? Ick. We can do better. */
5111 if (gimple_vdef (t))
5112 make_constraint_from (first_vi_for_offset (fi, fi_clobbers),
5113 anything_id);
5114 make_constraint_from (first_vi_for_offset (fi, fi_uses),
5115 anything_id);
5116 }
25a6a873
RG
5117}
5118
5119
910fdc79 5120/* Find the first varinfo in the same variable as START that overlaps with
5006671f 5121 OFFSET. Return NULL if we can't find one. */
910fdc79 5122
c58936b6 5123static varinfo_t
910fdc79
DB
5124first_vi_for_offset (varinfo_t start, unsigned HOST_WIDE_INT offset)
5125{
5006671f
RG
5126 /* If the offset is outside of the variable, bail out. */
5127 if (offset >= start->fullsize)
5128 return NULL;
5129
5130 /* If we cannot reach offset from start, lookup the first field
5131 and start from there. */
5132 if (start->offset > offset)
d6d305fe 5133 start = get_varinfo (start->head);
5006671f
RG
5134
5135 while (start)
910fdc79
DB
5136 {
5137 /* We may not find a variable in the field list with the actual
026c3cfd 5138 offset when we have glommed a structure to a variable.
910fdc79
DB
5139 In that case, however, offset should still be within the size
5140 of the variable. */
5006671f 5141 if (offset >= start->offset
de925a03 5142 && (offset - start->offset) < start->size)
5006671f
RG
5143 return start;
5144
d6d305fe 5145 start = vi_next (start);
910fdc79 5146 }
5006671f 5147
8971094d 5148 return NULL;
910fdc79
DB
5149}
5150
5006671f
RG
5151/* Find the first varinfo in the same variable as START that overlaps with
5152 OFFSET. If there is no such varinfo the varinfo directly preceding
5153 OFFSET is returned. */
5154
5155static varinfo_t
5156first_or_preceding_vi_for_offset (varinfo_t start,
5157 unsigned HOST_WIDE_INT offset)
5158{
5159 /* If we cannot reach offset from start, lookup the first field
5160 and start from there. */
5161 if (start->offset > offset)
d6d305fe 5162 start = get_varinfo (start->head);
5006671f
RG
5163
5164 /* We may not find a variable in the field list with the actual
026c3cfd 5165 offset when we have glommed a structure to a variable.
5006671f
RG
5166 In that case, however, offset should still be within the size
5167 of the variable.
5168 If we got beyond the offset we look for return the field
5169 directly preceding offset which may be the last field. */
5170 while (start->next
5171 && offset >= start->offset
de925a03 5172 && !((offset - start->offset) < start->size))
d6d305fe 5173 start = vi_next (start);
5006671f
RG
5174
5175 return start;
5176}
5177
910fdc79 5178
31de5b77
RG
5179/* This structure is used during pushing fields onto the fieldstack
5180 to track the offset of the field, since bitpos_of_field gives it
5181 relative to its immediate containing type, and we want it relative
5182 to the ultimate containing object. */
5183
5184struct fieldoff
5185{
ee7d4b57
RG
5186 /* Offset from the base of the base containing object to this field. */
5187 HOST_WIDE_INT offset;
31de5b77
RG
5188
5189 /* Size, in bits, of the field. */
ee7d4b57 5190 unsigned HOST_WIDE_INT size;
31de5b77 5191
ee7d4b57 5192 unsigned has_unknown_size : 1;
31de5b77 5193
0f8d6231
RG
5194 unsigned must_have_pointers : 1;
5195
ee7d4b57 5196 unsigned may_have_pointers : 1;
74d27244
RG
5197
5198 unsigned only_restrict_pointers : 1;
31de5b77
RG
5199};
5200typedef struct fieldoff fieldoff_s;
5201
31de5b77 5202
910fdc79
DB
5203/* qsort comparison function for two fieldoff's PA and PB */
5204
c58936b6 5205static int
910fdc79
DB
5206fieldoff_compare (const void *pa, const void *pb)
5207{
5208 const fieldoff_s *foa = (const fieldoff_s *)pa;
5209 const fieldoff_s *fob = (const fieldoff_s *)pb;
185ab3b6 5210 unsigned HOST_WIDE_INT foasize, fobsize;
c58936b6 5211
185ab3b6
RG
5212 if (foa->offset < fob->offset)
5213 return -1;
5214 else if (foa->offset > fob->offset)
5215 return 1;
910fdc79 5216
ee7d4b57
RG
5217 foasize = foa->size;
5218 fobsize = fob->size;
185ab3b6 5219 if (foasize < fobsize)
ee7d4b57 5220 return -1;
185ab3b6
RG
5221 else if (foasize > fobsize)
5222 return 1;
5223 return 0;
910fdc79
DB
5224}
5225
5226/* Sort a fieldstack according to the field offset and sizes. */
31de5b77 5227static void
9771b263 5228sort_fieldstack (vec<fieldoff_s> fieldstack)
910fdc79 5229{
9771b263 5230 fieldstack.qsort (fieldoff_compare);
910fdc79
DB
5231}
5232
b4cf8c9d
RG
5233/* Return true if T is a type that can have subvars. */
5234
5235static inline bool
5236type_can_have_subvars (const_tree t)
5237{
5238 /* Aggregates without overlapping fields can have subvars. */
5239 return TREE_CODE (t) == RECORD_TYPE;
5240}
5241
31de5b77
RG
5242/* Return true if V is a tree that we can have subvars for.
5243 Normally, this is any aggregate type. Also complex
5244 types which are not gimple registers can have subvars. */
5245
5246static inline bool
5247var_can_have_subvars (const_tree v)
5248{
5249 /* Volatile variables should never have subvars. */
5250 if (TREE_THIS_VOLATILE (v))
5251 return false;
5252
5253 /* Non decls or memory tags can never have subvars. */
5006671f 5254 if (!DECL_P (v))
31de5b77
RG
5255 return false;
5256
b4cf8c9d 5257 return type_can_have_subvars (TREE_TYPE (v));
31de5b77
RG
5258}
5259
0f8d6231
RG
5260/* Return true if T is a type that does contain pointers. */
5261
5262static bool
5263type_must_have_pointers (tree type)
5264{
5265 if (POINTER_TYPE_P (type))
5266 return true;
5267
5268 if (TREE_CODE (type) == ARRAY_TYPE)
5269 return type_must_have_pointers (TREE_TYPE (type));
5270
5271 /* A function or method can have pointers as arguments, so track
5272 those separately. */
5273 if (TREE_CODE (type) == FUNCTION_TYPE
5274 || TREE_CODE (type) == METHOD_TYPE)
5275 return true;
5276
5277 return false;
5278}
5279
5280static bool
5281field_must_have_pointers (tree t)
5282{
5283 return type_must_have_pointers (TREE_TYPE (t));
5284}
5285
d7705551
DN
5286/* Given a TYPE, and a vector of field offsets FIELDSTACK, push all
5287 the fields of TYPE onto fieldstack, recording their offsets along
5288 the way.
5289
5290 OFFSET is used to keep track of the offset in this entire
5291 structure, rather than just the immediately containing structure.
18abb35e
RG
5292 Returns false if the caller is supposed to handle the field we
5293 recursed for. */
910fdc79 5294
18abb35e 5295static bool
9771b263 5296push_fields_onto_fieldstack (tree type, vec<fieldoff_s> *fieldstack,
0f8d6231 5297 HOST_WIDE_INT offset)
910fdc79
DB
5298{
5299 tree field;
18abb35e 5300 bool empty_p = true;
31de5b77
RG
5301
5302 if (TREE_CODE (type) != RECORD_TYPE)
18abb35e 5303 return false;
3fe2f42a
RG
5304
5305 /* If the vector of fields is growing too big, bail out early.
9771b263 5306 Callers check for vec::length <= MAX_FIELDS_FOR_FIELD_SENSITIVE, make
3fe2f42a 5307 sure this fails. */
9771b263 5308 if (fieldstack->length () > MAX_FIELDS_FOR_FIELD_SENSITIVE)
18abb35e 5309 return false;
c58936b6 5310
910ad8de 5311 for (field = TYPE_FIELDS (type); field; field = DECL_CHAIN (field))
31de5b77
RG
5312 if (TREE_CODE (field) == FIELD_DECL)
5313 {
5314 bool push = false;
ee7d4b57 5315 HOST_WIDE_INT foff = bitpos_of_field (field);
31de5b77 5316
ee7d4b57
RG
5317 if (!var_can_have_subvars (field)
5318 || TREE_CODE (TREE_TYPE (field)) == QUAL_UNION_TYPE
5319 || TREE_CODE (TREE_TYPE (field)) == UNION_TYPE)
31de5b77 5320 push = true;
18abb35e 5321 else if (!push_fields_onto_fieldstack
0f8d6231 5322 (TREE_TYPE (field), fieldstack, offset + foff)
31de5b77
RG
5323 && (DECL_SIZE (field)
5324 && !integer_zerop (DECL_SIZE (field))))
5325 /* Empty structures may have actual size, like in C++. So
5326 see if we didn't push any subfields and the size is
5327 nonzero, push the field onto the stack. */
5328 push = true;
5329
5330 if (push)
910fdc79 5331 {
ee7d4b57
RG
5332 fieldoff_s *pair = NULL;
5333 bool has_unknown_size = false;
0f8d6231 5334 bool must_have_pointers_p;
ee7d4b57 5335
9771b263
DN
5336 if (!fieldstack->is_empty ())
5337 pair = &fieldstack->last ();
ee7d4b57 5338
3fd3b156
RG
5339 /* If there isn't anything at offset zero, create sth. */
5340 if (!pair
5341 && offset + foff != 0)
5342 {
f32682ca 5343 fieldoff_s e = {0, offset + foff, false, false, false, false};
9771b263 5344 pair = fieldstack->safe_push (e);
3fd3b156
RG
5345 }
5346
ee7d4b57 5347 if (!DECL_SIZE (field)
cc269bb6 5348 || !tree_fits_uhwi_p (DECL_SIZE (field)))
ee7d4b57
RG
5349 has_unknown_size = true;
5350
5351 /* If adjacent fields do not contain pointers merge them. */
0f8d6231 5352 must_have_pointers_p = field_must_have_pointers (field);
ee7d4b57 5353 if (pair
ee7d4b57 5354 && !has_unknown_size
a81b065a 5355 && !must_have_pointers_p
0f8d6231
RG
5356 && !pair->must_have_pointers
5357 && !pair->has_unknown_size
5358 && pair->offset + (HOST_WIDE_INT)pair->size == offset + foff)
ee7d4b57 5359 {
eb1ce453 5360 pair->size += tree_to_uhwi (DECL_SIZE (field));
ee7d4b57
RG
5361 }
5362 else
5363 {
f32682ca
DN
5364 fieldoff_s e;
5365 e.offset = offset + foff;
5366 e.has_unknown_size = has_unknown_size;
ee7d4b57 5367 if (!has_unknown_size)
eb1ce453 5368 e.size = tree_to_uhwi (DECL_SIZE (field));
ee7d4b57 5369 else
f32682ca
DN
5370 e.size = -1;
5371 e.must_have_pointers = must_have_pointers_p;
5372 e.may_have_pointers = true;
5373 e.only_restrict_pointers
74d27244
RG
5374 = (!has_unknown_size
5375 && POINTER_TYPE_P (TREE_TYPE (field))
5376 && TYPE_RESTRICT (TREE_TYPE (field)));
9771b263 5377 fieldstack->safe_push (e);
ee7d4b57 5378 }
31de5b77 5379 }
18abb35e
RG
5380
5381 empty_p = false;
31de5b77 5382 }
910fdc79 5383
18abb35e 5384 return !empty_p;
910fdc79
DB
5385}
5386
5006671f
RG
5387/* Count the number of arguments DECL has, and set IS_VARARGS to true
5388 if it is a varargs function. */
5389
5390static unsigned int
5391count_num_arguments (tree decl, bool *is_varargs)
5392{
de925a03 5393 unsigned int num = 0;
5006671f
RG
5394 tree t;
5395
de925a03
RG
5396 /* Capture named arguments for K&R functions. They do not
5397 have a prototype and thus no TYPE_ARG_TYPES. */
910ad8de 5398 for (t = DECL_ARGUMENTS (decl); t; t = DECL_CHAIN (t))
de925a03 5399 ++num;
c58936b6 5400
de925a03
RG
5401 /* Check if the function has variadic arguments. */
5402 for (t = TYPE_ARG_TYPES (TREE_TYPE (decl)); t; t = TREE_CHAIN (t))
5403 if (TREE_VALUE (t) == void_type_node)
5404 break;
4ee00913
DB
5405 if (!t)
5406 *is_varargs = true;
de925a03
RG
5407
5408 return num;
4ee00913
DB
5409}
5410
5411/* Creation function node for DECL, using NAME, and return the index
5412 of the variable we've created for the function. */
5413
27c2cfa6 5414static varinfo_t
4ee00913
DB
5415create_function_info_for (tree decl, const char *name)
5416{
25a6a873
RG
5417 struct function *fn = DECL_STRUCT_FUNCTION (decl);
5418 varinfo_t vi, prev_vi;
c58936b6 5419 tree arg;
4ee00913
DB
5420 unsigned int i;
5421 bool is_varargs = false;
25a6a873 5422 unsigned int num_args = count_num_arguments (decl, &is_varargs);
4ee00913
DB
5423
5424 /* Create the variable info. */
5425
0bbf2ffa 5426 vi = new_var_info (decl, name);
4ee00913 5427 vi->offset = 0;
4ee00913 5428 vi->size = 1;
25a6a873
RG
5429 vi->fullsize = fi_parm_base + num_args;
5430 vi->is_fn_info = 1;
5431 vi->may_have_pointers = false;
5432 if (is_varargs)
5433 vi->fullsize = ~0;
3e5937d7 5434 insert_vi_for_tree (vi->decl, vi);
4ee00913 5435
25a6a873
RG
5436 prev_vi = vi;
5437
5438 /* Create a variable for things the function clobbers and one for
5439 things the function uses. */
4ee00913 5440 {
25a6a873
RG
5441 varinfo_t clobbervi, usevi;
5442 const char *newname;
5443 char *tempname;
5444
582f770b 5445 tempname = xasprintf ("%s.clobber", name);
25a6a873
RG
5446 newname = ggc_strdup (tempname);
5447 free (tempname);
5448
5449 clobbervi = new_var_info (NULL, newname);
5450 clobbervi->offset = fi_clobbers;
5451 clobbervi->size = 1;
5452 clobbervi->fullsize = vi->fullsize;
5453 clobbervi->is_full_var = true;
5454 clobbervi->is_global_var = false;
5455 gcc_assert (prev_vi->offset < clobbervi->offset);
d6d305fe 5456 prev_vi->next = clobbervi->id;
25a6a873 5457 prev_vi = clobbervi;
25a6a873 5458
582f770b 5459 tempname = xasprintf ("%s.use", name);
25a6a873
RG
5460 newname = ggc_strdup (tempname);
5461 free (tempname);
5462
5463 usevi = new_var_info (NULL, newname);
5464 usevi->offset = fi_uses;
5465 usevi->size = 1;
5466 usevi->fullsize = vi->fullsize;
5467 usevi->is_full_var = true;
5468 usevi->is_global_var = false;
5469 gcc_assert (prev_vi->offset < usevi->offset);
d6d305fe 5470 prev_vi->next = usevi->id;
25a6a873 5471 prev_vi = usevi;
4ee00913
DB
5472 }
5473
25a6a873
RG
5474 /* And one for the static chain. */
5475 if (fn->static_chain_decl != NULL_TREE)
5476 {
5477 varinfo_t chainvi;
5478 const char *newname;
5479 char *tempname;
5480
582f770b 5481 tempname = xasprintf ("%s.chain", name);
25a6a873
RG
5482 newname = ggc_strdup (tempname);
5483 free (tempname);
5484
5485 chainvi = new_var_info (fn->static_chain_decl, newname);
5486 chainvi->offset = fi_static_chain;
5487 chainvi->size = 1;
5488 chainvi->fullsize = vi->fullsize;
5489 chainvi->is_full_var = true;
5490 chainvi->is_global_var = false;
5491 gcc_assert (prev_vi->offset < chainvi->offset);
d6d305fe 5492 prev_vi->next = chainvi->id;
25a6a873 5493 prev_vi = chainvi;
25a6a873
RG
5494 insert_vi_for_tree (fn->static_chain_decl, chainvi);
5495 }
5496
5497 /* Create a variable for the return var. */
5498 if (DECL_RESULT (decl) != NULL
5499 || !VOID_TYPE_P (TREE_TYPE (TREE_TYPE (decl))))
5500 {
5501 varinfo_t resultvi;
5502 const char *newname;
5503 char *tempname;
5504 tree resultdecl = decl;
5505
5506 if (DECL_RESULT (decl))
5507 resultdecl = DECL_RESULT (decl);
5508
582f770b 5509 tempname = xasprintf ("%s.result", name);
25a6a873
RG
5510 newname = ggc_strdup (tempname);
5511 free (tempname);
5512
5513 resultvi = new_var_info (resultdecl, newname);
5514 resultvi->offset = fi_result;
5515 resultvi->size = 1;
5516 resultvi->fullsize = vi->fullsize;
5517 resultvi->is_full_var = true;
5518 if (DECL_RESULT (decl))
0f8d6231 5519 resultvi->may_have_pointers = true;
25a6a873 5520 gcc_assert (prev_vi->offset < resultvi->offset);
d6d305fe 5521 prev_vi->next = resultvi->id;
25a6a873 5522 prev_vi = resultvi;
25a6a873
RG
5523 if (DECL_RESULT (decl))
5524 insert_vi_for_tree (DECL_RESULT (decl), resultvi);
5525 }
4ee00913 5526
6416ae7f 5527 /* Set up variables for each argument. */
25a6a873
RG
5528 arg = DECL_ARGUMENTS (decl);
5529 for (i = 0; i < num_args; i++)
c58936b6 5530 {
4ee00913
DB
5531 varinfo_t argvi;
5532 const char *newname;
5533 char *tempname;
4ee00913
DB
5534 tree argdecl = decl;
5535
5536 if (arg)
5537 argdecl = arg;
c58936b6 5538
582f770b 5539 tempname = xasprintf ("%s.arg%d", name, i);
4ee00913
DB
5540 newname = ggc_strdup (tempname);
5541 free (tempname);
5542
0bbf2ffa 5543 argvi = new_var_info (argdecl, newname);
25a6a873 5544 argvi->offset = fi_parm_base + i;
4ee00913 5545 argvi->size = 1;
e5bae89b 5546 argvi->is_full_var = true;
4ee00913 5547 argvi->fullsize = vi->fullsize;
25a6a873 5548 if (arg)
0f8d6231 5549 argvi->may_have_pointers = true;
25a6a873 5550 gcc_assert (prev_vi->offset < argvi->offset);
d6d305fe 5551 prev_vi->next = argvi->id;
25a6a873 5552 prev_vi = argvi;
4ee00913
DB
5553 if (arg)
5554 {
3e5937d7 5555 insert_vi_for_tree (arg, argvi);
910ad8de 5556 arg = DECL_CHAIN (arg);
4ee00913
DB
5557 }
5558 }
4cf4d6a3 5559
25a6a873
RG
5560 /* Add one representative for all further args. */
5561 if (is_varargs)
4ee00913 5562 {
25a6a873 5563 varinfo_t argvi;
4ee00913
DB
5564 const char *newname;
5565 char *tempname;
25a6a873 5566 tree decl;
c58936b6 5567
582f770b 5568 tempname = xasprintf ("%s.varargs", name);
4ee00913
DB
5569 newname = ggc_strdup (tempname);
5570 free (tempname);
5571
25a6a873 5572 /* We need sth that can be pointed to for va_start. */
7d6e2521 5573 decl = build_fake_var_decl (ptr_type_node);
25a6a873
RG
5574
5575 argvi = new_var_info (decl, newname);
5576 argvi->offset = fi_parm_base + num_args;
5577 argvi->size = ~0;
5578 argvi->is_full_var = true;
5579 argvi->is_heap_var = true;
5580 argvi->fullsize = vi->fullsize;
5581 gcc_assert (prev_vi->offset < argvi->offset);
d6d305fe 5582 prev_vi->next = argvi->id;
25a6a873 5583 prev_vi = argvi;
4ee00913 5584 }
0bbf2ffa 5585
27c2cfa6 5586 return vi;
c58936b6 5587}
4ee00913 5588
6c11790d 5589
c58936b6 5590/* Return true if FIELDSTACK contains fields that overlap.
6c11790d
DB
5591 FIELDSTACK is assumed to be sorted by offset. */
5592
5593static bool
9771b263 5594check_for_overlaps (vec<fieldoff_s> fieldstack)
6c11790d
DB
5595{
5596 fieldoff_s *fo = NULL;
5597 unsigned int i;
30d2662c 5598 HOST_WIDE_INT lastoffset = -1;
6c11790d 5599
9771b263 5600 FOR_EACH_VEC_ELT (fieldstack, i, fo)
6c11790d
DB
5601 {
5602 if (fo->offset == lastoffset)
5603 return true;
5604 lastoffset = fo->offset;
5605 }
5606 return false;
5607}
21392f19 5608
910fdc79
DB
5609/* Create a varinfo structure for NAME and DECL, and add it to VARMAP.
5610 This will also create any varinfo structures necessary for fields
5611 of DECL. */
5612
18abb35e
RG
5613static varinfo_t
5614create_variable_info_for_1 (tree decl, const char *name)
910fdc79 5615{
18abb35e 5616 varinfo_t vi, newvi;
82d6e6fc
KG
5617 tree decl_type = TREE_TYPE (decl);
5618 tree declsize = DECL_P (decl) ? DECL_SIZE (decl) : TYPE_SIZE (decl_type);
ef062b13 5619 auto_vec<fieldoff_s> fieldstack;
18abb35e
RG
5620 fieldoff_s *fo;
5621 unsigned int i;
c58936b6 5622
4ee00913 5623 if (!declsize
cc269bb6 5624 || !tree_fits_uhwi_p (declsize))
910fdc79 5625 {
18abb35e
RG
5626 vi = new_var_info (decl, name);
5627 vi->offset = 0;
910fdc79 5628 vi->size = ~0;
18abb35e
RG
5629 vi->fullsize = ~0;
5630 vi->is_unknown_size_var = true;
5631 vi->is_full_var = true;
0f8d6231 5632 vi->may_have_pointers = true;
18abb35e 5633 return vi;
910fdc79 5634 }
18abb35e
RG
5635
5636 /* Collect field information. */
5637 if (use_field_sensitive
5638 && var_can_have_subvars (decl)
27e2bd9f
RB
5639 /* ??? Force us to not use subfields for globals in IPA mode.
5640 Else we'd have to parse arbitrary initializers. */
18abb35e 5641 && !(in_ipa_mode
27e2bd9f 5642 && is_global_var (decl)))
910fdc79 5643 {
18abb35e
RG
5644 fieldoff_s *fo = NULL;
5645 bool notokay = false;
5646 unsigned int i;
5647
0f8d6231 5648 push_fields_onto_fieldstack (decl_type, &fieldstack, 0);
18abb35e 5649
9771b263 5650 for (i = 0; !notokay && fieldstack.iterate (i, &fo); i++)
18abb35e
RG
5651 if (fo->has_unknown_size
5652 || fo->offset < 0)
5653 {
5654 notokay = true;
5655 break;
5656 }
5657
5658 /* We can't sort them if we have a field with a variable sized type,
5659 which will make notokay = true. In that case, we are going to return
5660 without creating varinfos for the fields anyway, so sorting them is a
5661 waste to boot. */
5662 if (!notokay)
5663 {
5664 sort_fieldstack (fieldstack);
5665 /* Due to some C++ FE issues, like PR 22488, we might end up
5666 what appear to be overlapping fields even though they,
5667 in reality, do not overlap. Until the C++ FE is fixed,
5668 we will simply disable field-sensitivity for these cases. */
5669 notokay = check_for_overlaps (fieldstack);
5670 }
5671
5672 if (notokay)
9771b263 5673 fieldstack.release ();
18abb35e
RG
5674 }
5675
5676 /* If we didn't end up collecting sub-variables create a full
5677 variable for the decl. */
9771b263
DN
5678 if (fieldstack.length () <= 1
5679 || fieldstack.length () > MAX_FIELDS_FOR_FIELD_SENSITIVE)
18abb35e
RG
5680 {
5681 vi = new_var_info (decl, name);
5682 vi->offset = 0;
0f8d6231 5683 vi->may_have_pointers = true;
eb1ce453 5684 vi->fullsize = tree_to_uhwi (declsize);
910fdc79 5685 vi->size = vi->fullsize;
18abb35e 5686 vi->is_full_var = true;
9771b263 5687 fieldstack.release ();
18abb35e 5688 return vi;
910fdc79 5689 }
c58936b6 5690
18abb35e 5691 vi = new_var_info (decl, name);
eb1ce453 5692 vi->fullsize = tree_to_uhwi (declsize);
18abb35e 5693 for (i = 0, newvi = vi;
9771b263 5694 fieldstack.iterate (i, &fo);
d6d305fe 5695 ++i, newvi = vi_next (newvi))
18abb35e
RG
5696 {
5697 const char *newname = "NULL";
5698 char *tempname;
5699
5700 if (dump_file)
5701 {
582f770b
UB
5702 tempname
5703 = xasprintf ("%s." HOST_WIDE_INT_PRINT_DEC
5704 "+" HOST_WIDE_INT_PRINT_DEC, name,
5705 fo->offset, fo->size);
18abb35e
RG
5706 newname = ggc_strdup (tempname);
5707 free (tempname);
5708 }
5709 newvi->name = newname;
5710 newvi->offset = fo->offset;
5711 newvi->size = fo->size;
5712 newvi->fullsize = vi->fullsize;
5713 newvi->may_have_pointers = fo->may_have_pointers;
5714 newvi->only_restrict_pointers = fo->only_restrict_pointers;
9771b263 5715 if (i + 1 < fieldstack.length ())
d6d305fe
RB
5716 {
5717 varinfo_t tem = new_var_info (decl, name);
5718 newvi->next = tem->id;
5719 tem->head = vi->id;
5720 }
18abb35e
RG
5721 }
5722
18abb35e
RG
5723 return vi;
5724}
5725
5726static unsigned int
5727create_variable_info_for (tree decl, const char *name)
5728{
5729 varinfo_t vi = create_variable_info_for_1 (decl, name);
5730 unsigned int id = vi->id;
5731
5732 insert_vi_for_tree (decl, vi);
5733
1565af08
RG
5734 if (TREE_CODE (decl) != VAR_DECL)
5735 return id;
5736
18abb35e 5737 /* Create initial constraints for globals. */
d6d305fe 5738 for (; vi; vi = vi_next (vi))
13c6bff4 5739 {
18abb35e
RG
5740 if (!vi->may_have_pointers
5741 || !vi->is_global_var)
5742 continue;
5743
25a6a873 5744 /* Mark global restrict qualified pointers. */
18abb35e
RG
5745 if ((POINTER_TYPE_P (TREE_TYPE (decl))
5746 && TYPE_RESTRICT (TREE_TYPE (decl)))
5747 || vi->only_restrict_pointers)
d3553615 5748 {
aa098165
RB
5749 varinfo_t rvi
5750 = make_constraint_from_global_restrict (vi, "GLOBAL_RESTRICT");
5751 /* ??? For now exclude reads from globals as restrict sources
5752 if those are not (indirectly) from incoming parameters. */
5753 rvi->is_restrict_var = false;
d3553615
RG
5754 continue;
5755 }
25a6a873 5756
1565af08 5757 /* In non-IPA mode the initializer from nonlocal is all we need. */
25a6a873 5758 if (!in_ipa_mode
1565af08 5759 || DECL_HARD_REGISTER (decl))
25a6a873
RG
5760 make_copy_constraint (vi, nonlocal_id);
5761
d3553615
RG
5762 /* In IPA mode parse the initializer and generate proper constraints
5763 for it. */
1565af08 5764 else
25a6a873 5765 {
9041d2e6 5766 varpool_node *vnode = varpool_node::get (decl);
1565af08
RG
5767
5768 /* For escaped variables initialize them from nonlocal. */
9041d2e6 5769 if (!vnode->all_refs_explicit_p ())
1565af08
RG
5770 make_copy_constraint (vi, nonlocal_id);
5771
5772 /* If this is a global variable with an initializer and we are in
5773 IPA mode generate constraints for it. */
27e2bd9f
RB
5774 ipa_ref *ref;
5775 for (unsigned idx = 0; vnode->iterate_reference (idx, ref); ++idx)
25a6a873 5776 {
ef062b13 5777 auto_vec<ce_s> rhsc;
1565af08
RG
5778 struct constraint_expr lhs, *rhsp;
5779 unsigned i;
27e2bd9f 5780 get_constraint_for_address_of (ref->referred->decl, &rhsc);
1565af08 5781 lhs.var = vi->id;
25a6a873
RG
5782 lhs.offset = 0;
5783 lhs.type = SCALAR;
9771b263 5784 FOR_EACH_VEC_ELT (rhsc, i, rhsp)
25a6a873 5785 process_constraint (new_constraint (lhs, *rhsp));
1565af08
RG
5786 /* If this is a variable that escapes from the unit
5787 the initializer escapes as well. */
9041d2e6 5788 if (!vnode->all_refs_explicit_p ())
1565af08
RG
5789 {
5790 lhs.var = escaped_id;
5791 lhs.offset = 0;
5792 lhs.type = SCALAR;
9771b263 5793 FOR_EACH_VEC_ELT (rhsc, i, rhsp)
1565af08
RG
5794 process_constraint (new_constraint (lhs, *rhsp));
5795 }
25a6a873 5796 }
25a6a873 5797 }
13c6bff4 5798 }
910fdc79 5799
18abb35e 5800 return id;
910fdc79
DB
5801}
5802
5803/* Print out the points-to solution for VAR to FILE. */
5804
5006671f 5805static void
910fdc79
DB
5806dump_solution_for_var (FILE *file, unsigned int var)
5807{
5808 varinfo_t vi = get_varinfo (var);
5809 unsigned int i;
c58936b6
DB
5810 bitmap_iterator bi;
5811
25a6a873
RG
5812 /* Dump the solution for unified vars anyway, this avoids difficulties
5813 in scanning dumps in the testsuite. */
5814 fprintf (file, "%s = { ", vi->name);
5815 vi = get_varinfo (find (var));
5816 EXECUTE_IF_SET_IN_BITMAP (vi->solution, 0, i, bi)
5817 fprintf (file, "%s ", get_varinfo (i)->name);
5818 fprintf (file, "}");
5819
5820 /* But note when the variable was unified. */
5821 if (vi->id != var)
5822 fprintf (file, " same as %s", vi->name);
5823
5824 fprintf (file, "\n");
910fdc79
DB
5825}
5826
3d224d46 5827/* Print the points-to solution for VAR to stderr. */
910fdc79 5828
24e47c76 5829DEBUG_FUNCTION void
910fdc79
DB
5830debug_solution_for_var (unsigned int var)
5831{
3d224d46 5832 dump_solution_for_var (stderr, var);
910fdc79
DB
5833}
5834
910fdc79
DB
5835/* Create varinfo structures for all of the variables in the
5836 function for intraprocedural mode. */
5837
5838static void
628169e0 5839intra_create_variable_infos (struct function *fn)
910fdc79
DB
5840{
5841 tree t;
b23987ec 5842
6e7e772d 5843 /* For each incoming pointer argument arg, create the constraint ARG
0d3c82d6
RG
5844 = NONLOCAL or a dummy variable if it is a restrict qualified
5845 passed-by-reference argument. */
628169e0 5846 for (t = DECL_ARGUMENTS (fn->decl); t; t = DECL_CHAIN (t))
910fdc79 5847 {
d3553615 5848 varinfo_t p = get_vi_for_tree (t);
c58936b6 5849
bacd3fb6 5850 /* For restrict qualified pointers to objects passed by
960dcaf5
JJ
5851 reference build a real representative for the pointed-to object.
5852 Treat restrict qualified references the same. */
5853 if (TYPE_RESTRICT (TREE_TYPE (t))
5854 && ((DECL_BY_REFERENCE (t) && POINTER_TYPE_P (TREE_TYPE (t)))
b31799f4
EB
5855 || TREE_CODE (TREE_TYPE (t)) == REFERENCE_TYPE)
5856 && !type_contains_placeholder_p (TREE_TYPE (TREE_TYPE (t))))
bacd3fb6
RG
5857 {
5858 struct constraint_expr lhsc, rhsc;
5859 varinfo_t vi;
7d6e2521
RG
5860 tree heapvar = build_fake_var_decl (TREE_TYPE (TREE_TYPE (t)));
5861 DECL_EXTERNAL (heapvar) = 1;
1565af08 5862 vi = create_variable_info_for_1 (heapvar, "PARM_NOALIAS");
aa098165 5863 vi->is_restrict_var = 1;
1565af08 5864 insert_vi_for_tree (heapvar, vi);
d3553615 5865 lhsc.var = p->id;
bacd3fb6
RG
5866 lhsc.type = SCALAR;
5867 lhsc.offset = 0;
7d6e2521 5868 rhsc.var = vi->id;
bacd3fb6
RG
5869 rhsc.type = ADDRESSOF;
5870 rhsc.offset = 0;
5871 process_constraint (new_constraint (lhsc, rhsc));
d6d305fe 5872 for (; vi; vi = vi_next (vi))
1565af08
RG
5873 if (vi->may_have_pointers)
5874 {
5875 if (vi->only_restrict_pointers)
d3553615
RG
5876 make_constraint_from_global_restrict (vi, "GLOBAL_RESTRICT");
5877 else
5878 make_copy_constraint (vi, nonlocal_id);
1565af08 5879 }
bacd3fb6
RG
5880 continue;
5881 }
5882
74d27244
RG
5883 if (POINTER_TYPE_P (TREE_TYPE (t))
5884 && TYPE_RESTRICT (TREE_TYPE (t)))
d3553615
RG
5885 make_constraint_from_global_restrict (p, "PARM_RESTRICT");
5886 else
5887 {
d6d305fe 5888 for (; p; p = vi_next (p))
d3553615
RG
5889 {
5890 if (p->only_restrict_pointers)
5891 make_constraint_from_global_restrict (p, "PARM_RESTRICT");
5892 else if (p->may_have_pointers)
5893 make_constraint_from (p, nonlocal_id);
5894 }
5895 }
21392f19 5896 }
75af9746 5897
10bd6c5c 5898 /* Add a constraint for a result decl that is passed by reference. */
628169e0
RB
5899 if (DECL_RESULT (fn->decl)
5900 && DECL_BY_REFERENCE (DECL_RESULT (fn->decl)))
10bd6c5c 5901 {
628169e0 5902 varinfo_t p, result_vi = get_vi_for_tree (DECL_RESULT (fn->decl));
10bd6c5c 5903
d6d305fe 5904 for (p = result_vi; p; p = vi_next (p))
5006671f 5905 make_constraint_from (p, nonlocal_id);
10bd6c5c
RG
5906 }
5907
75af9746 5908 /* Add a constraint for the incoming static chain parameter. */
628169e0 5909 if (fn->static_chain_decl != NULL_TREE)
75af9746 5910 {
628169e0 5911 varinfo_t p, chain_vi = get_vi_for_tree (fn->static_chain_decl);
75af9746 5912
d6d305fe 5913 for (p = chain_vi; p; p = vi_next (p))
75af9746
RG
5914 make_constraint_from (p, nonlocal_id);
5915 }
910fdc79
DB
5916}
5917
1296c31f
DB
5918/* Structure used to put solution bitmaps in a hashtable so they can
5919 be shared among variables with the same points-to set. */
5920
5921typedef struct shared_bitmap_info
5922{
5923 bitmap pt_vars;
5924 hashval_t hashcode;
5925} *shared_bitmap_info_t;
e5cfc29f 5926typedef const struct shared_bitmap_info *const_shared_bitmap_info_t;
1296c31f 5927
bf190e8d
LC
5928/* Shared_bitmap hashtable helpers. */
5929
95fbe13e 5930struct shared_bitmap_hasher : free_ptr_hash <shared_bitmap_info>
bf190e8d 5931{
67f58944
TS
5932 static inline hashval_t hash (const shared_bitmap_info *);
5933 static inline bool equal (const shared_bitmap_info *,
5934 const shared_bitmap_info *);
bf190e8d 5935};
1296c31f
DB
5936
5937/* Hash function for a shared_bitmap_info_t */
5938
bf190e8d 5939inline hashval_t
67f58944 5940shared_bitmap_hasher::hash (const shared_bitmap_info *bi)
1296c31f 5941{
1296c31f
DB
5942 return bi->hashcode;
5943}
5944
5945/* Equality function for two shared_bitmap_info_t's. */
5946
bf190e8d 5947inline bool
67f58944
TS
5948shared_bitmap_hasher::equal (const shared_bitmap_info *sbi1,
5949 const shared_bitmap_info *sbi2)
1296c31f 5950{
1296c31f
DB
5951 return bitmap_equal_p (sbi1->pt_vars, sbi2->pt_vars);
5952}
5953
bf190e8d
LC
5954/* Shared_bitmap hashtable. */
5955
c203e8a7 5956static hash_table<shared_bitmap_hasher> *shared_bitmap_table;
bf190e8d 5957
1296c31f
DB
5958/* Lookup a bitmap in the shared bitmap hashtable, and return an already
5959 existing instance if there is one, NULL otherwise. */
5960
5961static bitmap
5962shared_bitmap_lookup (bitmap pt_vars)
5963{
bf190e8d 5964 shared_bitmap_info **slot;
1296c31f
DB
5965 struct shared_bitmap_info sbi;
5966
5967 sbi.pt_vars = pt_vars;
5968 sbi.hashcode = bitmap_hash (pt_vars);
7b765bed 5969
c203e8a7 5970 slot = shared_bitmap_table->find_slot (&sbi, NO_INSERT);
1296c31f
DB
5971 if (!slot)
5972 return NULL;
5973 else
bf190e8d 5974 return (*slot)->pt_vars;
1296c31f
DB
5975}
5976
5977
5978/* Add a bitmap to the shared bitmap hashtable. */
5979
5980static void
5981shared_bitmap_add (bitmap pt_vars)
5982{
bf190e8d 5983 shared_bitmap_info **slot;
1296c31f 5984 shared_bitmap_info_t sbi = XNEW (struct shared_bitmap_info);
7b765bed 5985
1296c31f
DB
5986 sbi->pt_vars = pt_vars;
5987 sbi->hashcode = bitmap_hash (pt_vars);
7b765bed 5988
c203e8a7 5989 slot = shared_bitmap_table->find_slot (sbi, INSERT);
1296c31f 5990 gcc_assert (!*slot);
bf190e8d 5991 *slot = sbi;
1296c31f
DB
5992}
5993
5994
4d7a65ea 5995/* Set bits in INTO corresponding to the variable uids in solution set FROM. */
910fdc79 5996
b8698a0f 5997static void
4d7a65ea 5998set_uids_in_ptset (bitmap into, bitmap from, struct pt_solution *pt)
910fdc79
DB
5999{
6000 unsigned int i;
6001 bitmap_iterator bi;
11924f8b
RB
6002 varinfo_t escaped_vi = get_varinfo (find (escaped_id));
6003 bool everything_escaped
6004 = escaped_vi->solution && bitmap_bit_p (escaped_vi->solution, anything_id);
f83ca251 6005
910fdc79
DB
6006 EXECUTE_IF_SET_IN_BITMAP (from, 0, i, bi)
6007 {
6008 varinfo_t vi = get_varinfo (i);
c58936b6 6009
e8ca4159
DN
6010 /* The only artificial variables that are allowed in a may-alias
6011 set are heap variables. */
6012 if (vi->is_artificial_var && !vi->is_heap_var)
6013 continue;
c58936b6 6014
11924f8b
RB
6015 if (everything_escaped
6016 || (escaped_vi->solution
6017 && bitmap_bit_p (escaped_vi->solution, i)))
6018 {
6019 pt->vars_contains_escaped = true;
6020 pt->vars_contains_escaped_heap = vi->is_heap_var;
6021 }
6022
5611cf0b
RG
6023 if (TREE_CODE (vi->decl) == VAR_DECL
6024 || TREE_CODE (vi->decl) == PARM_DECL
6025 || TREE_CODE (vi->decl) == RESULT_DECL)
58b82d2b 6026 {
25a6a873
RG
6027 /* If we are in IPA mode we will not recompute points-to
6028 sets after inlining so make sure they stay valid. */
6029 if (in_ipa_mode
6030 && !DECL_PT_UID_SET_P (vi->decl))
6031 SET_DECL_PT_UID (vi->decl, DECL_UID (vi->decl));
6032
5006671f
RG
6033 /* Add the decl to the points-to set. Note that the points-to
6034 set contains global variables. */
25a6a873 6035 bitmap_set_bit (into, DECL_PT_UID (vi->decl));
74d27244 6036 if (vi->is_global_var)
11924f8b 6037 pt->vars_contains_nonlocal = true;
e8ca4159 6038 }
910fdc79
DB
6039 }
6040}
e8ca4159
DN
6041
6042
4d7a65ea 6043/* Compute the points-to solution *PT for the variable VI. */
ce1b6498 6044
d394a308
RB
6045static struct pt_solution
6046find_what_var_points_to (varinfo_t orig_vi)
ce1b6498 6047{
4d7a65ea 6048 unsigned int i;
5006671f
RG
6049 bitmap_iterator bi;
6050 bitmap finished_solution;
6051 bitmap result;
1cfd38be 6052 varinfo_t vi;
d394a308 6053 struct pt_solution *pt;
5006671f
RG
6054
6055 /* This variable may have been collapsed, let's get the real
6056 variable. */
1cfd38be 6057 vi = get_varinfo (find (orig_vi->id));
5006671f 6058
d394a308 6059 /* See if we have already computed the solution and return it. */
b787e7a2 6060 pt_solution **slot = &final_solutions->get_or_insert (vi);
d394a308 6061 if (*slot != NULL)
b787e7a2 6062 return **slot;
d394a308
RB
6063
6064 *slot = pt = XOBNEW (&final_solutions_obstack, struct pt_solution);
6065 memset (pt, 0, sizeof (struct pt_solution));
6066
5006671f
RG
6067 /* Translate artificial variables into SSA_NAME_PTR_INFO
6068 attributes. */
6069 EXECUTE_IF_SET_IN_BITMAP (vi->solution, 0, i, bi)
6070 {
6071 varinfo_t vi = get_varinfo (i);
6072
6073 if (vi->is_artificial_var)
6074 {
6075 if (vi->id == nothing_id)
6076 pt->null = 1;
6077 else if (vi->id == escaped_id)
25a6a873
RG
6078 {
6079 if (in_ipa_mode)
6080 pt->ipa_escaped = 1;
6081 else
6082 pt->escaped = 1;
e8e938e0
RB
6083 /* Expand some special vars of ESCAPED in-place here. */
6084 varinfo_t evi = get_varinfo (find (escaped_id));
6085 if (bitmap_bit_p (evi->solution, nonlocal_id))
6086 pt->nonlocal = 1;
25a6a873 6087 }
5006671f
RG
6088 else if (vi->id == nonlocal_id)
6089 pt->nonlocal = 1;
6090 else if (vi->is_heap_var)
6091 /* We represent heapvars in the points-to set properly. */
6092 ;
ebd7d910
RB
6093 else if (vi->id == string_id)
6094 /* Nobody cares - STRING_CSTs are read-only entities. */
91deb937 6095 ;
5006671f 6096 else if (vi->id == anything_id
5006671f
RG
6097 || vi->id == integer_id)
6098 pt->anything = 1;
6099 }
6100 }
6101
6102 /* Instead of doing extra work, simply do not create
6103 elaborate points-to information for pt_anything pointers. */
d3553615 6104 if (pt->anything)
d394a308 6105 return *pt;
5006671f
RG
6106
6107 /* Share the final set of variables when possible. */
6108 finished_solution = BITMAP_GGC_ALLOC ();
6109 stats.points_to_sets_created++;
6110
4d7a65ea 6111 set_uids_in_ptset (finished_solution, vi->solution, pt);
5006671f
RG
6112 result = shared_bitmap_lookup (finished_solution);
6113 if (!result)
6114 {
6115 shared_bitmap_add (finished_solution);
6116 pt->vars = finished_solution;
6117 }
6118 else
6119 {
6120 pt->vars = result;
6121 bitmap_clear (finished_solution);
6122 }
d394a308
RB
6123
6124 return *pt;
5006671f
RG
6125}
6126
4d7a65ea 6127/* Given a pointer variable P, fill in its points-to set. */
5006671f
RG
6128
6129static void
4d7a65ea 6130find_what_p_points_to (tree p)
5006671f
RG
6131{
6132 struct ptr_info_def *pi;
7cc92f92 6133 tree lookup_p = p;
3e5937d7 6134 varinfo_t vi;
e8ca4159 6135
7cc92f92
RG
6136 /* For parameters, get at the points-to set for the actual parm
6137 decl. */
c58936b6 6138 if (TREE_CODE (p) == SSA_NAME
67386041 6139 && SSA_NAME_IS_DEFAULT_DEF (p)
6938f93f 6140 && (TREE_CODE (SSA_NAME_VAR (p)) == PARM_DECL
67386041 6141 || TREE_CODE (SSA_NAME_VAR (p)) == RESULT_DECL))
7cc92f92
RG
6142 lookup_p = SSA_NAME_VAR (p);
6143
15814ba0 6144 vi = lookup_vi_for_tree (lookup_p);
5006671f
RG
6145 if (!vi)
6146 return;
6147
6148 pi = get_ptr_info (p);
d394a308 6149 pi->pt = find_what_var_points_to (vi);
5006671f 6150}
7b765bed 6151
910fdc79 6152
5006671f 6153/* Query statistics for points-to solutions. */
c58936b6 6154
5006671f
RG
6155static struct {
6156 unsigned HOST_WIDE_INT pt_solution_includes_may_alias;
6157 unsigned HOST_WIDE_INT pt_solution_includes_no_alias;
6158 unsigned HOST_WIDE_INT pt_solutions_intersect_may_alias;
6159 unsigned HOST_WIDE_INT pt_solutions_intersect_no_alias;
6160} pta_stats;
e8ca4159 6161
5006671f
RG
6162void
6163dump_pta_stats (FILE *s)
6164{
6165 fprintf (s, "\nPTA query stats:\n");
6166 fprintf (s, " pt_solution_includes: "
6167 HOST_WIDE_INT_PRINT_DEC" disambiguations, "
6168 HOST_WIDE_INT_PRINT_DEC" queries\n",
6169 pta_stats.pt_solution_includes_no_alias,
6170 pta_stats.pt_solution_includes_no_alias
6171 + pta_stats.pt_solution_includes_may_alias);
6172 fprintf (s, " pt_solutions_intersect: "
6173 HOST_WIDE_INT_PRINT_DEC" disambiguations, "
6174 HOST_WIDE_INT_PRINT_DEC" queries\n",
6175 pta_stats.pt_solutions_intersect_no_alias,
6176 pta_stats.pt_solutions_intersect_no_alias
6177 + pta_stats.pt_solutions_intersect_may_alias);
6178}
e8ca4159 6179
9f09b13f 6180
5006671f
RG
6181/* Reset the points-to solution *PT to a conservative default
6182 (point to anything). */
7b765bed 6183
5006671f
RG
6184void
6185pt_solution_reset (struct pt_solution *pt)
6186{
6187 memset (pt, 0, sizeof (struct pt_solution));
6188 pt->anything = true;
6189}
1296c31f 6190
55b34b5f 6191/* Set the points-to solution *PT to point only to the variables
25a6a873
RG
6192 in VARS. VARS_CONTAINS_GLOBAL specifies whether that contains
6193 global variables and VARS_CONTAINS_RESTRICT specifies whether
6194 it contains restrict tag variables. */
55b34b5f
RG
6195
6196void
11924f8b
RB
6197pt_solution_set (struct pt_solution *pt, bitmap vars,
6198 bool vars_contains_nonlocal)
55b34b5f 6199{
55b34b5f
RG
6200 memset (pt, 0, sizeof (struct pt_solution));
6201 pt->vars = vars;
11924f8b
RB
6202 pt->vars_contains_nonlocal = vars_contains_nonlocal;
6203 pt->vars_contains_escaped
6204 = (cfun->gimple_df->escaped.anything
6205 || bitmap_intersect_p (cfun->gimple_df->escaped.vars, vars));
25a6a873
RG
6206}
6207
90fa9e17
RG
6208/* Set the points-to solution *PT to point only to the variable VAR. */
6209
6210void
6211pt_solution_set_var (struct pt_solution *pt, tree var)
6212{
6213 memset (pt, 0, sizeof (struct pt_solution));
6214 pt->vars = BITMAP_GGC_ALLOC ();
1b2bb171 6215 bitmap_set_bit (pt->vars, DECL_PT_UID (var));
11924f8b
RB
6216 pt->vars_contains_nonlocal = is_global_var (var);
6217 pt->vars_contains_escaped
6218 = (cfun->gimple_df->escaped.anything
6219 || bitmap_bit_p (cfun->gimple_df->escaped.vars, DECL_PT_UID (var)));
90fa9e17
RG
6220}
6221
25a6a873
RG
6222/* Computes the union of the points-to solutions *DEST and *SRC and
6223 stores the result in *DEST. This changes the points-to bitmap
6224 of *DEST and thus may not be used if that might be shared.
6225 The points-to bitmap of *SRC and *DEST will not be shared after
6226 this function if they were not before. */
6227
6228static void
6229pt_solution_ior_into (struct pt_solution *dest, struct pt_solution *src)
6230{
6231 dest->anything |= src->anything;
6232 if (dest->anything)
55b34b5f 6233 {
25a6a873
RG
6234 pt_solution_reset (dest);
6235 return;
55b34b5f 6236 }
25a6a873
RG
6237
6238 dest->nonlocal |= src->nonlocal;
6239 dest->escaped |= src->escaped;
6240 dest->ipa_escaped |= src->ipa_escaped;
6241 dest->null |= src->null;
11924f8b
RB
6242 dest->vars_contains_nonlocal |= src->vars_contains_nonlocal;
6243 dest->vars_contains_escaped |= src->vars_contains_escaped;
6244 dest->vars_contains_escaped_heap |= src->vars_contains_escaped_heap;
25a6a873
RG
6245 if (!src->vars)
6246 return;
6247
6248 if (!dest->vars)
6249 dest->vars = BITMAP_GGC_ALLOC ();
6250 bitmap_ior_into (dest->vars, src->vars);
55b34b5f
RG
6251}
6252
5006671f 6253/* Return true if the points-to solution *PT is empty. */
e8ca4159 6254
25a6a873 6255bool
5006671f
RG
6256pt_solution_empty_p (struct pt_solution *pt)
6257{
6258 if (pt->anything
6259 || pt->nonlocal)
6260 return false;
e8ca4159 6261
5006671f
RG
6262 if (pt->vars
6263 && !bitmap_empty_p (pt->vars))
6264 return false;
e8ca4159 6265
5006671f
RG
6266 /* If the solution includes ESCAPED, check if that is empty. */
6267 if (pt->escaped
6268 && !pt_solution_empty_p (&cfun->gimple_df->escaped))
6269 return false;
6270
25a6a873
RG
6271 /* If the solution includes ESCAPED, check if that is empty. */
6272 if (pt->ipa_escaped
6273 && !pt_solution_empty_p (&ipa_escaped_pt))
6274 return false;
6275
5006671f 6276 return true;
910fdc79
DB
6277}
6278
703ffc30
TV
6279/* Return true if the points-to solution *PT only point to a single var, and
6280 return the var uid in *UID. */
6281
6282bool
6283pt_solution_singleton_p (struct pt_solution *pt, unsigned *uid)
6284{
6285 if (pt->anything || pt->nonlocal || pt->escaped || pt->ipa_escaped
6286 || pt->null || pt->vars == NULL
6287 || !bitmap_single_bit_set_p (pt->vars))
6288 return false;
6289
6290 *uid = bitmap_first_set_bit (pt->vars);
6291 return true;
6292}
6293
5006671f 6294/* Return true if the points-to solution *PT includes global memory. */
63a4ef6f 6295
2f571334 6296bool
5006671f 6297pt_solution_includes_global (struct pt_solution *pt)
2f571334 6298{
5006671f
RG
6299 if (pt->anything
6300 || pt->nonlocal
11924f8b
RB
6301 || pt->vars_contains_nonlocal
6302 /* The following is a hack to make the malloc escape hack work.
6303 In reality we'd need different sets for escaped-through-return
6304 and escaped-to-callees and passes would need to be updated. */
6305 || pt->vars_contains_escaped_heap)
5006671f 6306 return true;
2f571334 6307
11924f8b 6308 /* 'escaped' is also a placeholder so we have to look into it. */
5006671f
RG
6309 if (pt->escaped)
6310 return pt_solution_includes_global (&cfun->gimple_df->escaped);
2f571334 6311
25a6a873
RG
6312 if (pt->ipa_escaped)
6313 return pt_solution_includes_global (&ipa_escaped_pt);
6314
6315 /* ??? This predicate is not correct for the IPA-PTA solution
6316 as we do not properly distinguish between unit escape points
6317 and global variables. */
6318 if (cfun->gimple_df->ipa_pta)
6319 return true;
6320
5006671f
RG
6321 return false;
6322}
2f571334 6323
5006671f
RG
6324/* Return true if the points-to solution *PT includes the variable
6325 declaration DECL. */
15c15196 6326
5006671f
RG
6327static bool
6328pt_solution_includes_1 (struct pt_solution *pt, const_tree decl)
6329{
6330 if (pt->anything)
6331 return true;
2f571334 6332
5006671f
RG
6333 if (pt->nonlocal
6334 && is_global_var (decl))
6335 return true;
2f571334 6336
5006671f 6337 if (pt->vars
25a6a873 6338 && bitmap_bit_p (pt->vars, DECL_PT_UID (decl)))
5006671f 6339 return true;
2f571334 6340
5006671f
RG
6341 /* If the solution includes ESCAPED, check it. */
6342 if (pt->escaped
6343 && pt_solution_includes_1 (&cfun->gimple_df->escaped, decl))
6344 return true;
2f571334 6345
25a6a873
RG
6346 /* If the solution includes ESCAPED, check it. */
6347 if (pt->ipa_escaped
6348 && pt_solution_includes_1 (&ipa_escaped_pt, decl))
6349 return true;
6350
5006671f 6351 return false;
2f571334 6352}
910fdc79 6353
5006671f
RG
6354bool
6355pt_solution_includes (struct pt_solution *pt, const_tree decl)
15c15196 6356{
5006671f
RG
6357 bool res = pt_solution_includes_1 (pt, decl);
6358 if (res)
6359 ++pta_stats.pt_solution_includes_may_alias;
6360 else
6361 ++pta_stats.pt_solution_includes_no_alias;
6362 return res;
6363}
15c15196 6364
5006671f
RG
6365/* Return true if both points-to solutions PT1 and PT2 have a non-empty
6366 intersection. */
15c15196 6367
5006671f
RG
6368static bool
6369pt_solutions_intersect_1 (struct pt_solution *pt1, struct pt_solution *pt2)
6370{
6371 if (pt1->anything || pt2->anything)
6372 return true;
15c15196 6373
5006671f
RG
6374 /* If either points to unknown global memory and the other points to
6375 any global memory they alias. */
6376 if ((pt1->nonlocal
6377 && (pt2->nonlocal
11924f8b 6378 || pt2->vars_contains_nonlocal))
5006671f 6379 || (pt2->nonlocal
11924f8b 6380 && pt1->vars_contains_nonlocal))
5006671f 6381 return true;
15c15196 6382
11924f8b
RB
6383 /* If either points to all escaped memory and the other points to
6384 any escaped memory they alias. */
6385 if ((pt1->escaped
6386 && (pt2->escaped
6387 || pt2->vars_contains_escaped))
6388 || (pt2->escaped
6389 && pt1->vars_contains_escaped))
6390 return true;
15c15196 6391
25a6a873
RG
6392 /* Check the escaped solution if required.
6393 ??? Do we need to check the local against the IPA escaped sets? */
6394 if ((pt1->ipa_escaped || pt2->ipa_escaped)
6395 && !pt_solution_empty_p (&ipa_escaped_pt))
6396 {
6397 /* If both point to escaped memory and that solution
6398 is not empty they alias. */
6399 if (pt1->ipa_escaped && pt2->ipa_escaped)
6400 return true;
6401
6402 /* If either points to escaped memory see if the escaped solution
6403 intersects with the other. */
6404 if ((pt1->ipa_escaped
6405 && pt_solutions_intersect_1 (&ipa_escaped_pt, pt2))
6406 || (pt2->ipa_escaped
6407 && pt_solutions_intersect_1 (&ipa_escaped_pt, pt1)))
6408 return true;
6409 }
6410
5006671f
RG
6411 /* Now both pointers alias if their points-to solution intersects. */
6412 return (pt1->vars
6413 && pt2->vars
6414 && bitmap_intersect_p (pt1->vars, pt2->vars));
6415}
6416
6417bool
6418pt_solutions_intersect (struct pt_solution *pt1, struct pt_solution *pt2)
6419{
6420 bool res = pt_solutions_intersect_1 (pt1, pt2);
6421 if (res)
6422 ++pta_stats.pt_solutions_intersect_may_alias;
6423 else
6424 ++pta_stats.pt_solutions_intersect_no_alias;
6425 return res;
15c15196
RG
6426}
6427
b7091901 6428
63a4ef6f
DN
6429/* Dump points-to information to OUTFILE. */
6430
5006671f 6431static void
910fdc79
DB
6432dump_sa_points_to_info (FILE *outfile)
6433{
910fdc79 6434 unsigned int i;
63a4ef6f 6435
e8ca4159 6436 fprintf (outfile, "\nPoints-to sets\n\n");
63a4ef6f 6437
910fdc79
DB
6438 if (dump_flags & TDF_STATS)
6439 {
6440 fprintf (outfile, "Stats:\n");
63a4ef6f 6441 fprintf (outfile, "Total vars: %d\n", stats.total_vars);
3e5937d7
DB
6442 fprintf (outfile, "Non-pointer vars: %d\n",
6443 stats.nonpointer_vars);
63a4ef6f
DN
6444 fprintf (outfile, "Statically unified vars: %d\n",
6445 stats.unified_vars_static);
63a4ef6f
DN
6446 fprintf (outfile, "Dynamically unified vars: %d\n",
6447 stats.unified_vars_dynamic);
6448 fprintf (outfile, "Iterations: %d\n", stats.iterations);
4ee00913 6449 fprintf (outfile, "Number of edges: %d\n", stats.num_edges);
3e5937d7
DB
6450 fprintf (outfile, "Number of implicit edges: %d\n",
6451 stats.num_implicit_edges);
910fdc79 6452 }
63a4ef6f 6453
d6d305fe 6454 for (i = 1; i < varmap.length (); i++)
25a6a873
RG
6455 {
6456 varinfo_t vi = get_varinfo (i);
6457 if (!vi->may_have_pointers)
b28ae58f 6458 continue;
25a6a873
RG
6459 dump_solution_for_var (outfile, i);
6460 }
910fdc79
DB
6461}
6462
6463
63a4ef6f
DN
6464/* Debug points-to information to stderr. */
6465
24e47c76 6466DEBUG_FUNCTION void
63a4ef6f
DN
6467debug_sa_points_to_info (void)
6468{
6469 dump_sa_points_to_info (stderr);
6470}
6471
6472
910fdc79
DB
6473/* Initialize the always-existing constraint variables for NULL
6474 ANYTHING, READONLY, and INTEGER */
6475
6476static void
6477init_base_vars (void)
6478{
6479 struct constraint_expr lhs, rhs;
0bbf2ffa
RG
6480 varinfo_t var_anything;
6481 varinfo_t var_nothing;
ebd7d910 6482 varinfo_t var_string;
0bbf2ffa
RG
6483 varinfo_t var_escaped;
6484 varinfo_t var_nonlocal;
0bbf2ffa
RG
6485 varinfo_t var_storedanything;
6486 varinfo_t var_integer;
910fdc79 6487
d6d305fe
RB
6488 /* Variable ID zero is reserved and should be NULL. */
6489 varmap.safe_push (NULL);
6490
910fdc79
DB
6491 /* Create the NULL variable, used to represent that a variable points
6492 to NULL. */
0bbf2ffa
RG
6493 var_nothing = new_var_info (NULL_TREE, "NULL");
6494 gcc_assert (var_nothing->id == nothing_id);
910fdc79
DB
6495 var_nothing->is_artificial_var = 1;
6496 var_nothing->offset = 0;
6497 var_nothing->size = ~0;
6498 var_nothing->fullsize = ~0;
13c2c08b 6499 var_nothing->is_special_var = 1;
b28ae58f
RG
6500 var_nothing->may_have_pointers = 0;
6501 var_nothing->is_global_var = 0;
910fdc79
DB
6502
6503 /* Create the ANYTHING variable, used to represent that a variable
6504 points to some unknown piece of memory. */
0bbf2ffa
RG
6505 var_anything = new_var_info (NULL_TREE, "ANYTHING");
6506 gcc_assert (var_anything->id == anything_id);
910fdc79
DB
6507 var_anything->is_artificial_var = 1;
6508 var_anything->size = ~0;
6509 var_anything->offset = 0;
910fdc79 6510 var_anything->fullsize = ~0;
13c2c08b 6511 var_anything->is_special_var = 1;
910fdc79
DB
6512
6513 /* Anything points to anything. This makes deref constraints just
c58936b6 6514 work in the presence of linked list and other p = *p type loops,
910fdc79 6515 by saying that *ANYTHING = ANYTHING. */
910fdc79
DB
6516 lhs.type = SCALAR;
6517 lhs.var = anything_id;
6518 lhs.offset = 0;
3e5937d7 6519 rhs.type = ADDRESSOF;
910fdc79
DB
6520 rhs.var = anything_id;
6521 rhs.offset = 0;
e8ca4159 6522
a5eadacc
DB
6523 /* This specifically does not use process_constraint because
6524 process_constraint ignores all anything = anything constraints, since all
6525 but this one are redundant. */
9771b263 6526 constraints.safe_push (new_constraint (lhs, rhs));
c58936b6 6527
ebd7d910
RB
6528 /* Create the STRING variable, used to represent that a variable
6529 points to a string literal. String literals don't contain
6530 pointers so STRING doesn't point to anything. */
6531 var_string = new_var_info (NULL_TREE, "STRING");
6532 gcc_assert (var_string->id == string_id);
6533 var_string->is_artificial_var = 1;
6534 var_string->offset = 0;
6535 var_string->size = ~0;
6536 var_string->fullsize = ~0;
6537 var_string->is_special_var = 1;
6538 var_string->may_have_pointers = 0;
c58936b6 6539
b7091901
RG
6540 /* Create the ESCAPED variable, used to represent the set of escaped
6541 memory. */
0bbf2ffa
RG
6542 var_escaped = new_var_info (NULL_TREE, "ESCAPED");
6543 gcc_assert (var_escaped->id == escaped_id);
b7091901
RG
6544 var_escaped->is_artificial_var = 1;
6545 var_escaped->offset = 0;
6546 var_escaped->size = ~0;
6547 var_escaped->fullsize = ~0;
6548 var_escaped->is_special_var = 0;
b7091901 6549
b7091901
RG
6550 /* Create the NONLOCAL variable, used to represent the set of nonlocal
6551 memory. */
0bbf2ffa
RG
6552 var_nonlocal = new_var_info (NULL_TREE, "NONLOCAL");
6553 gcc_assert (var_nonlocal->id == nonlocal_id);
b7091901
RG
6554 var_nonlocal->is_artificial_var = 1;
6555 var_nonlocal->offset = 0;
6556 var_nonlocal->size = ~0;
6557 var_nonlocal->fullsize = ~0;
6558 var_nonlocal->is_special_var = 1;
b7091901 6559
5006671f
RG
6560 /* ESCAPED = *ESCAPED, because escaped is may-deref'd at calls, etc. */
6561 lhs.type = SCALAR;
6562 lhs.var = escaped_id;
6563 lhs.offset = 0;
6564 rhs.type = DEREF;
6565 rhs.var = escaped_id;
6566 rhs.offset = 0;
6567 process_constraint (new_constraint (lhs, rhs));
6568
6569 /* ESCAPED = ESCAPED + UNKNOWN_OFFSET, because if a sub-field escapes the
6570 whole variable escapes. */
6571 lhs.type = SCALAR;
6572 lhs.var = escaped_id;
6573 lhs.offset = 0;
6574 rhs.type = SCALAR;
6575 rhs.var = escaped_id;
6576 rhs.offset = UNKNOWN_OFFSET;
6577 process_constraint (new_constraint (lhs, rhs));
6578
6579 /* *ESCAPED = NONLOCAL. This is true because we have to assume
6580 everything pointed to by escaped points to what global memory can
6581 point to. */
6582 lhs.type = DEREF;
6583 lhs.var = escaped_id;
6584 lhs.offset = 0;
6585 rhs.type = SCALAR;
6586 rhs.var = nonlocal_id;
6587 rhs.offset = 0;
6588 process_constraint (new_constraint (lhs, rhs));
6589
6590 /* NONLOCAL = &NONLOCAL, NONLOCAL = &ESCAPED. This is true because
6591 global memory may point to global memory and escaped memory. */
b7091901
RG
6592 lhs.type = SCALAR;
6593 lhs.var = nonlocal_id;
6594 lhs.offset = 0;
6595 rhs.type = ADDRESSOF;
5006671f
RG
6596 rhs.var = nonlocal_id;
6597 rhs.offset = 0;
6598 process_constraint (new_constraint (lhs, rhs));
6599 rhs.type = ADDRESSOF;
b7091901
RG
6600 rhs.var = escaped_id;
6601 rhs.offset = 0;
910fdc79 6602 process_constraint (new_constraint (lhs, rhs));
c58936b6 6603
9e39dba6
RG
6604 /* Create the STOREDANYTHING variable, used to represent the set of
6605 variables stored to *ANYTHING. */
0bbf2ffa
RG
6606 var_storedanything = new_var_info (NULL_TREE, "STOREDANYTHING");
6607 gcc_assert (var_storedanything->id == storedanything_id);
9e39dba6
RG
6608 var_storedanything->is_artificial_var = 1;
6609 var_storedanything->offset = 0;
6610 var_storedanything->size = ~0;
6611 var_storedanything->fullsize = ~0;
6612 var_storedanything->is_special_var = 0;
9e39dba6 6613
910fdc79 6614 /* Create the INTEGER variable, used to represent that a variable points
5006671f 6615 to what an INTEGER "points to". */
0bbf2ffa
RG
6616 var_integer = new_var_info (NULL_TREE, "INTEGER");
6617 gcc_assert (var_integer->id == integer_id);
910fdc79
DB
6618 var_integer->is_artificial_var = 1;
6619 var_integer->size = ~0;
6620 var_integer->fullsize = ~0;
6621 var_integer->offset = 0;
13c2c08b 6622 var_integer->is_special_var = 1;
a5eadacc 6623
21392f19
DB
6624 /* INTEGER = ANYTHING, because we don't know where a dereference of
6625 a random integer will point to. */
a5eadacc
DB
6626 lhs.type = SCALAR;
6627 lhs.var = integer_id;
6628 lhs.offset = 0;
3e5937d7 6629 rhs.type = ADDRESSOF;
a5eadacc
DB
6630 rhs.var = anything_id;
6631 rhs.offset = 0;
6632 process_constraint (new_constraint (lhs, rhs));
c58936b6 6633}
910fdc79 6634
4ee00913 6635/* Initialize things necessary to perform PTA */
910fdc79 6636
4ee00913
DB
6637static void
6638init_alias_vars (void)
910fdc79 6639{
e5bae89b
RG
6640 use_field_sensitive = (MAX_FIELDS_FOR_FIELD_SENSITIVE > 1);
6641
3e5937d7
DB
6642 bitmap_obstack_initialize (&pta_obstack);
6643 bitmap_obstack_initialize (&oldpta_obstack);
4ee00913 6644 bitmap_obstack_initialize (&predbitmap_obstack);
910fdc79 6645
9771b263
DN
6646 constraints.create (8);
6647 varmap.create (8);
b787e7a2 6648 vi_for_tree = new hash_map<tree, varinfo_t>;
355fe088 6649 call_stmt_vars = new hash_map<gimple *, varinfo_t>;
3e5937d7 6650
910fdc79 6651 memset (&stats, 0, sizeof (stats));
c203e8a7 6652 shared_bitmap_table = new hash_table<shared_bitmap_hasher> (511);
910fdc79 6653 init_base_vars ();
7d6e2521
RG
6654
6655 gcc_obstack_init (&fake_var_decl_obstack);
d394a308 6656
b787e7a2 6657 final_solutions = new hash_map<varinfo_t, pt_solution *>;
d394a308 6658 gcc_obstack_init (&final_solutions_obstack);
4ee00913
DB
6659}
6660
3e5937d7
DB
6661/* Remove the REF and ADDRESS edges from GRAPH, as well as all the
6662 predecessor edges. */
6663
6664static void
6665remove_preds_and_fake_succs (constraint_graph_t graph)
6666{
6667 unsigned int i;
6668
6669 /* Clear the implicit ref and address nodes from the successor
6670 lists. */
d6d305fe 6671 for (i = 1; i < FIRST_REF_NODE; i++)
3e5937d7
DB
6672 {
6673 if (graph->succs[i])
6674 bitmap_clear_range (graph->succs[i], FIRST_REF_NODE,
6675 FIRST_REF_NODE * 2);
6676 }
6677
6678 /* Free the successor list for the non-ref nodes. */
d6d305fe 6679 for (i = FIRST_REF_NODE + 1; i < graph->size; i++)
3e5937d7
DB
6680 {
6681 if (graph->succs[i])
6682 BITMAP_FREE (graph->succs[i]);
6683 }
6684
6685 /* Now reallocate the size of the successor list as, and blow away
6686 the predecessor bitmaps. */
9771b263 6687 graph->size = varmap.length ();
c22940cd 6688 graph->succs = XRESIZEVEC (bitmap, graph->succs, graph->size);
3e5937d7
DB
6689
6690 free (graph->implicit_preds);
6691 graph->implicit_preds = NULL;
6692 free (graph->preds);
6693 graph->preds = NULL;
6694 bitmap_obstack_release (&predbitmap_obstack);
6695}
6696
5c245b95 6697/* Solve the constraint set. */
4ee00913 6698
5006671f 6699static void
5c245b95 6700solve_constraints (void)
4ee00913 6701{
3e5937d7 6702 struct scc_info *si;
910fdc79 6703
21392f19
DB
6704 if (dump_file)
6705 fprintf (dump_file,
6706 "\nCollapsing static cycles and doing variable "
7b765bed
DB
6707 "substitution\n");
6708
9771b263 6709 init_graph (varmap.length () * 2);
b8698a0f 6710
7b765bed
DB
6711 if (dump_file)
6712 fprintf (dump_file, "Building predecessor graph\n");
3e5937d7 6713 build_pred_graph ();
b8698a0f 6714
7b765bed
DB
6715 if (dump_file)
6716 fprintf (dump_file, "Detecting pointer and location "
6717 "equivalences\n");
3e5937d7 6718 si = perform_var_substitution (graph);
b8698a0f 6719
7b765bed
DB
6720 if (dump_file)
6721 fprintf (dump_file, "Rewriting constraints and unifying "
6722 "variables\n");
6723 rewrite_constraints (graph, si);
fc93bcb6 6724
8576f20a 6725 build_succ_graph ();
fc93bcb6 6726
8d3e3924
RG
6727 free_var_substitution_info (si);
6728
8576f20a 6729 /* Attach complex constraints to graph nodes. */
7b765bed
DB
6730 move_complex_constraints (graph);
6731
6732 if (dump_file)
6733 fprintf (dump_file, "Uniting pointer but not location equivalent "
6734 "variables\n");
6735 unite_pointer_equivalences (graph);
6736
6737 if (dump_file)
6738 fprintf (dump_file, "Finding indirect cycles\n");
3e5937d7 6739 find_indirect_cycles (graph);
c58936b6 6740
3e5937d7
DB
6741 /* Implicit nodes and predecessors are no longer necessary at this
6742 point. */
6743 remove_preds_and_fake_succs (graph);
c58936b6 6744
8576f20a
RG
6745 if (dump_file && (dump_flags & TDF_GRAPH))
6746 {
6747 fprintf (dump_file, "\n\n// The constraint graph before solve-graph "
6748 "in dot format:\n");
6749 dump_constraint_graph (dump_file);
6750 fprintf (dump_file, "\n\n");
6751 }
6752
21392f19 6753 if (dump_file)
7b765bed 6754 fprintf (dump_file, "Solving graph\n");
c58936b6 6755
21392f19 6756 solve_graph (graph);
c58936b6 6757
8576f20a
RG
6758 if (dump_file && (dump_flags & TDF_GRAPH))
6759 {
6760 fprintf (dump_file, "\n\n// The constraint graph after solve-graph "
6761 "in dot format:\n");
6762 dump_constraint_graph (dump_file);
6763 fprintf (dump_file, "\n\n");
6764 }
6765
910fdc79
DB
6766 if (dump_file)
6767 dump_sa_points_to_info (dump_file);
5c245b95
RG
6768}
6769
6770/* Create points-to sets for the current function. See the comments
6771 at the start of the file for an algorithmic overview. */
6772
6773static void
6774compute_points_to_sets (void)
6775{
6776 basic_block bb;
6777 unsigned i;
6778 varinfo_t vi;
6779
6780 timevar_push (TV_TREE_PTA);
6781
6782 init_alias_vars ();
5c245b95 6783
628169e0 6784 intra_create_variable_infos (cfun);
5c245b95 6785
25a6a873 6786 /* Now walk all statements and build the constraint set. */
11cd3bed 6787 FOR_EACH_BB_FN (bb, cfun)
5c245b95 6788 {
538dd0b7
DM
6789 for (gphi_iterator gsi = gsi_start_phis (bb); !gsi_end_p (gsi);
6790 gsi_next (&gsi))
5c245b95 6791 {
538dd0b7 6792 gphi *phi = gsi.phi ();
5c245b95 6793
ea057359 6794 if (! virtual_operand_p (gimple_phi_result (phi)))
628169e0 6795 find_func_aliases (cfun, phi);
5c245b95
RG
6796 }
6797
538dd0b7
DM
6798 for (gimple_stmt_iterator gsi = gsi_start_bb (bb); !gsi_end_p (gsi);
6799 gsi_next (&gsi))
5c245b95 6800 {
355fe088 6801 gimple *stmt = gsi_stmt (gsi);
5c245b95 6802
628169e0 6803 find_func_aliases (cfun, stmt);
5c245b95
RG
6804 }
6805 }
6806
25a6a873
RG
6807 if (dump_file)
6808 {
6809 fprintf (dump_file, "Points-to analysis\n\nConstraints:\n\n");
6810 dump_constraints (dump_file, 0);
6811 }
6812
5c245b95
RG
6813 /* From the constraints compute the points-to sets. */
6814 solve_constraints ();
c58936b6 6815
3e8542ca 6816 /* Compute the points-to set for ESCAPED used for call-clobber analysis. */
d394a308 6817 cfun->gimple_df->escaped = find_what_var_points_to (get_varinfo (escaped_id));
5006671f
RG
6818
6819 /* Make sure the ESCAPED solution (which is used as placeholder in
6820 other solutions) does not reference itself. This simplifies
6821 points-to solution queries. */
6822 cfun->gimple_df->escaped.escaped = 0;
6823
6824 /* Compute the points-to sets for pointer SSA_NAMEs. */
6825 for (i = 0; i < num_ssa_names; ++i)
6826 {
6827 tree ptr = ssa_name (i);
6828 if (ptr
6829 && POINTER_TYPE_P (TREE_TYPE (ptr)))
4d7a65ea 6830 find_what_p_points_to (ptr);
5006671f 6831 }
e8ca4159 6832
d086d311 6833 /* Compute the call-used/clobbered sets. */
11cd3bed 6834 FOR_EACH_BB_FN (bb, cfun)
d086d311
RG
6835 {
6836 gimple_stmt_iterator gsi;
6837
6838 for (gsi = gsi_start_bb (bb); !gsi_end_p (gsi); gsi_next (&gsi))
6839 {
538dd0b7 6840 gcall *stmt;
d086d311 6841 struct pt_solution *pt;
538dd0b7
DM
6842
6843 stmt = dyn_cast <gcall *> (gsi_stmt (gsi));
6844 if (!stmt)
d086d311
RG
6845 continue;
6846
6847 pt = gimple_call_use_set (stmt);
6848 if (gimple_call_flags (stmt) & ECF_CONST)
6849 memset (pt, 0, sizeof (struct pt_solution));
3e8542ca 6850 else if ((vi = lookup_call_use_vi (stmt)) != NULL)
d086d311 6851 {
d394a308 6852 *pt = find_what_var_points_to (vi);
3e8542ca
RG
6853 /* Escaped (and thus nonlocal) variables are always
6854 implicitly used by calls. */
d086d311
RG
6855 /* ??? ESCAPED can be empty even though NONLOCAL
6856 always escaped. */
6857 pt->nonlocal = 1;
6858 pt->escaped = 1;
6859 }
6860 else
6861 {
3e8542ca
RG
6862 /* If there is nothing special about this call then
6863 we have made everything that is used also escape. */
d086d311
RG
6864 *pt = cfun->gimple_df->escaped;
6865 pt->nonlocal = 1;
6866 }
6867
6868 pt = gimple_call_clobber_set (stmt);
6869 if (gimple_call_flags (stmt) & (ECF_CONST|ECF_PURE|ECF_NOVOPS))
6870 memset (pt, 0, sizeof (struct pt_solution));
3e8542ca
RG
6871 else if ((vi = lookup_call_clobber_vi (stmt)) != NULL)
6872 {
d394a308 6873 *pt = find_what_var_points_to (vi);
3e8542ca
RG
6874 /* Escaped (and thus nonlocal) variables are always
6875 implicitly clobbered by calls. */
6876 /* ??? ESCAPED can be empty even though NONLOCAL
6877 always escaped. */
6878 pt->nonlocal = 1;
6879 pt->escaped = 1;
6880 }
d086d311
RG
6881 else
6882 {
3e8542ca
RG
6883 /* If there is nothing special about this call then
6884 we have made everything that is used also escape. */
d086d311
RG
6885 *pt = cfun->gimple_df->escaped;
6886 pt->nonlocal = 1;
6887 }
6888 }
6889 }
6890
e8ca4159 6891 timevar_pop (TV_TREE_PTA);
910fdc79
DB
6892}
6893
910fdc79
DB
6894
6895/* Delete created points-to sets. */
6896
5006671f 6897static void
e8ca4159 6898delete_points_to_sets (void)
910fdc79 6899{
7b765bed 6900 unsigned int i;
c58936b6 6901
c203e8a7
TS
6902 delete shared_bitmap_table;
6903 shared_bitmap_table = NULL;
3e5937d7
DB
6904 if (dump_file && (dump_flags & TDF_STATS))
6905 fprintf (dump_file, "Points to sets created:%d\n",
6906 stats.points_to_sets_created);
6907
b787e7a2
TS
6908 delete vi_for_tree;
6909 delete call_stmt_vars;
3e5937d7 6910 bitmap_obstack_release (&pta_obstack);
9771b263 6911 constraints.release ();
c58936b6 6912
7b765bed 6913 for (i = 0; i < graph->size; i++)
9771b263 6914 graph->complex[i].release ();
285463b5 6915 free (graph->complex);
21392f19 6916
3e5937d7 6917 free (graph->rep);
57250223 6918 free (graph->succs);
7b765bed
DB
6919 free (graph->pe);
6920 free (graph->pe_rep);
3e5937d7 6921 free (graph->indirect_cycles);
b5efa470
DB
6922 free (graph);
6923
9771b263 6924 varmap.release ();
dc5667a3
ML
6925 variable_info_pool.release ();
6926 constraint_pool.release ();
7d6e2521
RG
6927
6928 obstack_free (&fake_var_decl_obstack, NULL);
d394a308 6929
b787e7a2 6930 delete final_solutions;
d394a308 6931 obstack_free (&final_solutions_obstack, NULL);
910fdc79 6932}
973162ec 6933
aa098165
RB
6934/* Mark "other" loads and stores as belonging to CLIQUE and with
6935 base zero. */
6936
6937static bool
355fe088 6938visit_loadstore (gimple *, tree base, tree ref, void *clique_)
aa098165
RB
6939{
6940 unsigned short clique = (uintptr_t)clique_;
6941 if (TREE_CODE (base) == MEM_REF
6942 || TREE_CODE (base) == TARGET_MEM_REF)
6943 {
6944 tree ptr = TREE_OPERAND (base, 0);
6945 if (TREE_CODE (ptr) == SSA_NAME)
6946 {
6947 /* ??? We need to make sure 'ptr' doesn't include any of
6948 the restrict tags in its points-to set. */
6949 return false;
6950 }
6951
6952 /* For now let decls through. */
6953
6954 /* Do not overwrite existing cliques (that includes clique, base
6955 pairs we just set). */
6956 if (MR_DEPENDENCE_CLIQUE (base) == 0)
6957 {
6958 MR_DEPENDENCE_CLIQUE (base) = clique;
6959 MR_DEPENDENCE_BASE (base) = 0;
6960 }
6961 }
6962
6963 /* For plain decl accesses see whether they are accesses to globals
6964 and rewrite them to MEM_REFs with { clique, 0 }. */
6965 if (TREE_CODE (base) == VAR_DECL
6966 && is_global_var (base)
6967 /* ??? We can't rewrite a plain decl with the walk_stmt_load_store
6968 ops callback. */
6969 && base != ref)
6970 {
6971 tree *basep = &ref;
6972 while (handled_component_p (*basep))
6973 basep = &TREE_OPERAND (*basep, 0);
6974 gcc_assert (TREE_CODE (*basep) == VAR_DECL);
6975 tree ptr = build_fold_addr_expr (*basep);
6976 tree zero = build_int_cst (TREE_TYPE (ptr), 0);
6977 *basep = build2 (MEM_REF, TREE_TYPE (*basep), ptr, zero);
6978 MR_DEPENDENCE_CLIQUE (*basep) = clique;
6979 MR_DEPENDENCE_BASE (*basep) = 0;
6980 }
6981
6982 return false;
6983}
6984
6985/* If REF is a MEM_REF then assign a clique, base pair to it, updating
6986 CLIQUE, *RESTRICT_VAR and LAST_RUID. Return whether dependence info
6987 was assigned to REF. */
6988
6989static bool
6990maybe_set_dependence_info (tree ref, tree ptr,
6991 unsigned short &clique, varinfo_t restrict_var,
6992 unsigned short &last_ruid)
6993{
6994 while (handled_component_p (ref))
6995 ref = TREE_OPERAND (ref, 0);
6996 if ((TREE_CODE (ref) == MEM_REF
6997 || TREE_CODE (ref) == TARGET_MEM_REF)
6998 && TREE_OPERAND (ref, 0) == ptr)
6999 {
7000 /* Do not overwrite existing cliques. This avoids overwriting dependence
7001 info inlined from a function with restrict parameters inlined
7002 into a function with restrict parameters. This usually means we
7003 prefer to be precise in innermost loops. */
7004 if (MR_DEPENDENCE_CLIQUE (ref) == 0)
7005 {
7006 if (clique == 0)
7007 clique = ++cfun->last_clique;
7008 if (restrict_var->ruid == 0)
7009 restrict_var->ruid = ++last_ruid;
7010 MR_DEPENDENCE_CLIQUE (ref) = clique;
7011 MR_DEPENDENCE_BASE (ref) = restrict_var->ruid;
7012 return true;
7013 }
7014 }
7015 return false;
7016}
7017
7018/* Compute the set of independend memory references based on restrict
7019 tags and their conservative propagation to the points-to sets. */
7020
7021static void
7022compute_dependence_clique (void)
7023{
7024 unsigned short clique = 0;
7025 unsigned short last_ruid = 0;
7026 for (unsigned i = 0; i < num_ssa_names; ++i)
7027 {
7028 tree ptr = ssa_name (i);
7029 if (!ptr || !POINTER_TYPE_P (TREE_TYPE (ptr)))
7030 continue;
7031
7032 /* Avoid all this when ptr is not dereferenced? */
7033 tree p = ptr;
7034 if (SSA_NAME_IS_DEFAULT_DEF (ptr)
7035 && (TREE_CODE (SSA_NAME_VAR (ptr)) == PARM_DECL
7036 || TREE_CODE (SSA_NAME_VAR (ptr)) == RESULT_DECL))
7037 p = SSA_NAME_VAR (ptr);
7038 varinfo_t vi = lookup_vi_for_tree (p);
7039 if (!vi)
7040 continue;
7041 vi = get_varinfo (find (vi->id));
7042 bitmap_iterator bi;
7043 unsigned j;
7044 varinfo_t restrict_var = NULL;
7045 EXECUTE_IF_SET_IN_BITMAP (vi->solution, 0, j, bi)
7046 {
7047 varinfo_t oi = get_varinfo (j);
7048 if (oi->is_restrict_var)
7049 {
7050 if (restrict_var)
7051 {
7052 if (dump_file && (dump_flags & TDF_DETAILS))
7053 {
7054 fprintf (dump_file, "found restrict pointed-to "
7055 "for ");
7056 print_generic_expr (dump_file, ptr, 0);
7057 fprintf (dump_file, " but not exclusively\n");
7058 }
7059 restrict_var = NULL;
7060 break;
7061 }
7062 restrict_var = oi;
7063 }
7064 /* NULL is the only other valid points-to entry. */
7065 else if (oi->id != nothing_id)
7066 {
7067 restrict_var = NULL;
7068 break;
7069 }
7070 }
7071 /* Ok, found that ptr must(!) point to a single(!) restrict
7072 variable. */
7073 /* ??? PTA isn't really a proper propagation engine to compute
7074 this property.
7075 ??? We could handle merging of two restricts by unifying them. */
7076 if (restrict_var)
7077 {
7078 /* Now look at possible dereferences of ptr. */
7079 imm_use_iterator ui;
355fe088 7080 gimple *use_stmt;
aa098165
RB
7081 FOR_EACH_IMM_USE_STMT (use_stmt, ui, ptr)
7082 {
7083 /* ??? Calls and asms. */
7084 if (!gimple_assign_single_p (use_stmt))
7085 continue;
7086 maybe_set_dependence_info (gimple_assign_lhs (use_stmt), ptr,
7087 clique, restrict_var, last_ruid);
7088 maybe_set_dependence_info (gimple_assign_rhs1 (use_stmt), ptr,
7089 clique, restrict_var, last_ruid);
7090 }
7091 }
7092 }
7093
7094 if (clique == 0)
7095 return;
7096
7097 /* Assign the BASE id zero to all accesses not based on a restrict
7098 pointer. That way they get disabiguated against restrict
7099 accesses but not against each other. */
7100 /* ??? For restricts derived from globals (thus not incoming
7101 parameters) we can't restrict scoping properly thus the following
7102 is too aggressive there. For now we have excluded those globals from
7103 getting into the MR_DEPENDENCE machinery. */
7104 basic_block bb;
7105 FOR_EACH_BB_FN (bb, cfun)
7106 for (gimple_stmt_iterator gsi = gsi_start_bb (bb);
7107 !gsi_end_p (gsi); gsi_next (&gsi))
7108 {
355fe088 7109 gimple *stmt = gsi_stmt (gsi);
aa098165
RB
7110 walk_stmt_load_store_ops (stmt, (void *)(uintptr_t)clique,
7111 visit_loadstore, visit_loadstore);
7112 }
7113}
5006671f
RG
7114
7115/* Compute points-to information for every SSA_NAME pointer in the
7116 current function and compute the transitive closure of escaped
7117 variables to re-initialize the call-clobber states of local variables. */
7118
7119unsigned int
7120compute_may_aliases (void)
7121{
25a6a873
RG
7122 if (cfun->gimple_df->ipa_pta)
7123 {
7124 if (dump_file)
7125 {
7126 fprintf (dump_file, "\nNot re-computing points-to information "
7127 "because IPA points-to information is available.\n\n");
7128
7129 /* But still dump what we have remaining it. */
7130 dump_alias_info (dump_file);
25a6a873
RG
7131 }
7132
7133 return 0;
7134 }
7135
5006671f
RG
7136 /* For each pointer P_i, determine the sets of variables that P_i may
7137 point-to. Compute the reachability set of escaped and call-used
7138 variables. */
7139 compute_points_to_sets ();
7140
7141 /* Debugging dumps. */
7142 if (dump_file)
824f71b9 7143 dump_alias_info (dump_file);
5006671f 7144
aa098165
RB
7145 /* Compute restrict-based memory disambiguations. */
7146 compute_dependence_clique ();
7147
5006671f
RG
7148 /* Deallocate memory used by aliasing data structures and the internal
7149 points-to solution. */
7150 delete_points_to_sets ();
7151
7152 gcc_assert (!need_ssa_update_p (cfun));
7153
7154 return 0;
7155}
7156
5006671f
RG
7157/* A dummy pass to cause points-to information to be computed via
7158 TODO_rebuild_alias. */
7159
27a4cd48
DM
7160namespace {
7161
7162const pass_data pass_data_build_alias =
7163{
7164 GIMPLE_PASS, /* type */
7165 "alias", /* name */
7166 OPTGROUP_NONE, /* optinfo_flags */
27a4cd48
DM
7167 TV_NONE, /* tv_id */
7168 ( PROP_cfg | PROP_ssa ), /* properties_required */
7169 0, /* properties_provided */
7170 0, /* properties_destroyed */
7171 0, /* todo_flags_start */
7172 TODO_rebuild_alias, /* todo_flags_finish */
5006671f
RG
7173};
7174
27a4cd48
DM
7175class pass_build_alias : public gimple_opt_pass
7176{
7177public:
c3284718
RS
7178 pass_build_alias (gcc::context *ctxt)
7179 : gimple_opt_pass (pass_data_build_alias, ctxt)
27a4cd48
DM
7180 {}
7181
7182 /* opt_pass methods: */
1a3d085c 7183 virtual bool gate (function *) { return flag_tree_pta; }
27a4cd48
DM
7184
7185}; // class pass_build_alias
7186
7187} // anon namespace
7188
7189gimple_opt_pass *
7190make_pass_build_alias (gcc::context *ctxt)
7191{
7192 return new pass_build_alias (ctxt);
7193}
7194
6b8ed145
RG
7195/* A dummy pass to cause points-to information to be computed via
7196 TODO_rebuild_alias. */
7197
27a4cd48
DM
7198namespace {
7199
7200const pass_data pass_data_build_ealias =
7201{
7202 GIMPLE_PASS, /* type */
7203 "ealias", /* name */
7204 OPTGROUP_NONE, /* optinfo_flags */
27a4cd48
DM
7205 TV_NONE, /* tv_id */
7206 ( PROP_cfg | PROP_ssa ), /* properties_required */
7207 0, /* properties_provided */
7208 0, /* properties_destroyed */
7209 0, /* todo_flags_start */
7210 TODO_rebuild_alias, /* todo_flags_finish */
6b8ed145
RG
7211};
7212
27a4cd48
DM
7213class pass_build_ealias : public gimple_opt_pass
7214{
7215public:
c3284718
RS
7216 pass_build_ealias (gcc::context *ctxt)
7217 : gimple_opt_pass (pass_data_build_ealias, ctxt)
27a4cd48
DM
7218 {}
7219
7220 /* opt_pass methods: */
1a3d085c 7221 virtual bool gate (function *) { return flag_tree_pta; }
27a4cd48
DM
7222
7223}; // class pass_build_ealias
7224
7225} // anon namespace
7226
7227gimple_opt_pass *
7228make_pass_build_ealias (gcc::context *ctxt)
7229{
7230 return new pass_build_ealias (ctxt);
7231}
7232
5006671f 7233
25a6a873
RG
7234/* IPA PTA solutions for ESCAPED. */
7235struct pt_solution ipa_escaped_pt
11924f8b 7236 = { true, false, false, false, false, false, false, false, NULL };
25a6a873 7237
39e2db00
JH
7238/* Associate node with varinfo DATA. Worker for
7239 cgraph_for_node_and_aliases. */
7240static bool
7241associate_varinfo_to_alias (struct cgraph_node *node, void *data)
7242{
67348ccc
DM
7243 if ((node->alias || node->thunk.thunk_p)
7244 && node->analyzed)
7245 insert_vi_for_tree (node->decl, (varinfo_t)data);
39e2db00
JH
7246 return false;
7247}
7248
4ee00913 7249/* Execute the driver for IPA PTA. */
c2924966 7250static unsigned int
4ee00913
DB
7251ipa_pta_execute (void)
7252{
7253 struct cgraph_node *node;
2c8326a5 7254 varpool_node *var;
25a6a873 7255 int from;
3e5937d7 7256
4ee00913 7257 in_ipa_mode = 1;
5c245b95 7258
4ee00913 7259 init_alias_vars ();
c58936b6 7260
1565af08
RG
7261 if (dump_file && (dump_flags & TDF_DETAILS))
7262 {
d52f5295 7263 symtab_node::dump_table (dump_file);
1565af08
RG
7264 fprintf (dump_file, "\n");
7265 }
7266
5c245b95 7267 /* Build the constraints. */
65c70e6b 7268 FOR_EACH_DEFINED_FUNCTION (node)
4ee00913 7269 {
27c2cfa6 7270 varinfo_t vi;
5c245b95
RG
7271 /* Nodes without a body are not interesting. Especially do not
7272 visit clones at this point for now - we get duplicate decls
7273 there for inline clones at least. */
70486010 7274 if (!node->has_gimple_body_p () || node->global.inlined_to)
5c245b95 7275 continue;
d52f5295 7276 node->get_body ();
5c245b95 7277
1565af08
RG
7278 gcc_assert (!node->clone_of);
7279
67348ccc
DM
7280 vi = create_function_info_for (node->decl,
7281 alias_get_name (node->decl));
d52f5295
ML
7282 node->call_for_symbol_thunks_and_aliases
7283 (associate_varinfo_to_alias, vi, true);
4ee00913 7284 }
5c245b95 7285
25a6a873 7286 /* Create constraints for global variables and their initializers. */
65c70e6b 7287 FOR_EACH_VARIABLE (var)
27c2cfa6 7288 {
67348ccc 7289 if (var->alias && var->analyzed)
cd35bcf7 7290 continue;
27c2cfa6 7291
67348ccc 7292 get_vi_for_tree (var->decl);
27c2cfa6 7293 }
25a6a873
RG
7294
7295 if (dump_file)
7296 {
7297 fprintf (dump_file,
7298 "Generating constraints for global initializers\n\n");
7299 dump_constraints (dump_file, 0);
7300 fprintf (dump_file, "\n");
7301 }
9771b263 7302 from = constraints.length ();
25a6a873 7303
65c70e6b 7304 FOR_EACH_DEFINED_FUNCTION (node)
4ee00913 7305 {
5c245b95
RG
7306 struct function *func;
7307 basic_block bb;
4ee00913 7308
5c245b95 7309 /* Nodes without a body are not interesting. */
d52f5295 7310 if (!node->has_gimple_body_p () || node->clone_of)
5c245b95 7311 continue;
c58936b6 7312
5c245b95 7313 if (dump_file)
27c2cfa6
RG
7314 {
7315 fprintf (dump_file,
fec39fa6 7316 "Generating constraints for %s", node->name ());
67348ccc 7317 if (DECL_ASSEMBLER_NAME_SET_P (node->decl))
27c2cfa6 7318 fprintf (dump_file, " (%s)",
960bfb69 7319 IDENTIFIER_POINTER
67348ccc 7320 (DECL_ASSEMBLER_NAME (node->decl)));
27c2cfa6
RG
7321 fprintf (dump_file, "\n");
7322 }
c58936b6 7323
67348ccc 7324 func = DECL_STRUCT_FUNCTION (node->decl);
628169e0 7325 gcc_assert (cfun == NULL);
726a989a 7326
1565af08
RG
7327 /* For externally visible or attribute used annotated functions use
7328 local constraints for their arguments.
7329 For local functions we see all callers and thus do not need initial
7330 constraints for parameters. */
67348ccc
DM
7331 if (node->used_from_other_partition
7332 || node->externally_visible
4b1db766
RB
7333 || node->force_output
7334 || node->address_taken)
194313e2 7335 {
628169e0 7336 intra_create_variable_infos (func);
194313e2
RG
7337
7338 /* We also need to make function return values escape. Nothing
7339 escapes by returning from main though. */
67348ccc 7340 if (!MAIN_NAME_P (DECL_NAME (node->decl)))
194313e2
RG
7341 {
7342 varinfo_t fi, rvi;
67348ccc 7343 fi = lookup_vi_for_tree (node->decl);
194313e2
RG
7344 rvi = first_vi_for_offset (fi, fi_result);
7345 if (rvi && rvi->offset == fi_result)
7346 {
7347 struct constraint_expr includes;
7348 struct constraint_expr var;
7349 includes.var = escaped_id;
7350 includes.offset = 0;
7351 includes.type = SCALAR;
7352 var.var = rvi->id;
7353 var.offset = 0;
7354 var.type = SCALAR;
7355 process_constraint (new_constraint (includes, var));
7356 }
7357 }
7358 }
4ee00913 7359
5c245b95
RG
7360 /* Build constriants for the function body. */
7361 FOR_EACH_BB_FN (bb, func)
7362 {
538dd0b7 7363 for (gphi_iterator gsi = gsi_start_phis (bb); !gsi_end_p (gsi);
5c245b95
RG
7364 gsi_next (&gsi))
7365 {
538dd0b7 7366 gphi *phi = gsi.phi ();
c58936b6 7367
ea057359 7368 if (! virtual_operand_p (gimple_phi_result (phi)))
628169e0 7369 find_func_aliases (func, phi);
5c245b95 7370 }
3e5937d7 7371
538dd0b7
DM
7372 for (gimple_stmt_iterator gsi = gsi_start_bb (bb); !gsi_end_p (gsi);
7373 gsi_next (&gsi))
5c245b95 7374 {
355fe088 7375 gimple *stmt = gsi_stmt (gsi);
3e5937d7 7376
628169e0
RB
7377 find_func_aliases (func, stmt);
7378 find_func_clobbers (func, stmt);
5c245b95
RG
7379 }
7380 }
c58936b6 7381
25a6a873
RG
7382 if (dump_file)
7383 {
7384 fprintf (dump_file, "\n");
7385 dump_constraints (dump_file, from);
7386 fprintf (dump_file, "\n");
7387 }
9771b263 7388 from = constraints.length ();
5c245b95 7389 }
c58936b6 7390
5c245b95
RG
7391 /* From the constraints compute the points-to sets. */
7392 solve_constraints ();
c58936b6 7393
25a6a873
RG
7394 /* Compute the global points-to sets for ESCAPED.
7395 ??? Note that the computed escape set is not correct
7396 for the whole unit as we fail to consider graph edges to
7397 externally visible functions. */
d394a308 7398 ipa_escaped_pt = find_what_var_points_to (get_varinfo (escaped_id));
25a6a873
RG
7399
7400 /* Make sure the ESCAPED solution (which is used as placeholder in
7401 other solutions) does not reference itself. This simplifies
7402 points-to solution queries. */
7403 ipa_escaped_pt.ipa_escaped = 0;
7404
7405 /* Assign the points-to sets to the SSA names in the unit. */
65c70e6b 7406 FOR_EACH_DEFINED_FUNCTION (node)
25a6a873
RG
7407 {
7408 tree ptr;
7409 struct function *fn;
7410 unsigned i;
25a6a873 7411 basic_block bb;
25a6a873
RG
7412
7413 /* Nodes without a body are not interesting. */
d52f5295 7414 if (!node->has_gimple_body_p () || node->clone_of)
25a6a873
RG
7415 continue;
7416
67348ccc 7417 fn = DECL_STRUCT_FUNCTION (node->decl);
25a6a873
RG
7418
7419 /* Compute the points-to sets for pointer SSA_NAMEs. */
9771b263 7420 FOR_EACH_VEC_ELT (*fn->gimple_df->ssa_names, i, ptr)
25a6a873
RG
7421 {
7422 if (ptr
7423 && POINTER_TYPE_P (TREE_TYPE (ptr)))
7424 find_what_p_points_to (ptr);
7425 }
7426
25a6a873
RG
7427 /* Compute the call-use and call-clobber sets for indirect calls
7428 and calls to external functions. */
7429 FOR_EACH_BB_FN (bb, fn)
7430 {
7431 gimple_stmt_iterator gsi;
7432
7433 for (gsi = gsi_start_bb (bb); !gsi_end_p (gsi); gsi_next (&gsi))
7434 {
538dd0b7 7435 gcall *stmt;
25a6a873 7436 struct pt_solution *pt;
92b3326b 7437 varinfo_t vi, fi;
25a6a873
RG
7438 tree decl;
7439
538dd0b7
DM
7440 stmt = dyn_cast <gcall *> (gsi_stmt (gsi));
7441 if (!stmt)
25a6a873
RG
7442 continue;
7443
92b3326b 7444 /* Handle direct calls to functions with body. */
25a6a873
RG
7445 decl = gimple_call_fndecl (stmt);
7446 if (decl
92b3326b
RB
7447 && (fi = lookup_vi_for_tree (decl))
7448 && fi->is_fn_info)
7449 {
7450 *gimple_call_clobber_set (stmt)
7451 = find_what_var_points_to
7452 (first_vi_for_offset (fi, fi_clobbers));
7453 *gimple_call_use_set (stmt)
7454 = find_what_var_points_to
7455 (first_vi_for_offset (fi, fi_uses));
7456 }
7457 /* Handle direct calls to external functions. */
7458 else if (decl)
25a6a873
RG
7459 {
7460 pt = gimple_call_use_set (stmt);
7461 if (gimple_call_flags (stmt) & ECF_CONST)
7462 memset (pt, 0, sizeof (struct pt_solution));
7463 else if ((vi = lookup_call_use_vi (stmt)) != NULL)
7464 {
d394a308 7465 *pt = find_what_var_points_to (vi);
25a6a873
RG
7466 /* Escaped (and thus nonlocal) variables are always
7467 implicitly used by calls. */
7468 /* ??? ESCAPED can be empty even though NONLOCAL
7469 always escaped. */
7470 pt->nonlocal = 1;
7471 pt->ipa_escaped = 1;
7472 }
7473 else
7474 {
7475 /* If there is nothing special about this call then
7476 we have made everything that is used also escape. */
7477 *pt = ipa_escaped_pt;
7478 pt->nonlocal = 1;
7479 }
7480
7481 pt = gimple_call_clobber_set (stmt);
7482 if (gimple_call_flags (stmt) & (ECF_CONST|ECF_PURE|ECF_NOVOPS))
7483 memset (pt, 0, sizeof (struct pt_solution));
7484 else if ((vi = lookup_call_clobber_vi (stmt)) != NULL)
7485 {
d394a308 7486 *pt = find_what_var_points_to (vi);
25a6a873
RG
7487 /* Escaped (and thus nonlocal) variables are always
7488 implicitly clobbered by calls. */
7489 /* ??? ESCAPED can be empty even though NONLOCAL
7490 always escaped. */
7491 pt->nonlocal = 1;
7492 pt->ipa_escaped = 1;
7493 }
7494 else
7495 {
7496 /* If there is nothing special about this call then
7497 we have made everything that is used also escape. */
7498 *pt = ipa_escaped_pt;
7499 pt->nonlocal = 1;
7500 }
7501 }
25a6a873 7502 /* Handle indirect calls. */
92b3326b
RB
7503 else if (!decl
7504 && (fi = get_fi_for_callee (stmt)))
25a6a873
RG
7505 {
7506 /* We need to accumulate all clobbers/uses of all possible
7507 callees. */
7508 fi = get_varinfo (find (fi->id));
7509 /* If we cannot constrain the set of functions we'll end up
7510 calling we end up using/clobbering everything. */
7511 if (bitmap_bit_p (fi->solution, anything_id)
7512 || bitmap_bit_p (fi->solution, nonlocal_id)
7513 || bitmap_bit_p (fi->solution, escaped_id))
7514 {
7515 pt_solution_reset (gimple_call_clobber_set (stmt));
7516 pt_solution_reset (gimple_call_use_set (stmt));
7517 }
7518 else
7519 {
7520 bitmap_iterator bi;
7521 unsigned i;
7522 struct pt_solution *uses, *clobbers;
7523
7524 uses = gimple_call_use_set (stmt);
7525 clobbers = gimple_call_clobber_set (stmt);
7526 memset (uses, 0, sizeof (struct pt_solution));
7527 memset (clobbers, 0, sizeof (struct pt_solution));
7528 EXECUTE_IF_SET_IN_BITMAP (fi->solution, 0, i, bi)
7529 {
7530 struct pt_solution sol;
7531
7532 vi = get_varinfo (i);
7533 if (!vi->is_fn_info)
7534 {
7535 /* ??? We could be more precise here? */
7536 uses->nonlocal = 1;
7537 uses->ipa_escaped = 1;
7538 clobbers->nonlocal = 1;
7539 clobbers->ipa_escaped = 1;
7540 continue;
7541 }
7542
7543 if (!uses->anything)
7544 {
d394a308
RB
7545 sol = find_what_var_points_to
7546 (first_vi_for_offset (vi, fi_uses));
25a6a873
RG
7547 pt_solution_ior_into (uses, &sol);
7548 }
7549 if (!clobbers->anything)
7550 {
d394a308
RB
7551 sol = find_what_var_points_to
7552 (first_vi_for_offset (vi, fi_clobbers));
25a6a873
RG
7553 pt_solution_ior_into (clobbers, &sol);
7554 }
7555 }
7556 }
7557 }
7558 }
7559 }
7560
7561 fn->gimple_df->ipa_pta = true;
7562 }
7563
5c245b95 7564 delete_points_to_sets ();
c58936b6 7565
4ee00913 7566 in_ipa_mode = 0;
5c245b95 7567
c2924966 7568 return 0;
4ee00913 7569}
c58936b6 7570
27a4cd48
DM
7571namespace {
7572
7573const pass_data pass_data_ipa_pta =
7574{
7575 SIMPLE_IPA_PASS, /* type */
7576 "pta", /* name */
7577 OPTGROUP_NONE, /* optinfo_flags */
27a4cd48
DM
7578 TV_IPA_PTA, /* tv_id */
7579 0, /* properties_required */
7580 0, /* properties_provided */
7581 0, /* properties_destroyed */
7582 0, /* todo_flags_start */
11924f8b 7583 0, /* todo_flags_finish */
4ee00913 7584};
27a4cd48
DM
7585
7586class pass_ipa_pta : public simple_ipa_opt_pass
7587{
7588public:
c3284718
RS
7589 pass_ipa_pta (gcc::context *ctxt)
7590 : simple_ipa_opt_pass (pass_data_ipa_pta, ctxt)
27a4cd48
DM
7591 {}
7592
7593 /* opt_pass methods: */
1a3d085c
TS
7594 virtual bool gate (function *)
7595 {
7596 return (optimize
7597 && flag_ipa_pta
7598 /* Don't bother doing anything if the program has errors. */
7599 && !seen_error ());
7600 }
7601
be55bfe6 7602 virtual unsigned int execute (function *) { return ipa_pta_execute (); }
27a4cd48
DM
7603
7604}; // class pass_ipa_pta
7605
7606} // anon namespace
7607
7608simple_ipa_opt_pass *
7609make_pass_ipa_pta (gcc::context *ctxt)
7610{
7611 return new pass_ipa_pta (ctxt);
7612}