PIPS
mappings.c File Reference
#include <stdio.h>
#include "genC.h"
#include "linear.h"
#include "ri.h"
#include "effects.h"
#include "ri-util.h"
#include "workspace-util.h"
#include "prettyprint.h"
#include "effects-util.h"
#include "constants.h"
#include "misc.h"
#include "arithmetique.h"
#include "vecteur.h"
#include "contrainte.h"
#include "effects-simple.h"
#include "effects-generic.h"
#include "transformer.h"
#include "semantics.h"
#include "preprocessor.h"
#include "properties.h"
+ Include dependency graph for mappings.c:

Go to the source code of this file.

Functions

static void reset_equivalence_equalities ()
 
transformer tf_equivalence_equalities_add (transformer tf)
 mappings.c More...
 
static void add_equivalence_equality (entity e, entity eq)
 
void add_equivalenced_values (entity e, entity eq, bool readonly)
 
static void add_interprocedural_value_entities (entity e)
 ???? More...
 
static void add_interprocedural_new_value_entity (entity e)
 
static void add_intraprocedural_value_entities_unconditionally (entity e)
 
void add_intraprocedural_value_entities (entity e)
 Use to be static, but may be called from ri_to_transformer. More...
 
void add_or_kill_equivalenced_variables (entity e, bool readonly)
 Look for variables equivalenced with e. More...
 
static void allocate_module_value_mappings (entity m)
 
void add_implicit_interprocedural_write_effects (entity al, list el)
 It is assumed that al is an abstract location that is written and which may conflict with effects in effect list el. More...
 
static bool entity_for_value_mapping_p (entity e)
 
static void add_intraprocedural_field_entities (reference r, list fl)
 
static void add_interprocedural_field_entities (reference r, list fl)
 
static void add_inter_or_intraprocedural_field_entities (reference r, list fl, bool intra_p)
 Check which fields combined with r would lead to analyzed values and recurse for fields which are struct themselves. More...
 
static void add_reference_values (reference r, bool write_p, bool global_p)
 
static void create_values_for_simple_effect (effect e, entity m)
 If effect e meets all conditions to represent a location whose value could and should be analyzed, create the related values. More...
 
static bool add_values_for_simple_effects_of_statement (statement s)
 Declare value entities necessary to analyze locations defined by proper effects. More...
 
static void values_for_current_module_intraprocedural_simple_effects (void)
 
void module_to_value_mappings (entity m)
 void module_to_value_mappings(entity m): build hash tables between variables and values (old, new and intermediate), and between values and names for module m, as well as equivalence equalities More...
 
bool value_mappings_compatible_vector_p (Pvecteur iv)
 transform a vector based on variable entities into a vector based on new value entities when possible; does nothing most of the time; does a little in the presence of equivalenced variables More...
 
list variables_to_values (list list_mod)
 
list variable_to_values (entity e)
 
list dynamic_variables_to_values (list list_mod)
 Build the list of values to be projected when the declaration list list_mod is no longer valid because a block is closed/left. More...
 
list variables_to_old_values (list list_mod)
 
void variables_to_new_values (Pvecteur v)
 replace variables by new values which is necessary for equivalenced variables More...
 
void upwards_vect_rename (Pvecteur v, transformer post)
 Renaming of variables in v according to transformations occuring later. More...
 

Variables

static Pcontrainte equivalence_equalities = CONTRAINTE_UNDEFINED
 Variable value mappings package. More...
 

Function Documentation

◆ add_equivalence_equality()

static void add_equivalence_equality ( entity  e,
entity  eq 
)
static

assumes e and eq are different

Strange: there is no macro to chain a contrainte on a list of contrainte

Definition at line 93 of file mappings.c.

94 {
95  /* assumes e and eq are different */
96  Pvecteur v = vect_new((Variable) e, 1);
97  Pcontrainte c;
98 
99  vect_add_elem(&v, (Variable) eq, -1);
100  c = contrainte_make(v);
101  /* Strange: there is no macro to chain a contrainte on a list of
102  contrainte */
105 }
Pcontrainte contrainte_make(Pvecteur pv)
Pcontrainte contrainte_make(Pvecteur pv): allocation et initialisation d'une contrainte avec un vecte...
Definition: alloc.c:73
Pcontrainte eq
element du vecteur colonne du systeme donne par l'analyse
Definition: sc_gram.c:108
static Pcontrainte equivalence_equalities
Variable value mappings package.
Definition: mappings.c:74
struct Scontrainte * succ
le type des coefficients dans les vecteurs: Value est defini dans le package arithmetique
Definition: vecteur-local.h:89
void * Variable
arithmetique is a requirement for vecteur, but I do not want to inforce it in all pips files....
Definition: vecteur-local.h:60
Pvecteur vect_new(Variable var, Value coeff)
Pvecteur vect_new(Variable var,Value coeff): allocation d'un vecteur colineaire au vecteur de base va...
Definition: alloc.c:110
void vect_add_elem(Pvecteur *pvect, Variable var, Value val)
void vect_add_elem(Pvecteur * pvect, Variable var, Value val): addition d'un vecteur colineaire au ve...
Definition: unaires.c:72

References contrainte_make(), eq, equivalence_equalities, Scontrainte::succ, vect_add_elem(), and vect_new().

Referenced by add_equivalenced_values().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ add_equivalenced_values()

void add_equivalenced_values ( entity  e,
entity  eq,
bool  readonly 
)

e and eq are assumed to be different scalar variables of the same analyzed type

eq will be seen as e, as far as values are concerned, but for printing

new equalities e::new == eq::new and e::old == eq::old have to be added to the preconditions just before they are stored; since eq should never be written no eq::old should appear; thus the first equation is enough

By definition, all variables are conflicting with themselves but this is assumed filtered out above.

add the equivalence equations

Parameters
eqq
readonlyeadonly

Definition at line 107 of file mappings.c.

108 {
109  /* e and eq are assumed to be different scalar variables of the same
110  analyzed type */
111  /* eq will be seen as e, as far as values are concerned,
112  but for printing */
113  /* new equalities e#new == eq#new and e#old == eq#old
114  have to be added to the preconditions just before they
115  are stored; since eq should never be written no eq#old
116  should appear; thus the first equation is enough */
117 
118  /* By definition, all variables are conflicting
119  with themselves but this is assumed filtered out above. */
120 
121  pips_assert("e is not eq", e!=eq);
122 
123  add_synonym_values(e, eq, readonly);
124  /* add the equivalence equations */
126 
127 }
#define pips_assert(what, predicate)
common macros, two flavors depending on NDEBUG
Definition: misc-local.h:172
static void add_equivalence_equality(entity e, entity eq)
Definition: mappings.c:93
void add_synonym_values(entity, entity, bool)
Definition: value.c:1578

References add_equivalence_equality(), add_synonym_values(), eq, and pips_assert.

Referenced by add_or_kill_equivalenced_variables().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ add_implicit_interprocedural_write_effects()

void add_implicit_interprocedural_write_effects ( entity  al,
list  el 
)

It is assumed that al is an abstract location that is written and which may conflict with effects in effect list el.

If there is a conflict, than the variable associated to this effect is written.

It should be generalized to non-interprocedural cases.

Parameters
all
ell

Definition at line 382 of file mappings.c.

