PIPS
size.c File Reference
#include <stdio.h>
#include <string.h>
#include <ctype.h>
#include "linear.h"
#include "genC.h"
#include "ri.h"
#include "ri-util.h"
#include "misc.h"
+ Include dependency graph for size.c:

Go to the source code of this file.

Macros

#define INTERVAL_INTERSECTION(a, b, c, d)   (!((b) <= (c) || (d) <= (a)))
 

Functions

int number_of_initial_values (list args)
 Functions to compute the numer of bytes required to store a variable or an object of a given type in memory; used by memory allocation functions in parsers, when allocation is possible (STATIC and DYNAMIC). More...
 
bool SizeOfArray (entity e, int *s)
 This function computes the total size of a variable in bytes, ie. More...
 
int array_size (entity a)
 
Value ValueSizeOfArray (entity e)
 
int CSafeSizeOfArray (entity a)
 BEGIN_EOLE. More...
 
int entity_memory_size (entity dt)
 
int type_memory_size (type t)
 
_int SizeOfElements (basic b)
 This function returns the length in bytes of the Fortran or C type represented by a basic, except for a varying size string (formal parameter). More...
 
int element_number (basic b, list ld)
 END_EOLE. More...
 
bool NumberOfElements (basic b, list ld, int *n)
 
Value ValueNumberOfElements (list ld)
 
int SizeOfIthDimension (entity e, int i)
 this function returns the size of the ith dimension of a variable e. More...
 
int dimension_size (dimension d)
 this function computes the size of a dimension. More...
 
expression SizeOfDimension (dimension d)
 
static void * do_sizeofdimension_reduction (void *v, const list l)
 
expression SizeOfDimensions (list dims)
 computes the product of all dimensions in dims More...
 
Value ValueSizeOfDimension (dimension d)
 FI: I do not understand the "Value" cast. More...
 
int ExpressionToInt (expression e)
 this function computes the value of an integer constant expression and returns it to the calling function. More...
 
int NumberOfDimension (entity e)
 
void set_entity_to_size ()
 
void reset_entity_to_size ()
 
void safe_reset_entity_to_size ()
 In case of error handling, PIPS may try to reset this table twice. More...
 
int storage_space_of_variable (entity v)
 
bool variable_entities_may_conflict_p (entity e1, entity e2)
 

Variables

static hash_table entity_to_size = hash_table_undefined
 a hash table to map entities to their numbers of elements More...
 

Macro Definition Documentation

◆ INTERVAL_INTERSECTION

#define INTERVAL_INTERSECTION (   a,
  b,
  c,
 
)    (!((b) <= (c) || (d) <= (a)))

Definition at line 680 of file size.c.

Function Documentation

◆ array_size()

int array_size ( entity  a)

Definition at line 195 of file size.c.

196 {
197  int s = 0;
198 
199  if(!SizeOfArray(a, &s)) {
200  pips_internal_error("Array \"%s\" with illegal varying array size",
201  entity_name(a));
202  }
203  return s;
204 }
#define pips_internal_error
Definition: misc-local.h:149
#define entity_name(x)
Definition: ri.h:2790
bool SizeOfArray(entity e, int *s)
This function computes the total size of a variable in bytes, ie.
Definition: size.c:87

References entity_name, pips_internal_error, and SizeOfArray().

+ Here is the call graph for this function:

◆ CSafeSizeOfArray()

int CSafeSizeOfArray ( entity  a)

BEGIN_EOLE.

  • please do not remove this line Lines between BEGIN_EOLE and END_EOLE tags are automatically included in the EOLE project (JZ - 11/98)

should be a pips_user_error() to avoid useless and dangerous results

Definition at line 225 of file size.c.

226 {
227  int s;
228 
229  if(!SizeOfArray(a, &s)) {
230  pips_user_warning("Varying size for array \"%s\"\n", entity_name(a));
231  /* should be a pips_user_error() to avoid useless and dangerous
232  results */
233  pips_user_warning("Not yet supported properly by PIPS\n");
234  }
235 
236  return s;
237 }
#define pips_user_warning
Definition: misc-local.h:146

References entity_name, pips_user_warning, and SizeOfArray().

Referenced by ComputeAreaOffset(), SizeOfElements(), and type_memory_size().

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

◆ dimension_size()

int dimension_size ( dimension  d)

this function computes the size of a dimension.

Definition at line 491 of file size.c.

492 {
493  expression sod= SizeOfDimension(d);
494  intptr_t i;
495  if(expression_integer_value(sod,&i))
496  free_expression(sod);
497  else
498  pips_internal_error("dimension is not constant, use SizeOfDimension instead");
499  return i;
500 }
void free_expression(expression p)
Definition: ri.c:853
bool expression_integer_value(expression e, intptr_t *pval)
Definition: eval.c:792
expression SizeOfDimension(dimension d)
Definition: size.c:503
#define intptr_t
Definition: stdint.in.h:294

References expression_integer_value(), free_expression(), intptr_t, pips_internal_error, and SizeOfDimension().

Referenced by ComputeNewSizeOfIthDimension(), loadstore_type_conversion_string(), make_emulated_shared_variable(), normalize_microcode_anotate(), reference_offset(), template_ranges_to_processors_ranges(), and type_memory_size().

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

◆ do_sizeofdimension_reduction()

static void* do_sizeofdimension_reduction ( void *  v,
const list  l 
)
static

Definition at line 513 of file size.c.

514 {
516  (expression)v,
518 }
#define CAR(pcons)
Get the value of the first element of a list.
Definition: newgen_list.h:92
#define MULTIPLY_OPERATOR_NAME
expression make_op_exp(char *op_name, expression exp1, expression exp2)
================================================================
Definition: expression.c:2012

