PIPS
prettyprint.c
Go to the documentation of this file.
1 /*
2 
3  $Id: prettyprint.c 23065 2016-03-02 09:05:50Z coelho $
4 
5  Copyright 1989-2016 MINES ParisTech
6 
7  This file is part of PIPS.
8 
9  PIPS is free software: you can redistribute it and/or modify it
10  under the terms of the GNU General Public License as published by
11  the Free Software Foundation, either version 3 of the License, or
12  any later version.
13 
14  PIPS is distributed in the hope that it will be useful, but WITHOUT ANY
15  WARRANTY; without even the implied warranty of MERCHANTABILITY or
16  FITNESS FOR A PARTICULAR PURPOSE.
17 
18  See the GNU General Public License for more details.
19 
20  You should have received a copy of the GNU General Public License
21  along with PIPS. If not, see <http://www.gnu.org/licenses/>.
22 
23 */
24 #ifdef HAVE_CONFIG_H
25  #include "pips_config.h"
26 #endif
27 /* package convex effects : Be'atrice Creusillet 5/97
28  *
29  * File: prettyprint.c
30  * ~~~~~~~~~~~~~~~~~~~
31  *
32  * This File contains the prettyprinting functions.
33  *
34  */
35 
36 #include <stdio.h>
37 #include <string.h>
38 #include <limits.h>
39 
40 #include "linear.h"
41 
42 #include "genC.h"
43 #include "ri.h"
44 #include "effects.h"
45 #include "text.h"
46 #include "database.h"
47 
48 #include "misc.h"
49 #include "ri-util.h"
50 #include "prettyprint.h"
51 #include "effects-util.h"
52 #include "top-level.h"
53 #include "properties.h"
54 
55 #include "effects-generic.h"
56 #include "effects-convex.h"
57 
58 #include "text-util.h"
59 #include "pipsdbm.h"
60 #include "resources.h"
61 
62 #define REGION_FORESYS_PREFIX "C$REG"
63 
64 
65 string
66 region_sc_to_string(string __attribute__ ((unused)) s,
67  Psysteme __attribute__ ((unused)) ps)
68 {
69  pips_internal_error("implementation dropped");
70  return string_undefined;
71 }
72 
73 
74 
75 #define append(s) add_to_current_line(line_buffer, s, str_prefix, t_reg)
76 
77 /* text text_region(effect reg)
78  * input : a region
79  * output : a text consisting of several lines of commentaries,
80  * representing the region
81  * modifies : nothing
82  */
84 {
85  text t_reg = make_text(NIL);
86 
87  if(store_effect_p(reg)
88  || !get_bool_property("PRETTYPRINT_MEMORY_EFFECTS_ONLY")) {
89  bool foresys = get_bool_property("PRETTYPRINT_FOR_FORESYS");
90  string str_prefix =
94  reference r;
95  action ac;
96  action_kind ak;
97  approximation ap;
98  descriptor ed = effect_descriptor(reg);
99  Psysteme sc;
100  list /* of string */ ls;
101 
102  if(effect_undefined_p(reg))
103  {
104  free_text(t_reg); // t_reg should be used instead of make_text()
105  user_log("[text_region] unexpected effect undefined\n");
106  return make_text(CONS(SENTENCE,
108  strdup(concatenate(str_prefix, "<REGION_UNDEFINED>\n", NULL))),
109  NIL));
110  }
111  /* else the effect is defined...
112  */
113 
114  /* PREFIX
115  */
117  if (!foresys) append(" <");
118 
119  /* REFERENCE
120  */
121  r = effect_any_reference(reg);
122  ls = foresys? Words_Reference(r): effect_words_reference(r);
123 
124  MAP(STRING, s, append(s), ls);
125  gen_free_string_list(ls); ls = NIL;
126 
127  /* ACTION and APPROXIMATION
128  */
129  ac = effect_action(reg);
130  ak = action_to_action_kind(ac);
131  ap = effect_approximation(reg);
132 
133  if (foresys)
134  {
135  append(", RGSTAT(");
136  append(action_read_p(ac) ? "R," : "W,");
137  append(approximation_may_p(ap) ? "MAY), " : "EXACT), ");
138  }
139  else /* PIPS prettyprint */
140  {
141  append("-");
143  /* To preserve the current output, actions on store are
144  implicit, actions on environment and type declaration are
145  specified */
146  if(!action_kind_store_p(ak))
148  append(approximation_may_p(ap) ? "-MAY" : "-EXACT");
149  append("-");
150  }
151 
152  /* SYSTEM
153  * sorts in such a way that constraints with phi variables come first.
154  */
155  if(descriptor_none_p(ed)) {
156  /* FI: there is no system; it's equivalent to an empty one... */
157  append("{}");
158  } else {
159  sc = sc_copy(region_system(reg));
161  system_sorted_text_format(line_buffer, str_prefix, t_reg, sc,
163  vect_contains_phi_p, foresys);
164 
165  sc_rm(sc);
166  }
167  /* CLOSE
168  */
169  if (!foresys) append(">");
170  close_current_line(line_buffer, t_reg,str_prefix);
171  }
172 
173  return t_reg;
174 }
175 
176 /* print the constraint system of a region
177  *
178  * Used for debugging, e.g. called from gdb
179  */
180 void print_region_sc(effect r)
181 {
183  if(descriptor_none_p(d)) {
184  fprintf(stderr, "No descriptor\n");
185  }
186  else {
187  Psysteme sc = region_system(r);
189  }
190 }
191 
192 
193 /* text text_array_regions(list l_reg, string ifread, string ifwrite)
194  * input : a list of regions
195  * output : a text representing this list of regions.
196  * comment : if the number of array regions is not nul, and if
197  * PRETTYPRINT_LOOSE is true, then empty lines are
198  * added before and after the text of the list of regions.
199  */
200 static text
201 text_array_regions(list l_reg, string ifread, string ifwrite)
202 {
203  text reg_text = make_text(NIL);
204  /* in case of loose_prettyprint, at least one region to print? */
205  bool loose_p = get_bool_property("PRETTYPRINT_LOOSE");
206  bool one_p = false;
207 
208  set_action_interpretation(ifread, ifwrite);
209 
210  /* GO: No redundant test anymore, see text_statement_array_regions */
211  if (l_reg != (list) HASH_UNDEFINED_VALUE && l_reg != list_undefined)
212  {
213  gen_sort_list(l_reg, (int (*)(const void *,const void *)) effect_compare);
214  FOREACH(EFFECT, reg, l_reg)
215  {
216  if(store_effect_p(reg)
217  || !get_bool_property("PRETTYPRINT_MEMORY_EFFECTS_ONLY")) {
218  entity ent = effect_entity(reg);
219  if ( anywhere_effect_p(reg)
220  || malloc_effect_p(reg)
221  || get_bool_property("PRETTYPRINT_SCALAR_REGIONS")
222  || ! entity_non_pointer_scalar_p(ent))
223  {
224  if (loose_p && !one_p )
225  {
226  ADD_SENTENCE_TO_TEXT(reg_text,
228  strdup("\n")));
229  one_p = true;
230  }
231  MERGE_TEXTS(reg_text, text_region(reg));
232  }
233  }
234  }
235 
236  if (loose_p && one_p)
237  ADD_SENTENCE_TO_TEXT(reg_text,
239  strdup("\n")));
240  }
241 
243  return reg_text;
244 }
245 ␌
246 /* practical interfaces
247  */
249 { return text_array_regions(l, ACTION_IN, ACTION_OUT);}
250 
252 { return text_array_regions(l, ACTION_READ, ACTION_WRITE);}
253 
255 { return text_array_regions(l, ACTION_COPYIN, ACTION_COPYOUT);}
256 
258 { return text_array_regions(l, ACTION_PRIVATE, ACTION_PRIVATE);}
259 
260 /*********************************************************** ABSOLETE MAYBE? */
261 
262 /* CALLGRAPH/ICFG stuff (should be OBSOLETE?)
263  */
264 static text
265 get_text_regions_for_module(
266  const char* module_name,
267  string resource_name,
268  string ifread,
269  string ifwrite)
270 {
271  text t;
272  entity mod;
273  list /* of effect */ le =
276 
277  /* the current entity may be used for minimal names... */
280  t = text_array_regions(le, ifread, ifwrite);
282  return t;
283 }
284 
285 text get_text_regions(const string module_name)
286 {
287  return get_text_regions_for_module
288  (module_name, DBR_SUMMARY_REGIONS, ACTION_READ, ACTION_WRITE);
289 }
290 
292 {
293  return get_text_regions_for_module
294  (module_name, DBR_IN_SUMMARY_REGIONS, ACTION_IN, ACTION_OUT);
295 }
296 
298 {
299  return get_text_regions_for_module
300  (module_name, DBR_OUT_SUMMARY_REGIONS, ACTION_IN, ACTION_OUT);
301 }
302 
303 /*********************************************************** DEBUG FUNCTIONS */
304 
305 /* void print_regions(list pc)
306  * input : a list of regions.
307  * modifies : nothing.
308  * comment : prints the list of regions on stderr .
309  */
310 static void print_regions_with_action(list pc, string ifread, string ifwrite)
311 {
312  set_action_interpretation(ifread, ifwrite);
313 
314  if (pc == NIL) {
315  fprintf(stderr,"\t<NONE>\n");
316  }
317  else {
318  FOREACH(EFFECT, ef, pc) {
319  print_region(ef);
320  fprintf(stderr,"\n");
321  }
322  }
323 
325 }
326 
327 /* external interfaces
328  *
329  * NW:
330  * before calling
331  * "print_inout_regions"
332  * or "print_rw_regions"
333  * or "print_copyinout_regions"
334  * or "print_private_regions"
335  *
336  * "module_to_value_mappings" must be called to set up the
337  * hash table to translate value into value names
338  */
339 void print_rw_regions(list l)
340 { print_regions_with_action(l, ACTION_READ, ACTION_WRITE);}
341 
343 { print_regions_with_action(l, ACTION_IN, ACTION_OUT);}
344 
346 { print_regions_with_action(l, ACTION_COPYIN, ACTION_COPYOUT);}
347 
349 { print_regions_with_action(l, ACTION_PRIVATE, ACTION_PRIVATE);}
350 
351 void print_regions(list l) { print_rw_regions(l);}
352 
353 /* void print_regions(effect r)
354  * input : a region.
355  * modifies : nothing.
356  * comment : prints the region on stderr using words_region.
357  *
358  * NW:
359  * before calling "print_region" or "text_region"
360  *
361  * "module_to_value_mappings" must be called to set up the
362  * hash table to translate value into value names
363  * (see comment for "module_to_value_mappings" for what must be done
364  * before that is called)
365  *
366  * and also "set_action_interpretation" with arguments:
367  * ACTION_READ, ACTION_WRITE to label regions as R/W
368  * ACTION_IN, ACTION_OUT to label regions as IN/OUT
369  * ACTION_COPYIN, ACTION_COPYOUT to label regions as COPYIN/COPYOUT
370  * ACTION_PRIVATE, ACTION_PRIVATE to label regions as PRIVATE
371  *
372  * like this:
373  *
374  * const char* module_name;
375  * entity module;
376  * ...
377  * (set up call to module_to_value_mappings as indicated in its comments)
378  * ...
379  * module_to_value_mappings(module);
380  * set_action_interpretation(ACTION_IN, ACTION_OUT);
381  *
382  * (that's it, but after the call to "print_region" or "text_region",
383  * don't forget to do:)
384  *
385  * reset_action_interpretation();
386  * (resets after call to module_to_value_mappings as indicated in its comments)
387  *
388  * FI: Regions/Effects related to store and environment mutations are not
389  * displayed because they have no descriptors, but by two LFs.
390  */
391 void print_region(effect r)
392 {
393  fprintf(stderr,"\n");
394  if(effect_region_p(r)) {
395  text t = text_region(r);
396  print_text(stderr, t);
397  free_text(t);
398  }
399  /* FI: uncommented to introduce environment and type declaration
400  regions/effects */
401  /* else print_words(stderr, words_effect(r)); */
402  else {
403  // FI: this is not homogeneous with the regions
404  //print_words(stderr, words_effect(r));
405  // This is even worse
406  /*
407  list el = CONS(EFFECT, r, NIL);
408  text t = simple_rw_effects_to_text(el);
409  print_text(stderr, t);
410  free_text(t);
411  gen_free_list(el);
412  */
413  // FI: let's homogeneize the outputs...
414  text t = text_region(r);
415  print_text(stderr, t);
416  free_text(t);
417  }
418  fprintf(stderr,"\n");
419 }
420 
421 
422 
423 /************************************************* STATISTICS FOR OPERATORS */
424 
425 
426 void print_regions_op_statistics(char __attribute__ ((unused)) *mod_name,
427  int regions_type)
428 {
429  pips_assert("true", mod_name==mod_name && regions_type==regions_type);
430  /*
431  string prefix = string_undefined;
432 
433  switch (regions_type) {
434  case R_RW :
435  prefix = "rrw-";
436  break;
437  case R_IN :
438  prefix = "rin-";
439  break;
440  case R_OUT :
441  prefix = "rout-";
442  break;
443  }
444 
445  print_proj_op_statistics(mod_name, prefix);
446  print_umust_statistics(mod_name, prefix);
447  print_umay_statistics(mod_name, prefix);
448  print_dsup_statistics(mod_name, prefix); */
449  /* print_dinf_statistics(mod_name, prefix); */
450 
451 }
452 
453 
454 /***************************************************************** SORTING */
void user_log(const char *format,...)
Definition: message.c:234
sentence make_sentence(enum sentence_utype tag, void *val)
Definition: text.c:59
text make_text(list a)
Definition: text.c:107
void free_text(text p)
Definition: text.c:74
#define REGION_FORESYS_PREFIX
Definition: prettyprint.c:60
#define append(s)
text text_region_no_action(effect reg) input : a region output : a text consisting of several lines o...
Definition: prettyprint.c:77
int is_inferior_cell_descriptor_pvarval(Pvecteur *pvarval1, Pvecteur *pvarval2)
weight function for Pvecteur passed as argument to sc_lexicographic_sort in prettyprint functions inv...
Definition: compare.c:305
int effect_compare(effect *peff1, effect *peff2)
Compares two effects for sorting.
Definition: compare.c:187
void system_sorted_text_format(string line, string prefix, text txt, Psysteme ps, string(*variable_name)(Variable), bool(*put_first)(Pvecteur), bool a_la_fortran)
lower level hook for regions.
#define resource_name(x)
Definition: database.h:108
#define region_system(reg)
#define effect_region_p(e)
void print_copyinout_regions(list)
text get_text_regions(const string)
void print_regions(list)
void print_rw_regions(list)
text text_copyinout_array_regions(list)
text text_rw_array_regions(list)
text text_region(effect)
void print_region_sc(effect)
void print_private_regions(list)
text text_inout_array_regions(list)
void print_regions_op_statistics(char *, int)
text text_private_array_regions(list)
void print_inout_regions(list)
string region_sc_to_string(string, Psysteme)
prettyprint.c
text get_text_in_regions(const string)
text get_text_out_regions(const string)
#define ACTION_WRITE
#define ACTION_IN
#define ACTION_OUT
#define ACTION_READ
#define ACTION_COPYIN
#define ACTION_COPYOUT
#define ACTION_PRIVATE
string action_interpretation(int tag)
void reset_action_interpretation(void)
void set_action_interpretation(string, string)
prettyprint.c
#define effect_any_reference(e)
FI: cannot be used as a left hand side.
list effect_words_reference(reference obj)
made from words_reference this function can print entity_name instead of entity_local_name,...
Definition: prettyprint.c:68
const char * pips_region_user_name(entity ent)
char * pips_region_user_name(entity ent) output : the name of entity.
Definition: prettyprint.c:169
action_kind action_to_action_kind(action)
Without the consistency test, this function would certainly be inlined.
Definition: effects.c:1048
entity effect_entity(effect)
cproto-generated files
Definition: effects.c:52
bool store_effect_p(effect)
Definition: effects.c:1062
bool malloc_effect_p(effect)
Definition: effects.c:478
bool anywhere_effect_p(effect)
Is it an anywhere effect? ANYMMODULE:ANYWHERE
Definition: effects.c:346
string action_kind_to_string(action_kind)
Definition: effects.c:995
bool vect_contains_phi_p(Pvecteur)
bool vect_contains_phi_p(Pvecteur v) input : a vector output : true if v contains a PHI variable,...
Definition: effects.c:1427
#define effect_undefined_p(x)
Definition: effects.h:615
#define action_kind_store_p(x)
Definition: effects.h:259
#define effect_action(x)
Definition: effects.h:642
#define approximation_may_p(x)
Definition: effects.h:363
#define action_tag(x)
Definition: effects.h:310
#define action_read_p(x)
Definition: effects.h:311
#define effect_descriptor(x)
Definition: effects.h:646
#define effects_effects(x)
Definition: effects.h:710
#define descriptor_none_p(x)
Definition: effects.h:602
#define effect_approximation(x)
Definition: effects.h:644
#define EFFECT(x)
EFFECT.
Definition: effects.h:608
const char * module_name(const char *s)
Return the module part of an entity name.
Definition: entity_names.c:296
bool get_bool_property(const string)
FC 2015-07-20: yuk, moved out to prevent an include cycle dependency include "properties....
#define STRING(x)
Definition: genC.h:87
void reset_current_module_entity(void)
Reset the current module entity.
Definition: static.c:97
entity set_current_module_entity(entity)
static.c
Definition: static.c:66
#define NIL
The empty list (nil in Lisp)
Definition: newgen_list.h:47
void gen_free_string_list(list ls)
Definition: list.c:564
#define CONS(_t_, _i_, _l_)
List element cell constructor (insert an element at the beginning of a list)
Definition: newgen_list.h:150
#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 list_undefined
Undefined list definition :-)
Definition: newgen_list.h:69
#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
void gen_sort_list(list l, gen_cmp_func_t compare)
Sorts a list of gen_chunks in place, to avoid allocations...
Definition: list.c:796
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
#define pips_assert(what, predicate)
common macros, two flavors depending on NDEBUG
Definition: misc-local.h:172
#define pips_internal_error
Definition: misc-local.h:149
string concatenate(const char *,...)
Return the concatenation of the given strings.
Definition: string.c:183
#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
#define string_undefined
Definition: newgen_types.h:40
string get_comment_sentinel()
Start a single line comment.
Definition: misc.c:154
string get_comment_continuation()
Start a single line comment with continuation (blank spaces)
Definition: misc.c:167
list Words_Reference(reference obj)
Definition: misc.c:786
#define print_region(x)
Definition: print.c:343
static int * line_buffer
le buffer contenant la ligne que l'on doit lire en avance pour se rendre compte qu'on a finit de lire...
Definition: reader.c:251
entity module_name_to_entity(const char *mn)
This is an alias for local_name_to_top_level_entity.
Definition: entity.c:1479
bool entity_non_pointer_scalar_p(entity)
Definition: variable.c:1193
void sc_rm(Psysteme ps)
void sc_rm(Psysteme ps): liberation de l'espace memoire occupe par le systeme de contraintes ps;
Definition: sc_alloc.c:277
Psysteme sc_copy(Psysteme ps)
Psysteme sc_copy(Psysteme ps): duplication d'un systeme (allocation et copie complete des champs sans...
Definition: sc_alloc.c:230
void sc_print(Psysteme ps, get_variable_name_t nom_var)
void sc_print()
Definition: sc_io.c:194
int fprintf()
test sc_min : ce test s'appelle par : programme fichier1.data fichier2.data ...
char * strdup()
void sc_lexicographic_sort(Psysteme sc, int(*compare)(Pvecteur *, Pvecteur *))
Minimize first the lexico-graphic weight of each constraint according to the comparison function "com...
Definition: sc_unaires.c:206
static bool __attribute__((unused))
Definition: prettyprint.c:435
The structure used to build lists in NewGen.
Definition: newgen_list.h:41
#define FORESYS_CONTINUATION_PREFIX
#define MERGE_TEXTS(r, t)
#define ADD_SENTENCE_TO_TEXT(t, p)
#define MAX_LINE_LENGTH
maximum length of a line when prettyprinting...
void print_text(FILE *fd, text t)
Definition: print.c:195
void close_current_line(string, text, string)
Definition: util.c:235
#define SENTENCE(x)
newgen_unformatted_domain_defined
Definition: text.h:36
@ is_sentence_formatted
Definition: text.h:57
char *(* get_variable_name_t)(Variable)
Definition: vecteur-local.h:62