383 {
384  type alt = entity_type(al);
385 
386  if(type_unknown_p(alt)
387  || type_area_p(alt) // FI: Let's agree about typing issues!
388  || get_bool_property("ALIASING_ACROSS_TYPES")
389  || overloaded_type_p(alt)) {
390  FOREACH(EFFECT, ef, el) {
392  entity v = reference_variable(r);
393 
395  && entities_may_conflict_p(al, v)
398  }
399  }
400  }
401  else {
402  FOREACH(EFFECT, ef, el) {
404  entity v = reference_variable(r);
405  type vt = ultimate_type(entity_type(v));
406 
408  && entities_may_conflict_p(al, v)
409  && type_equal_p(alt, vt)) {
411  pips_internal_error("Effects cannot be related to dummy parameters.");
413  }
414  }
415  }
416 }
bool entity_abstract_location_p(entity al)
#define effect_any_reference(e)
FI: cannot be used as a left hand side.
#define EFFECT(x)
EFFECT.
Definition: effects.h:608
bool get_bool_property(const string)
FC 2015-07-20: yuk, moved out to prevent an include cycle dependency include "properties....
bool entities_may_conflict_p(entity e1, entity e2)
Check if two entities may conflict.
Definition: conflicts.c:984
#define FOREACH(_fe_CASTER, _fe_item, _fe_list)
Apply/map an instruction block on all the elements of a list.
Definition: newgen_list.h:179
#define pips_internal_error
Definition: misc-local.h:149
bool dummy_parameter_entity_p(entity p)
is p a dummy parameter?
Definition: entity.c:1941
type ultimate_type(type)
Definition: type.c:3466
bool type_equal_p(type, type)
Definition: type.c:547
bool overloaded_type_p(type)
Returns true if t is a variable type with a basic overloaded.
Definition: type.c:2666
#define type_unknown_p(x)
Definition: ri.h:2956
#define reference_variable(x)
Definition: ri.h:2326
#define type_area_p(x)
Definition: ri.h:2944
#define entity_type(x)
Definition: ri.h:2792
static void add_interprocedural_value_entities(entity e)
????
Definition: mappings.c:133
bool analyzable_scalar_entity_p(entity)
The entity type is one of the analyzed types.
Definition: value.c:471

References add_interprocedural_value_entities(), analyzable_scalar_entity_p(), dummy_parameter_entity_p(), EFFECT, effect_any_reference, entities_may_conflict_p(), entity_abstract_location_p(), entity_type, FOREACH, get_bool_property(), overloaded_type_p(), pips_internal_error, reference_variable, type_area_p, type_equal_p(), type_unknown_p, and ultimate_type().

Referenced by module_to_value_mappings().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ add_inter_or_intraprocedural_field_entities()

static void add_inter_or_intraprocedural_field_entities ( reference  r,
list  fl,
bool  intra_p 
)
static

Check which fields combined with r would lead to analyzed values and recurse for fields which are struct themselves.

A similar function would be useful to handle struct assignments in semantics or points-to or effect analysis.

Definition at line 435 of file mappings.c.

436 {
437  FOREACH(ENTITY, f, fl) {
439  if(analyzed_type_p(t)) {
441  entity l = make_location_entity(fr); // Do not free fr as it should be the initial value
442  if(!entity_has_values_p(l)) {
443  if(intra_p)
445  else
447  }
448  }
449  else if(struct_type_p(t)) {
451  list nfl = struct_type_to_fields(t);
452  if(intra_p)
454  else
456  free_reference(fr);
457  }
458  }
459 }
void free_reference(reference p)
Definition: ri.c:2050
reference copy_reference(reference p)
REFERENCE.
Definition: ri.c:2047
entity make_location_entity(reference)
locations.c
Definition: locations.c:274
reference simple_reference_add_field_dimension(reference, entity)
Do not check anything, just add f as a last subscript.
Definition: effects.c:1581
int f(int off1, int off2, int n, float r[n], float a[n], float b[n])
Definition: offsets.c:15
type entity_basic_concrete_type(entity)
retrieves or computes and then returns the basic concrete type of an entity
Definition: type.c:3677
list struct_type_to_fields(type)
Definition: type.c:5798
bool struct_type_p(type)
Returns true if t is of type derived and if the derived type is a struct.
Definition: type.c:3121
#define ENTITY(x)
ENTITY.
Definition: ri.h:2755
void add_intraprocedural_value_entities(entity e)
Use to be static, but may be called from ri_to_transformer.
Definition: mappings.c:181
static void add_interprocedural_field_entities(reference r, list fl)
Definition: mappings.c:466
static void add_intraprocedural_field_entities(reference r, list fl)
Definition: mappings.c:461
The structure used to build lists in NewGen.
Definition: newgen_list.h:41
bool entity_has_values_p(entity)
This function could be made more robust by checking the storage of e.
Definition: value.c:911
bool analyzed_type_p(type)
The type t is one of the analyzed types.
Definition: value.c:367

References add_interprocedural_field_entities(), add_interprocedural_value_entities(), add_intraprocedural_field_entities(), add_intraprocedural_value_entities(), analyzed_type_p(), copy_reference(), ENTITY, entity_basic_concrete_type(), entity_has_values_p(), f(), FOREACH, free_reference(), make_location_entity(), simple_reference_add_field_dimension(), struct_type_p(), and struct_type_to_fields().

Referenced by add_interprocedural_field_entities(), and add_intraprocedural_field_entities().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ add_interprocedural_field_entities()

static void add_interprocedural_field_entities ( reference  r,
list  fl 
)
static

Definition at line 466 of file mappings.c.

467 {
469 }
static void add_inter_or_intraprocedural_field_entities(reference r, list fl, bool intra_p)
Check which fields combined with r would lead to analyzed values and recurse for fields which are str...
Definition: mappings.c:435

References add_inter_or_intraprocedural_field_entities().

Referenced by add_inter_or_intraprocedural_field_entities(), and module_to_value_mappings().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ add_interprocedural_new_value_entity()

static void add_interprocedural_new_value_entity ( entity  e)
static

CA: information on aliasing variables erased

Definition at line 152 of file mappings.c.

153 {
154  pips_debug(8,"add_interprocedural_new_value_entities" "for %s\n",
155  entity_name(e));
156  if(!entity_has_values_p(e)) {
158  if((a=value_alias(e))==entity_undefined){
159  add_new_value(e);
160  /* CA: information on aliasing variables erased*/
162  }
163  else {
164  add_new_alias_value(e,a);
165  }
166  }
167 }
#define pips_debug
these macros use the GNU extensions that allow variadic macros, including with an empty list.
Definition: misc-local.h:145
#define entity_undefined
Definition: ri.h:2761
#define entity_name(x)
Definition: ri.h:2790
void add_or_kill_equivalenced_variables(entity e, bool readonly)
Look for variables equivalenced with e.
Definition: mappings.c:204
void add_new_value(entity)
Definition: value.c:1386
entity value_alias(entity)
Static aliasing.
Definition: value.c:1729
void add_new_alias_value(entity, entity)
Definition: value.c:1396

References add_new_alias_value(), add_new_value(), add_or_kill_equivalenced_variables(), entity_has_values_p(), entity_name, entity_undefined, pips_debug, and value_alias().

Referenced by add_reference_values(), and module_to_value_mappings().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ add_interprocedural_value_entities()

static void add_interprocedural_value_entities ( entity  e)
static

????

void add_interprocedural_value_entities

Definition at line 133 of file mappings.c.

134 {
135  pips_debug(8,"for %s\n", entity_name(e));
136  if(!entity_has_values_p(e)) {
138  if((a=value_alias(e))==entity_undefined){
139  add_new_value(e);
140  add_old_value(e);
143  }
144  else {
145  add_new_alias_value(e,a);
146  add_old_alias_value(e,a);
148  }
149  }
150 }
void add_intermediate_alias_value(entity, entity)
Definition: value.c:1495
void add_old_alias_value(entity, entity)
Definition: value.c:1463
void add_intermediate_value(entity)
Definition: value.c:1476
void add_old_value(entity)
Definition: value.c:1440

References add_intermediate_alias_value(), add_intermediate_value(), add_new_alias_value(), add_new_value(), add_old_alias_value(), add_old_value(), add_or_kill_equivalenced_variables(), entity_has_values_p(), entity_name, entity_undefined, pips_debug, and value_alias().

Referenced by add_implicit_interprocedural_write_effects(), add_inter_or_intraprocedural_field_entities(), add_reference_values(), and module_to_value_mappings().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ add_intraprocedural_field_entities()

static void add_intraprocedural_field_entities ( reference  r,
list  fl 
)
static

Definition at line 461 of file mappings.c.

462 {
464 }

References add_inter_or_intraprocedural_field_entities().

Referenced by add_inter_or_intraprocedural_field_entities(), and module_to_value_mappings().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ add_intraprocedural_value_entities()

void add_intraprocedural_value_entities ( entity  e)

Use to be static, but may be called from ri_to_transformer.

void add_intraprocedural_value_entities(entity e)

Definition at line 181 of file mappings.c.

182 {
184 
185  pips_debug(8, "for %s\n", entity_name(e));
186  if(!entity_has_values_p(e) && type_variable_p(ut) ) {
188  }
189 }
#define type_variable_p(x)
Definition: ri.h:2947
static void add_intraprocedural_value_entities_unconditionally(entity e)
Definition: mappings.c:169