References CAR, DIMENSION, make_op_exp(), MULTIPLY_OPERATOR_NAME, and SizeOfDimension().

Referenced by SizeOfDimensions().

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

◆ element_number()

int element_number ( basic  b,
list  ld 
)

END_EOLE.

this function computes the number of elements of a variable. ld is the list of dimensions of the variable

Parameters
ldd

Definition at line 391 of file size.c.

392 {
393  int en = 0;
394 
395  if(!NumberOfElements(b, ld, &en)) {
396  pips_internal_error("Probably varying size array");
397  }
398 
399  return en;
400 }
bool NumberOfElements(basic b, list ld, int *n)
Definition: size.c:403

References NumberOfElements(), and pips_internal_error.

Referenced by compile_one_reduction(), max_size_of_processors(), and processor_loop().

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

◆ entity_memory_size()

int entity_memory_size ( entity  dt)

dt is assumed to be a derived type: struct, union, and maybe enum

Parameters
dtt

Definition at line 239 of file size.c.

240 {
241  /* dt is assumed to be a derived type: struct, union, and maybe enum */
242  type t = ultimate_type(entity_type(dt));
243  int s = type_memory_size(t);
244 
245  return s;
246 }
type ultimate_type(type)
Definition: type.c:3466
#define entity_type(x)
Definition: ri.h:2792
int type_memory_size(type t)
Definition: size.c:248

References entity_type, type_memory_size(), and ultimate_type().

Referenced by reductions_rewrite(), and SizeOfElements().

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

◆ ExpressionToInt()

int ExpressionToInt ( expression  e)

this function computes the value of an integer constant expression and returns it to the calling function.

it aborts if the expression is not constant.

See expression_integer_value() to check before aborting

Definition at line 562 of file size.c.

563 {
564  value v;
565  constant c;
566  int i = -1;
567 
568  v = EvalExpression(e);
569 
570  if (value_constant_p(v)) {
571  c = value_constant(v);
572  if (constant_int_p(c)) {
573  i = constant_int(c);
574  }
575  else {
576  pips_internal_error("integer constant expected");
577  }
578  }
579  else {
580  pips_internal_error("constant expected\n");
581  }
582 
583  free_value(v);
584  return i;
585 }
void free_value(value p)
Definition: ri.c:2787
value EvalExpression(expression e)
Evaluate statically an expression.
Definition: eval.c:108
#define value_constant(x)
Definition: ri.h:3073
#define constant_int(x)
Definition: ri.h:850
#define value_constant_p(x)
Definition: ri.h:3071
#define constant_int_p(x)
Definition: ri.h:848

References constant_int, constant_int_p, EvalExpression(), free_value(), pips_internal_error, value_constant, and value_constant_p.

Referenced by get_entity_dimensions(), OffsetOfReference(), SizeOfRange(), and ValueOfIthLowerBound().

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

◆ number_of_initial_values()

int number_of_initial_values ( list  args)

Functions to compute the numer of bytes required to store a variable or an object of a given type in memory; used by memory allocation functions in parsers, when allocation is possible (STATIC and DYNAMIC).

size.c

If the size is unknown, the variable is allocated in the STACK area. See ri.pdf, section about "area".

Parameters
argsrgs

Definition at line 44 of file size.c.

45 {
46  int niv = 0;
47  list carg = list_undefined;
48 
49  for(carg=args; !ENDP(carg); POP(carg)) {
50  expression e = EXPRESSION(CAR(carg));
51 
52  if(expression_call_p(e)) {
54  entity f = call_function(c);
55  list sargs = call_arguments(c);
56 
58  niv += number_of_initial_values(sargs);
59  }
60  else
61  niv++;
62  }
63  else
64  niv++;
65  }
66 
67  return niv;
68 }
#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 list_undefined
Undefined list definition :-)
Definition: newgen_list.h:69
int f(int off1, int off2, int n, float r[n], float a[n], float b[n])
Definition: offsets.c:15
#define ENTITY_BRACE_INTRINSIC_P(e)
C initialization expression.
bool expression_call_p(expression e)
Definition: expression.c:415
#define call_function(x)
Definition: ri.h:709
#define EXPRESSION(x)
EXPRESSION.
Definition: ri.h:1217
#define syntax_call(x)
Definition: ri.h:2736
#define call_arguments(x)
Definition: ri.h:711
#define expression_syntax(x)
Definition: ri.h:1247
int number_of_initial_values(list args)
Functions to compute the numer of bytes required to store a variable or an object of a given type in ...
Definition: size.c:44
The structure used to build lists in NewGen.
Definition: newgen_list.h:41

References call_arguments, call_function, CAR, ENDP, ENTITY_BRACE_INTRINSIC_P, EXPRESSION, expression_call_p(), expression_syntax, f(), list_undefined, number_of_initial_values(), POP, and syntax_call.

Referenced by number_of_initial_values(), and SizeOfArray().

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

◆ NumberOfDimension()

int NumberOfDimension ( entity  e)

Definition at line 588 of file size.c.

589 {
590  type t = entity_type(e);
591  int nd;
592  cons *pc;
593 
595 
597  nd = 0;
598 
599  while (! ENDP(pc)) {
600  nd += 1;
601  pc = CDR(pc);
602  }
603 
604  return(nd);
605 }
#define CDR(pcons)
Get the list less its first element.
Definition: newgen_list.h:111
#define assert(ex)
Definition: newgen_assert.h:41
#define type_variable(x)
Definition: ri.h:2949
#define variable_dimensions(x)
Definition: ri.h:3122
#define type_variable_p(x)
Definition: ri.h:2947

