1 /* Interprocedural Identical Code Folding pass
2    Copyright (C) 2014-2019 Free Software Foundation, Inc.
3 
4    Contributed by Jan Hubicka <hubicka@ucw.cz> and Martin Liska <mliska@suse.cz>
5 
6 This file is part of GCC.
7 
8 GCC is free software; you can redistribute it and/or modify it under
9 the terms of the GNU General Public License as published by the Free
10 Software Foundation; either version 3, or (at your option) any later
11 version.
12 
13 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
14 WARRANTY; without even the implied warranty of MERCHANTABILITY or
15 FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
16 for more details.
17 
18 You should have received a copy of the GNU General Public License
19 along with GCC; see the file COPYING3.  If not see
20 <http://www.gnu.org/licenses/>.  */
21 
22 #include "config.h"
23 #include "system.h"
24 #include "coretypes.h"
25 #include "backend.h"
26 #include "rtl.h"
27 #include "tree.h"
28 #include "gimple.h"
29 #include "tree-pass.h"
30 #include "ssa.h"
31 #include "cgraph.h"
32 #include "data-streamer.h"
33 #include "gimple-pretty-print.h"
34 #include "alias.h"
35 #include "fold-const.h"
36 #include "gimple-iterator.h"
37 #include "ipa-utils.h"
38 #include "tree-eh.h"
39 #include "builtins.h"
40 #include "attribs.h"
41 
42 #include "ipa-icf-gimple.h"
43 
44 namespace ipa_icf_gimple {
45 
46 /* Initialize internal structures for a given SOURCE_FUNC_DECL and
47    TARGET_FUNC_DECL. Strict polymorphic comparison is processed if
48    an option COMPARE_POLYMORPHIC is true. For special cases, one can
49    set IGNORE_LABELS to skip label comparison.
50    Similarly, IGNORE_SOURCE_DECLS and IGNORE_TARGET_DECLS are sets
51    of declarations that can be skipped.  */
52 
func_checker(tree source_func_decl,tree target_func_decl,bool compare_polymorphic,bool ignore_labels,hash_set<symtab_node * > * ignored_source_nodes,hash_set<symtab_node * > * ignored_target_nodes)53 func_checker::func_checker (tree source_func_decl, tree target_func_decl,
54 			    bool compare_polymorphic,
55 			    bool ignore_labels,
56 			    hash_set<symtab_node *> *ignored_source_nodes,
57 			    hash_set<symtab_node *> *ignored_target_nodes)
58   : m_source_func_decl (source_func_decl), m_target_func_decl (target_func_decl),
59     m_ignored_source_nodes (ignored_source_nodes),
60     m_ignored_target_nodes (ignored_target_nodes),
61     m_compare_polymorphic (compare_polymorphic),
62     m_ignore_labels (ignore_labels)
63 {
64   function *source_func = DECL_STRUCT_FUNCTION (source_func_decl);
65   function *target_func = DECL_STRUCT_FUNCTION (target_func_decl);
66 
67   unsigned ssa_source = SSANAMES (source_func)->length ();
68   unsigned ssa_target = SSANAMES (target_func)->length ();
69 
70   m_source_ssa_names.create (ssa_source);
71   m_target_ssa_names.create (ssa_target);
72 
73   for (unsigned i = 0; i < ssa_source; i++)
74     m_source_ssa_names.safe_push (-1);
75 
76   for (unsigned i = 0; i < ssa_target; i++)
77     m_target_ssa_names.safe_push (-1);
78 }
79 
80 /* Memory release routine.  */
81 
~func_checker()82 func_checker::~func_checker ()
83 {
84   m_source_ssa_names.release();
85   m_target_ssa_names.release();
86 }
87 
88 /* Verifies that trees T1 and T2 are equivalent from perspective of ICF.  */
89 
90 bool
compare_ssa_name(tree t1,tree t2)91 func_checker::compare_ssa_name (tree t1, tree t2)
92 {
93   gcc_assert (TREE_CODE (t1) == SSA_NAME);
94   gcc_assert (TREE_CODE (t2) == SSA_NAME);
95 
96   unsigned i1 = SSA_NAME_VERSION (t1);
97   unsigned i2 = SSA_NAME_VERSION (t2);
98 
99   if (m_source_ssa_names[i1] == -1)
100     m_source_ssa_names[i1] = i2;
101   else if (m_source_ssa_names[i1] != (int) i2)
102     return false;
103 
104   if(m_target_ssa_names[i2] == -1)
105     m_target_ssa_names[i2] = i1;
106   else if (m_target_ssa_names[i2] != (int) i1)
107     return false;
108 
109   if (SSA_NAME_IS_DEFAULT_DEF (t1))
110     {
111       tree b1 = SSA_NAME_VAR (t1);
112       tree b2 = SSA_NAME_VAR (t2);
113 
114       if (b1 == NULL && b2 == NULL)
115 	return true;
116 
117       if (b1 == NULL || b2 == NULL || TREE_CODE (b1) != TREE_CODE (b2))
118 	return return_false ();
119 
120       return compare_cst_or_decl (b1, b2);
121     }
122 
123   return true;
124 }
125 
126 /* Verification function for edges E1 and E2.  */
127 
128 bool
compare_edge(edge e1,edge e2)129 func_checker::compare_edge (edge e1, edge e2)
130 {
131   if (e1->flags != e2->flags)
132     return false;
133 
134   bool existed_p;
135 
136   edge &slot = m_edge_map.get_or_insert (e1, &existed_p);
137   if (existed_p)
138     return return_with_debug (slot == e2);
139   else
140     slot = e2;
141 
142   /* TODO: filter edge probabilities for profile feedback match.  */
143 
144   return true;
145 }
146 
147 /* Verification function for declaration trees T1 and T2 that
148    come from functions FUNC1 and FUNC2.  */
149 
150 bool
compare_decl(tree t1,tree t2)151 func_checker::compare_decl (tree t1, tree t2)
152 {
153   if (!auto_var_in_fn_p (t1, m_source_func_decl)
154       || !auto_var_in_fn_p (t2, m_target_func_decl))
155     return return_with_debug (t1 == t2);
156 
157   tree_code t = TREE_CODE (t1);
158   if ((t == VAR_DECL || t == PARM_DECL || t == RESULT_DECL)
159       && DECL_BY_REFERENCE (t1) != DECL_BY_REFERENCE (t2))
160     return return_false_with_msg ("DECL_BY_REFERENCE flags are different");
161 
162   if (!compatible_types_p (TREE_TYPE (t1), TREE_TYPE (t2)))
163     return return_false ();
164 
165   /* TODO: we are actually too strict here.  We only need to compare if
166      T1 can be used in polymorphic call.  */
167   if (TREE_ADDRESSABLE (t1)
168       && m_compare_polymorphic
169       && !compatible_polymorphic_types_p (TREE_TYPE (t1), TREE_TYPE (t2),
170 					  false))
171     return return_false ();
172 
173   if ((t == VAR_DECL || t == PARM_DECL || t == RESULT_DECL)
174       && DECL_BY_REFERENCE (t1)
175       && m_compare_polymorphic
176       && !compatible_polymorphic_types_p (TREE_TYPE (t1), TREE_TYPE (t2),
177 					  true))
178     return return_false ();
179 
180   bool existed_p;
181 
182   tree &slot = m_decl_map.get_or_insert (t1, &existed_p);
183   if (existed_p)
184     return return_with_debug (slot == t2);
185   else
186     slot = t2;
187 
188   return true;
189 }
190 
191 /* Return true if T1 and T2 are same for purposes of ipa-polymorphic-call
192    analysis.  COMPARE_PTR indicates if types of pointers needs to be
193    considered.  */
194 
195 bool
compatible_polymorphic_types_p(tree t1,tree t2,bool compare_ptr)196 func_checker::compatible_polymorphic_types_p (tree t1, tree t2,
197 					      bool compare_ptr)
198 {
199   gcc_assert (TREE_CODE (t1) != FUNCTION_TYPE && TREE_CODE (t1) != METHOD_TYPE);
200 
201   /* Pointer types generally give no information.  */
202   if (POINTER_TYPE_P (t1))
203     {
204       if (!compare_ptr)
205 	return true;
206       return func_checker::compatible_polymorphic_types_p (TREE_TYPE (t1),
207 							   TREE_TYPE (t2),
208 							   false);
209     }
210 
211   /* If types contain a polymorphic types, match them.  */
212   bool c1 = contains_polymorphic_type_p (t1);
213   bool c2 = contains_polymorphic_type_p (t2);
214   if (!c1 && !c2)
215     return true;
216   if (!c1 || !c2)
217     return return_false_with_msg ("one type is not polymorphic");
218   if (!types_must_be_same_for_odr (t1, t2))
219     return return_false_with_msg ("types are not same for ODR");
220   return true;
221 }
222 
223 /* Return true if types are compatible from perspective of ICF.  */
224 bool
compatible_types_p(tree t1,tree t2)225 func_checker::compatible_types_p (tree t1, tree t2)
226 {
227   if (TREE_CODE (t1) != TREE_CODE (t2))
228     return return_false_with_msg ("different tree types");
229 
230   if (TYPE_RESTRICT (t1) != TYPE_RESTRICT (t2))
231     return return_false_with_msg ("restrict flags are different");
232 
233   if (!types_compatible_p (t1, t2))
234     return return_false_with_msg ("types are not compatible");
235 
236   /* We do a lot of unnecesary matching of types that are not being
237      accessed and thus do not need to be compatible.  In longer term we should
238      remove these checks on all types which are not accessed as memory
239      locations.
240 
241      For time being just avoid calling get_alias_set on types that are not
242      having alias sets defined at all.  */
243   if (type_with_alias_set_p (t1) && type_with_alias_set_p (t2)
244       && get_alias_set (t1) != get_alias_set (t2))
245     return return_false_with_msg ("alias sets are different");
246 
247   return true;
248 }
249 
250 /* Function compare for equality given memory operands T1 and T2.  */
251 
252 bool
compare_memory_operand(tree t1,tree t2)253 func_checker::compare_memory_operand (tree t1, tree t2)
254 {
255   if (!t1 && !t2)
256     return true;
257   else if (!t1 || !t2)
258     return false;
259 
260   ao_ref r1, r2;
261   ao_ref_init (&r1, t1);
262   ao_ref_init (&r2, t2);
263 
264   tree b1 = ao_ref_base (&r1);
265   tree b2 = ao_ref_base (&r2);
266 
267   bool source_is_memop = DECL_P (b1) || INDIRECT_REF_P (b1)
268 			 || TREE_CODE (b1) == MEM_REF
269 			 || TREE_CODE (b1) == TARGET_MEM_REF;
270 
271   bool target_is_memop = DECL_P (b2) || INDIRECT_REF_P (b2)
272 			 || TREE_CODE (b2) == MEM_REF
273 			 || TREE_CODE (b2) == TARGET_MEM_REF;
274 
275   /* Compare alias sets for memory operands.  */
276   if (source_is_memop && target_is_memop)
277     {
278       if (TREE_THIS_VOLATILE (t1) != TREE_THIS_VOLATILE (t2))
279 	return return_false_with_msg ("different operand volatility");
280 
281       if (ao_ref_alias_set (&r1) != ao_ref_alias_set (&r2)
282 	  || ao_ref_base_alias_set (&r1) != ao_ref_base_alias_set (&r2))
283 	return return_false_with_msg ("ao alias sets are different");
284 
285       /* We can't simply use get_object_alignment_1 on the full
286          reference as for accesses with variable indexes this reports
287 	 too conservative alignment.  We also can't use the ao_ref_base
288 	 base objects as ao_ref_base happily strips MEM_REFs around
289 	 decls even though that may carry alignment info.  */
290       b1 = t1;
291       while (handled_component_p (b1))
292 	b1 = TREE_OPERAND (b1, 0);
293       b2 = t2;
294       while (handled_component_p (b2))
295 	b2 = TREE_OPERAND (b2, 0);
296       unsigned int align1, align2;
297       unsigned HOST_WIDE_INT tem;
298       get_object_alignment_1 (b1, &align1, &tem);
299       get_object_alignment_1 (b2, &align2, &tem);
300       if (align1 != align2)
301 	return return_false_with_msg ("different access alignment");
302 
303       /* Similarly we have to compare dependence info where equality
304          tells us we are safe (even some unequal values would be safe
305 	 but then we have to maintain a map of bases and cliques).  */
306       unsigned short clique1 = 0, base1 = 0, clique2 = 0, base2 = 0;
307       if (TREE_CODE (b1) == MEM_REF)
308 	{
309 	  clique1 = MR_DEPENDENCE_CLIQUE (b1);
310 	  base1 = MR_DEPENDENCE_BASE (b1);
311 	}
312       if (TREE_CODE (b2) == MEM_REF)
313 	{
314 	  clique2 = MR_DEPENDENCE_CLIQUE (b2);
315 	  base2 = MR_DEPENDENCE_BASE (b2);
316 	}
317       if (clique1 != clique2 || base1 != base2)
318 	return return_false_with_msg ("different dependence info");
319     }
320 
321   return compare_operand (t1, t2);
322 }
323 
324 /* Function compare for equality given trees T1 and T2 which
325    can be either a constant or a declaration type.  */
326 
327 bool
compare_cst_or_decl(tree t1,tree t2)328 func_checker::compare_cst_or_decl (tree t1, tree t2)
329 {
330   bool ret;
331 
332   switch (TREE_CODE (t1))
333     {
334     case INTEGER_CST:
335     case COMPLEX_CST:
336     case VECTOR_CST:
337     case STRING_CST:
338     case REAL_CST:
339       {
340 	ret = compatible_types_p (TREE_TYPE (t1), TREE_TYPE (t2))
341 	      && operand_equal_p (t1, t2, OEP_ONLY_CONST);
342 	return return_with_debug (ret);
343       }
344     case FUNCTION_DECL:
345       /* All function decls are in the symbol table and known to match
346 	 before we start comparing bodies.  */
347       return true;
348     case VAR_DECL:
349       return return_with_debug (compare_variable_decl (t1, t2));
350     case FIELD_DECL:
351       {
352 	tree offset1 = DECL_FIELD_OFFSET (t1);
353 	tree offset2 = DECL_FIELD_OFFSET (t2);
354 
355 	tree bit_offset1 = DECL_FIELD_BIT_OFFSET (t1);
356 	tree bit_offset2 = DECL_FIELD_BIT_OFFSET (t2);
357 
358 	ret = compare_operand (offset1, offset2)
359 	      && compare_operand (bit_offset1, bit_offset2);
360 
361 	return return_with_debug (ret);
362       }
363     case LABEL_DECL:
364       {
365 	if (t1 == t2)
366 	  return true;
367 
368 	int *bb1 = m_label_bb_map.get (t1);
369 	int *bb2 = m_label_bb_map.get (t2);
370 
371 	/* Labels can point to another function (non-local GOTOs).  */
372 	return return_with_debug (bb1 != NULL && bb2 != NULL && *bb1 == *bb2);
373       }
374     case PARM_DECL:
375     case RESULT_DECL:
376     case CONST_DECL:
377       {
378 	ret = compare_decl (t1, t2);
379 	return return_with_debug (ret);
380       }
381     default:
382       gcc_unreachable ();
383     }
384 }
385 
386 /* Function responsible for comparison of various operands T1 and T2.
387    If these components, from functions FUNC1 and FUNC2, are equal, true
388    is returned.  */
389 
390 bool
compare_operand(tree t1,tree t2)391 func_checker::compare_operand (tree t1, tree t2)
392 {
393   tree x1, x2, y1, y2, z1, z2;
394   bool ret;
395 
396   if (!t1 && !t2)
397     return true;
398   else if (!t1 || !t2)
399     return false;
400 
401   tree tt1 = TREE_TYPE (t1);
402   tree tt2 = TREE_TYPE (t2);
403 
404   if (!func_checker::compatible_types_p (tt1, tt2))
405     return false;
406 
407   if (TREE_CODE (t1) != TREE_CODE (t2))
408     return return_false ();
409 
410   switch (TREE_CODE (t1))
411     {
412     case CONSTRUCTOR:
413       {
414 	unsigned length1 = CONSTRUCTOR_NELTS (t1);
415 	unsigned length2 = CONSTRUCTOR_NELTS (t2);
416 
417 	if (length1 != length2)
418 	  return return_false ();
419 
420 	for (unsigned i = 0; i < length1; i++)
421 	  if (!compare_operand (CONSTRUCTOR_ELT (t1, i)->value,
422 				CONSTRUCTOR_ELT (t2, i)->value))
423 	    return return_false();
424 
425 	return true;
426       }
427     case ARRAY_REF:
428     case ARRAY_RANGE_REF:
429       /* First argument is the array, second is the index.  */
430       x1 = TREE_OPERAND (t1, 0);
431       x2 = TREE_OPERAND (t2, 0);
432       y1 = TREE_OPERAND (t1, 1);
433       y2 = TREE_OPERAND (t2, 1);
434 
435       if (!compare_operand (array_ref_low_bound (t1),
436 			    array_ref_low_bound (t2)))
437 	return return_false_with_msg ("");
438       if (!compare_operand (array_ref_element_size (t1),
439 			    array_ref_element_size (t2)))
440 	return return_false_with_msg ("");
441 
442       if (!compare_operand (x1, x2))
443 	return return_false_with_msg ("");
444       return compare_operand (y1, y2);
445     case MEM_REF:
446       {
447 	x1 = TREE_OPERAND (t1, 0);
448 	x2 = TREE_OPERAND (t2, 0);
449 	y1 = TREE_OPERAND (t1, 1);
450 	y2 = TREE_OPERAND (t2, 1);
451 
452 	/* See if operand is an memory access (the test originate from
453 	 gimple_load_p).
454 
455 	In this case the alias set of the function being replaced must
456 	be subset of the alias set of the other function.  At the moment
457 	we seek for equivalency classes, so simply require inclussion in
458 	both directions.  */
459 
460 	if (!func_checker::compatible_types_p (TREE_TYPE (x1), TREE_TYPE (x2)))
461 	  return return_false ();
462 
463 	if (!compare_operand (x1, x2))
464 	  return return_false_with_msg ("");
465 
466 	/* Type of the offset on MEM_REF does not matter.  */
467 	return known_eq (wi::to_poly_offset (y1), wi::to_poly_offset (y2));
468       }
469     case COMPONENT_REF:
470       {
471 	x1 = TREE_OPERAND (t1, 0);
472 	x2 = TREE_OPERAND (t2, 0);
473 	y1 = TREE_OPERAND (t1, 1);
474 	y2 = TREE_OPERAND (t2, 1);
475 
476 	ret = compare_operand (x1, x2)
477 	      && compare_cst_or_decl (y1, y2);
478 
479 	return return_with_debug (ret);
480       }
481     /* Virtual table call.  */
482     case OBJ_TYPE_REF:
483       {
484 	if (!compare_ssa_name (OBJ_TYPE_REF_EXPR (t1), OBJ_TYPE_REF_EXPR (t2)))
485 	  return return_false ();
486 	if (opt_for_fn (m_source_func_decl, flag_devirtualize)
487 	    && virtual_method_call_p (t1))
488 	  {
489 	    if (tree_to_uhwi (OBJ_TYPE_REF_TOKEN (t1))
490 		!= tree_to_uhwi (OBJ_TYPE_REF_TOKEN (t2)))
491 	      return return_false_with_msg ("OBJ_TYPE_REF token mismatch");
492 	    if (!types_same_for_odr (obj_type_ref_class (t1),
493 				     obj_type_ref_class (t2)))
494 	      return return_false_with_msg ("OBJ_TYPE_REF OTR type mismatch");
495 	    if (!compare_operand (OBJ_TYPE_REF_OBJECT (t1),
496 				  OBJ_TYPE_REF_OBJECT (t2)))
497 	      return return_false_with_msg ("OBJ_TYPE_REF object mismatch");
498 	  }
499 
500 	return return_with_debug (true);
501       }
502     case IMAGPART_EXPR:
503     case REALPART_EXPR:
504     case ADDR_EXPR:
505       {
506 	x1 = TREE_OPERAND (t1, 0);
507 	x2 = TREE_OPERAND (t2, 0);
508 
509 	ret = compare_operand (x1, x2);
510 	return return_with_debug (ret);
511       }
512     case BIT_FIELD_REF:
513       {
514 	x1 = TREE_OPERAND (t1, 0);
515 	x2 = TREE_OPERAND (t2, 0);
516 	y1 = TREE_OPERAND (t1, 1);
517 	y2 = TREE_OPERAND (t2, 1);
518 	z1 = TREE_OPERAND (t1, 2);
519 	z2 = TREE_OPERAND (t2, 2);
520 
521 	ret = compare_operand (x1, x2)
522 	      && compare_cst_or_decl (y1, y2)
523 	      && compare_cst_or_decl (z1, z2);
524 
525 	return return_with_debug (ret);
526       }
527     case SSA_NAME:
528 	return compare_ssa_name (t1, t2);
529     case INTEGER_CST:
530     case COMPLEX_CST:
531     case VECTOR_CST:
532     case STRING_CST:
533     case REAL_CST:
534     case FUNCTION_DECL:
535     case VAR_DECL:
536     case FIELD_DECL:
537     case LABEL_DECL:
538     case PARM_DECL:
539     case RESULT_DECL:
540     case CONST_DECL:
541       return compare_cst_or_decl (t1, t2);
542     default:
543       return return_false_with_msg ("Unknown TREE code reached");
544     }
545 }
546 
547 bool
compare_asm_inputs_outputs(tree t1,tree t2)548 func_checker::compare_asm_inputs_outputs (tree t1, tree t2)
549 {
550   gcc_assert (TREE_CODE (t1) == TREE_LIST);
551   gcc_assert (TREE_CODE (t2) == TREE_LIST);
552 
553   for (; t1; t1 = TREE_CHAIN (t1))
554     {
555       if (!t2)
556 	return false;
557 
558       if (!compare_operand (TREE_VALUE (t1), TREE_VALUE (t2)))
559 	return return_false ();
560 
561       tree p1 = TREE_PURPOSE (t1);
562       tree p2 = TREE_PURPOSE (t2);
563 
564       gcc_assert (TREE_CODE (p1) == TREE_LIST);
565       gcc_assert (TREE_CODE (p2) == TREE_LIST);
566 
567       if (strcmp (TREE_STRING_POINTER (TREE_VALUE (p1)),
568 		  TREE_STRING_POINTER (TREE_VALUE (p2))) != 0)
569 	return return_false ();
570 
571       t2 = TREE_CHAIN (t2);
572     }
573 
574   if (t2)
575     return return_false ();
576 
577   return true;
578 }
579 
580 /* Verifies that trees T1 and T2 do correspond.  */
581 
582 bool
compare_variable_decl(tree t1,tree t2)583 func_checker::compare_variable_decl (tree t1, tree t2)
584 {
585   bool ret = false;
586 
587   if (t1 == t2)
588     return true;
589 
590   if (DECL_ALIGN (t1) != DECL_ALIGN (t2))
591     return return_false_with_msg ("alignments are different");
592 
593   if (DECL_HARD_REGISTER (t1) != DECL_HARD_REGISTER (t2))
594     return return_false_with_msg ("DECL_HARD_REGISTER are different");
595 
596   if (DECL_HARD_REGISTER (t1)
597       && DECL_ASSEMBLER_NAME (t1) != DECL_ASSEMBLER_NAME (t2))
598     return return_false_with_msg ("HARD REGISTERS are different");
599 
600   /* Symbol table variables are known to match before we start comparing
601      bodies.  */
602   if (decl_in_symtab_p (t1))
603     return decl_in_symtab_p (t2);
604   ret = compare_decl (t1, t2);
605 
606   return return_with_debug (ret);
607 }
608 
609 
610 /* Function visits all gimple labels and creates corresponding
611    mapping between basic blocks and labels.  */
612 
613 void
parse_labels(sem_bb * bb)614 func_checker::parse_labels (sem_bb *bb)
615 {
616   for (gimple_stmt_iterator gsi = gsi_start_bb (bb->bb); !gsi_end_p (gsi);
617        gsi_next (&gsi))
618     {
619       gimple *stmt = gsi_stmt (gsi);
620 
621       if (glabel *label_stmt = dyn_cast <glabel *> (stmt))
622 	{
623 	  tree t = gimple_label_label (label_stmt);
624 	  gcc_assert (TREE_CODE (t) == LABEL_DECL);
625 
626 	  m_label_bb_map.put (t, bb->bb->index);
627 	}
628     }
629 }
630 
631 /* Basic block equivalence comparison function that returns true if
632    basic blocks BB1 and BB2 (from functions FUNC1 and FUNC2) correspond.
633 
634    In general, a collection of equivalence dictionaries is built for types
635    like SSA names, declarations (VAR_DECL, PARM_DECL, ..). This infrastructure
636    is utilized by every statement-by-statement comparison function.  */
637 
638 bool
compare_bb(sem_bb * bb1,sem_bb * bb2)639 func_checker::compare_bb (sem_bb *bb1, sem_bb *bb2)
640 {
641   gimple_stmt_iterator gsi1, gsi2;
642   gimple *s1, *s2;
643 
644   gsi1 = gsi_start_nondebug_bb (bb1->bb);
645   gsi2 = gsi_start_nondebug_bb (bb2->bb);
646 
647   while (!gsi_end_p (gsi1))
648     {
649       if (gsi_end_p (gsi2))
650 	return return_false ();
651 
652       s1 = gsi_stmt (gsi1);
653       s2 = gsi_stmt (gsi2);
654 
655       int eh1 = lookup_stmt_eh_lp_fn
656 		(DECL_STRUCT_FUNCTION (m_source_func_decl), s1);
657       int eh2 = lookup_stmt_eh_lp_fn
658 		(DECL_STRUCT_FUNCTION (m_target_func_decl), s2);
659 
660       if (eh1 != eh2)
661 	return return_false_with_msg ("EH regions are different");
662 
663       if (gimple_code (s1) != gimple_code (s2))
664 	return return_false_with_msg ("gimple codes are different");
665 
666       switch (gimple_code (s1))
667 	{
668 	case GIMPLE_CALL:
669 	  if (!compare_gimple_call (as_a <gcall *> (s1),
670 				    as_a <gcall *> (s2)))
671 	    return return_different_stmts (s1, s2, "GIMPLE_CALL");
672 	  break;
673 	case GIMPLE_ASSIGN:
674 	  if (!compare_gimple_assign (s1, s2))
675 	    return return_different_stmts (s1, s2, "GIMPLE_ASSIGN");
676 	  break;
677 	case GIMPLE_COND:
678 	  if (!compare_gimple_cond (s1, s2))
679 	    return return_different_stmts (s1, s2, "GIMPLE_COND");
680 	  break;
681 	case GIMPLE_SWITCH:
682 	  if (!compare_gimple_switch (as_a <gswitch *> (s1),
683 				      as_a <gswitch *> (s2)))
684 	    return return_different_stmts (s1, s2, "GIMPLE_SWITCH");
685 	  break;
686 	case GIMPLE_DEBUG:
687 	  break;
688 	case GIMPLE_EH_DISPATCH:
689 	  if (gimple_eh_dispatch_region (as_a <geh_dispatch *> (s1))
690 	      != gimple_eh_dispatch_region (as_a <geh_dispatch *> (s2)))
691 	    return return_different_stmts (s1, s2, "GIMPLE_EH_DISPATCH");
692 	  break;
693 	case GIMPLE_RESX:
694 	  if (!compare_gimple_resx (as_a <gresx *> (s1),
695 				    as_a <gresx *> (s2)))
696 	    return return_different_stmts (s1, s2, "GIMPLE_RESX");
697 	  break;
698 	case GIMPLE_LABEL:
699 	  if (!compare_gimple_label (as_a <glabel *> (s1),
700 				     as_a <glabel *> (s2)))
701 	    return return_different_stmts (s1, s2, "GIMPLE_LABEL");
702 	  break;
703 	case GIMPLE_RETURN:
704 	  if (!compare_gimple_return (as_a <greturn *> (s1),
705 				      as_a <greturn *> (s2)))
706 	    return return_different_stmts (s1, s2, "GIMPLE_RETURN");
707 	  break;
708 	case GIMPLE_GOTO:
709 	  if (!compare_gimple_goto (s1, s2))
710 	    return return_different_stmts (s1, s2, "GIMPLE_GOTO");
711 	  break;
712 	case GIMPLE_ASM:
713 	  if (!compare_gimple_asm (as_a <gasm *> (s1),
714 				   as_a <gasm *> (s2)))
715 	    return return_different_stmts (s1, s2, "GIMPLE_ASM");
716 	  break;
717 	case GIMPLE_PREDICT:
718 	case GIMPLE_NOP:
719 	  break;
720 	default:
721 	  return return_false_with_msg ("Unknown GIMPLE code reached");
722 	}
723 
724       gsi_next_nondebug (&gsi1);
725       gsi_next_nondebug (&gsi2);
726     }
727 
728   if (!gsi_end_p (gsi2))
729     return return_false ();
730 
731   return true;
732 }
733 
734 /* Verifies for given GIMPLEs S1 and S2 that
735    call statements are semantically equivalent.  */
736 
737 bool
compare_gimple_call(gcall * s1,gcall * s2)738 func_checker::compare_gimple_call (gcall *s1, gcall *s2)
739 {
740   unsigned i;
741   tree t1, t2;
742 
743   if (gimple_call_num_args (s1) != gimple_call_num_args (s2))
744     return false;
745 
746   t1 = gimple_call_fn (s1);
747   t2 = gimple_call_fn (s2);
748   if (!compare_operand (t1, t2))
749     return return_false ();
750 
751   /* Compare flags.  */
752   if (gimple_call_internal_p (s1) != gimple_call_internal_p (s2)
753       || gimple_call_ctrl_altering_p (s1) != gimple_call_ctrl_altering_p (s2)
754       || gimple_call_tail_p (s1) != gimple_call_tail_p (s2)
755       || gimple_call_return_slot_opt_p (s1) != gimple_call_return_slot_opt_p (s2)
756       || gimple_call_from_thunk_p (s1) != gimple_call_from_thunk_p (s2)
757       || gimple_call_va_arg_pack_p (s1) != gimple_call_va_arg_pack_p (s2)
758       || gimple_call_alloca_for_var_p (s1) != gimple_call_alloca_for_var_p (s2))
759     return false;
760 
761   if (gimple_call_internal_p (s1)
762       && gimple_call_internal_fn (s1) != gimple_call_internal_fn (s2))
763     return false;
764 
765   tree fntype1 = gimple_call_fntype (s1);
766   tree fntype2 = gimple_call_fntype (s2);
767   if ((fntype1 && !fntype2)
768       || (!fntype1 && fntype2)
769       || (fntype1 && !types_compatible_p (fntype1, fntype2)))
770     return return_false_with_msg ("call function types are not compatible");
771 
772   if (fntype1 && fntype2 && comp_type_attributes (fntype1, fntype2) != 1)
773     return return_false_with_msg ("different fntype attributes");
774 
775   tree chain1 = gimple_call_chain (s1);
776   tree chain2 = gimple_call_chain (s2);
777   if ((chain1 && !chain2)
778       || (!chain1 && chain2)
779       || !compare_operand (chain1, chain2))
780     return return_false_with_msg ("static call chains are different");
781 
782   /* Checking of argument.  */
783   for (i = 0; i < gimple_call_num_args (s1); ++i)
784     {
785       t1 = gimple_call_arg (s1, i);
786       t2 = gimple_call_arg (s2, i);
787 
788       if (!compare_memory_operand (t1, t2))
789 	return return_false_with_msg ("memory operands are different");
790     }
791 
792   /* Return value checking.  */
793   t1 = gimple_get_lhs (s1);
794   t2 = gimple_get_lhs (s2);
795 
796   return compare_memory_operand (t1, t2);
797 }
798 
799 
800 /* Verifies for given GIMPLEs S1 and S2 that
801    assignment statements are semantically equivalent.  */
802 
803 bool
compare_gimple_assign(gimple * s1,gimple * s2)804 func_checker::compare_gimple_assign (gimple *s1, gimple *s2)
805 {
806   tree arg1, arg2;
807   tree_code code1, code2;
808   unsigned i;
809 
810   code1 = gimple_expr_code (s1);
811   code2 = gimple_expr_code (s2);
812 
813   if (code1 != code2)
814     return false;
815 
816   code1 = gimple_assign_rhs_code (s1);
817   code2 = gimple_assign_rhs_code (s2);
818 
819   if (code1 != code2)
820     return false;
821 
822   for (i = 0; i < gimple_num_ops (s1); i++)
823     {
824       arg1 = gimple_op (s1, i);
825       arg2 = gimple_op (s2, i);
826 
827       if (!compare_memory_operand (arg1, arg2))
828 	return return_false_with_msg ("memory operands are different");
829     }
830 
831 
832   return true;
833 }
834 
835 /* Verifies for given GIMPLEs S1 and S2 that
836    condition statements are semantically equivalent.  */
837 
838 bool
compare_gimple_cond(gimple * s1,gimple * s2)839 func_checker::compare_gimple_cond (gimple *s1, gimple *s2)
840 {
841   tree t1, t2;
842   tree_code code1, code2;
843 
844   code1 = gimple_expr_code (s1);
845   code2 = gimple_expr_code (s2);
846 
847   if (code1 != code2)
848     return false;
849 
850   t1 = gimple_cond_lhs (s1);
851   t2 = gimple_cond_lhs (s2);
852 
853   if (!compare_operand (t1, t2))
854     return false;
855 
856   t1 = gimple_cond_rhs (s1);
857   t2 = gimple_cond_rhs (s2);
858 
859   return compare_operand (t1, t2);
860 }
861 
862 /* Verifies that tree labels T1 and T2 correspond in FUNC1 and FUNC2.  */
863 
864 bool
compare_tree_ssa_label(tree t1,tree t2)865 func_checker::compare_tree_ssa_label (tree t1, tree t2)
866 {
867   return compare_operand (t1, t2);
868 }
869 
870 /* Verifies for given GIMPLE_LABEL stmts S1 and S2 that
871    label statements are semantically equivalent.  */
872 
873 bool
compare_gimple_label(const glabel * g1,const glabel * g2)874 func_checker::compare_gimple_label (const glabel *g1, const glabel *g2)
875 {
876   if (m_ignore_labels)
877     return true;
878 
879   tree t1 = gimple_label_label (g1);
880   tree t2 = gimple_label_label (g2);
881 
882   if (FORCED_LABEL (t1) || FORCED_LABEL (t2))
883     return return_false_with_msg ("FORCED_LABEL");
884 
885   /* As the pass build BB to label mapping, no further check is needed.  */
886   return true;
887 }
888 
889 /* Verifies for given GIMPLE_SWITCH stmts S1 and S2 that
890    switch statements are semantically equivalent.  */
891 
892 bool
compare_gimple_switch(const gswitch * g1,const gswitch * g2)893 func_checker::compare_gimple_switch (const gswitch *g1, const gswitch *g2)
894 {
895   unsigned lsize1, lsize2, i;
896 
897   lsize1 = gimple_switch_num_labels (g1);
898   lsize2 = gimple_switch_num_labels (g2);
899 
900   if (lsize1 != lsize2)
901     return false;
902 
903   tree t1 = gimple_switch_index (g1);
904   tree t2 = gimple_switch_index (g2);
905 
906   if (!compare_operand (t1, t2))
907     return false;
908 
909   for (i = 0; i < lsize1; i++)
910     {
911       tree label1 = gimple_switch_label (g1, i);
912       tree label2 = gimple_switch_label (g2, i);
913 
914       /* Label LOW and HIGH comparison.  */
915       tree low1 = CASE_LOW (label1);
916       tree low2 = CASE_LOW (label2);
917 
918       if (!tree_int_cst_equal (low1, low2))
919 	return return_false_with_msg ("case low values are different");
920 
921       tree high1 = CASE_HIGH (label1);
922       tree high2 = CASE_HIGH (label2);
923 
924       if (!tree_int_cst_equal (high1, high2))
925 	return return_false_with_msg ("case high values are different");
926 
927       if (TREE_CODE (label1) == CASE_LABEL_EXPR
928 	  && TREE_CODE (label2) == CASE_LABEL_EXPR)
929 	{
930 	  label1 = CASE_LABEL (label1);
931 	  label2 = CASE_LABEL (label2);
932 
933 	  if (!compare_operand (label1, label2))
934 	    return return_false_with_msg ("switch label_exprs are different");
935 	}
936       else if (!tree_int_cst_equal (label1, label2))
937 	return return_false_with_msg ("switch labels are different");
938     }
939 
940   return true;
941 }
942 
943 /* Verifies for given GIMPLE_RETURN stmts S1 and S2 that
944    return statements are semantically equivalent.  */
945 
946 bool
compare_gimple_return(const greturn * g1,const greturn * g2)947 func_checker::compare_gimple_return (const greturn *g1, const greturn *g2)
948 {
949   tree t1, t2;
950 
951   t1 = gimple_return_retval (g1);
952   t2 = gimple_return_retval (g2);
953 
954   /* Void return type.  */
955   if (t1 == NULL && t2 == NULL)
956     return true;
957   else
958     return compare_operand (t1, t2);
959 }
960 
961 /* Verifies for given GIMPLEs S1 and S2 that
962    goto statements are semantically equivalent.  */
963 
964 bool
compare_gimple_goto(gimple * g1,gimple * g2)965 func_checker::compare_gimple_goto (gimple *g1, gimple *g2)
966 {
967   tree dest1, dest2;
968 
969   dest1 = gimple_goto_dest (g1);
970   dest2 = gimple_goto_dest (g2);
971 
972   if (TREE_CODE (dest1) != TREE_CODE (dest2) || TREE_CODE (dest1) != SSA_NAME)
973     return false;
974 
975   return compare_operand (dest1, dest2);
976 }
977 
978 /* Verifies for given GIMPLE_RESX stmts S1 and S2 that
979    resx statements are semantically equivalent.  */
980 
981 bool
compare_gimple_resx(const gresx * g1,const gresx * g2)982 func_checker::compare_gimple_resx (const gresx *g1, const gresx *g2)
983 {
984   return gimple_resx_region (g1) == gimple_resx_region (g2);
985 }
986 
987 /* Verifies for given GIMPLEs S1 and S2 that ASM statements are equivalent.
988    For the beginning, the pass only supports equality for
989    '__asm__ __volatile__ ("", "", "", "memory")'.  */
990 
991 bool
compare_gimple_asm(const gasm * g1,const gasm * g2)992 func_checker::compare_gimple_asm (const gasm *g1, const gasm *g2)
993 {
994   if (gimple_asm_volatile_p (g1) != gimple_asm_volatile_p (g2))
995     return false;
996 
997   if (gimple_asm_input_p (g1) != gimple_asm_input_p (g2))
998     return false;
999 
1000   if (gimple_asm_inline_p (g1) != gimple_asm_inline_p (g2))
1001     return false;
1002 
1003   if (gimple_asm_ninputs (g1) != gimple_asm_ninputs (g2))
1004     return false;
1005 
1006   if (gimple_asm_noutputs (g1) != gimple_asm_noutputs (g2))
1007     return false;
1008 
1009   /* We do not suppport goto ASM statement comparison.  */
1010   if (gimple_asm_nlabels (g1) || gimple_asm_nlabels (g2))
1011     return false;
1012 
1013   if (gimple_asm_nclobbers (g1) != gimple_asm_nclobbers (g2))
1014     return false;
1015 
1016   if (strcmp (gimple_asm_string (g1), gimple_asm_string (g2)) != 0)
1017     return return_false_with_msg ("ASM strings are different");
1018 
1019   for (unsigned i = 0; i < gimple_asm_ninputs (g1); i++)
1020     {
1021       tree input1 = gimple_asm_input_op (g1, i);
1022       tree input2 = gimple_asm_input_op (g2, i);
1023 
1024       if (!compare_asm_inputs_outputs (input1, input2))
1025 	return return_false_with_msg ("ASM input is different");
1026     }
1027 
1028   for (unsigned i = 0; i < gimple_asm_noutputs (g1); i++)
1029     {
1030       tree output1 = gimple_asm_output_op (g1, i);
1031       tree output2 = gimple_asm_output_op (g2, i);
1032 
1033       if (!compare_asm_inputs_outputs (output1, output2))
1034 	return return_false_with_msg ("ASM output is different");
1035     }
1036 
1037   for (unsigned i = 0; i < gimple_asm_nclobbers (g1); i++)
1038     {
1039       tree clobber1 = gimple_asm_clobber_op (g1, i);
1040       tree clobber2 = gimple_asm_clobber_op (g2, i);
1041 
1042       if (!operand_equal_p (TREE_VALUE (clobber1), TREE_VALUE (clobber2),
1043 			    OEP_ONLY_CONST))
1044 	return return_false_with_msg ("ASM clobber is different");
1045     }
1046 
1047   return true;
1048 }
1049 
1050 } // ipa_icf_gimple namespace
1051