References add_intraprocedural_value_entities_unconditionally(), entity_basic_concrete_type(), entity_has_values_p(), entity_name, pips_debug, and type_variable_p.

Referenced by add_inter_or_intraprocedural_field_entities(), add_reference_values(), and module_to_value_mappings().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ add_intraprocedural_value_entities_unconditionally()

static void add_intraprocedural_value_entities_unconditionally ( entity  e)
static

Definition at line 169 of file mappings.c.

170 {
171  pips_debug(8, "for %s\n", entity_name(e));
172  add_new_value(e);
176 }
void add_local_old_value(entity)
Definition: value.c:1509
void add_local_intermediate_value(entity)
Definition: value.c:1526

References add_local_intermediate_value(), add_local_old_value(), add_new_value(), add_or_kill_equivalenced_variables(), entity_name, and pips_debug.

Referenced by add_intraprocedural_value_entities(), and module_to_value_mappings().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ add_or_kill_equivalenced_variables()

void add_or_kill_equivalenced_variables ( entity  e,
bool  readonly 
)

Look for variables equivalenced with e.

e already has values associated although it may not be a canonical representative of its equivalence class...

Forget dynamic aliasing between formal parameters.

Handle intraprocedural aliasing only.

Do not handle interprocedural aliasing: this does not seem to be the right place because too many synonyms, not visible from the current procedure, are introduced (global_shared = area_layout(type_area(t));

potential canonical representative for all variables equivalenced with e

Is e intraprocedurally equivalenced/aliased with an array or a non-analyzable variable which would make e and all its aliased variables unanalyzable?

Since the equivalence is reflexive, no need to process e==eq again.

Since the equivalence is symetrical, eq may have been processed already.

this approximate test by Pierre Jouvelot should be replaced by an exact test but it does not really matter; an exact test could only be useful in presence of arrays; and in presence of arrays we do nothing here

if it's not, go ahead: it exists at least one eq such that e and eq are different, are scalars and have the same analyzable type. All eq conflicting with e meets these conditions.

Declare values for the canonical representative re

Give values to re which should have none and remove values of e. Assume that e and re are local variables.

If it is intra-procedurally equivalenced, set the synonyms as read-only variables

if eq is an integer scalar variable it does not only have a destructive effect

Variable e is equivalenced with an array or a non-integer variable and cannot be analyzed; it must be removed from the hash tables.

semantics analysis should be performed on this kind of variable but it has probably been eliminated earlier; no equivalence possible anyway!

to be dealt with later if we assume non-standard dynamic aliasing between formal parameters

Parameters
readonlyeadonly

Definition at line 204 of file mappings.c.

205 {
206  storage s = entity_storage(e);
207  entity re = e; /* potential canonical representative for all variables equivalenced with e */
208 
209  pips_debug(8, "Begin for %s %s\n", entity_name(e),
210  readonly? "readonly" : "read/write");
211 
212  pips_assert("e has values", entity_has_values_p(e));
213 
214  if(storage_ram_p(s)) {
215  list local_shared = ram_shared(storage_ram(s));
216  bool array_equivalenced = false;
217  entity sec = ram_section(storage_ram(s));
218  type t = entity_type(sec);
219  list ce = list_undefined;
220 
221  pips_assert("t is an area", type_area_p(t));
222 
223  /* Is e intraprocedurally equivalenced/aliased with an array or a
224  * non-analyzable variable which would make e and all its aliased
225  * variables unanalyzable? */
226  for(ce=local_shared; !ENDP(ce); POP(ce)) {
227  entity eq = ENTITY(CAR(ce));
228 
229  /* Since the equivalence is reflexive, no need to process e==eq again. */
230  if(e==eq) continue;
231  /* Since the equivalence is symetrical, eq may have been processed
232  already. */
233  if(entity_has_values_p(eq)) continue;
234 
235  /* this approximate test by Pierre Jouvelot should be
236  replaced by an exact test but it does not really matter;
237  an exact test could only be useful in presence of arrays;
238  and in presence of arrays we do nothing here */
240  pips_user_warning("Values for variable %s are not analyzed because "
241  "%s is aliased with scalar variable %s with non "
242  "analyzed type %s or with array variable\n",
245  array_equivalenced = true;
246  break;
247  }
248 
251  pips_user_warning("Values for variable %s of type %s are not analyzed because "
252  "%s is aliased with scalar variable %s with different "
253  "type %s\n",
257  array_equivalenced = true;
258  break;
259  }
260  }
261  if(entities_may_conflict_p(e, eq) && strcmp(entity_name(eq), entity_name(re))<0) {
262  re = eq;
263  }
264  }
265 
266  /* if it's not, go ahead: it exists at least one eq such that e and eq
267  are different, are scalars and have the same analyzable type. All
268  eq conflicting with e meets these conditions. */
269  if(!array_equivalenced) {
270 
271  /* Declare values for the canonical representative re */
272  if(e!=re) {
273  pips_debug(8, "Canonical representative is %s\n", entity_local_name(re));
274  /* Give values to re which should have none and remove values of
275  e. Assume that e and re are local variables. */
276  pips_assert("re has no values", !entity_has_values_p(re));
277  remove_entity_values(e, readonly);
278  add_new_value(re);
279  if(!readonly) {
280  add_old_value(re);
282  }
283  }
284 
285  /* If it is intra-procedurally equivalenced, set the synonyms as
286  * read-only variables
287  */
288  for(ce=local_shared; !ENDP(ce); POP(ce)) {
289  entity eq = ENTITY(CAR(ce));
290 
291  if(re==eq) continue;
292  if(entities_may_conflict_p(re, eq)) {
293  /* if eq is an integer scalar variable it does not
294  only have a destructive effect */
295  add_equivalenced_values(re, eq, readonly);
296  }
297  }
298  }
299  else {
300  /* Variable e is equivalenced with an array or a non-integer
301  * variable and cannot be analyzed; it must be removed from
302  * the hash tables.
303  */
304  remove_entity_values(e, readonly);
305  }
306  }
307  else if(storage_return_p(s)) {
308  /* semantics analysis should be performed on this kind of variable
309  but it has probably been eliminated earlier; no equivalence
310  possible anyway! */
311  // FI: the warning message is not useful. See formal parameters
312  // pips_user_warning("storage return\n");
313  ;
314  }
315  else if(storage_formal_p(s))
316  /* to be dealt with later if we assume non-standard dynamic
317  aliasing between formal parameters */
318  ;
319  else
320  pips_internal_error("unproper storage = %d (%s), for entity %s", storage_tag(s), storage_to_string(s), entity_name(e));
321 
322  pips_debug(8, "End for %s\n", entity_name(e));
323 }
#define ENDP(l)
Test if a list is empty.
Definition: newgen_list.h:66
#define POP(l)
Modify a list pointer to point on the next element of the list.
Definition: newgen_list.h:59
#define CAR(pcons)
Get the value of the first element of a list.
Definition: newgen_list.h:92
#define list_undefined
Undefined list definition :-)
Definition: newgen_list.h:69
#define pips_user_warning
Definition: misc-local.h:146
const char * entity_local_name(entity e)
entity_local_name modified so that it does not core when used in vect_fprint, since someone thought t...
Definition: entity.c:453
string storage_to_string(storage s)
Definition: entity.c:2030
string type_to_string(const type)
type.c
Definition: type.c:51
#define storage_formal_p(x)
Definition: ri.h:2522
#define storage_tag(x)
Definition: ri.h:2515
#define entity_storage(x)
Definition: ri.h:2794
#define storage_ram_p(x)
Definition: ri.h:2519
#define ram_section(x)
Definition: ri.h:2249
#define storage_ram(x)
Definition: ri.h:2521
#define ram_shared(x)
Definition: ri.h:2253
#define storage_return_p(x)
Definition: ri.h:2516
void add_equivalenced_values(entity e, entity eq, bool readonly)
Definition: mappings.c:107
void remove_entity_values(entity, bool)
Definition: value.c:1545

References add_equivalenced_values(), add_intermediate_value(), add_new_value(), add_old_value(), analyzable_scalar_entity_p(), CAR, ENDP, entities_may_conflict_p(), ENTITY, entity_has_values_p(), entity_local_name(), entity_name, entity_storage, entity_type, eq, list_undefined, pips_assert, pips_debug, pips_internal_error, pips_user_warning, POP, ram_section, ram_shared, remove_entity_values(), storage_formal_p, storage_ram, storage_ram_p, storage_return_p, storage_tag, storage_to_string(), type_area_p, type_equal_p(), and type_to_string().