References assert, CDR, ENDP, entity_type, type_variable, type_variable_p, and variable_dimensions.

Referenced by add_bound_arguments(), align_check(), array_as_template(), array_bounds_list(), array_distribution_similar_p(), array_ranges_to_template_ranges(), array_with_numerical_bounds_p(), block_distributed_p(), caller_list_of_bounds(), clean_distributed_io_system(), clean_shared_io_system(), compute_receive_content(), conformant_entities_p(), create_init_common_param_for_arrays(), create_init_common_param_for_processors(), create_init_common_param_for_templates(), create_parameters_h(), define_node_processor_id(), entity_unbounded_p(), extract_the_align(), extract_the_distribute(), full_linearization(), generate_compute_local_indices(), hpfc_broadcast_buffers(), hpfc_compute_align_constraints(), hpfc_compute_distribute_constraints(), hpfc_compute_entity_to_new_declaration(), hpfc_compute_lid(), hpfc_compute_unicity_constraints(), make_guard_expression(), make_reference_expression(), normalize_distribute(), number_of_distributed_dimensions(), one_message_guards_and_neighbour(), partial_linearization(), put_variables_in_ordered_lists(), reduction_parameters(), reference_to_points_to_sinks(), region_translation_init(), replicated_p(), st_generate_packing(), step_local_regionArray(), template_ranges_to_processors_ranges(), text_equivalence_class(), and update_overlaps_of().

+ Here is the caller graph for this function:

◆ NumberOfElements()

bool NumberOfElements ( basic  b,
list  ld,
int n 
)

do we have many elements at the lower typedef levels?

let's take care of the current level

Parameters
ldd

Definition at line 403 of file size.c.

404 {
405  list pc;
406  int ne = 1;
407  bool ok = true;
408  int sne = 1;
409 
410  /* do we have many elements at the lower typedef levels? */
411  if(basic_typedef_p(b)) {
412  entity e = basic_typedef(b);
413  // Lots of asserts skipped here
415 
417  }
418 
419  /* let's take care of the current level */
420  if(ok) {
421  for (pc = ld; pc != NULL && ok; pc = CDR(pc)) {
423  intptr_t s;
425  free_expression(sod);
426  ne *= s;
427  }
428  }
429 
430  *n = ne*sne;
431  return ok;
432 }
#define basic_typedef_p(x)
Definition: ri.h:641
#define basic_typedef(x)
Definition: ri.h:643
#define variable_basic(x)
Definition: ri.h:3120
static bool ok

References basic_typedef, basic_typedef_p, CAR, CDR, DIMENSION, entity_type, expression_integer_value(), free_expression(), intptr_t, NumberOfElements(), ok, SizeOfDimension(), type_variable, variable_basic, and variable_dimensions.

Referenced by element_number(), expression_reference_number(), number_of_items(), NumberOfElements(), and SizeOfArray().

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

◆ reset_entity_to_size()

void reset_entity_to_size ( void  )

Definition at line 635 of file size.c.

636 {
638  pips_internal_error("hash table should have been allocated");
639  }
640  else {
643  }
644 }
void hash_table_free(hash_table htp)
this function deletes a hash table that is no longer useful.
Definition: hash.c:327
#define hash_table_undefined
Value of an undefined hash_table.
Definition: newgen_hash.h:49
static hash_table entity_to_size
a hash table to map entities to their numbers of elements
Definition: size.c:623

References entity_to_size, hash_table_free(), hash_table_undefined, and pips_internal_error.

Referenced by create_workspace().

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

◆ safe_reset_entity_to_size()

void safe_reset_entity_to_size ( void  )

In case of error handling, PIPS may try to reset this table twice.

Definition at line 647 of file size.c.

References entity_to_size, hash_table_free(), and hash_table_undefined.

Referenced by close_workspace().

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

◆ set_entity_to_size()

void set_entity_to_size ( void  )

hash_table_clear(entity_to_size);

Definition at line 625 of file size.c.

626 {
628  pips_internal_error("hash table should have been deallocated");
629  /* hash_table_clear(entity_to_size); */
630  }
631 
633 }
hash_table hash_table_make(hash_key_type key_type, size_t size)
Definition: hash.c:294
@ hash_pointer
Definition: newgen_hash.h:32

References entity_to_size, hash_pointer, hash_table_make(), hash_table_undefined, and pips_internal_error.

Referenced by create_workspace(), and open_workspace().

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

◆ SizeOfArray()

bool SizeOfArray ( entity  e,
int s 
)

This function computes the total size of a variable in bytes, ie.

the product of the number of elements and the size of each element in byte, when this size is a constant.

Arrays cannot be sized by a variable according to Fortran 77 standard, unless they are formal parameters (see SafeSizeOfArray). This restriction is lifted for arrays allocated in the area STACK.

Arrays can be sized by expressions according to C latest standard (see Validation/C_syntax/array_declarators.c). Then their sizes are not available at compile time and their addresses in stack cannot be computed at compiler time (see CSafeSizeOfArray).

Since the size is returned in a signed int, there is a maximum PIPS size for an array.

Let's try to use the initial value

FI: should eveb be freed?

Is it an array of characters initialized with a string expression?

Is it a call to the BRACE_INTRINSIC operator?

This is too simple unfortunately: OK, but why? which test case?

ne = gen_length(args);

Should be a call to CParserError()...

Check for other dimensions which must be all declared: the first dimension only can be implicit

Already taken care of by "ni"

Check for 32 bit signed overflows

Definition at line 87 of file size.c.