Referenced by add_interprocedural_new_value_entity(), add_interprocedural_value_entities(), and add_intraprocedural_value_entities_unconditionally().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ add_reference_values()

static void add_reference_values ( reference  r,
bool  write_p,
bool  global_p 
)
static

Definition at line 470 of file mappings.c.

471 {
473  if(global_p) {
474  if(write_p)
476  else
478  }
479  else {
480  if(write_p)
482  else
484  }
485 }
static void add_interprocedural_new_value_entity(entity e)
Definition: mappings.c:152

References add_interprocedural_new_value_entity(), add_interprocedural_value_entities(), add_intraprocedural_value_entities(), and make_location_entity().

Referenced by create_values_for_simple_effect().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ add_values_for_simple_effects_of_statement()

static bool add_values_for_simple_effects_of_statement ( statement  s)
static

Declare value entities necessary to analyze locations defined by proper effects.

Definition at line 528 of file mappings.c.

529 {
530  // #include "effects-generic.h"
534 
535  if(!get_bool_property("CONSTANT_PATH_EFFECTS")) {
536  list el = effects_effects(fx);
537  FOREACH(EFFECT, e, el) {
538  list cel = list_undefined;
539  if(pt_to_list_undefined_p()) {
540  // FI: use of a generic effect function
541  effect (*effect_dup_func_save)(effect eff) = effect_dup_func;
542  effect (*reference_to_effect_func_save)(reference, action, bool) = reference_to_effect_func;
546  effect_dup_func = effect_dup_func_save;
547  reference_to_effect_func = reference_to_effect_func_save;
548  }
549  else {
550  // FI: hopefully, the context is not used for simple effects...
553  }
554  FOREACH(EFFECT, ce, cel)
557  FOREACH(EFFECT, ce, cel)
560  gen_full_free_list(cel);
561  }
562  }
563  else {
564  list el = effects_effects(fx);
565  FOREACH(EFFECT, e, el) {
568  }
569  FOREACH(EFFECT, e, el) {
572  }
573  }
574 
575  return true;
576 }
effect copy_effect(effect p)
EFFECT.
Definition: effects.c:448
struct _newgen_struct_reference_ * reference
Definition: compsec.h:14
struct _newgen_struct_action_ * action
Definition: compsec.h:21
struct _newgen_struct_effect_ * effect
Definition: dg.h:21
effects load_proper_rw_effects(statement)
list effect_to_constant_path_effects_with_no_pointer_information(effect)
effect(* reference_to_effect_func)(reference, action, bool)
effect(* effect_dup_func)(effect eff)
effect reference_to_reference_effect(reference, action, bool)
list effect_to_constant_path_effects_with_points_to(effect, statement, transformer)
Definition: eval.c:284
#define effect_write_p(eff)
bool store_effect_p(effect)
Definition: effects.c:1062
bool pt_to_list_undefined_p(void)
points_to.c
bool store_independent_effect_p(effect)
Does this effect define the same set of memory locations regardless of the current (environment and) ...
Definition: effects.c:636
#define effects_effects(x)
Definition: effects.h:710
void gen_full_free_list(list l)
Definition: genClib.c:1023
entity get_current_module_entity(void)
Get the entity of the current module.
Definition: static.c:85
int bool
we cannot use an enum or stdbool because we need to be compatible with newgen, thus boolean need to h...
Definition: newgen_types.h:78
#define transformer_undefined
Definition: ri.h:2847
static void create_values_for_simple_effect(effect e, entity m)
If effect e meets all conditions to represent a location whose value could and should be analyzed,...
Definition: mappings.c:490
Definition: delay.c:253

References copy_effect(), create_values_for_simple_effect(), EFFECT, effect_dup_func, effect_to_constant_path_effects_with_no_pointer_information(), effect_to_constant_path_effects_with_points_to(), effect_write_p, effects_effects, FOREACH, gen_full_free_list(), get_bool_property(), get_current_module_entity(), list_undefined, load_proper_rw_effects(), pt_to_list_undefined_p(), reference_to_effect_func, reference_to_reference_effect(), store_effect_p(), store_independent_effect_p(), and transformer_undefined.

Referenced by values_for_current_module_intraprocedural_simple_effects().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ allocate_module_value_mappings()

static void allocate_module_value_mappings ( entity  m)
static

this routine tries to estimate the sizes of the hash tables, although the hashtable package has enlarging capability; its usefulness is limited... but keep at least hash table allocations!

FI: not a good estimate for C codes with local delcarations

count interprocedural effects on scalar integer variables before allocating hash tables; too many entries might be expected because the same variable could appear many times, at least twice, once in a read effect and once in a write effect; entries for arrays equivalenced with scalar variables are ignored; some slack is added before allocating the hash tables; module_inter_effects are (should be) included into module_intra_effects

add 50 % slack for underestimation (some more slack will be added by the hash package

the hash package does not like very small sizes

overapproximate intermediate value number

allocate hash tables

Definition at line 325 of file mappings.c.

326 {
327  /* this routine tries to estimate the sizes of the hash tables,
328  although the hashtable package has enlarging capability;
329  its usefulness is limited... but keep at least hash table
330  allocations! */
331 
332  /* FI: not a good estimate for C codes with local delcarations */
333  list module_intra_effects = load_module_intraprocedural_effects(m);
334  int old_value_number = 0;
335  int intermediate_value_number = 0;
336  int new_value_number = 0;
337 
338  /* count interprocedural effects on scalar integer variables
339  before allocating hash tables; too many entries might be
340  expected because the same variable could appear many times,
341  at least twice, once in a read effect and once in a write
342  effect; entries for arrays equivalenced with scalar variables
343  are ignored; some slack is added before allocating the hash
344  tables; module_inter_effects are (should be) included into
345  module_intra_effects */
346  FOREACH(EFFECT, ef, module_intra_effects)
347  {
349  action a = effect_action(ef);
350  // The estimation is poor when abstract effects occur
352  new_value_number++;
353  if(action_write_p(a))
354  old_value_number++;
355  }
356 
357  /* add 50 % slack for underestimation (some more slack will be added
358  by the hash package */
359  new_value_number *= 3; new_value_number /= 2;
360  old_value_number *= 3; old_value_number /= 2;
361  /* the hash package does not like very small sizes */
362  new_value_number = MAX(10,new_value_number);
363  old_value_number = MAX(10,old_value_number);
364  /* overapproximate intermediate value number */
365  intermediate_value_number = old_value_number;
366 
367  pips_debug(8, "old_value_number = %d\n", old_value_number);
368  pips_debug(8, "new_value_number = %d\n", new_value_number);
369 
370  /* allocate hash tables */
371  allocate_value_mappings(new_value_number, old_value_number,
372  intermediate_value_number);
373 }
list load_module_intraprocedural_effects(entity e)
#define effect_action(x)
Definition: effects.h:642
#define action_write_p(x)
Definition: effects.h:314
bool integer_scalar_entity_p(entity)
integer_scalar_entity_p() is obsolete; use entity_integer_scalar_p()
Definition: variable.c:1137
#define MAX(x, y)
Definition: string.c:110
void allocate_value_mappings(int, int, int)
Definition: value.c:1165

References action_write_p, allocate_value_mappings(), EFFECT, effect_action, effect_any_reference, FOREACH, integer_scalar_entity_p(), load_module_intraprocedural_effects(), MAX, pips_debug, and reference_variable.

Referenced by module_to_value_mappings().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ create_values_for_simple_effect()

static void create_values_for_simple_effect ( effect  e,
entity  m 
)
static

If effect e meets all conditions to represent a location whose value could and should be analyzed, create the related values.

|| storage_return_p(vs)

Definition at line 490 of file mappings.c.

491 {
492  if(store_effect_p(e)) {
495  entity v = reference_variable(r);
496  if(entity_variable_p(v)
500  storage vs = entity_storage(v);
501  if(storage_ram_p(vs)
502  || storage_formal_p(vs)
503  /* || storage_return_p(vs)*/) {
504  // atomic_points_to_reference_p(r)
505  // scalar_reference_p(r))
507  if(analyzed_type_p(t)) { // implies scalar_type_p(t)
508  // FI: the effect may be local to the module or visible outside;
509  // the effect may be a read or a write
510  bool write_p = action_write_p(effect_action(e));
511  bool global_p = global_variable_p(v)
514  add_reference_values(r, write_p, global_p);
515  }
516  }
517  }
518  }
519  }
520  return;
521 }
type points_to_reference_to_concrete_type(reference)
Definition: type.c:685
bool generic_atomic_points_to_reference_p(reference, bool)
Is it a unique concrete memory location?
Definition: points_to.c:489
#define entity_variable_p(e)
An entity_variable_p(e) may hide a typedef and hence a functional type.
bool effects_package_entity_p(entity e)
checks if an entity is an IO_EFFECTS_PACKAGE_NAME, a MALLOC_EFFECTS_NAME or a RAND_EFFECTS_PACKAGE_NA...
Definition: entity.c:1181
bool formal_context_variable_p(entity)
Such pseudo-variables are generated by the points-to analysis.
Definition: variable.c:1535
bool variable_is_a_module_formal_parameter_p(entity, entity)
Definition: variable.c:1547
bool place_holder_variable_p(entity)
Definition: variable.c:2069
bool global_variable_p(entity)
Is v a global variable such as "int i;".
Definition: variable.c:1510
static void add_reference_values(reference r, bool write_p, bool global_p)
Definition: mappings.c:470