88 {
89  type et = entity_type(e);
90  type uet = ultimate_type(et);
91  variable a, ua;
92  bool ok = true;
93  int se = -1;
94  int ne = -1;
95  int mne = -1;
96 
98  a = type_variable(et);
99  ua = type_variable(uet);
100 
101  se = SizeOfElements(variable_basic(ua));
102 
104 
105  if(!ok) {
106  /* Let's try to use the initial value */
107  value ev = entity_initial(e);
108  if(!value_undefined_p(ev)) {
109  if(value_expression_p(ev)) {
110  expression eve = value_expression(ev);
111  //type evet = expression_to_type(eve);
112  basic eveb = basic_of_expression(eve); /* FI: should eveb be freed? */
113 
114  /* Is it an array of characters initialized with a string expression? */
115  if(char_type_p(et) && !basic_undefined_p(eveb) && basic_string_p(eveb)) {
116  ne = string_type_size(eveb);
117  ok = true;
118  }
119  else if(expression_call_p(eve)) {
120  call evec = syntax_call(expression_syntax(eve));
121  entity f = call_function(evec);
122  list args = call_arguments(evec);
123 
124  /* Is it a call to the BRACE_INTRINSIC operator? */
126  /* This is too simple unfortunately: OK, but why? which
127  test case? */
128  /* ne = gen_length(args); */
129  int ni = number_of_initial_values(args);
130  //int nf = number_of_fields(et);
131  int nf = 1;
132 
133  if(type_variable_p(uet)) {
134  variable ev = type_variable(uet);
135  basic eb = variable_basic(ev);
136  if(basic_derived_p(eb)) {
137  entity de = basic_derived(eb);
138  nf = number_of_items(entity_type(de));
139  }
140  }
141  ne = ni/nf;
142  if (nf*ne!=ni) {
143  /* Should be a call to CParserError()... */
144  //pips_user_error("Number of initialization values (%d) incompatible"
145  // " with number of type fields (%d)\n", ni, nf);
146  // let's assume the source code is correct...
147  ne = gen_length(args);
148  }
149  ok = true;
150  }
151  /* Check for other dimensions which must be all declared: the
152  first dimension only can be implicit */
153  /* Already taken care of by "ni" */
154  /*
155  if(ok && gen_length(variable_dimensions(a))>1) {
156  bool sok = false;
157  int sne = -1;
158  sok = NumberOfElements(variable_basic(a), CDR(variable_dimensions(a)), &sne);
159  if(sok) {
160  ne *= sne;
161  }
162  else {
163  ok = false;
164  }
165  }
166  */
167  }
168  }
169  else if(value_constant_p(ev)) {
170  pips_internal_error("Not implemented yet");
171  }
172  }
173  }
174 
175  /* Check for 32 bit signed overflows */
176  mne = se>0 ? INT_MAX/se : INT_MAX;
177 
178  if(ok) {
179  if(mne>=ne)
180  *s = ne*se;
181  else {
182  pips_user_warning("Array size incompatible with 32 bit signed integers\n"
183  "Maximum number of elements: %d, number of elements declared: %d\n",
184  mne, ne);
185  ok = false;
186  }
187  }
188  else {
189  *s = se;
190  }
191 
192  return ok;
193 }
size_t gen_length(const list l)
Definition: list.c:150
basic basic_of_expression(expression)
basic basic_of_expression(expression exp): Makes a basic of the same basic as the expression "exp".
Definition: type.c:1383
int number_of_items(type)
Same as above, but arrays in struct are taken into account.
Definition: type.c:3925
int string_type_size(basic)
Definition: type.c:1047
bool char_type_p(type)
return true whether ‘t’ is a char or an unsigned char
Definition: type.c:2877
#define value_undefined_p(x)
Definition: ri.h:3017
#define basic_derived(x)
Definition: ri.h:640
#define basic_derived_p(x)
Definition: ri.h:638
#define basic_undefined_p(x)
Definition: ri.h:557
#define basic_string_p(x)
Definition: ri.h:629
#define value_expression_p(x)
Definition: ri.h:3080
#define value_expression(x)
Definition: ri.h:3082
#define entity_initial(x)
Definition: ri.h:2796
_int SizeOfElements(basic b)
This function returns the length in bytes of the Fortran or C type represented by a basic,...
Definition: size.c:297

References assert, basic_derived, basic_derived_p, basic_of_expression(), basic_string_p, basic_undefined_p, call_arguments, call_function, char_type_p(), ENTITY_BRACE_INTRINSIC_P, entity_initial, entity_type, expression_call_p(), expression_syntax, f(), gen_length(), number_of_initial_values(), number_of_items(), NumberOfElements(), ok, pips_internal_error, pips_user_warning, SizeOfElements(), string_type_size(), syntax_call, type_variable, type_variable_p, ultimate_type(), value_constant_p, value_expression, value_expression_p, value_undefined_p, variable_basic, and variable_dimensions.

Referenced by add_any_variable_to_area(), alias_check(), array_size(), common_members_of_module(), ComputeAddresses(), CSafeSizeOfArray(), current_offset_of_area(), dump_common_layout(), formal_variable_add_aliases(), fprint_any_environment(), GenericAddLocalEntityToDeclarations(), gfc2pips_computeAdressesOfArea(), gfc2pips_symbol2data_instruction(), impact_check(), MakeStorageRam(), new_add_any_variable_to_area(), print_C_common_layout(), print_common_layout(), ram_variable_add_aliases(), SafeSizeOfArray(), same_or_equivalence_argument_add_aliases(), and storage_space_of_variable().

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

◆ SizeOfDimension()

expression SizeOfDimension ( dimension  d)

Definition at line 503 of file size.c.

504 {
505  return
509  )
510  ;
511 }
expression copy_expression(expression p)
EXPRESSION.
Definition: ri.c:850
#define MINUS_OPERATOR_NAME
#define PLUS_OPERATOR_NAME
expression int_to_expression(_int i)
transform an int into an expression and generate the corresponding entity if necessary; it is not cle...
Definition: expression.c:1188
#define dimension_lower(x)
Definition: ri.h:980
#define dimension_upper(x)
Definition: ri.h:982

References copy_expression(), dimension_lower, dimension_upper, int_to_expression(), make_op_exp(), MINUS_OPERATOR_NAME, and PLUS_OPERATOR_NAME.

Referenced by dimension_size(), dimensions_to_dma(), do_sizeofdimension_reduction(), do_terapix_warmup_patching(), NumberOfElements(), and SizeOfIthDimension().

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

◆ SizeOfDimensions()

expression SizeOfDimensions ( list  dims)

computes the product of all dimensions in dims

Parameters
dimsims

Definition at line 522 of file size.c.

523 {
525 }
void * gen_reduce(void *r, void *(*fp)(void *, const list), const list l)
Definition: list.c:180
static void * do_sizeofdimension_reduction(void *v, const list l)
Definition: size.c:513

References do_sizeofdimension_reduction(), gen_reduce(), and int_to_expression().

Referenced by dimensions_to_dma(), do_group_constants_terapix(), do_group_count_elements_reduce(), do_linearize_array_reference(), do_linearize_type(), and makeTransfertSizeExpression().

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

◆ SizeOfElements()

_int SizeOfElements ( basic  b)

This function returns the length in bytes of the Fortran or C type represented by a basic, except for a varying size string (formal parameter).

What is the semantics for bitfields? Return its size rounded to a byte number large enough to fit, and not the size in bit.

Some of these values are target architecture dependent: e == 1 character e == 2 short int e == 4 int e == 6 long int e == 8 long long int They are defined in ri-util-local.h To be consistent with the machine compiling and executing PIPS, we could use a switch(e) and the corresponding sizeof().

As for int, e encodes some fine typing information: remove it

pips_assert("SizeOfElements", gen_consistent_p(b));

Size can be zero, i.e. unknown, for an external variable

Definition at line 297 of file size.c.

298 {
299  int e = -1;
300 
301  switch (basic_tag(b)) {
302  case is_basic_int:
303  {
304  /* Some of these values are target architecture dependent:
305  e == 1 character
306  e == 2 short int
307  e == 4 int
308  e == 6 long int
309  e == 8 long long int
310  They are defined in ri-util-local.h
311  To be consistent with the machine compiling and executing
312  PIPS, we could use a switch(e) and the corresponding sizeof().
313  */
314 
315  e = basic_int(b);
316  e = e % 10;
319  break;
320  }
321  case is_basic_float:
322  e = basic_float(b);
323  break;
324  case is_basic_logical:
325  e = basic_logical(b);
326  break;
327  case is_basic_complex:
328  e = basic_complex(b);
329  /* As for int, e encodes some fine typing information: remove it */
330  e = (e/8)*8;
331  break;
332  case is_basic_string: {
334 
335  /* pips_assert("SizeOfElements", gen_consistent_p(b)); */
336 
339  else if(value_symbolic_p(basic_string(b)))
341  else
342  user_error("SizeOfElements",
343  "Sizing of character variable by illegal value (tag=%d)",
344  basic_tag(b));
345 
346  if(constant_int_p(c))
347  e = constant_int(c);
348  else
349  user_error("SizeOfElements",
350  "Sizing of character variable by non-integer constant");
351  break;
352  }
353  case is_basic_bit: {
355  if(constant_int_p(c))
356  // Get the size in bits:
357  e = constant_int(c);
358  else
359  user_error("SizeOfElements",
360  "Sizing of bit-field is non-integer constant");
361  // Round the size to full byte number:
362  e = (e + 7)/8;
363  }
364  break;
365  case is_basic_pointer:
367  break;
368  case is_basic_derived:
370  break;
371  case is_basic_typedef:
373  break;
374  default:
375  pips_internal_error("Ill. tag %d for basic", basic_tag(b));
376  }
377 
378  /* Size can be zero, i.e. unknown, for an external variable */
379  //pips_assert("e is not zero", e!=0);
380 
381  return e;
382 }
#define user_error(fn,...)
Definition: misc-local.h:265
#define DEFAULT_INTEGER_TYPE_SIZE
#define DEFAULT_LONG_INTEGER_TYPE_SIZE
#define DEFAULT_POINTER_TYPE_SIZE
@ is_basic_derived
Definition: ri.h:579
@ is_basic_string
Definition: ri.h:576
@ is_basic_float
Definition: ri.h:572
@ is_basic_bit
Definition: ri.h:577
@ is_basic_pointer
Definition: ri.h:578
@ is_basic_int
Definition: ri.h:571
@ is_basic_logical
Definition: ri.h:573
@ is_basic_typedef
Definition: ri.h:580
@ is_basic_complex
Definition: ri.h:575
#define basic_int(x)
Definition: ri.h:616
#define symbolic_constant(x)
Definition: ri.h:2599
#define basic_tag(x)
Definition: ri.h:613
#define value_symbolic(x)
Definition: ri.h:3070
#define basic_logical(x)
Definition: ri.h:622
#define value_symbolic_p(x)
Definition: ri.h:3068
#define basic_float(x)
Definition: ri.h:619
#define basic_bit(x)
Definition: ri.h:634
#define basic_complex(x)
Definition: ri.h:628
#define constant_undefined
Definition: ri.h:802
#define basic_string(x)
Definition: ri.h:631
int entity_memory_size(entity dt)
Definition: size.c:239
int CSafeSizeOfArray(entity a)
BEGIN_EOLE.
Definition: size.c:225