References action_write_p, add_reference_values(), analyzed_type_p(), effect_action, effect_any_reference, effects_package_entity_p(), entity_abstract_location_p(), entity_storage, entity_variable_p, formal_context_variable_p(), generic_atomic_points_to_reference_p(), global_variable_p(), place_holder_variable_p(), points_to_reference_to_concrete_type(), reference_variable, storage_formal_p, storage_ram_p, store_effect_p(), and variable_is_a_module_formal_parameter_p().

Referenced by add_values_for_simple_effects_of_statement().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ dynamic_variables_to_values()

list dynamic_variables_to_values ( list  list_mod)

Build the list of values to be projected when the declaration list list_mod is no longer valid because a block is closed/left.

Values for static variables are preserved. Values for heap variables also, in case their values are computed in the future...

This may not be the best algorithm when locations are used because the list of locations may be much longer, especially for arrays, than the list of values appearing in the transformer.

Parameters
list_modist_mod

Definition at line 1007 of file mappings.c.

1008 {
1009  list list_val = NIL;
1010 
1011  FOREACH(ENTITY, e, list_mod) {
1012  if(entity_has_values_p(e)
1013  && (variable_dynamic_p(e) || variable_stack_p(e))) {
1014  entity v_old = entity_to_old_value(e);
1015  entity v_new = entity_to_new_value(e);
1016 
1017  list_val = CONS(ENTITY, v_old, list_val);
1018  list_val = CONS(ENTITY, v_new, list_val);
1019  }
1020  }
1021  return list_val;
1022 }
#define NIL
The empty list (nil in Lisp)
Definition: newgen_list.h:47
#define CONS(_t_, _i_, _l_)
List element cell constructor (insert an element at the beginning of a list)
Definition: newgen_list.h:150
bool variable_dynamic_p(entity)
Definition: variable.c:1586
bool variable_stack_p(entity)
Definition: variable.c:1593
entity entity_to_new_value(entity)
Definition: value.c:859
entity entity_to_old_value(entity)
Definition: value.c:869

References CONS, ENTITY, entity_has_values_p(), entity_to_new_value(), entity_to_old_value(), FOREACH, NIL, variable_dynamic_p(), and variable_stack_p().

Referenced by statement_to_transformer(), and statement_to_transformer_list().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ entity_for_value_mapping_p()

static bool entity_for_value_mapping_p ( entity  e)
static

Definition at line 418 of file mappings.c.

419 {
421  && !typedef_entity_p(e)
422  && !entity_field_p(e);
423 }
bool entity_not_constant_or_intrinsic_p(entity e)
Default entity filter for get_referenced_entities()
Definition: entity.c:3050
bool typedef_entity_p(entity e)
Definition: entity.c:1902
bool entity_field_p(entity e)
e is the field of a structure
Definition: entity.c:857

References entity_field_p(), entity_not_constant_or_intrinsic_p(), and typedef_entity_p().

Referenced by module_to_value_mappings().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ module_to_value_mappings()

void module_to_value_mappings ( entity  m)

void module_to_value_mappings(entity m): build hash tables between variables and values (old, new and intermediate), and between values and names for module m, as well as equivalence equalities

NW: before calling "module_to_value_mappings" to set up the hash table to translate value into value names for module with name (string) module_name do:

set_current_module_entity( local_name_to_top_level_entity(module_name) );

(the following call is only necessary if a variable of type entity such as "module" is not already set) module = get_current_module_entity();

set_current_module_statement( (statement) db_get_memory_resource(DBR_CODE, module_name, true) ); set_cumulated_rw_effects((statement_effects) db_get_memory_resource(DBR_CUMULATED_EFFECTS, module_name, true));

(that's it, but we musn't forget to reset everything after the call to "module_to_value_mappings", as below)

reset_current_module_statement(); reset_cumulated_rw_effects(); reset_current_module_entity(); free_value_mappings();

free_value_mappings();

reset local intermediate value counter for make_local_intermediate_value_entity and make_local_old_value_entity

module_inter_effects = code_effects(value_code(entity_initial(m)));

look for interprocedural write effects on scalar analyzable variables and generate proper entries into hash tables

In C, write effects on scalar formal parameter are masked by the value passing mode but the copy may nevertheless be written inside the function.

To keep the summary transformer consistent although the return value has no old value

look for interprocedural read effects on scalar analyzable variables and generate proper entries into hash tables

static variables have an old value too

look for intraprocedural write effects on scalar analyzable variables and generate proper entries into hash tables

look for intraprocedural read effects on scalar analyzable variables and generate proper entry into value name hash table if it has not been entered before; interprocedural read effects are implicitly dealed with since they are included; most entities are likely to have been encountered before; however in parameters and uninitialized variables have to be dealt with