References basic_bit, basic_complex, basic_derived, basic_float, basic_int, basic_logical, basic_string, basic_tag, basic_typedef, constant_int, constant_int_p, constant_undefined, CSafeSizeOfArray(), DEFAULT_INTEGER_TYPE_SIZE, DEFAULT_LONG_INTEGER_TYPE_SIZE, DEFAULT_POINTER_TYPE_SIZE, entity_memory_size(), is_basic_bit, is_basic_complex, is_basic_derived, is_basic_float, is_basic_int, is_basic_logical, is_basic_pointer, is_basic_string, is_basic_typedef, pips_internal_error, symbolic_constant, user_error, value_constant, value_constant_p, value_symbolic, and value_symbolic_p.

Referenced by abc_with_allocation_size(), alias_check(), array_size_stride(), basic_maximum(), consecutive_expression_p(), distance_between_expression(), edge_cost_polynome(), formal_variable_add_aliases(), get_optimal_opcode(), get_symbol_table(), get_vect_name_from_data(), impact_check(), interprocedural_abc_arrays(), make_datum_movement(), make_movement_scalar_wp65(), make_movements_loop_body_wp65(), ram_variable_add_aliases(), region_translation_init(), same_or_equivalence_argument_add_aliases(), size_of_regions(), SizeOfArray(), SizeOfIthDimension(), subscript_value_stride(), text_equivalence_class(), type_and_size_of_var(), type_memory_size(), ValueSizeOfArray(), and variables_width_filter().

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

◆ SizeOfIthDimension()

int SizeOfIthDimension ( entity  e,
int  i 
)

this function returns the size of the ith dimension of a variable e.

if called for the 0th dimension, it returns the variable element size.

Definition at line 453 of file size.c.

454 {
455  list pc = NIL;
456  intptr_t s = 0;
457 
458  if (!type_variable_p(entity_type(e))) {
459  fprintf(stderr, "[SizeOfIthDimension] not a variable\n");
460  abort();
461  }
462 
463  if (i == 0)
465 
467 
468  while (pc != NULL && --i > 0)
469  pc = CDR(pc);
470 
471  if (pc == NULL) {
472  fprintf(stderr, "[SizeOfIthDimension] not enough dimensions\n");
473  abort();
474  }
475 
477  if(!(expression_integer_value(sod, &s))) {
478  fprintf(stderr, "[SizeOfIthDimension] Non constant %dth dimension\n", i);
479  abort();
480  }
481  free_expression(sod);
482 
483  return s;
484 }
#define NIL
The empty list (nil in Lisp)
Definition: newgen_list.h:47
#define abort()
Definition: misc-local.h:53
int fprintf()
test sc_min : ce test s'appelle par : programme fichier1.data fichier2.data ...

References abort, CAR, CDR, DIMENSION, entity_type, expression_integer_value(), fprintf(), free_expression(), intptr_t, NIL, SizeOfDimension(), SizeOfElements(), type_variable, type_variable_p, variable_basic, and variable_dimensions.

Referenced by array_distribution_similar_p(), ComputeNewSizeOfIthDimension(), create_init_common_param_for_arrays(), hpfc_broadcast_buffers(), hpfc_compute_distribute_constraints(), NormalizeOneTemplateDistribution(), OffsetOfReference(), one_message_guards_and_neighbour(), processor_number(), same_alignment_p(), and text_equivalence_class().

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

◆ storage_space_of_variable()

int storage_space_of_variable ( entity  v)

Storage size is expressed in bytes

Definition at line 656 of file size.c.

657 {
658  /* Storage size is expressed in bytes */
659  int l;
660  char * s;
661 
663  user_warning("storage_space_of_variable",
664  "hash table should have been allocated\n");
666  }
667  s = hash_get(entity_to_size, (char *) v);
668  l = (_int) s;
669  if (s == HASH_UNDEFINED_VALUE) {
670  if(!SizeOfArray(v, &l)) {
671  fprintf(stderr, "[storage_space_of_variable] Non constant array size\n");
672  abort();
673  }
674  hash_put(entity_to_size, (char *) v, (char *) (_int) l);
675  }
676 
677  return l;
678 }
void * hash_get(const hash_table htp, const void *key)
this function retrieves in the hash table pointed to by htp the couple whose key is equal to key.
Definition: hash.c:449
void hash_put(hash_table htp, const void *key, const void *val)
This functions stores a couple (key,val) in the hash table pointed to by htp.
Definition: hash.c:364
#define user_warning(fn,...)
Definition: misc-local.h:262
#define HASH_UNDEFINED_VALUE
value returned by hash_get() when the key is not found; could also be called HASH_KEY_NOT_FOUND,...
Definition: newgen_hash.h:56
intptr_t _int
_INT
Definition: newgen_types.h:53

References abort, entity_to_size, fprintf(), hash_get(), hash_pointer, hash_put(), hash_table_make(), hash_table_undefined, HASH_UNDEFINED_VALUE, SizeOfArray(), and user_warning.

Referenced by create_new_common_variable(), and variable_entities_may_conflict_p().

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

◆ type_memory_size()

int type_memory_size ( type  t)

Seems to be the case for defined types; FI: why are they allocated in RAM while they only exist at compile time ?

How is it implemented? 32 bit integer?

A struct (or a union) may be hidden, with its declaration located in the source code of a library. For instance, "_IO_FILE_plus" in stdio.h. Since it contains at least one byte, let set s to 1? Or let the caller deal with the problem?

Definition at line 248 of file size.c.

249 {
250  int s = 0;
251 
252  switch(type_tag(t)) {
253  case is_type_statement:
254  case is_type_area:
255  case is_type_functional:
256  case is_type_varargs:
257  case is_type_unknown:
258  case is_type_void:
259  pips_internal_error("arg. with ill. tag %d", type_tag(t));
260  break;
261  case is_type_variable:
262  {
263  /* Seems to be the case for defined types; FI: why are they
264  allocated in RAM while they only exist at compile time ? */
267  s*=dimension_size(dim);
268 
269  } break;
270  case is_type_struct:
271  MAP(ENTITY, v, {s+=CSafeSizeOfArray(v);}, type_struct(t));
272  break;
273  case is_type_union:
274  MAP(ENTITY, v, {s = s>CSafeSizeOfArray(v)? s : CSafeSizeOfArray(v);}, type_union(t));
275  break;
276  case is_type_enum:
277  s = 4; /* How is it implemented? 32 bit integer? */
278  break;
279  default:
280  pips_internal_error("arg. with unknown tag %d", type_tag(t));
281  break;
282  }
283  /* A struct (or a union) may be hidden, with its declaration
284  located in the source code of a library. For instance,
285  "_IO_FILE_plus" in stdio.h. Since it contains at least one byte,
286  let set s to 1? Or let the caller deal with the problem? */
287  // s = s>0? s : 1;
288  return s;
289 }
#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 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
#define type_struct(x)
Definition: ri.h:2964
#define type_tag(x)
Definition: ri.h:2940
#define ENTITY(x)
ENTITY.
Definition: ri.h:2755
@ is_type_varargs
Definition: ri.h:2902
@ is_type_void
Definition: ri.h:2904
@ is_type_enum
Definition: ri.h:2907
@ is_type_statement
Definition: ri.h:2898
@ is_type_functional
Definition: ri.h:2901
@ is_type_variable
Definition: ri.h:2900
@ is_type_union
Definition: ri.h:2906
@ is_type_area
Definition: ri.h:2899
@ is_type_unknown
Definition: ri.h:2903
@ is_type_struct
Definition: ri.h:2905
#define type_union(x)
Definition: ri.h:2967
int dimension_size(dimension d)
this function computes the size of a dimension.
Definition: size.c:491

References CSafeSizeOfArray(), DIMENSION, dimension_size(), ENTITY, FOREACH, is_type_area, is_type_enum, is_type_functional, is_type_statement, is_type_struct, is_type_union, is_type_unknown, is_type_varargs, is_type_variable, is_type_void, MAP, pips_internal_error, SizeOfElements(), type_struct, type_tag, type_union, type_variable, variable_basic, and variable_dimensions.

Referenced by entity_memory_size(), EvalSizeofexpression(), get_type_max_width(), and partial_eval_syntax().

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

◆ ValueNumberOfElements()

Value ValueNumberOfElements ( list  ld)
Parameters
ldd

Definition at line 435 of file size.c.

436 {
437  list pc;
438  Value ne = VALUE_ONE;
439 
440  for (pc = ld; pc != NULL; pc = CDR(pc)) {
442  }
443 
444  return(ne);
445 }
int Value
#define VALUE_ONE
#define value_mult(v, w)
whether the default is protected or not this define makes no sense any more...
Value ValueSizeOfDimension(dimension d)
FI: I do not understand the "Value" cast.
Definition: size.c:531

References CAR, CDR, DIMENSION, value_mult, VALUE_ONE, and ValueSizeOfDimension().

Referenced by simd_replace_parameters(), and ValueSizeOfArray().

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

◆ ValueSizeOfArray()

Value ValueSizeOfArray ( entity  e)

Definition at line 206 of file size.c.

207 {
208  variable a;
209  Value longueur, taille_elt;
210 
212  a = type_variable(entity_type(e));
213 
214  taille_elt = (Value) SizeOfElements(variable_basic(a));
216 
217  return(value_mult(taille_elt,longueur));
218 }
Value ValueNumberOfElements(list ld)
Definition: size.c:435

References assert, entity_type, SizeOfElements(), type_variable, type_variable_p, value_mult, ValueNumberOfElements(), variable_basic, and variable_dimensions.

Referenced by equivalent_entity_compare(), and text_equivalence_class().

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

◆ ValueSizeOfDimension()

Value ValueSizeOfDimension ( dimension  d)

FI: I do not understand the "Value" cast.

Definition at line 531 of file size.c.

532 {
533  Value dl, du;
534  intptr_t l = 0 ;
535  intptr_t u = 0;
536  bool ok;
537 
539  du = (Value) u;
541  dl = (Value) l;
542 
543  if(!ok) {
544  fprintf(stderr, "[ValueSizeOfIthDimension] Non constant dimension\n");
545  abort();
546  }
547 
548  return(value_plus(value_minus(du,dl), VALUE_ONE));
549 }
#define value_minus(v1, v2)
#define value_plus(v1, v2)
binary operators on values

References abort, dimension_lower, dimension_upper, expression_integer_value(), fprintf(), intptr_t, ok, value_minus, VALUE_ONE, and value_plus.

Referenced by ValueNumberOfElements().

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

◆ variable_entities_may_conflict_p()

bool variable_entities_may_conflict_p ( entity  e1,
entity  e2 
)

Can we have and check static aliasing in a1?

Let's assume we are dealing with Fortran code, but another test should be added about the current module language. No test on dynamic aliasing since we are dealing here with direct read and write effects.