FI: although it may only be read within this procedure, e might be written in another one thru a COMMON; this write is not visible from OUT, but only from a caller of out; because we have only a local intraprocedural or a global interprocedural view of aliasing, we have to create useless values:-(

add_new_value(e);

Note: this makes the control structure of this procedure obsolete!

This call is useless because it only is effective if entity_has_values_p() is true: add_intraprocedural_value_entities(e);

A stronger call to the same subroutine is included in the previous call: add_or_kill_equivalenced_variables(e, true);

scan declarations to make sure that private variables are taken into account; assume a read and write effects on these variables, although they may not even be used.

Only intraprocedural variables can be privatized (1 Aug. 92)

This should be useless if return variables are taken into account by effect analysis. No problem with Fortran because the return variable really is assigned a value. Not obvious in C because the assignment is implicit in the return statement. In C the return variable is more like a value: it cannot be re-assigned.

FI: Only return variables are forgotten by effects

FI: no, this is wrong in C; local variables are dropped from effect when their declaration statements are processed. They cannot be found in the effects of the module statement.

We need references to all fields, direct or indirect when a field is itself a struct

scan other referenced variables to make sure everyone has an entry in the symbol table

|| storage_return_p(es)

We need references to all fields, direct or indirect when a field is itself a struct

Beware of struct return values which may generate additional locations and location values

To be sure to retrieve all relevant locations, including array elements

for debug, print hash tables

Definition at line 624 of file mappings.c.

625 {
626  list module_inter_effects;
627  list module_intra_effects;
628 
629  pips_debug(8,"begin for module %s\n", module_local_name(m));
630 
631  pips_assert("m is a module", entity_module_p(m));
632 
633  // hook cleanup in free_value_mappings
635  /* free_value_mappings(); */
636 
638 
639  /* reset local intermediate value counter for
640  make_local_intermediate_value_entity and
641  make_local_old_value_entity */
646 
647  /* module_inter_effects = code_effects(value_code(entity_initial(m))); */
648  module_inter_effects = load_summary_effects(m);
649 
650  /* look for interprocedural write effects on scalar analyzable variables
651  and generate proper entries into hash tables */
652  FOREACH(EFFECT, ef, module_inter_effects) {
653  if(store_effect_p(ef)) {
655  entity e = reference_variable(r);
656  action a = effect_action(ef);
657  if(analyzable_scalar_entity_p(e) // check type
659  && (
660  action_write_p(a)
661  ||
662  /* In C, write effects on scalar formal parameter are
663  masked by the value passing mode but the copy may
664  nevertheless be written inside the function. */
665  (c_module_p(m) && entity_formal_p(e))
666  ||
667  /* To keep the summary transformer consistent
668  although the return value has no old value */
670  ))
671  )
673  else if(entity_abstract_location_p(e) && action_write_p(a)) {
674  add_implicit_interprocedural_write_effects(e, module_inter_effects);
675  }
678  if(analyzed_type_p(t)) {
681  }
682  free_type(t);
683  }
684  }
685  }
686 
687  /* look for interprocedural read effects on scalar analyzable variables
688  and generate proper entries into hash tables */
689  FOREACH(EFFECT, ef, module_inter_effects) {
690  if(store_effect_p(ef)) {
692  action a = effect_action(ef);
694  if(c_module_p(m) &&
696  /* static variables have an old value too */
698  )
699  )
701  else
703  }
704  }
705  }
706 
707  module_intra_effects = load_module_intraprocedural_effects(m);
708 
709  /* look for intraprocedural write effects on scalar analyzable variables
710  and generate proper entries into hash tables */
711  FOREACH(EFFECT, ef, module_intra_effects) {
712  if(store_effect_p(ef)) {
714  action a = effect_action(ef);
718  }
719  else {
722  && !entity_heap_location_p(e))
724  }
725  }
726  else if(constant_path_analyzed_p() && action_write_p(a)) {
728 
729  if (analyzed_reference_p(rlhs)) {
730  entity le = make_location_entity(rlhs);
732  }
733  }
734  }
735  }
736 
737  /* look for intraprocedural read effects on scalar analyzable variables
738  and generate proper entry into value name hash table if it has
739  not been entered before; interprocedural read effects are implicitly
740  dealed with since they are included;
741  most entities are likely to have been encountered before; however
742  in parameters and uninitialized variables have to be dealt with */
743  FOREACH(EFFECT, ef, module_intra_effects) {
744  if(store_effect_p(ef)) {
747  /* FI: although it may only be read within this procedure, e
748  * might be written in another one thru a COMMON; this write
749  * is not visible from OUT, but only from a caller of out;
750  * because we have only a local intraprocedural or a global
751  * interprocedural view of aliasing, we have to create useless
752  * values:-(
753  *
754  * add_new_value(e);
755  *
756  * Note: this makes the control structure of this procedure
757  * obsolete!
758  */
759  /* This call is useless because it only is effective if
760  * entity_has_values_p() is true:
761  * add_intraprocedural_value_entities(e);
762  */
765  && !entity_heap_location_p(e))
767  /* A stronger call to the same subroutine is included in
768  * the previous call:
769  * add_or_kill_equivalenced_variables(e, true);
770  */
771  }
772  }
773  }
774 
775  /* scan declarations to make sure that private variables are
776  * taken into account; assume a read and write effects on these
777  * variables, although they may not even be used.
778  *
779  * Only intraprocedural variables can be privatized (1 Aug. 92)
780  */
782  FOREACH(ENTITY, e, dl) {
786  /* This should be useless if return variables are taken
787  into account by effect analysis. No problem with
788  Fortran because the return variable really is assigned
789  a value. Not obvious in C because the assignment is
790  implicit in the return statement. In C the return
791  variable is more like a value: it cannot be re-assigned. */
793  }
794  else {
796  }
797  }
798  else if(entity_variable_p(e) && !entity_abstract_location_p(e)) {
799  storage es = entity_storage(e);
800  // FI: do not process named or derived types
801  //if(storage_ram_p(es) || storage_return_p(es)) {
802  /* FI: Only return variables are forgotten by effects
803  *
804  * FI: no, this is wrong in C; local variables are dropped
805  * from effect when their declaration statements are
806  * processed. They cannot be found in the effects of the
807  * module statement.
808  */
809  if(storage_ram_p(es) || storage_return_p(es)) {
812  /* We need references to all fields, direct or indirect when
813  * a field is itself a struct
814  */
815  reference r = make_reference(e, NIL);
816  list fl = struct_type_to_fields(t);
818  free_reference(r);
819  }
820  }
821  }
822  }
823 
824  /* scan other referenced variables to make sure everyone has an
825  * entry in the symbol table
826  */
828  SET_FOREACH(entity, e, re) {
830  pips_assert("should not go there ?", !storage_return_p(entity_storage(e)));
832  }
833  }
834 
835  // FI: to analyze array elements with constant subscripts, we would
836  // need to get a list of all constant atomic references with types
837  // that are analyzed.
838 
839  // FI: for points-to analysis, we need to know all formal virtual
840  // entities that have been created by the points-to pass. It is not
841  // clear the information may be retrieved from the module statement
842  // cumulated effect, especially if scopes are used by the
843  // programmer, or the module summary cumulated effects.
845  SET_FOREACH(entity, e, re) {
846  // FI: place holder variables are supposed to have been removed
847  // from internal representation by C parser?
849  storage es = entity_storage(e);
850  if(storage_ram_p(es)/* || storage_return_p(es)*/) {
852  if(struct_type_p(t)) {
853  /* We need references to all fields, direct or indirect when
854  * a field is itself a struct
855  */
856  reference r = make_reference(e, NIL);
857  list fl = struct_type_to_fields(t);
859  free_reference(r);
860  }
861  }
862  }
863  }
864  }
865  set_free(re);
866 
867  /* Beware of struct return values which may generate additional
868  * locations and location values
869  */
871  const char * module_name = entity_local_name(m);
872  callees c = (callees) db_get_memory_resource(DBR_CALLEES,
873  module_name,
874  true);
875  list lc = callees_callees(c);
876  FOREACH(STRING, callee_name, lc) {
877  entity f = module_name_to_entity(callee_name);
880  if(struct_type_p(rt)) {
882  reference rvr = make_reference(rv, NIL);
883  list fl = struct_type_to_fields(rt);
885  free_reference(rvr);
886  }
887  }
888  }
889 
890  /* To be sure to retrieve all relevant locations, including array elements */
893  }
894 
895  /* for debug, print hash tables */
896  ifdebug(8) {
897  pips_debug(8, "hash tables for module %s\n", module_local_name(m));
900  }
901 
902  pips_debug(1, "Number of analyzed variables for module %s: %d\n",
905  pips_debug(1, "Number of analyzed values for module %s: %d\n",
908 
909  pips_debug(8,"end for module %s\n", module_local_name(m));
910 }
reference make_reference(entity a1, list a2)
Definition: ri.c:2083
void free_type(type p)
Definition: ri.c:2658
bool entity_heap_location_p(entity b)
package abstract location.
bool entity_typed_anywhere_locations_p(entity e)
Test if an entity is the bottom of the lattice.
bool entity_anywhere_locations_p(entity e)
test if an entity is the bottom of the lattice
list load_summary_effects(entity e)
FI->FI, FI->BC: these two functions should be moved into effects-util or effects-simple.
bool location_entity_p(entity)
Definition: locations.c:349
reference cell_any_reference(cell)
API for reference.
Definition: effects.c:77
#define action_read_p(x)
Definition: effects.h:311
#define effect_cell(x)
Definition: effects.h:640
const char * module_name(const char *s)
Return the module part of an entity name.
Definition: entity_names.c:296
#define STRING(x)
Definition: genC.h:87
statement get_current_module_statement(void)
Get the current module statement.
Definition: static.c:208
bool gen_true(__attribute__((unused)) gen_chunk *unused)
Return true and ignore the argument.
Definition: genClib.c:2780
string db_get_memory_resource(const char *rname, const char *oname, bool pure)
Return the pointer to the resource, whatever it is.
Definition: database.c:755
void reset_hooks_register(reset_func_t)
reset_hooks.c
Definition: reset_hooks.c:44
#define SET_FOREACH(type_name, the_item, the_set)
enumerate set elements in their internal order.
Definition: newgen_set.h:78
void set_free(set)
Definition: set.c:332
bool entity_formal_p(entity p)
is p a formal parameter?
Definition: entity.c:1935
bool c_module_p(entity m)
Test if a module "m" is written in C.
Definition: entity.c:2777
set get_referenced_entities_filtered(void *elem, bool(*chunk_filter)(void *), bool(*entity_filter)(entity))
Same as get_referenced_entities, but will only consider entities that fulfills entity_filter and will...
Definition: entity.c:2982
entity module_name_to_entity(const char *mn)
This is an alias for local_name_to_top_level_entity.
Definition: entity.c:1479
const char * module_local_name(entity e)
Returns the module local user name.
Definition: entity.c:582
bool entity_module_p(entity e)
Definition: entity.c:683
entity function_to_return_value(entity m)
Returns the entity rv that carries the value returned by module m, when m is not a C void function or...
Definition: module.c:509
bool entity_static_variable_p(entity)
return true if the entity is declared with the keyword static
Definition: variable.c:1146
type compute_basic_concrete_type(type)
computes a new type which is the basic concrete type of the input type (this new type is not stored i...
Definition: type.c:3556
struct _newgen_struct_callees_ * callees
Definition: ri.h:55
#define functional_result(x)
Definition: ri.h:1444
#define callees_callees(x)
Definition: ri.h:675
#define type_functional(x)
Definition: ri.h:2952
static bool entity_for_value_mapping_p(entity e)
Definition: mappings.c:418
static void allocate_module_value_mappings(entity m)
Definition: mappings.c:325
static void reset_equivalence_equalities()
Definition: mappings.c:76
static void values_for_current_module_intraprocedural_simple_effects(void)
Definition: mappings.c:578
void add_implicit_interprocedural_write_effects(entity al, list el)
It is assumed that al is an abstract location that is written and which may conflict with effects in ...
Definition: mappings.c:382
#define ifdebug(n)
Definition: sg.c:47
FI: I do not understand why the type is duplicated at the set level.
Definition: set.c:59
bool analyzed_reference_p(reference)
FI: Nelson explains the motivation for can_be_constant_path_p() but I do not understand them.
Definition: value.c:518
void reset_value_counters(void)
Definition: value.c:244
void set_analyzed_types(void)
Definition: value.c:271
void test_mapping_entry_consistency(void)
Definition: value.c:1113
bool constant_path_analyzed_p(void)
Definition: value.c:330
void reset_temporary_value_counter(void)
Definition: value.c:250
int aproximate_number_of_analyzed_variables(void)
Definition: value.c:1153
void print_value_mappings(void)
Definition: value.c:993
void error_reset_value_mappings(void)
To be called by error handler only.
Definition: value.c:1205
int number_of_analyzed_values(void)
Definition: value.c:1148
list current_module_declarations()
Definition: module.c:78

References action_read_p, action_write_p, add_implicit_interprocedural_write_effects(), add_interprocedural_field_entities(), add_interprocedural_new_value_entity(), add_interprocedural_value_entities(), add_intraprocedural_field_entities(), add_intraprocedural_value_entities(), add_intraprocedural_value_entities_unconditionally(), allocate_module_value_mappings(), analyzable_scalar_entity_p(), analyzed_reference_p(), analyzed_type_p(), aproximate_number_of_analyzed_variables(), c_module_p(), callees_callees, cell_any_reference(), compute_basic_concrete_type(), constant_path_analyzed_p(), current_module_declarations(), db_get_memory_resource(), EFFECT, effect_action, effect_any_reference, effect_cell, effects_package_entity_p(), ENTITY, entity_abstract_location_p(), entity_anywhere_locations_p(), entity_basic_concrete_type(), entity_for_value_mapping_p(), entity_formal_p(), entity_has_values_p(), entity_heap_location_p(), entity_local_name(), entity_module_p(), entity_static_variable_p(), entity_storage, entity_typed_anywhere_locations_p(), entity_variable_p, error_reset_value_mappings(), f(), FOREACH, free_reference(), free_type(), function_to_return_value(), functional_result, gen_true(), get_current_module_statement(), get_referenced_entities_filtered(), ifdebug, load_module_intraprocedural_effects(), load_summary_effects(), location_entity_p(), make_location_entity(), make_reference(), module_local_name(), module_name(), module_name_to_entity(), NIL, number_of_analyzed_values(), pips_assert, pips_debug, place_holder_variable_p(), points_to_reference_to_concrete_type(), print_value_mappings(), reference_variable, reset_equivalence_equalities(), reset_hooks_register(), reset_temporary_value_counter(), reset_value_counters(), set_analyzed_types(), SET_FOREACH, set_free(), storage_ram_p, storage_return_p, store_effect_p(), STRING, struct_type_p(), struct_type_to_fields(), test_mapping_entry_consistency(), type_functional, and values_for_current_module_intraprocedural_simple_effects().

Referenced by add_alias_pairs_for_this_caller(), alias_classes(), alias_lists(), alias_pairs(), aliases_text(), any_complexities(), array_expansion(), bdsc_code_instrumentation(), call_site_to_module_precondition_text(), comp_regions(), continuation_conditions(), dsc_code_parallelization(), generic_module_name_to_transformers(), generic_print_xml_application(), get_any_comp_regions_text(), get_continuation_condition_text(), get_semantic_text(), hbdsc_parallelization(), init_convex_in_out_regions(), init_convex_rw_regions(), init_convex_summary_in_out_regions(), init_convex_summary_rw_regions(), initial_precondition(), isolate_statement(), kernel_data_mapping(), kernel_load_store_engine(), module_name_to_preconditions(), module_name_to_total_preconditions(), out_regions_from_caller_to_callee(), partial_eval(), phrase_comEngine_distributor(), phrase_distributor(), phrase_distributor_control_code(), pragma_outliner(), print_initial_precondition(), print_program_precondition(), program_precondition(), safescale_distributor(), safescale_module_analysis(), sequence_dependence_graph(), solve_hardware_constraints(), spire_distributed_unstructured_to_structured(), summary_precondition(), summary_total_postcondition(), and update_precondition_with_call_site_preconditions().

+ Here is the caller graph for this function:

◆ reset_equivalence_equalities()

static void reset_equivalence_equalities ( )
static

Definition at line 76 of file mappings.c.

77 {
80  }
81 }
#define CONTRAINTE_UNDEFINED
Pcontrainte contraintes_free(Pcontrainte pc)
Pcontrainte contraintes_free(Pcontrainte pc): desallocation de toutes les contraintes de la liste pc.
Definition: alloc.c:226

References CONTRAINTE_UNDEFINED, contraintes_free(), and equivalence_equalities.

Referenced by module_to_value_mappings().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ tf_equivalence_equalities_add()

transformer tf_equivalence_equalities_add ( transformer  tf)

mappings.c

I need here a contraintes_dup() that is not yet available in Linear and I cannot change Linear just before the DRET meeting; I've got to modify transformer_equalities_add() and to give it a behavior different from transformer_equality_add()

Parameters
tff

Definition at line 83 of file mappings.c.

84 {
85  /* I need here a contraintes_dup() that is not yet available
86  in Linear and I cannot change Linear just before the DRET meeting;
87  I've got to modify transformer_equalities_add() and to give it
88  a behavior different from transformer_equality_add() */
90  return tf;
91 }
transformer transformer_equalities_add(transformer tf, Pcontrainte eqs)
Definition: basic.c:391

References equivalence_equalities, and transformer_equalities_add().

Referenced by statement_to_postcondition(), and statement_to_total_precondition().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ upwards_vect_rename()

void upwards_vect_rename ( Pvecteur  v,
transformer  post 
)

Renaming of variables in v according to transformations occuring later.

If a variable is modified by post, its old value must be used in v

FI: it would probably ne more efficient to scan va and vb than the argument list...

Parameters
postost

Definition at line 1062 of file mappings.c.

1063 {
1064  /* FI: it would probably ne more efficient to
1065  * scan va and vb than the argument list...
1066  */
1067  list modified_values = transformer_arguments(post);
1068 
1069  FOREACH(ENTITY, v_new, modified_values) {
1070  entity v_init = new_value_to_old_value(v_new);
1071 
1072  (void) vect_variable_rename(v, (Variable) v_new,
1073  (Variable) v_init);
1074  }
1075 }
Pvecteur vect_variable_rename(Pvecteur v, Variable v_old, Variable v_new)
Pvecteur vect_variable_rename(Pvecteur v, Variable v_old, Variable v_new): rename the potential coord...
Definition: base.c:366
#define transformer_arguments(x)
Definition: ri.h:2871
entity new_value_to_old_value(entity)
Definition: value.c:1710

References ENTITY, FOREACH, new_value_to_old_value(), transformer_arguments, and vect_variable_rename().

Referenced by add_declaration_list_information(), add_reference_information(), and transformer_add_integer_relation_information().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ value_mappings_compatible_vector_p()

bool value_mappings_compatible_vector_p ( Pvecteur  iv)

transform a vector based on variable entities into a vector based on new value entities when possible; does nothing most of the time; does a little in the presence of equivalenced variables

Ugly because it has a hidden side effect on v to handle Fortran equivalences and because its implementation is dependent on type Pvecteur.

Assume that the value mappings are available (as implied by the function's name!), which may not be true when dealing with call sites.

The variable may denote a constant with compatible type

or a temporary variable

Or a variable value

Or a phi variable, when transformers are computed by the region analysis

Or the vector cannot be used in the semantics analysis

Parameters
ivv

Definition at line 924 of file mappings.c.

925 {
926  Pvecteur v = iv;
927  for(;!VECTEUR_NUL_P(v); v = v->succ) {
928  if(vecteur_var(v) != TCST) {
929  entity e = (entity) vecteur_var(v);
930 
931  /* The variable may denote a constant with compatible type */
932  if(entity_constant_p(e) && !analyzed_constant_p(e)) {
933  return false;
934  }
935 
936  /* or a temporary variable */
937  else if(local_temporary_value_entity_p(e)) {
938  ;
939  }
940 
941  /* Or a variable value */
942  else if(entity_has_values_p(e)) {
943  entity new_v = entity_to_new_value(e);
944 
945  if(new_v != entity_undefined)
946  vecteur_var(v) = (Variable) new_v;
947  else
948  return false;
949  }
950 
951  /* Or a phi variable, when transformers are computed by the
952  region analysis */
953  else if(variable_phi_p(e)) {
954  ;
955  }
956 
957  /* Or the vector cannot be used in the semantics analysis */
958  else {
959  return false;
960  }
961  }
962  }
963  return true;
964 }
struct _newgen_struct_entity_ * entity
Definition: abc_private.h:14
#define variable_phi_p(e)
true if e is a phi variable PHI entities have a name like: REGIONS:PHI#, where # is a number.
#define entity_constant_p(e)
struct Svecteur * succ
Definition: vecteur-local.h:92
bool analyzed_constant_p(entity)
The constant may appear as a variable in the linear systems.
Definition: value.c:487
bool local_temporary_value_entity_p(entity)
Definition: value.c:654
#define TCST
VARIABLE REPRESENTANT LE TERME CONSTANT.
#define vecteur_var(v)
#define VECTEUR_NUL_P(v)

References analyzed_constant_p(), entity_constant_p, entity_has_values_p(), entity_to_new_value(), entity_undefined, local_temporary_value_entity_p(), Svecteur::succ, TCST, variable_phi_p, VECTEUR_NUL_P, and vecteur_var.

Referenced by add_affine_bound_conditions(), add_declaration_list_information(), add_loop_index_exit_value(), add_loop_skip_condition(), add_reference_information(), affine_to_transformer(), integer_divide_to_transformer(), integer_right_shift_to_transformer(), simple_affine_to_transformer(), transformer_add_integer_relation_information(), and transformer_add_loop_index_incrementation().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ values_for_current_module_intraprocedural_simple_effects()

static void values_for_current_module_intraprocedural_simple_effects ( void  )
static

Definition at line 578 of file mappings.c.

579 {
581  if(!get_bool_property("CONSTANT_PATH_EFFECTS")) {
582  pips_user_warning("Property \"CONSTANT_PATH_EFFECTS\" is set to its "
583  "experimental value, false.");
584  }
587  gen_null);
588  return;
589 }
#define gen_recurse(start, domain_number, flt, rwt)
Definition: genC.h:283
void gen_null(__attribute__((unused)) void *unused)
Ignore the argument.
Definition: genClib.c:2752
#define statement_domain
newgen_sizeofexpression_domain_defined
Definition: ri.h:362
static bool add_values_for_simple_effects_of_statement(statement s)
Declare value entities necessary to analyze locations defined by proper effects.
Definition: mappings.c:528

References add_values_for_simple_effects_of_statement(), gen_null(), gen_recurse, get_bool_property(), get_current_module_statement(), pips_user_warning, and statement_domain.

Referenced by module_to_value_mappings().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ variable_to_values()

list variable_to_values ( entity  e)

Definition at line 982 of file mappings.c.

983 {
984  list list_val = NIL;
985 
986  if(entity_has_values_p(e)) {
987  entity v_old = entity_to_old_value(e);
988  entity v_new = entity_to_new_value(e);
989 
990  list_val = CONS(ENTITY, v_old, list_val);
991  list_val = CONS(ENTITY, v_new, list_val);
992  }
993 
994  return list_val;
995 }

References CONS, ENTITY, entity_has_values_p(), entity_to_new_value(), entity_to_old_value(), and NIL.

Referenced by statement_to_postcondition().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ variables_to_new_values()

void variables_to_new_values ( Pvecteur  v)

replace variables by new values which is necessary for equivalenced variables

Definition at line 1038 of file mappings.c.

1039 {
1040  Pvecteur elem = VECTEUR_UNDEFINED;
1041 
1042  for(elem = v; !VECTEUR_NUL_P(elem); elem = vecteur_succ(elem)) {
1043  entity var = (entity) vecteur_var(elem);
1044 
1045  if(vecteur_var(elem)!=TCST) {
1046  entity v_new = entity_to_new_value(var);
1047 
1048  if(v_new!=var) {
1049  (void) vect_variable_rename(v, (Variable) var,
1050  (Variable) v_new);
1051  }
1052  }
1053  }
1054 }
#define VECTEUR_UNDEFINED
#define vecteur_succ(v)

References entity_to_new_value(), TCST, vect_variable_rename(), VECTEUR_NUL_P, vecteur_succ, VECTEUR_UNDEFINED, and vecteur_var.

Referenced by transformer_add_integer_relation_information().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ variables_to_old_values()

list variables_to_old_values ( list  list_mod)
Parameters
list_modist_mod

Definition at line 1024 of file mappings.c.

1025 {
1026  list list_val = NIL;
1027 
1028  MAP(ENTITY, e, {
1029  entity v_old = entity_to_old_value(e);
1030 
1031  list_val = CONS(ENTITY, v_old, list_val);
1032  }, list_mod);
1033  return list_val;
1034 }
#define MAP(_map_CASTER, _map_item, _map_code, _map_list)
Apply/map an instruction block on all the elements of a list (old fashioned)
Definition: newgen_list.h:226

References CONS, ENTITY, entity_to_old_value(), MAP, and NIL.

Referenced by recompute_loop_transformer().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ variables_to_values()

list variables_to_values ( list  list_mod)
Parameters
list_modist_mod

Definition at line 966 of file mappings.c.

967 {
968  list list_val = NIL;
969 
970  FOREACH(ENTITY, e, list_mod) {
971  if(entity_has_values_p(e)) {
972  entity v_old = entity_to_old_value(e);
973  entity v_new = entity_to_new_value(e);
974 
975  list_val = CONS(ENTITY, v_old, list_val);
976  list_val = CONS(ENTITY, v_new, list_val);
977  }
978  }
979  return list_val;
980 }

References CONS, ENTITY, entity_has_values_p(), entity_to_new_value(), entity_to_old_value(), FOREACH, and NIL.

Referenced by recompute_loop_transformer(), and statement_to_postcondition().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

Variable Documentation

◆ equivalence_equalities

Pcontrainte equivalence_equalities = CONTRAINTE_UNDEFINED
static

Variable value mappings package.

Establish mappings between analyzed scalar variable entities and variable value entities for a given module (see transformer/value.c).

Handle static aliasing in Fortran, i.e. equivalences too.

Cannot handle more than one module at a time: no recursivity on modules or chaos will occur.

See package value.c for more information on functions more or less independent of the internal representation.

Francois Irigoin, 20 April 1990 To convert non constant effects into constant effects FORTRAN 77 EQUIVALENCE

Definition at line 74 of file mappings.c.

Referenced by add_equivalence_equality(), reset_equivalence_equalities(), and tf_equivalence_equalities_add().