return(r1 != ram_undefined && r2 != ram_undefined && f1 == f2 && a1 == a2 && INTERVAL_INTERSECTION(o1, l1, o2, l2));

FI: it's too late to check if r1 and r2 are defined: you already have core dumped! also, f1 and f2 are not relevant since location are governed by area a1 and a2

Parameters
e11
e22

Definition at line 689 of file size.c.

690 {
691  bool intersect_p = false;
692  storage s1, s2;
693  ram r1 = ram_undefined, r2 = ram_undefined;
694  int o1, o2, l1, l2;
695  entity f1, f2, a1, a2;
696 
697  if(same_entity_p(e1, e2)) return true;
698 
699  s1 = entity_storage(e1);
700  s2 = entity_storage(e2);
701 
702  if (! (storage_ram_p(s1) && storage_ram_p(s2))) {
703  // Conflicts may exist beween array elements when an array is
704  // a formal parameter
705  if( ! (storage_formal_p(s1) && storage_formal_p(s2)) ) {
706  return false;
707  }
708  else {
709  formal f1 = storage_formal(s1);
710  formal f2 = storage_formal(s2);
711  entity e1 = formal_function(f1);
712  entity e2 = formal_function(f2);
713  if(e1==e2) {
714  int o1 = formal_offset(f1);
715  int o2 = formal_offset(f2);
716  return o1==o2;
717  }
718  return false;
719  }
720  }
721 
722  r1 = storage_ram(s1);
723  r2 = storage_ram(s2);
724 
725  a1 = ram_section(r1);
726  a2 = ram_section(r2);
727 
728  if(a1!=a2) return false;
729 
730  /* Can we have and check static aliasing in a1? */
731  if(stack_area_p(a1))
732  return false;
733 
734  if(heap_area_p(a1))
735  return false;
736 
737  // FI: we create aliasing in C between an array and its elements
738  // This is used to analyse the value of array elements
739  if (false && c_module_p(get_current_module_entity()))
740  return false;
741 
742  /* Let's assume we are dealing with Fortran code, but another test
743  should be added about the current module language. No test on
744  dynamic aliasing since we are dealing here with direct read and
745  write effects. */
746  o1 = ram_offset(r1);
747  o2 = ram_offset(r2);
748 
749  if(o1==o2) return true;
750 
751  f1 = ram_function(r1);
752  f2 = ram_function(r2);
753 
754  if(f1==f2 && (ENDP(ram_shared(r1)) || ENDP(ram_shared(r2))))
755  return false;
756 
757  l1 = storage_space_of_variable(e1);
758  l1 = l1+o1-1;
759 
760 
761  l2 = storage_space_of_variable(e2);
762  l2 = l2+o2-1;
763 
764  /* return(r1 != ram_undefined && r2 != ram_undefined &&
765  f1 == f2 && a1 == a2 &&
766  INTERVAL_INTERSECTION(o1, l1, o2, l2)); */
767 
768  /* FI: it's too late to check if r1 and r2 are defined:
769  * you already have core dumped!
770  * also, f1 and f2 are not relevant since location are governed
771  * by area a1 and a2
772  */
773 
774  intersect_p = ( a1 == a2 && INTERVAL_INTERSECTION(o1, l1, o2, l2));
775 
776  return intersect_p;
777 }
entity get_current_module_entity(void)
Get the entity of the current module.
Definition: static.c:85
int f2(int off1, int off2, int w, int n, float r[n], float a[n], float b[n])
Definition: offsets.c:1
bool stack_area_p(entity aire)
Definition: area.c:104
bool heap_area_p(entity aire)
Definition: area.c:86
bool same_entity_p(entity e1, entity e2)
predicates on entities
Definition: entity.c:1321
bool c_module_p(entity m)
Test if a module "m" is written in C.
Definition: entity.c:2777
#define formal_offset(x)
Definition: ri.h:1408
#define storage_formal_p(x)
Definition: ri.h:2522
#define ram_undefined
Definition: ri.h:2221
#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_formal(x)
Definition: ri.h:2524
#define formal_function(x)
Definition: ri.h:1406
#define storage_ram(x)
Definition: ri.h:2521
#define ram_function(x)
Definition: ri.h:2247
#define ram_shared(x)
Definition: ri.h:2253
#define ram_offset(x)
Definition: ri.h:2251
s1
Definition: set.c:247
int storage_space_of_variable(entity v)
Definition: size.c:656
#define INTERVAL_INTERSECTION(a, b, c, d)
Definition: size.c:680

References c_module_p(), ENDP, entity_storage, f2(), formal_function, formal_offset, get_current_module_entity(), heap_area_p(), INTERVAL_INTERSECTION, ram_function, ram_offset, ram_section, ram_shared, ram_undefined, s1, same_entity_p(), stack_area_p(), storage_formal, storage_formal_p, storage_ram, storage_ram_p, and storage_space_of_variable().

Referenced by entities_maymust_conflict_p(), references_may_conflict_p(), and SaveChains().

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

Variable Documentation

◆ entity_to_size

hash_table entity_to_size = hash_table_undefined
static

a hash table to map entities to their numbers of elements

This table is critical to compute use-def chains at an acceptable speed because the computation of a variable allocated space is very slow. Declaration are preserved in PIPS and constant expressions must be evaluated.

Note: the current implementation is not safe. The hash table may be kept from module to module (which should be OK) and from workspace to workspace, which is not.

This is an unusual object because it's life time is the workspace life time and not the module analysis life time. This hash table acts as a cache of the symbol table.

Definition at line 623 of file size.c.

Referenced by reset_entity_to_size(), safe_reset_entity_to_size(), set_entity_to_size(), and storage_space_of_variable().