• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
2 // -*- Mode: C++ -*-
3 //
4 // Copyright (C) 2013-2022 Red Hat, Inc.
5 //
6 // Author: Dodji Seketeli
7 
8 /// @file
9 ///
10 /// Types of the main internal representation of libabigail.
11 ///
12 /// This internal representation abstracts the artifacts that make up
13 /// an application binary interface.
14 
15 #ifndef __ABG_IR_H__
16 #define __ABG_IR_H__
17 
18 #include <assert.h>
19 #include <stdint.h>
20 #include <cstdlib>
21 #include <functional>
22 #include <set>
23 #include <unordered_map>
24 #include "abg-cxx-compat.h"
25 #include "abg-fwd.h"
26 #include "abg-hash.h"
27 #include "abg-traverse.h"
28 #include "abg-config.h"
29 
30 /// @file
31 ///
32 /// This file contains the declarations of the Internal Representation
33 /// of libabigail.
34 
35 /// @defgroup Memory Memory management
36 /// @{
37 ///
38 /// How objects' lifetime is handled in libabigail.
39 ///
40 /// For memory management and garbage collection of libabigail's IR
41 /// artifacts, we use std::shared_ptr and std::weak_ptr.
42 ///
43 /// When manipulating these IR artifacts, there are a few rules to keep in
44 /// mind.
45 ///
46 /// <b>The declaration for a type is owned by only one scope </b>
47 ///
48 /// This means that for each instance of abigail::type_base (a type) there
49 /// is an instance of abigail::scope_decl that owns a @ref
50 /// abigail::decl_base_sptr (a shared pointer to an abigail::decl_base)
51 /// that points to the declaration of that type.  The
52 /// abigail::type_base_sptr is added to the scope using the function
53 /// abigail::add_decl_to_scope().
54 ///
55 /// There is a kind of type that is usually not syntactically owned by
56 /// a scope: it's function type.  In libabigail, function types are
57 /// represented by abigail::function_type and abigail::method_type.
58 /// These types must be owned by the translation unit they originate
59 /// from.  Adding them to the translation unit must be done by a call
60 /// to the method function
61 /// abigail::translation::bind_function_type_life_time().
62 ///
63 /// <b> A declaration that has a type does NOT own the type </b>
64 ///
65 /// This means that, for instance, in an abigail::var_decl (a variable
66 /// declaration), the type of the declaration is not owned by the
67 /// declaration.  In other (concrete) words, the variable declaration
68 /// doesn't have a shared pointer to the type.  Rather, it has a *weak*
69 /// pointer to its type.  That means that it has a data member of type
70 /// abigail::type_base_wptr that contains the type of the declaration.
71 ///
72 /// But then abigail::var_decl::get_type() returns a shared pointer that
73 /// is constructed from the internal weak pointer to the type.  That way,
74 /// users of the type of the var can own a temporary reference on it and
75 /// be assured that the type's life time is long enough for their need.
76 ///
77 /// Likewise, data members, function and template parameters similarly
78 /// have weak pointers on their type.
79 ///
80 /// If, for a reason, you really need to keep a type alive for the
81 /// entire lifetime of the type system, then you can bind the life
82 /// time of that type to the life time of the @ref environment that is
83 /// supposed to outlive the type system.  You do that by passing the
84 /// type to the function environment::keep_type_alive().
85 ///
86 /// @}
87 
88 namespace abigail
89 {
90 
91 /// The namespace of the internal representation of ABI artifacts like
92 /// types and decls.
93 namespace ir
94 {
95 
96 // Inject some std types in here.
97 using std::unordered_map;
98 
99 /// A convenience typedef for an unordered set of pointer values
100 typedef unordered_set<uintptr_t> pointer_set;
101 
102 /// Functor to hash a canonical type by using its pointer value.
103 struct canonical_type_hash
104 {
105   size_t operator()(const type_base_sptr& l) const;
106   size_t operator()(const type_base *l) const;
107 }; //end struct canonical_type_hash
108 
109 /// Helper typedef for an unordered set of type_base_sptr which uses
110 /// pointer value to tell its members appart, because the members are
111 /// canonical types.
112 typedef unordered_set<type_base_sptr,
113 		      canonical_type_hash> canonical_type_sptr_set_type;
114 
115 /// Helper typedef for a vector of pointer to type_base.
116 typedef vector<type_base*> type_base_ptrs_type;
117 
118 /// Helper typedef for a vector of shared pointer to a type_base.
119 typedef vector<type_base_sptr> type_base_sptrs_type;
120 
121 void
122 sort_types(const canonical_type_sptr_set_type& types,
123 	   vector<type_base_sptr>& result);
124 
125 /// This is an abstraction of the set of resources necessary to manage
126 /// several aspects of the internal representations of the Abigail
127 /// library.
128 ///
129 /// An environment can be seen as the boundaries in which all related
130 /// Abigail artifacts live.  So before doing anything using this
131 /// library, the first thing to create is, well, you know it now, an
132 /// environment.
133 ///
134 /// Note that the lifetime of environment objects must be longer than
135 /// the lifetime of any other type in the Abigail system.  So a given
136 /// instance of @ref environment must stay around as long as you are
137 /// using libabigail.  It's only when you are done using the library
138 /// that you can de-allocate the environment instance.
139 class environment
140 {
141 public:
142   struct priv;
143   std::unique_ptr<priv> priv_;
144 
145   /// A convenience typedef for a map of canonical types.  The key is
146   /// the pretty representation string of a particular type and the
147   /// value is the vector of canonical types that have the same pretty
148   /// representation string.
149   typedef std::unordered_map<string, std::vector<type_base_sptr> >
150       canonical_types_map_type;
151 
152   environment();
153 
154   virtual ~environment();
155 
156   canonical_types_map_type&
157   get_canonical_types_map();
158 
159   const canonical_types_map_type&
160   get_canonical_types_map() const;
161 
162   const type_base_sptr&
163   get_void_type() const;
164 
165   const type_base_sptr&
166   get_variadic_parameter_type() const;
167 
168   bool
169   canonicalization_is_done() const;
170 
171   void
172   canonicalization_is_done(bool);
173 
174   bool
175   do_on_the_fly_canonicalization() const;
176 
177   void
178   do_on_the_fly_canonicalization(bool f);
179 
180   bool
181   decl_only_class_equals_definition() const;
182 
183   void
184   decl_only_class_equals_definition(bool f) const;
185 
186   bool
187   is_void_type(const type_base_sptr&) const;
188 
189   bool
190   is_void_type(const type_base*) const;
191 
192   bool
193   is_variadic_parameter_type(const type_base*) const;
194 
195   bool
196   is_variadic_parameter_type(const type_base_sptr&) const;
197 
198   interned_string
199   intern(const string&) const;
200 
201   const config&
202   get_config() const;
203 
204   bool
205   user_set_analyze_exported_interfaces_only() const;
206 
207   void
208   analyze_exported_interfaces_only(bool f);
209 
210   bool
211   analyze_exported_interfaces_only() const;
212 
213 #ifdef WITH_DEBUG_SELF_COMPARISON
214   void
215   set_self_comparison_debug_input(const corpus_sptr& corpus);
216 
217   void
218   get_self_comparison_debug_inputs(corpus_sptr& first_corpus,
219 				   corpus_sptr& second_corpus);
220 
221   void
222   self_comparison_debug_is_on(bool);
223 
224   bool
225   self_comparison_debug_is_on() const;
226 #endif
227 
228 #ifdef WITH_DEBUG_TYPE_CANONICALIZATION
229   void
230   debug_type_canonicalization_is_on(bool flag);
231 
232   bool
233   debug_type_canonicalization_is_on() const;
234 
235   void
236   debug_die_canonicalization_is_on(bool flag);
237 
238   bool
239   debug_die_canonicalization_is_on() const;
240 #endif
241 
242   vector<type_base_sptr>* get_canonical_types(const char* name);
243 
244   type_base* get_canonical_type(const char* name, unsigned index);
245 
246 #ifdef WITH_DEBUG_SELF_COMPARISON
247   unordered_map<string, uintptr_t>&
248   get_type_id_canonical_type_map() const;
249 
250   unordered_map<uintptr_t, string>&
251   get_pointer_type_id_map();
252 
253   string
254   get_type_id_from_pointer(uintptr_t ptr);
255 
256   uintptr_t
257   get_canonical_type_from_type_id(const char*);
258 #endif
259 
260   friend class class_or_union;
261   friend class class_decl;
262   friend class function_type;
263 
264   friend void keep_type_alive(type_base_sptr);
265 }; // end class environment
266 
267 class location_manager;
268 /// @brief The source location of a token.
269 ///
270 /// This represents the location of a token coming from a given
271 /// translation unit.  This location is actually an abstraction of
272 /// cursor in the table of all the locations of all the tokens of the
273 /// translation unit.  That table is managed by the @ref location_manager
274 /// type.  To get the file path, line and column numbers associated to
275 /// a given instance of @ref location, you need to use the
276 /// location_manager::expand_location method.
277 class location
278 {
279   unsigned		value_;
280   // The location manager to use to decode the value above.  There is
281   // one location manager per translation unit, and the location
282   // manager's life time is managed by its translation unit.
283   location_manager*	loc_manager_;
284   // Whether the location is artificial.  Being artificial means that
285   // the location wasn't generated by the original emitter of the
286   // metadata (i.e, the compiler if the metadata is debug info).  For
287   // instance, implicit location derived from the position of XML
288   // elements in the abixml file is represented as artificial
289   // locations.
290   bool			is_artificial_;
291 
location(unsigned v,location_manager * m)292   location(unsigned v, location_manager* m)
293     : value_(v), loc_manager_(m), is_artificial_(false)
294   {}
295 
296   /// Get the location manager to use to decode the value of this
297   /// location.
298   ///
299   /// @return the location manager for the current location value.
300   location_manager*
get_location_manager()301   get_location_manager() const
302   {return loc_manager_;}
303 
304 public:
305 
306   /// Test if the location is artificial.
307   ///
308   /// Being artificial means that the location wasn't generated by the
309   /// original emitter of the metadata (i.e, the compiler if the
310   /// metadata is debug info).  For instance, the implicit location
311   /// derived from the position of a given XML element in the abixml
312   /// file is represented as artificial locations.  The same XML
313   /// element might carry a non-artificial (natural?) location that was
314   /// originally emitted by the compiler that generated the original
315   /// debug info the abixml file is derived from.
316   ///
317   /// @return true iff the location is artificial.
318   bool
get_is_artificial()319   get_is_artificial() const
320   {return is_artificial_;}
321 
322   /// Set the artificial-ness of the location.
323   ///
324   /// Being artificial means that the location wasn't generated by the
325   /// original emitter of the metadata (i.e, the compiler if the
326   /// metadata is debug info).  For instance, the implicit location
327   /// derived from the position of a given XML element in the abixml
328   /// file is represented as artificial locations.  The same XML
329   /// element might carry a non-artificial (natural?) location that
330   /// was originally emitted by the compiler that generated the
331   /// original debug info the abixml file is derived from.
332   ///
333   /// @param f the new artificial-ness state.
334   void
set_is_artificial(bool f)335   set_is_artificial(bool f)
336   {is_artificial_ = f;}
337 
338   /// Copy constructor of the location.
339   ///
340   /// @param l the location to copy from.
location(const location & l)341   location(const location& l)
342     : value_(l.value_),
343       loc_manager_(l.loc_manager_),
344       is_artificial_(l.is_artificial_)
345   {}
346 
347   /// Assignment operator of the location.
348   ///
349   /// @param l the location to assign to the current one.
350   location&
351   operator=(const location& l)
352   {
353     value_ = l.value_;
354     loc_manager_ = l.loc_manager_;
355     is_artificial_ = l.is_artificial_;
356     return *this;
357   }
358 
359   /// Default constructor for the @ref location type.
location()360   location()
361     : value_(), loc_manager_(), is_artificial_()
362   {}
363 
364   /// Get the value of the location.
365   unsigned
get_value()366   get_value() const
367   {return value_;}
368 
369   /// Convert the location into a boolean.
370   ///
371   /// @return true iff the value of the location is different from
372   /// zero.
373   operator bool() const
374   {return !!value_;}
375 
376   /// Equality operator of the @ref location type.
377   ///
378   /// @param other the other location to compare against.
379   ///
380   /// @return true iff both locations are equal.
381   bool
382   operator==(const location &other) const
383   {return value_ == other.value_;}
384 
385   /// "Less than" operator of the @ref location type.
386   ///
387   /// @parm other the other location type to compare against.
388   ///
389   /// @return true iff the current instance is less than the @p other
390   /// one.
391   bool
392   operator<(const location &other) const
393   {return value_ < other.value_;}
394 
395   /// Expand the current location into a tripplet file path, line and
396   /// column number.
397   ///
398   /// @param path the output parameter this function sets the expanded
399   /// path to.
400   ///
401   /// @param line the output parameter this function sets the expanded
402   /// line number to.
403   ///
404   /// @param column the output parameter this function sets the
405   /// expanded column number to.
406   void
407   expand(std::string& path, unsigned& line, unsigned& column) const;
408 
409   string
410   expand(void) const;
411 
412   friend class location_manager;
413 }; // end class location
414 
415 /// @brief The entry point to manage locations.
416 ///
417 /// This type keeps a table of all the locations for tokens of a
418 /// given translation unit.
419 class location_manager
420 {
421   struct priv;
422   std::unique_ptr<priv> priv_;
423 
424 public:
425 
426   location_manager();
427 
428   ~location_manager();
429 
430   location
431   create_new_location(const std::string& fle, size_t lne, size_t col);
432 
433   void
434   expand_location(const location& location, std::string& path,
435 		  unsigned& line, unsigned& column) const;
436 };
437 
438 /// The base of an entity of the intermediate representation that is
439 /// to be traversed.
440 struct ir_traversable_base : public traversable_base
441 {
442   /// Traverse a given IR node and its children, calling an visitor on
443   /// each node.
444   ///
445   /// @param v the visitor to call on each traversed node.
446   ///
447   /// @return true if the all the IR node tree was traversed.
448   virtual bool
449   traverse(ir_node_visitor& v);
450 }; // end class ir_traversable_base
451 
452 /// The hashing functor for using instances of @ref type_or_decl_base
453 /// as values in a hash map or set.
454 struct type_or_decl_hash
455 {
456 
457   /// Function-call Operator to hash the string representation of an
458   /// ABI artifact.
459   ///
460   /// @param artifact the ABI artifact to hash.
461   ///
462   /// @return the hash value of the string representation of @p
463   /// artifact.
464   size_t
operatortype_or_decl_hash465   operator()(const type_or_decl_base *artifact) const
466   {
467     string repr =  get_pretty_representation(artifact);
468     std::hash<string> do_hash;
469     return do_hash(repr);
470   }
471 
472   /// Function-call Operator to hash the string representation of an
473   /// ABI artifact.
474   ///
475   /// @param artifact the ABI artifact to hash.
476   ///
477   /// @return the hash value of the string representation of @p
478   /// artifact.
479   size_t
operatortype_or_decl_hash480   operator()(const type_or_decl_base_sptr& artifact) const
481   {return operator()(artifact.get());}
482 }; // end struct type_or_decl_hash
483 
484 /// The comparison functor for using instances of @ref
485 /// type_or_decl_base as values in a hash map or set.
486 struct type_or_decl_equal
487 {
488 
489   /// The function-call operator to compare the string representations
490   /// of two ABI artifacts.
491   ///
492   /// @param l the left hand side ABI artifact operand of the
493   /// comparison.
494   ///
495   /// @param r the right hand side ABI artifact operand of the
496   /// comparison.
497   ///
498   /// @return true iff the string representation of @p l equals the one
499   /// of @p r.
500   bool
operatortype_or_decl_equal501   operator()(const type_or_decl_base *l, const type_or_decl_base *r) const
502   {
503     string repr1 = get_pretty_representation(l);
504     string repr2 = get_pretty_representation(r);
505 
506     return repr1 == repr2;
507   }
508 
509   /// The function-call operator to compare the string representations
510   /// of two ABI artifacts.
511   ///
512   /// @param l the left hand side ABI artifact operand of the
513   /// comparison.
514   ///
515   /// @param r the right hand side ABI artifact operand of the
516   /// comparison.
517   ///
518   /// @return true iff the string representation of @p l equals the one
519   /// of @p r.
520   bool
operatortype_or_decl_equal521   operator()(const type_or_decl_base_sptr &l,
522 	     const type_or_decl_base_sptr &r) const
523   {return operator()(l.get(), r.get());}
524 }; // end type_or_decl_equal
525 
526 /// A convenience typedef for a hash set of type_or_decl_base_sptr
527 typedef unordered_set<type_or_decl_base_sptr,
528 		      type_or_decl_hash,
529 		      type_or_decl_equal> artifact_sptr_set_type;
530 
531 /// A convenience typedef for a hash set of const type_or_decl_base*
532 typedef unordered_set<const type_or_decl_base*,
533 		      type_or_decl_hash,
534 		      type_or_decl_equal> artifact_ptr_set_type;
535 
536 /// A convenience typedef for a map which key is a string and which
537 /// value is a @ref type_base_wptr.
538 typedef unordered_map<string, type_base_wptr> string_type_base_wptr_map_type;
539 
540 /// A convenience typedef for a map which key is an @ref
541 /// interned_string and which value is a @ref type_base_wptr.
542 typedef unordered_map<interned_string, type_base_wptr, hash_interned_string>
543 istring_type_base_wptr_map_type;
544 
545 /// A convenience typedef for a map which key is an @ref
546 /// interned_string and which value is a @ref type_base_wptr.
547 typedef unordered_map<interned_string,
548 		      type_or_decl_base_sptr,
549 		      hash_interned_string>
550 istring_type_or_decl_base_sptr_map_type;
551 
552 /// This is a type that aggregates maps of all the kinds of types that
553 /// are supported by libabigail.
554 ///
555 /// For instance, the type_maps contains a map of string to basic
556 /// type, a map of string to class type, a map of string to union
557 /// types, etc.  The key of a map entry is the pretty representation
558 /// of the type, and the value of the map entry is the type.
559 class type_maps
560 {
561   struct priv;
562   std::unique_ptr<priv> priv_;
563 
564 public:
565 
566   type_maps();
567 
568   ~type_maps();
569 
570   bool
571   empty() const;
572 
573   const istring_type_base_wptrs_map_type&
574   basic_types() const;
575 
576   istring_type_base_wptrs_map_type&
577   basic_types();
578 
579   const istring_type_base_wptrs_map_type&
580   class_types() const;
581 
582   istring_type_base_wptrs_map_type&
583   class_types();
584 
585   istring_type_base_wptrs_map_type&
586   union_types();
587 
588   const istring_type_base_wptrs_map_type&
589   union_types() const;
590 
591   istring_type_base_wptrs_map_type&
592   enum_types();
593 
594   const istring_type_base_wptrs_map_type&
595   enum_types() const;
596 
597   istring_type_base_wptrs_map_type&
598   typedef_types();
599 
600   const istring_type_base_wptrs_map_type&
601   typedef_types() const;
602 
603   istring_type_base_wptrs_map_type&
604   qualified_types();
605 
606   const istring_type_base_wptrs_map_type&
607   qualified_types() const;
608 
609   istring_type_base_wptrs_map_type&
610   pointer_types();
611 
612   const istring_type_base_wptrs_map_type&
613   pointer_types() const;
614 
615   istring_type_base_wptrs_map_type&
616   reference_types();
617 
618   const istring_type_base_wptrs_map_type&
619   reference_types() const;
620 
621   istring_type_base_wptrs_map_type&
622   array_types();
623 
624   const istring_type_base_wptrs_map_type&
625   array_types() const;
626 
627   const istring_type_base_wptrs_map_type&
628   subrange_types() const;
629 
630   istring_type_base_wptrs_map_type&
631   subrange_types();
632 
633   istring_type_base_wptrs_map_type&
634   function_types();
635 
636   const istring_type_base_wptrs_map_type&
637   function_types() const;
638 
639   const vector<type_base_wptr>&
640   get_types_sorted_by_name() const;
641 }; // end class type_maps;
642 
643 /// This is the abstraction of the set of relevant artefacts (types,
644 /// variable declarations, functions, templates, etc) bundled together
645 /// into a translation unit.
646 class translation_unit : public traversable_base
647 {
648   struct priv;
649   std::unique_ptr<priv> priv_;
650 
651   // Forbidden
652   translation_unit() = delete;
653 
654 public:
655   /// Convenience typedef for a shared pointer on a @ref global_scope.
656   typedef shared_ptr<scope_decl> global_scope_sptr;
657 
658   /// The language of the translation unit.
659   enum language
660   {
661     LANG_UNKNOWN = 0,
662     LANG_Cobol74,
663     LANG_Cobol85,
664     LANG_C89,
665     LANG_C99,
666     LANG_C11,
667     LANG_C,
668     LANG_C_plus_plus_03,
669     LANG_C_plus_plus_11,
670     LANG_C_plus_plus_14,
671     LANG_C_plus_plus,
672     LANG_ObjC,
673     LANG_ObjC_plus_plus,
674     LANG_Fortran77,
675     LANG_Fortran90,
676     LANG_Fortran95,
677     LANG_Ada83,
678     LANG_Ada95,
679     LANG_Pascal83,
680     LANG_Modula2,
681     LANG_Java,
682     LANG_PLI,
683     LANG_UPC,
684     LANG_D,
685     LANG_Python,
686     LANG_Go,
687     LANG_Rust,
688     LANG_Mips_Assembler
689   };
690 
691 public:
692   translation_unit(const ir::environment&	env,
693 		   const std::string&		path,
694 		   char			address_size = 0);
695 
696   virtual ~translation_unit();
697 
698   const environment&
699   get_environment() const;
700 
701   language
702   get_language() const;
703 
704   void
705   set_language(language l);
706 
707   const std::string&
708   get_path() const;
709 
710   void
711   set_path(const string&);
712 
713   const std::string&
714   get_compilation_dir_path() const;
715 
716   void
717   set_compilation_dir_path(const std::string&);
718 
719   const std::string&
720   get_absolute_path() const;
721 
722   void
723   set_corpus(corpus*);
724 
725   const corpus*
726   get_corpus() const;
727 
728   corpus*
729   get_corpus();
730 
731   const scope_decl_sptr&
732   get_global_scope() const;
733 
734   scope_decl_sptr&
735   get_global_scope();
736 
737   const type_maps&
738   get_types() const;
739 
740   type_maps&
741   get_types();
742 
743   const vector<function_type_sptr>&
744   get_live_fn_types() const;
745 
746   location_manager&
747   get_loc_mgr();
748 
749   const location_manager&
750   get_loc_mgr() const;
751 
752   bool
753   is_empty() const;
754 
755   char
756   get_address_size() const;
757 
758   void
759   set_address_size(char);
760 
761   bool
762   is_constructed() const;
763 
764   void
765   set_is_constructed(bool);
766 
767   bool
768   operator==(const translation_unit&) const;
769 
770   bool
771   operator!=(const translation_unit&) const;
772 
773   void
774   bind_function_type_life_time(function_type_sptr) const;
775 
776   virtual bool
777   traverse(ir_node_visitor& v);
778 
779   friend function_type_sptr
780   lookup_function_type_in_translation_unit(const function_type& t,
781 					   const translation_unit& tu);
782 
783   friend function_type_sptr
784   synthesize_function_type_from_translation_unit(const function_type& fn_type,
785 						 translation_unit& tu);
786 
787   friend type_base_sptr
788   synthesize_type_from_translation_unit(const type_base_sptr& type,
789 					translation_unit& tu);
790 };//end class translation_unit
791 
792 /// A comparison functor to compare translation units based on their
793 /// absolute paths.
794 struct shared_translation_unit_comp
795 {
796   /// Compare two translations units based on their absolute paths.
797   ///
798   /// @param lhs the first translation unit to consider for the
799   /// comparison.
800   ///
801   /// @param rhs the second translatin unit to consider for the
802   /// comparison.
803   bool
operatorshared_translation_unit_comp804   operator()(const translation_unit_sptr& lhs,
805 	     const translation_unit_sptr& rhs) const
806   {return lhs->get_absolute_path() < rhs->get_absolute_path();}
807 }; // end struct shared_translation_unit_comp
808 
809 /// Convenience typedef for an ordered set of @ref
810 /// translation_unit_sptr.
811 typedef std::set<translation_unit_sptr,
812 		 shared_translation_unit_comp> translation_units;
813 
814 string
815 translation_unit_language_to_string(translation_unit::language);
816 
817 translation_unit::language
818 string_to_translation_unit_language(const string&);
819 
820 bool
821 is_c_language(translation_unit::language l);
822 
823 bool
824 is_cplus_plus_language(translation_unit::language l);
825 
826 bool
827 is_java_language(translation_unit::language l);
828 
829 bool
830 is_ada_language(translation_unit::language l);
831 
832 bool
833 operator==(const translation_unit_sptr&, const translation_unit_sptr&);
834 
835 bool
836 operator!=(const translation_unit_sptr&, const translation_unit_sptr&);
837 
838 /// Access specifier for class members.
839 enum access_specifier
840 {
841   no_access,
842   public_access,
843   protected_access,
844   private_access,
845 };
846 
847 class elf_symbol;
848 /// A convenience typedef for a shared pointer to elf_symbol.
849 typedef shared_ptr<elf_symbol> elf_symbol_sptr;
850 
851 /// A convenience typedef for a weak pointer to elf_symbol.
852 typedef weak_ptr<elf_symbol> elf_symbol_wptr;
853 
854 /// Convenience typedef for a map which key is a string and which
855 /// value if the elf symbol of the same name.
856 typedef std::unordered_map<string, elf_symbol_sptr>
857 string_elf_symbol_sptr_map_type;
858 
859 /// Convenience typedef for a shared pointer to an
860 /// string_elf_symbol_sptr_map_type.
861 typedef shared_ptr<string_elf_symbol_sptr_map_type>
862 string_elf_symbol_sptr_map_sptr;
863 
864 /// Convenience typedef for a vector of elf_symbol
865 typedef std::vector<elf_symbol_sptr> elf_symbols;
866 
867 /// Convenience typedef for a map which key is a string and which
868 /// value is a vector of elf_symbol.
869 typedef std::unordered_map<string, elf_symbols>
870 string_elf_symbols_map_type;
871 
872 /// Convenience typedef for a shared pointer to
873 /// string_elf_symbols_map_type.
874 typedef shared_ptr<string_elf_symbols_map_type> string_elf_symbols_map_sptr;
875 
876 /// Abstraction of an elf symbol.
877 ///
878 /// This is useful when a given corpus has been read from an ELF file.
879 /// In that case, a given decl might be associated to its underlying
880 /// ELF symbol, if that decl is publicly exported in the ELF file.  In
881 /// that case, comparing decls might involve comparing their
882 /// underlying symbols as well.
883 class elf_symbol
884 {
885 public:
886   /// The type of a symbol.
887   enum type
888   {
889     NOTYPE_TYPE = 0,
890     OBJECT_TYPE,
891     FUNC_TYPE,
892     SECTION_TYPE,
893     FILE_TYPE,
894     COMMON_TYPE,
895     TLS_TYPE,
896     GNU_IFUNC_TYPE
897   };
898 
899   /// The binding of a symbol.
900   enum binding
901   {
902     LOCAL_BINDING = 0,
903     GLOBAL_BINDING,
904     WEAK_BINDING,
905     GNU_UNIQUE_BINDING
906   };
907 
908   /// The visibility of the symbol.
909   enum visibility
910   {
911     DEFAULT_VISIBILITY,
912     PROTECTED_VISIBILITY,
913     HIDDEN_VISIBILITY,
914     INTERNAL_VISIBILITY,
915   };
916 
917   /// Inject the elf_symbol::version here.
918   class version;
919 
920 private:
921   struct priv;
922   std::unique_ptr<priv> priv_;
923 
924   elf_symbol();
925 
926   elf_symbol(const environment& e,
927 	     size_t		i,
928 	     size_t		s,
929 	     const string&	n,
930 	     type		t,
931 	     binding		b,
932 	     bool		d,
933 	     bool		c,
934 	     const version&	ve,
935 	     visibility		vi,
936 	     bool		is_in_ksymtab = false,
937 	     const abg_compat::optional<uint32_t>&	crc = {},
938 	     const abg_compat::optional<std::string>&	ns = {},
939 	     bool		is_suppressed = false);
940 
941   elf_symbol(const elf_symbol&);
942 
943   elf_symbol&
944   operator=(const elf_symbol& s);
945 
946 public:
947 
948   static elf_symbol_sptr
949   create(const environment&	e,
950 	 size_t		i,
951 	 size_t		s,
952 	 const string&		n,
953 	 type			t,
954 	 binding		b,
955 	 bool			d,
956 	 bool			c,
957 	 const version&	ve,
958 	 visibility		vi,
959 	 bool			is_in_ksymtab = false,
960 	 const abg_compat::optional<uint32_t>&		crc = {},
961 	 const abg_compat::optional<std::string>&	ns = {},
962 	 bool						is_suppressed = false);
963 
964   const environment&
965   get_environment() const;
966 
967   size_t
968   get_index() const;
969 
970   void
971   set_index(size_t);
972 
973   const string&
974   get_name() const;
975 
976   void
977   set_name(const string& n);
978 
979   type
980   get_type() const;
981 
982   void
983   set_type(type t);
984 
985   size_t
986   get_size() const;
987 
988   void
989   set_size(size_t);
990 
991   binding
992   get_binding() const;
993 
994   void
995   set_binding(binding b);
996 
997   version&
998   get_version() const;
999 
1000   void
1001   set_version(const version& v);
1002 
1003   void
1004   set_visibility(visibility v);
1005 
1006   visibility
1007   get_visibility() const;
1008 
1009   bool
1010   is_defined() const;
1011 
1012   void
1013   is_defined(bool d);
1014 
1015   bool
1016   is_public() const;
1017 
1018   bool
1019   is_function() const;
1020 
1021   bool
1022   is_variable() const;
1023 
1024   bool
1025   is_in_ksymtab() const;
1026 
1027   void
1028   set_is_in_ksymtab(bool is_in_ksymtab);
1029 
1030   const abg_compat::optional<uint32_t>&
1031   get_crc() const;
1032 
1033   void
1034   set_crc(const abg_compat::optional<uint32_t>& crc);
1035 
1036   const abg_compat::optional<std::string>&
1037   get_namespace() const;
1038 
1039   void
1040   set_namespace(const abg_compat::optional<std::string>& ns);
1041 
1042   bool
1043   is_suppressed() const;
1044 
1045   void
1046   set_is_suppressed(bool is_suppressed);
1047 
1048   const elf_symbol_sptr
1049   get_main_symbol() const;
1050 
1051   elf_symbol_sptr
1052   get_main_symbol();
1053 
1054   bool
1055   is_main_symbol() const;
1056 
1057   elf_symbol_sptr
1058   update_main_symbol(const std::string&);
1059 
1060   elf_symbol_sptr
1061   get_next_alias() const;
1062 
1063   bool
1064   has_aliases() const;
1065 
1066   int
1067   get_number_of_aliases() const;
1068 
1069   void
1070   add_alias(const elf_symbol_sptr&);
1071 
1072   bool
1073   is_common_symbol() const;
1074 
1075   bool
1076   has_other_common_instances() const;
1077 
1078   elf_symbol_sptr
1079   get_next_common_instance() const;
1080 
1081   void
1082   add_common_instance(const elf_symbol_sptr&);
1083 
1084   const string&
1085   get_id_string() const;
1086 
1087   elf_symbol_sptr
1088   get_alias_from_name(const string& name) const;
1089 
1090   elf_symbol_sptr
1091   get_alias_which_equals(const elf_symbol& other) const;
1092 
1093   string
1094   get_aliases_id_string(const string_elf_symbols_map_type& symtab,
1095 			bool include_symbol_itself = true) const;
1096 
1097   string
1098   get_aliases_id_string(bool include_symbol_itself = true) const;
1099 
1100   static bool
1101   get_name_and_version_from_id(const string& id,
1102 			       string& name,
1103 			       string& ver);
1104 
1105   bool
1106   operator==(const elf_symbol&) const;
1107 
1108   bool
1109   does_alias(const elf_symbol&) const;
1110 }; // end class elf_symbol.
1111 
1112 std::ostream&
1113 operator<<(std::ostream& o, elf_symbol::type t);
1114 
1115 std::ostream&
1116 operator<<(std::ostream& o, elf_symbol::binding t);
1117 
1118 std::ostream&
1119 operator<<(std::ostream& o, elf_symbol::visibility t);
1120 
1121 bool
1122 string_to_elf_symbol_type(const string&, elf_symbol::type&);
1123 
1124 bool
1125 string_to_elf_symbol_binding(const string&, elf_symbol::binding&);
1126 
1127 bool
1128 string_to_elf_symbol_visibility(const string&, elf_symbol::visibility&);
1129 
1130 bool
1131 elf_symbol_is_function(elf_symbol::type);
1132 
1133 bool
1134 elf_symbol_is_variable(elf_symbol::type);
1135 
1136 bool
1137 operator==(const elf_symbol_sptr& lhs, const elf_symbol_sptr& rhs);
1138 
1139 bool
1140 operator!=(const elf_symbol_sptr& lhs, const elf_symbol_sptr& rhs);
1141 
1142 bool
1143 elf_symbols_alias(const elf_symbol& s1, const elf_symbol& s2);
1144 
1145 void
1146 compute_aliases_for_elf_symbol(const elf_symbol& symbol,
1147 			       const string_elf_symbols_map_type& symtab,
1148 			       vector<elf_symbol_sptr>& alias_set);
1149 
1150 /// The abstraction of the version of an ELF symbol.
1151 class elf_symbol::version
1152 {
1153   struct priv;
1154   std::unique_ptr<priv> priv_;
1155 
1156 public:
1157   version();
1158 
1159   version(const string& v,
1160 	  bool is_default);
1161 
1162   version(const version& v);
1163 
1164   ~version();
1165 
1166   operator const string&() const;
1167 
1168   const string&
1169   str() const;
1170 
1171   void
1172   str(const string& s);
1173 
1174   bool
1175   is_default() const;
1176 
1177   void
1178   is_default(bool f);
1179 
1180   bool
1181   is_empty() const;
1182 
1183   bool
1184   operator==(const version& o) const;
1185 
1186   bool
1187   operator!=(const version& o) const;
1188 
1189   version&
1190   operator=(const version& o);
1191 };// end class elf_symbol::version
1192 
1193 class context_rel;
1194 /// A convenience typedef for shared pointers to @ref context_rel
1195 typedef shared_ptr<context_rel> context_rel_sptr;
1196 
1197 /// The abstraction of the relationship between an entity and its
1198 /// containing scope (its context).  That relationship can carry
1199 /// properties like access rights (if the parent is a class_decl),
1200 /// etc.
1201 ///
1202 /// But importantly, this relationship carries a pointer to the
1203 /// actualy parent.
1204 class context_rel
1205 {
1206 protected:
1207   scope_decl*		scope_;
1208   enum access_specifier access_;
1209   bool			is_static_;
1210 
1211 public:
context_rel()1212   context_rel()
1213     : scope_(0),
1214       access_(no_access),
1215       is_static_(false)
1216   {}
1217 
context_rel(scope_decl * s)1218   context_rel(scope_decl* s)
1219     : scope_(s),
1220       access_(no_access),
1221       is_static_(false)
1222   {}
1223 
context_rel(scope_decl * s,access_specifier a,bool f)1224   context_rel(scope_decl* s,
1225 	      access_specifier a,
1226 	      bool f)
1227     : scope_(s),
1228       access_(a),
1229       is_static_(f)
1230   {}
1231 
1232   scope_decl*
get_scope()1233   get_scope() const
1234   {return scope_;}
1235 
1236   access_specifier
get_access_specifier()1237   get_access_specifier() const
1238   {return access_;}
1239 
1240   void
set_access_specifier(access_specifier a)1241   set_access_specifier(access_specifier a)
1242   {access_ = a;}
1243 
1244   bool
get_is_static()1245   get_is_static() const
1246   {return is_static_;}
1247 
1248   void
set_is_static(bool s)1249   set_is_static(bool s)
1250   {is_static_ = s;}
1251 
1252   void
set_scope(scope_decl * s)1253   set_scope(scope_decl* s)
1254   {scope_ = s;}
1255 
1256   bool
1257   operator==(const context_rel& o)const
1258   {
1259     return (access_ == o.access_
1260 	    && is_static_ == o.is_static_);
1261   }
1262 
1263   /// Inequality operator.
1264   ///
1265   /// @param o the other instance of @ref context_rel to compare the
1266   /// current instance against.
1267   ///
1268   /// @return true iff the current instance of @ref context_rel is
1269   /// different from @p o.
1270   bool
1271   operator!=(const context_rel& o) const
1272   {return !operator==(o);}
1273 
1274   virtual ~context_rel();
1275 };// end class context_rel
1276 
1277 /// A bitfield that gives callers of abigail::ir::equals() some
1278 /// insight about how different two internal representation artifacts
1279 /// are.
1280 enum change_kind
1281 {
1282   NO_CHANGE_KIND = 0,
1283 
1284   /// This means that a given IR artifact has a local type change.
1285   LOCAL_TYPE_CHANGE_KIND = 1 << 0,
1286 
1287   /// This means that a given IR artifact has a local non-type change.
1288   /// That is a change that is carried by the artifact itself, not by
1289   /// its type.
1290   LOCAL_NON_TYPE_CHANGE_KIND = 1 << 1,
1291 
1292   /// Testing (anding) against this mask means that a given IR artifact has
1293   /// local differences, with respect to the other artifact it was compared
1294   /// against. A local change is a change that is carried by the artifact
1295   /// itself (or its type), rather than by one off its sub-types.
1296   ALL_LOCAL_CHANGES_MASK = LOCAL_TYPE_CHANGE_KIND | LOCAL_NON_TYPE_CHANGE_KIND,
1297 
1298   /// This means that a given IR artifact has changes in some of its
1299   /// sub-types, with respect to the other artifact it was compared
1300   /// against.
1301   SUBTYPE_CHANGE_KIND = 1 << 2,
1302 };// end enum change_kind
1303 
1304 change_kind
1305 operator|(change_kind, change_kind);
1306 
1307 change_kind
1308 operator&(change_kind, change_kind);
1309 
1310 change_kind&
1311 operator|=(change_kind&, change_kind);
1312 
1313 change_kind&
1314 operator&=(change_kind&, change_kind);
1315 
1316 bool
1317 maybe_compare_as_member_decls(const decl_base& l,
1318 			      const decl_base& r,
1319 			      change_kind* k);
1320 
1321 bool
1322 equals(const decl_base&, const decl_base&, change_kind*);
1323 
1324 /// The base class of both types and declarations.
1325 class type_or_decl_base : public ir_traversable_base
1326 {
1327   struct priv;
1328   mutable std::unique_ptr<priv> priv_;
1329 
1330   type_or_decl_base();
1331   type_or_decl_base(const type_or_decl_base&);
1332 
1333 protected:
1334 
1335   /// This is a bitmap type which instance is meant to contain the
1336   /// runtime type of a given ABI artifact.  Bits of the identifiers
1337   /// of the type of a given artifact as well as the types it inherits
1338   /// from are to be set to 1.
1339   enum type_or_decl_kind
1340   {
1341     ABSTRACT_TYPE_OR_DECL,
1342     ABSTRACT_DECL_BASE = 1,
1343     ABSTRACT_SCOPE_DECL = 1 << 1,
1344     GLOBAL_SCOPE_DECL = 1 << 2,
1345     NAMESPACE_DECL = 1 << 3,
1346     VAR_DECL = 1 << 4,
1347     FUNCTION_DECL = 1 << 5,
1348     FUNCTION_PARAMETER_DECL = 1 << 6,
1349     METHOD_DECL = 1 << 7,
1350     TEMPLATE_DECL = 1 << 8,
1351     ABSTRACT_TYPE_BASE = 1 << 9,
1352     ABSTRACT_SCOPE_TYPE_DECL = 1 << 10,
1353     BASIC_TYPE = 1 << 11,
1354     QUALIFIED_TYPE = 1 << 12,
1355     POINTER_TYPE = 1 << 13,
1356     REFERENCE_TYPE = 1 << 14,
1357     ARRAY_TYPE = 1 << 15,
1358     ENUM_TYPE = 1 << 16,
1359     TYPEDEF_TYPE = 1 << 17,
1360     CLASS_TYPE = 1 << 18,
1361     UNION_TYPE = 1 << 19,
1362     FUNCTION_TYPE = 1 << 20,
1363     METHOD_TYPE = 1 << 21,
1364   }; // end enum type_or_decl_kind
1365 
1366   enum type_or_decl_kind
1367   kind() const;
1368 
1369   void
1370   kind(enum type_or_decl_kind);
1371 
1372   const void*
1373   runtime_type_instance() const;
1374 
1375   void*
1376   runtime_type_instance();
1377 
1378   void
1379   runtime_type_instance(void*);
1380 
1381   const void*
1382   type_or_decl_base_pointer() const;
1383 
1384   void*
1385   type_or_decl_base_pointer();
1386 
1387   bool hashing_started() const;
1388 
1389   void hashing_started(bool) const;
1390 
1391   type_or_decl_base&
1392   operator=(const type_or_decl_base&);
1393 
1394 public:
1395 
1396   type_or_decl_base(const environment&,
1397 		    enum type_or_decl_kind k = ABSTRACT_TYPE_OR_DECL);
1398 
1399   virtual ~type_or_decl_base();
1400 
1401   bool
1402   get_is_artificial() const;
1403 
1404   void
1405   set_is_artificial(bool);
1406 
1407   const environment&
1408   get_environment() const;
1409 
1410   void
1411   set_artificial_location(const location &);
1412 
1413   location&
1414   get_artificial_location() const;
1415 
1416   bool
1417   has_artificial_location() const;
1418 
1419   const corpus*
1420   get_corpus() const;
1421 
1422   corpus*
1423   get_corpus();
1424 
1425   void
1426   set_translation_unit(translation_unit*);
1427 
1428   const translation_unit*
1429   get_translation_unit() const;
1430 
1431   translation_unit*
1432   get_translation_unit();
1433 
1434   virtual bool
1435   traverse(ir_node_visitor&);
1436 
1437   virtual string
1438   get_pretty_representation(bool internal = false,
1439 			    bool qualified_name = true) const = 0;
1440 
1441   friend type_or_decl_base::type_or_decl_kind
1442   operator|(type_or_decl_base::type_or_decl_kind,
1443 	    type_or_decl_base::type_or_decl_kind);
1444 
1445   friend type_or_decl_base::type_or_decl_kind&
1446   operator|=(type_or_decl_base::type_or_decl_kind&,
1447 	     type_or_decl_base::type_or_decl_kind);
1448 
1449   friend type_or_decl_base::type_or_decl_kind
1450   operator&(type_or_decl_base::type_or_decl_kind,
1451 	    type_or_decl_base::type_or_decl_kind);
1452 
1453   friend type_or_decl_base::type_or_decl_kind&
1454   operator&=(type_or_decl_base::type_or_decl_kind&,
1455 	     type_or_decl_base::type_or_decl_kind);
1456 
1457   friend class_decl*
1458   is_class_type(const type_or_decl_base*);
1459 
1460   friend pointer_type_def*
1461   is_pointer_type(type_or_decl_base*);
1462 
1463   friend type_base*
1464   is_type(const type_or_decl_base*);
1465 
1466   friend decl_base*
1467   is_decl(const type_or_decl_base* d);
1468 }; // end class type_or_decl_base
1469 
1470 type_or_decl_base::type_or_decl_kind
1471 operator|(type_or_decl_base::type_or_decl_kind,
1472 	  type_or_decl_base::type_or_decl_kind);
1473 
1474 type_or_decl_base::type_or_decl_kind&
1475 operator|=(type_or_decl_base::type_or_decl_kind&,
1476 	   type_or_decl_base::type_or_decl_kind);
1477 
1478 type_or_decl_base::type_or_decl_kind
1479 operator&(type_or_decl_base::type_or_decl_kind,
1480 	  type_or_decl_base::type_or_decl_kind);
1481 
1482 type_or_decl_base::type_or_decl_kind&
1483 operator&=(type_or_decl_base::type_or_decl_kind&,
1484 	   type_or_decl_base::type_or_decl_kind);
1485 
1486 bool
1487 operator==(const type_or_decl_base&, const type_or_decl_base&);
1488 
1489 bool
1490 operator==(const type_or_decl_base_sptr&, const type_or_decl_base_sptr&);
1491 
1492 bool
1493 operator!=(const type_or_decl_base_sptr&, const type_or_decl_base_sptr&);
1494 
1495 /// The base type of all declarations.
1496 class decl_base : public virtual type_or_decl_base
1497 {
1498   // Forbidden
1499   decl_base();
1500 
1501   struct priv;
1502 
1503 protected:
1504 
1505   const interned_string&
1506   peek_qualified_name() const;
1507 
1508   void
1509   clear_qualified_name();
1510 
1511   void
1512   set_qualified_name(const interned_string&) const;
1513 
1514   const interned_string&
1515   peek_temporary_qualified_name() const;
1516 
1517   void
1518   set_temporary_qualified_name(const interned_string&) const;
1519 
1520 public:
1521   // This is public because some internals of the library need to
1522   // update it.  But it's opaque to client code anyway, so no big
1523   // deal.  Also, it's not handled by a shared_ptr because accessing
1524   // the data members of the priv struct for this decl_base shows up
1525   // on performance profiles when dealing with big binaries with a lot
1526   // of types; dereferencing the shared_ptr involves locking of some
1527   // sort and that is slower than just dereferencing a pointer likere
1528   // here.  There are other types for which the priv pointer is
1529   // managed using shared_ptr just fine, because those didn't show up
1530   // during our performance profiling.
1531   priv* priv_;
1532 
1533   /// Facility to hash instances of decl_base.
1534   struct hash;
1535 
1536   /// ELF visibility
1537   enum visibility
1538   {
1539     VISIBILITY_NONE,
1540     VISIBILITY_DEFAULT,
1541     VISIBILITY_PROTECTED,
1542     VISIBILITY_HIDDEN,
1543     VISIBILITY_INTERNAL
1544   };
1545 
1546   /// ELF binding
1547   enum binding
1548   {
1549     BINDING_NONE,
1550     BINDING_LOCAL,
1551     BINDING_GLOBAL,
1552     BINDING_WEAK
1553   };
1554 
1555   virtual void
1556   set_scope(scope_decl*);
1557 
1558 protected:
1559   const context_rel*
1560   get_context_rel() const;
1561 
1562   context_rel*
1563   get_context_rel();
1564 
1565   void
1566   set_context_rel(context_rel *c);
1567   decl_base(const decl_base&);
1568 
1569 public:
1570   decl_base(const environment& e,
1571 	    const string& name,
1572 	    const location& locus,
1573 	    const string& mangled_name = "",
1574 	    visibility vis = VISIBILITY_DEFAULT);
1575 
1576   decl_base(const environment& e,
1577 	    const interned_string& name,
1578 	    const location& locus,
1579 	    const interned_string& mangled_name = interned_string(),
1580 	    visibility vis = VISIBILITY_DEFAULT);
1581 
1582   decl_base(const environment&, const location&);
1583 
1584   virtual bool
1585   operator==(const decl_base&) const;
1586 
1587   virtual bool
1588   operator!=(const decl_base&) const;
1589 
1590   virtual bool
1591   traverse(ir_node_visitor& v);
1592 
1593   virtual ~decl_base();
1594 
1595   virtual size_t
1596   get_hash() const;
1597 
1598   virtual string
1599   get_pretty_representation(bool internal = false,
1600 			    bool qualified_name = true) const;
1601 
1602   virtual void
1603   get_qualified_name(interned_string& qualified_name,
1604 		     bool internal = false) const;
1605 
1606   virtual const interned_string&
1607   get_qualified_name(bool internal = false) const;
1608 
1609   virtual const interned_string&
1610   get_scoped_name() const;
1611 
1612   bool
1613   get_is_in_public_symbol_table() const;
1614 
1615   void
1616   set_is_in_public_symbol_table(bool);
1617 
1618   const location&
1619   get_location() const;
1620 
1621   void
1622   set_location(const location& l);
1623 
1624   const interned_string&
1625   get_name() const;
1626 
1627   const interned_string&
1628   get_qualified_parent_name() const;
1629 
1630   void
1631   set_name(const string& n);
1632 
1633   bool
1634   get_is_anonymous() const;
1635 
1636   void
1637   set_is_anonymous(bool);
1638 
1639   bool
1640   get_has_anonymous_parent() const;
1641 
1642   bool
1643   get_is_anonymous_or_has_anonymous_parent() const;
1644 
1645   typedef_decl_sptr
1646   get_naming_typedef() const;
1647 
1648   void
1649   set_naming_typedef(const typedef_decl_sptr&);
1650 
1651   const interned_string&
1652   get_linkage_name() const;
1653 
1654   virtual void
1655   set_linkage_name(const string& m);
1656 
1657   scope_decl*
1658   get_scope() const;
1659 
1660   visibility
1661   get_visibility() const;
1662 
1663   void
1664   set_visibility(visibility v);
1665 
1666   const decl_base_sptr
1667   get_earlier_declaration() const;
1668 
1669   void
1670   set_earlier_declaration(const decl_base_sptr&);
1671 
1672   const decl_base_sptr
1673   get_definition_of_declaration() const;
1674 
1675   void
1676   set_definition_of_declaration(const decl_base_sptr&);
1677 
1678   const decl_base*
1679   get_naked_definition_of_declaration() const;
1680 
1681   bool
1682   get_is_declaration_only() const;
1683 
1684   void
1685   set_is_declaration_only(bool f);
1686 
1687   friend type_base_sptr
1688   canonicalize(type_base_sptr);
1689 
1690   friend bool
1691   equals(const decl_base&, const decl_base&, change_kind*);
1692 
1693   friend bool
1694   equals(const var_decl&, const var_decl&, change_kind*);
1695 
1696   friend bool
1697   maybe_compare_as_member_decls(const decl_base& l,
1698 				const decl_base& r,
1699 				change_kind* k);
1700 
1701   friend decl_base_sptr
1702   add_decl_to_scope(decl_base_sptr decl, scope_decl* scpe);
1703 
1704   friend void
1705   remove_decl_from_scope(decl_base_sptr);
1706 
1707   friend decl_base_sptr
1708   insert_decl_into_scope(decl_base_sptr,
1709 			 vector<shared_ptr<decl_base> >::iterator,
1710 			 scope_decl*);
1711 
1712   friend enum access_specifier
1713   get_member_access_specifier(const decl_base& d);
1714 
1715   friend enum access_specifier
1716   get_member_access_specifier(const decl_base_sptr& d);
1717 
1718   friend void
1719   set_member_access_specifier(decl_base& d,
1720 			      access_specifier a);
1721 
1722   friend bool
1723   get_member_is_static(const decl_base& d);
1724 
1725   friend bool
1726   get_member_is_static(const decl_base_sptr& d);
1727 
1728   friend void
1729   set_member_is_static(const decl_base_sptr& d, bool s);
1730 
1731   friend void
1732   set_member_is_static(decl_base& d, bool s);
1733 
1734   friend bool
1735   get_member_function_is_virtual(const function_decl& f);
1736 
1737   friend void
1738   set_member_function_is_virtual(function_decl&, bool);
1739 
1740   friend class class_or_union;
1741   friend class class_decl;
1742   friend class scope_decl;
1743 };// end class decl_base
1744 
1745 bool
1746 operator==(const decl_base_sptr&, const decl_base_sptr&);
1747 
1748 bool
1749 operator!=(const decl_base_sptr&, const decl_base_sptr&);
1750 
1751 bool
1752 operator==(const type_base_sptr&, const type_base_sptr&);
1753 
1754 bool
1755 operator!=(const type_base_sptr&, const type_base_sptr&);
1756 
1757 std::ostream&
1758 operator<<(std::ostream&, decl_base::visibility);
1759 
1760 std::ostream&
1761 operator<<(std::ostream&, decl_base::binding);
1762 
1763 bool
1764 equals(const scope_decl&, const scope_decl&, change_kind*);
1765 
1766 /// A declaration that introduces a scope.
1767 class scope_decl : public virtual decl_base
1768 {
1769   struct priv;
1770   std::unique_ptr<priv> priv_;
1771 
1772 public:
1773 
1774   /// Convenience typedef for a vector of @ref decl_base_sptr.
1775   typedef std::vector<decl_base_sptr >	declarations;
1776   /// Convenience typedef for a vector of @ref function_type_sptr.
1777   typedef std::vector<function_type_sptr >	function_types;
1778   /// Convenience typedef for a vector of @ref scope_decl_sptr.
1779   typedef std::vector<scope_decl_sptr>	scopes;
1780 
1781   scope_decl();
1782 
1783 protected:
1784   virtual decl_base_sptr
1785   add_member_decl(const decl_base_sptr& member);
1786 
1787   decl_base_sptr
1788   insert_member_decl(decl_base_sptr member, declarations::iterator before);
1789 
1790   virtual void
1791   remove_member_decl(decl_base_sptr member);
1792 
1793 public:
1794   struct hash;
1795 
1796   scope_decl(const environment& env,
1797 	     const string& name, const location& locus,
1798 	     visibility	vis = VISIBILITY_DEFAULT);
1799 
1800   scope_decl(const environment& env, location& l);
1801 
1802   virtual size_t
1803   get_hash() const;
1804 
1805   virtual bool
1806   operator==(const decl_base&) const;
1807 
1808   const canonical_type_sptr_set_type&
1809   get_canonical_types() const;
1810 
1811   canonical_type_sptr_set_type&
1812   get_canonical_types();
1813 
1814   const type_base_sptrs_type&
1815   get_sorted_canonical_types() const;
1816 
1817   const declarations&
1818   get_member_decls() const;
1819 
1820   declarations&
1821   get_member_decls();
1822 
1823   const declarations&
1824   get_sorted_member_decls() const;
1825 
1826   virtual size_t
1827   get_num_anonymous_member_classes() const;
1828 
1829   virtual size_t
1830   get_num_anonymous_member_unions() const;
1831 
1832   virtual size_t
1833   get_num_anonymous_member_enums() const;
1834 
1835   scopes&
1836   get_member_scopes();
1837 
1838   const scopes&
1839   get_member_scopes() const;
1840 
1841   bool
1842   is_empty() const;
1843 
1844   bool
1845   find_iterator_for_member(const decl_base*, declarations::iterator&);
1846 
1847   bool
1848   find_iterator_for_member(const decl_base_sptr, declarations::iterator&);
1849 
1850   void
1851   insert_member_type(type_base_sptr t,
1852 		     declarations::iterator before);
1853 
1854   void
1855   add_member_type(type_base_sptr t);
1856 
1857   type_base_sptr
1858   add_member_type(type_base_sptr t, access_specifier a);
1859 
1860   void
1861   remove_member_type(type_base_sptr t);
1862 
1863   const type_base_sptrs_type&
1864   get_member_types() const;
1865 
1866   const type_base_sptrs_type&
1867   get_sorted_member_types() const;
1868 
1869   type_base_sptr
1870   find_member_type(const string& name) const;
1871 
1872   virtual bool
1873   traverse(ir_node_visitor&);
1874 
1875   virtual ~scope_decl();
1876 
1877   friend decl_base_sptr
1878   add_decl_to_scope(decl_base_sptr decl, scope_decl* scope);
1879 
1880   friend decl_base_sptr
1881   insert_decl_into_scope(decl_base_sptr decl,
1882 			 scope_decl::declarations::iterator before,
1883 			 scope_decl* scope);
1884 
1885   friend void
1886   remove_decl_from_scope(decl_base_sptr decl);
1887 
1888   friend type_base_sptr
1889   canonicalize(type_base_sptr);
1890 };//end class scope_decl
1891 
1892 bool
1893 operator==(const scope_decl_sptr&, const scope_decl_sptr&);
1894 
1895 bool
1896 operator!=(const scope_decl_sptr&, const scope_decl_sptr&);
1897 
1898 /// Hasher for the @ref scope_decl type.
1899 struct scope_decl::hash
1900 {
1901   size_t
1902   operator()(const scope_decl& d) const;
1903 
1904   size_t
1905   operator()(const scope_decl* d) const;
1906 };
1907 
1908 /// This abstracts the global scope of a given translation unit.
1909 ///
1910 /// Only one instance of this class must be present in a given
1911 /// translation_unit.  That instance is implicitely created the first
1912 /// time translatin_unit::get_global_scope is invoked.
1913 class global_scope : public scope_decl
1914 {
1915   translation_unit* translation_unit_;
1916 
1917   global_scope(translation_unit *tu);
1918 
1919 public:
1920 
1921   friend class translation_unit;
1922 
1923   translation_unit*
get_translation_unit()1924   get_translation_unit() const
1925   {return translation_unit_;}
1926 
1927   virtual ~global_scope();
1928 };
1929 
1930 bool
1931 equals(const type_base&, const type_base&, change_kind*);
1932 
1933 /// An abstraction helper for type declarations
1934 class type_base : public virtual type_or_decl_base
1935 {
1936   struct priv;
1937 
1938 public:
1939   // This priv pointer is not handled by a shared_ptr because
1940   // accessing the data members of the priv struct for this type_base
1941   // shows up on performance profiles when dealing with big binaries
1942   // with a lot of types; dereferencing the shared_ptr involves
1943   // locking of some sort and that is slower than just dereferencing a
1944   // pointer likere here.  There are other types for which the priv
1945   // pointer is managed using shared_ptr just fine, because those
1946   // didn't show up during our performance profiling.
1947   priv* priv_;
1948 
1949 private:
1950   // Forbid this.
1951   type_base();
1952 
1953   static type_base_sptr
1954   get_canonical_type_for(type_base_sptr);
1955 
1956 protected:
1957   virtual void
1958   on_canonical_type_set();
1959 
1960 public:
1961 
1962   /// A hasher for type_base types.
1963   struct hash;
1964 
1965   /// A hasher for types.  It gets the dynamic type of the current
1966   /// instance of type and hashes it accordingly.  Note that the hashing
1967   /// function of this hasher must be updated each time a new kind of
1968   /// type is added to the IR.
1969   struct dynamic_hash;
1970 
1971   /// A hasher for shared_ptr<type_base> that will hash it based on the
1972   /// runtime type of the type pointed to.
1973   struct shared_ptr_hash;
1974 
1975   type_base(const environment& e, size_t s, size_t a);
1976 
1977   friend type_base_sptr canonicalize(type_base_sptr);
1978 
1979   type_base_sptr
1980   get_canonical_type() const;
1981 
1982   type_base*
1983   get_naked_canonical_type() const;
1984 
1985   const interned_string&
1986   get_cached_pretty_representation(bool internal = false) const;
1987 
1988   virtual bool
1989   operator==(const type_base&) const;
1990 
1991   virtual bool
1992   operator!=(const type_base&) const;
1993 
1994   virtual bool
1995   traverse(ir_node_visitor&);
1996 
1997   virtual ~type_base();
1998 
1999   virtual void
2000   set_size_in_bits(size_t);
2001 
2002   virtual size_t
2003   get_size_in_bits() const;
2004 
2005   virtual void
2006   set_alignment_in_bits(size_t);
2007 
2008   virtual size_t
2009   get_alignment_in_bits() const;
2010 };//end class type_base
2011 
2012 /// Hash functor for instances of @ref type_base.
2013 struct type_base::hash
2014 {
2015   size_t
2016   operator()(const type_base& t) const;
2017 
2018   size_t
2019   operator()(const type_base* t) const;
2020 
2021   size_t
2022   operator()(const type_base_sptr t) const;
2023 }; // end struct type_base::hash
2024 
2025 /// A predicate for deep equality of instances of
2026 /// type_base*
2027 struct type_ptr_equal
2028 {
2029   bool
operatortype_ptr_equal2030   operator()(const type_base* l, const type_base* r) const
2031   {
2032     if (!!l != !!r)
2033       return false;
2034 
2035     if (l == r)
2036       return true;
2037 
2038     if (l)
2039       return *l == *r;
2040 
2041     return true;
2042   }
2043 };
2044 
2045 /// A predicate for deep equality of instances of
2046 /// shared_ptr<type_base>
2047 struct type_shared_ptr_equal
2048 {
2049   bool
operatortype_shared_ptr_equal2050   operator()(const type_base_sptr l, const type_base_sptr r) const
2051   {
2052     if (!!l != !!r)
2053       return false;
2054 
2055     if (l.get() == r.get())
2056       return true;
2057 
2058     if (l)
2059       return *l == *r;
2060 
2061     return true;
2062   }
2063 };
2064 
2065 bool
2066 equals(const type_decl&, const type_decl&, change_kind*);
2067 
2068 /// A basic type declaration that introduces no scope.
2069 class type_decl : public virtual decl_base, public virtual type_base
2070 {
2071   // Forbidden.
2072   type_decl();
2073 
2074 public:
2075 
2076   /// Facility to hash instance of type_decl
2077   struct hash;
2078 
2079   type_decl(const environment&	env,
2080 	    const string&	name,
2081 	    size_t		size_in_bits,
2082 	    size_t		alignment_in_bits,
2083 	    const location&	locus,
2084 	    const string&	mangled_name = "",
2085 	    visibility		vis = VISIBILITY_DEFAULT);
2086 
2087   virtual bool
2088   operator==(const type_base&) const;
2089 
2090   virtual bool
2091   operator==(const decl_base&) const;
2092 
2093   virtual bool
2094   operator==(const type_decl&) const;
2095 
2096   bool operator!=(const type_decl&)const;
2097 
2098   virtual void
2099   get_qualified_name(interned_string& qualified_name,
2100 		     bool internal = false) const;
2101 
2102   virtual const interned_string&
2103   get_qualified_name(bool internal = false) const;
2104 
2105   virtual string
2106   get_pretty_representation(bool internal = false,
2107 			    bool qualified_name = true) const;
2108 
2109   virtual bool
2110   traverse(ir_node_visitor&);
2111 
2112   virtual ~type_decl();
2113 };// end class type_decl.
2114 
2115 bool
2116 equals(const scope_type_decl&, const scope_type_decl&, change_kind*);
2117 
2118 bool
2119 operator==(const type_decl_sptr&, const type_decl_sptr&);
2120 
2121 bool
2122 operator!=(const type_decl_sptr&, const type_decl_sptr&);
2123 
2124 /// A type that introduces a scope.
2125 class scope_type_decl : public scope_decl, public virtual type_base
2126 {
2127   scope_type_decl();
2128 
2129 public:
2130 
2131   /// Hasher for instances of scope_type_decl
2132   struct hash;
2133 
2134   scope_type_decl(const environment& env, const string& name,
2135 		  size_t size_in_bits, size_t alignment_in_bits,
2136 		  const location& locus, visibility vis = VISIBILITY_DEFAULT);
2137 
2138   virtual bool
2139   operator==(const decl_base&) const;
2140 
2141   virtual bool
2142   operator==(const type_base&) const;
2143 
2144   virtual bool
2145   traverse(ir_node_visitor&);
2146 
2147   virtual ~scope_type_decl();
2148 };
2149 
2150 /// The abstraction of a namespace declaration
2151 class namespace_decl : public scope_decl
2152 {
2153 public:
2154 
2155   namespace_decl(const environment& env, const string& name,
2156 		 const location& locus, visibility vis = VISIBILITY_DEFAULT);
2157 
2158   virtual string
2159   get_pretty_representation(bool internal = false,
2160 			    bool qualified_name = true) const;
2161 
2162   virtual bool
2163   operator==(const decl_base&) const;
2164 
2165   virtual bool
2166   traverse(ir_node_visitor&);
2167 
2168   virtual ~namespace_decl();
2169 
2170   bool is_empty_or_has_empty_sub_namespaces() const;
2171 };// end class namespace_decl
2172 
2173 /// A convenience typedef for vectors of @ref namespace_decl_sptr
2174 typedef vector<namespace_decl_sptr> namespaces_type;
2175 
2176 bool
2177 equals(const qualified_type_def&, const qualified_type_def&, change_kind*);
2178 
2179 /// The abstraction of a qualified type.
2180 class qualified_type_def : public virtual type_base, public virtual decl_base
2181 {
2182   class priv;
2183   std::unique_ptr<priv> priv_;
2184 
2185   // Forbidden.
2186   qualified_type_def();
2187 
2188 protected:
2189   string build_name(bool, bool internal = false) const;
2190   virtual void on_canonical_type_set();
2191 
2192 public:
2193 
2194   /// A Hasher for instances of qualified_type_def
2195   struct hash;
2196 
2197   /// Bit field values representing the cv qualifiers of the
2198   /// underlying type.
2199   enum CV
2200   {
2201     CV_NONE = 0,
2202     CV_CONST = 1,
2203     CV_VOLATILE = 1 << 1,
2204     CV_RESTRICT = 1 << 2
2205   };
2206 
2207   qualified_type_def(type_base_sptr type, CV quals, const location& locus);
2208 
2209   qualified_type_def(const environment& env, CV quals, const location& locus);
2210 
2211   virtual size_t
2212   get_size_in_bits() const;
2213 
2214   virtual bool
2215   operator==(const decl_base&) const;
2216 
2217   virtual bool
2218   operator==(const type_base&) const;
2219 
2220   virtual bool
2221   operator==(const qualified_type_def&) const;
2222 
2223   CV
2224   get_cv_quals() const;
2225 
2226   void
2227   set_cv_quals(CV cv_quals);
2228 
2229   string
2230   get_cv_quals_string_prefix() const;
2231 
2232   type_base_sptr
2233   get_underlying_type() const;
2234 
2235   void
2236   set_underlying_type(const type_base_sptr&);
2237 
2238   virtual void
2239   get_qualified_name(interned_string& qualified_name,
2240 		     bool internal = false) const;
2241 
2242   virtual const interned_string&
2243   get_qualified_name(bool internal = false) const;
2244 
2245   virtual bool
2246   traverse(ir_node_visitor& v);
2247 
2248   virtual ~qualified_type_def();
2249 }; // end class qualified_type_def.
2250 
2251 bool
2252 operator==(const qualified_type_def_sptr&, const qualified_type_def_sptr&);
2253 
2254 bool
2255 operator!=(const qualified_type_def_sptr&, const qualified_type_def_sptr&);
2256 
2257 qualified_type_def::CV
2258 operator|(qualified_type_def::CV, qualified_type_def::CV);
2259 
2260 qualified_type_def::CV&
2261 operator|=(qualified_type_def::CV&, qualified_type_def::CV);
2262 
2263 qualified_type_def::CV&
2264 operator&=(qualified_type_def::CV&, qualified_type_def::CV);
2265 
2266 qualified_type_def::CV
2267 operator&(qualified_type_def::CV, qualified_type_def::CV);
2268 
2269 qualified_type_def::CV
2270 operator~(qualified_type_def::CV);
2271 
2272 std::ostream&
2273 operator<<(std::ostream&, qualified_type_def::CV);
2274 
2275 string
2276 get_string_representation_of_cv_quals(const qualified_type_def::CV);
2277 
2278 interned_string
2279 get_name_of_qualified_type(const type_base_sptr& underlying_type,
2280 			   qualified_type_def::CV quals,
2281 			   bool qualified = true, bool internal = false);
2282 
2283 qualified_type_def_sptr
2284 lookup_qualified_type(const type_base_sptr&,
2285 		      qualified_type_def::CV,
2286 		      const translation_unit&);
2287 bool
2288 equals(const pointer_type_def&, const pointer_type_def&, change_kind*);
2289 
2290 /// The abstraction of a pointer type.
2291 class pointer_type_def : public virtual type_base, public virtual decl_base
2292 {
2293   struct priv;
2294   std::unique_ptr<priv> priv_;
2295 
2296   // Forbidden.
2297   pointer_type_def();
2298 
2299 protected:
2300   virtual void on_canonical_type_set();
2301 
2302 public:
2303 
2304   /// A hasher for instances of pointer_type_def
2305   struct hash;
2306 
2307   pointer_type_def(const type_base_sptr& pointed_to_type, size_t size_in_bits,
2308 		   size_t alignment_in_bits, const location& locus);
2309 
2310   pointer_type_def(const environment& env, size_t size_in_bits,
2311 		   size_t alignment_in_bits, const location& locus);
2312 
2313   void
2314   set_pointed_to_type(const type_base_sptr&);
2315 
2316   virtual bool
2317   operator==(const decl_base&) const;
2318 
2319   virtual bool
2320   operator==(const type_base&) const;
2321 
2322   bool
2323   operator==(const pointer_type_def&) const;
2324 
2325   const type_base_sptr
2326   get_pointed_to_type() const;
2327 
2328   type_base*
2329   get_naked_pointed_to_type() const;
2330 
2331   virtual void
2332   get_qualified_name(interned_string&, bool internal = false) const;
2333 
2334   virtual const interned_string&
2335   get_qualified_name(bool internal = false) const;
2336 
2337   virtual bool
2338   traverse(ir_node_visitor& v);
2339 
2340   virtual ~pointer_type_def();
2341 }; // end class pointer_type_def
2342 
2343 bool
2344 operator==(const pointer_type_def_sptr&, const pointer_type_def_sptr&);
2345 
2346 bool
2347 operator!=(const pointer_type_def_sptr&, const pointer_type_def_sptr&);
2348 
2349 bool
2350 equals(const reference_type_def&, const reference_type_def&, change_kind*);
2351 
2352 
2353 /// Abstracts a reference type.
2354 class reference_type_def : public virtual type_base, public virtual decl_base
2355 {
2356   type_base_wptr	pointed_to_type_;
2357   bool			is_lvalue_;
2358 
2359   // Forbidden.
2360   reference_type_def();
2361 
2362 protected:
2363   virtual void on_canonical_type_set();
2364 
2365 public:
2366 
2367   /// Hasher for intances of reference_type_def.
2368   struct hash;
2369 
2370   reference_type_def(const type_base_sptr pointed_to_type,
2371 		     bool lvalue, size_t size_in_bits,
2372 		     size_t alignment_in_bits, const location& locus);
2373 
2374   reference_type_def(const environment& env, bool lvalue, size_t size_in_bits,
2375 		     size_t alignment_in_bits, const location& locus);
2376 
2377   void
2378   set_pointed_to_type(type_base_sptr& pointed_to_type);
2379 
2380   virtual bool
2381   operator==(const decl_base&) const;
2382 
2383   virtual bool
2384   operator==(const type_base&) const;
2385 
2386   bool
2387   operator==(const reference_type_def&) const;
2388 
2389   type_base_sptr
2390   get_pointed_to_type() const;
2391 
2392   bool
2393   is_lvalue() const;
2394 
2395   virtual void
2396   get_qualified_name(interned_string& qualified_name,
2397 		     bool internal = false) const;
2398 
2399   virtual const interned_string&
2400   get_qualified_name(bool internal = false) const;
2401 
2402   virtual string
2403   get_pretty_representation(bool internal = false,
2404 			    bool qualified_name = true) const;
2405 
2406   virtual bool
2407   traverse(ir_node_visitor& v);
2408 
2409   virtual ~reference_type_def();
2410 }; // end class reference_type_def
2411 
2412 bool
2413 operator==(const reference_type_def_sptr&, const reference_type_def_sptr&);
2414 
2415 bool
2416 operator!=(const reference_type_def_sptr&, const reference_type_def_sptr&);
2417 
2418 bool
2419 equals(const array_type_def&, const array_type_def&, change_kind*);
2420 
2421 /// The abstraction of an array type.
2422 class array_type_def : public virtual type_base, public virtual decl_base
2423 {
2424   struct priv;
2425   std::unique_ptr<priv> priv_;
2426 
2427   // Forbidden.
2428   array_type_def();
2429 
2430   void update_size();
2431 
2432 public:
2433 
2434   /// Hasher for intances of array_type_def.
2435   struct hash;
2436 
2437   class subrange_type;
2438 
2439   /// Convenience typedef for a shared pointer on a @ref
2440   /// function_decl::subrange
2441   typedef shared_ptr<subrange_type> subrange_sptr;
2442 
2443   /// Convenience typedef for a vector of @ref subrange_sptr
2444   typedef std::vector<subrange_sptr> subranges_type;
2445 
2446   /// Abstraction for an array range type, like in Ada, or just for an
2447   /// array dimension like in C or C++.
2448   class subrange_type : public virtual type_base,  public virtual decl_base
2449   {
2450     struct priv;
2451     std::unique_ptr<priv> priv_;
2452 
2453     // Forbidden.
2454     subrange_type();
2455   public:
2456 
2457     virtual ~subrange_type();
2458     /// This class is to hold the value of the bound of a subrange.
2459     /// The value can be either signed or unsigned, at least when it
2460     /// comes from DWARF.  The class keeps the sign information, but
2461     /// allows users to access the value as signed or unsigned as they
2462     /// see fit.
2463     class bound_value
2464     {
2465     public:
2466       enum signedness
2467       {
2468 	UNSIGNED_SIGNEDNESS,
2469 	SIGNED_SIGNEDNESS
2470       };
2471 
2472     private:
2473       signedness s_;
2474 
2475     public:
2476       union
2477       {
2478 	uint64_t unsigned_;
2479 	int64_t signed_;
2480       } v_;
2481       bound_value();
2482       bound_value(uint64_t);
2483       bound_value(int64_t);
2484       enum signedness get_signedness() const;
2485       void set_signedness(enum signedness s);
2486       int64_t get_signed_value() const;
2487       uint64_t get_unsigned_value();
2488       void set_unsigned(uint64_t v);
2489       void set_signed(int64_t v);
2490       bool operator==(const bound_value&) const;
2491     }; //end class bound_value
2492 
2493     /// Hasher for an instance of array::subrange
2494     struct hash;
2495 
2496     subrange_type(const environment&	env,
2497 		  const string&	name,
2498 		  bound_value		lower_bound,
2499 		  bound_value		upper_bound,
2500 		  const type_base_sptr& underlying_type,
2501 		  const location&	loc,
2502 		  translation_unit::language l = translation_unit::LANG_C11);
2503 
2504     subrange_type(const environment& env,
2505 		  const string& name,
2506 		  bound_value lower_bound,
2507 		  bound_value upper_bound,
2508 		  const location& loc,
2509 		  translation_unit::language l = translation_unit::LANG_C11);
2510 
2511     subrange_type(const environment& env,
2512 		  const string& name,
2513 		  bound_value upper_bound,
2514 		  const location& loc,
2515 		  translation_unit::language l = translation_unit::LANG_C11);
2516 
2517     type_base_sptr
2518     get_underlying_type() const;
2519 
2520     void
2521     set_underlying_type(const type_base_sptr &);
2522 
2523     int64_t
2524     get_upper_bound() const;
2525 
2526     int64_t
2527     get_lower_bound() const;
2528 
2529     void
2530     set_upper_bound(int64_t ub);
2531 
2532     void
2533     set_lower_bound(int64_t lb);
2534 
2535     uint64_t
2536     get_length() const;
2537 
2538     bool
2539     is_infinite() const;
2540 
2541     void
2542     is_infinite(bool);
2543 
2544     translation_unit::language
2545     get_language() const;
2546 
2547     virtual bool
2548     operator==(const decl_base&) const;
2549 
2550     virtual bool
2551     operator==(const type_base&) const;
2552 
2553     bool
2554     operator==(const subrange_type& o) const;
2555 
2556     bool
2557     operator!=(const subrange_type& o) const;
2558 
2559     string
2560     as_string() const;
2561 
2562     static string
2563     vector_as_string(const vector<subrange_sptr>&);
2564 
2565     virtual string
2566     get_pretty_representation(bool internal = false,
2567 			      bool qualified_name = true) const;
2568 
2569     virtual bool
2570     traverse(ir_node_visitor&);
2571   }; // end class subrange_type
2572 
2573   array_type_def(const type_base_sptr type,
2574 		 const std::vector<subrange_sptr>& subs,
2575 		 const location& locus);
2576 
2577   array_type_def(const environment& env,
2578 		 const std::vector<subrange_sptr>& subs,
2579 		 const location& locus);
2580 
2581   translation_unit::language
2582   get_language() const;
2583 
2584   virtual bool
2585   operator==(const decl_base&) const;
2586 
2587   virtual bool
2588   operator==(const type_base&) const;
2589 
2590   virtual void
2591   get_qualified_name(interned_string& qualified_name,
2592 		     bool internal = false) const;
2593 
2594   virtual const interned_string&
2595   get_qualified_name(bool internal = false) const;
2596 
2597   const type_base_sptr
2598   get_element_type() const;
2599 
2600   void
2601   set_element_type(const type_base_sptr& element_type);
2602 
2603   virtual void
2604   append_subranges(const std::vector<subrange_sptr>& subs);
2605 
2606   virtual int
2607   get_dimension_count() const;
2608 
2609   virtual bool
2610   is_infinite() const;
2611 
2612   virtual string
2613   get_pretty_representation(bool internal = false,
2614 			    bool qualified_name = true) const;
2615 
2616   virtual string
2617   get_subrange_representation() const;
2618 
2619   virtual bool
2620   traverse(ir_node_visitor& v);
2621 
2622   const location&
2623   get_location() const;
2624 
2625   const std::vector<subrange_sptr>&
2626   get_subranges() const;
2627 
2628   virtual ~array_type_def();
2629 
2630 }; // end class array_type_def
2631 
2632 array_type_def::subrange_type*
2633 is_subrange_type(const type_or_decl_base *type);
2634 
2635 array_type_def::subrange_sptr
2636 is_subrange_type(const type_or_decl_base_sptr &type);
2637 
2638 bool
2639 equals(const enum_type_decl&, const enum_type_decl&, change_kind*);
2640 
2641 /// Abstracts a declaration for an enum type.
2642 class enum_type_decl : public virtual type_base, public virtual decl_base
2643 {
2644   class priv;
2645   std::unique_ptr<priv> priv_;
2646 
2647   // Forbidden
2648   enum_type_decl();
2649 
2650 public:
2651 
2652   /// A hasher for an enum_type_decl.
2653   struct hash;
2654 
2655   /// Enumerator Datum.
2656   class enumerator;
2657 
2658   /// Convenience typedef for a list of @ref enumerator.
2659   typedef std::vector<enumerator> enumerators;
2660 
2661   /// Constructor of an enum type declaration.
2662   ///
2663   /// @param name the name of the enum
2664   ///
2665   /// @param locus the locus at which the enum appears in the source
2666   /// code.
2667   ///
2668   /// @param underlying_type the underlying type of the enum
2669   ///
2670   /// @param enms a list of enumerators for this enum.
2671   ///
2672   /// @param mangled_name the mangled name of the enum type.
2673   ///
2674   /// @param vis the visibility of instances of this type.
2675   enum_type_decl(const string&		name,
2676 		 const location&	locus,
2677 		 type_base_sptr	underlying_type,
2678 		 enumerators&		enms,
2679 		 const string&		mangled_name = "",
2680 		 visibility		vis = VISIBILITY_DEFAULT);
2681 
2682   type_base_sptr
2683   get_underlying_type() const;
2684 
2685   const enumerators&
2686   get_enumerators() const;
2687 
2688   enumerators&
2689   get_enumerators();
2690 
2691   virtual string
2692   get_pretty_representation(bool internal = false,
2693 			    bool qualified_name = true) const;
2694 
2695   virtual bool
2696   operator==(const decl_base&) const;
2697 
2698   virtual bool
2699   operator==(const type_base&) const;
2700 
2701   virtual bool
2702   traverse(ir_node_visitor& v);
2703 
2704   virtual ~enum_type_decl();
2705 
2706   friend bool
2707   enum_has_non_name_change(const enum_type_decl& l,
2708 			   const enum_type_decl& r,
2709 			   change_kind* k);
2710 }; // end class enum_type_decl
2711 
2712 bool
2713 operator==(const enum_type_decl_sptr& l, const enum_type_decl_sptr& r);
2714 
2715 bool
2716 operator!=(const enum_type_decl_sptr& l, const enum_type_decl_sptr& r);
2717 
2718 bool
2719 enum_has_non_name_change(const enum_type_decl& l,
2720 			 const enum_type_decl& r,
2721 			 change_kind* k);
2722 
2723 /// The abstraction of an enumerator
2724 class enum_type_decl::enumerator
2725 {
2726   class priv;
2727   std::unique_ptr<priv> priv_;
2728 
2729 public:
2730 
2731   enumerator();
2732 
2733   ~enumerator();
2734 
2735   enumerator(const string& name, int64_t value);
2736 
2737   enumerator(const enumerator&);
2738 
2739   enumerator&
2740   operator=(const enumerator&);
2741 
2742   bool
2743   operator==(const enumerator& other) const;
2744 
2745   bool
2746   operator!=(const enumerator& other) const;
2747 
2748   const string&
2749   get_name() const;
2750 
2751   const string&
2752   get_qualified_name(bool internal = false) const;
2753 
2754   void
2755   set_name(const string& n);
2756 
2757   int64_t
2758   get_value() const;
2759 
2760   void
2761   set_value(int64_t v);
2762 
2763   enum_type_decl*
2764   get_enum_type() const;
2765 
2766   void
2767   set_enum_type(enum_type_decl*);
2768 }; // end class enum_type_def::enumerator
2769 
2770 bool
2771 equals(const typedef_decl&, const typedef_decl&, change_kind*);
2772 
2773 /// The abstraction of a typedef declaration.
2774 class typedef_decl : public virtual type_base, public virtual decl_base
2775 {
2776   struct priv;
2777   std::unique_ptr<priv> priv_;
2778 
2779   // Forbidden
2780   typedef_decl();
2781 
2782 public:
2783 
2784   /// Hasher for the typedef_decl type.
2785   struct hash;
2786 
2787   typedef_decl(const string& name,
2788 	       const type_base_sptr underlying_type,
2789 	       const location& locus,
2790 	       const string& mangled_name = "",
2791 	       visibility vis = VISIBILITY_DEFAULT);
2792 
2793   typedef_decl(const string& name,
2794 	       const environment& env,
2795 	       const location& locus,
2796 	       const string& mangled_name = "",
2797 	       visibility vis = VISIBILITY_DEFAULT);
2798 
2799   virtual size_t
2800   get_size_in_bits() const;
2801 
2802   virtual size_t
2803   get_alignment_in_bits() const;
2804 
2805   virtual bool
2806   operator==(const decl_base&) const;
2807 
2808   virtual bool
2809   operator==(const type_base&) const;
2810 
2811   virtual string
2812   get_pretty_representation(bool internal = false,
2813 			    bool qualified_name = true) const;
2814 
2815   type_base_sptr
2816   get_underlying_type() const;
2817 
2818   void
2819   set_underlying_type(const type_base_sptr&);
2820 
2821   virtual bool
2822   traverse(ir_node_visitor&);
2823 
2824   virtual ~typedef_decl();
2825 };// end class typedef_decl
2826 
2827 /// The abstraction for a data member context relationship.  This
2828 /// relates a data member to its parent class.
2829 ///
2830 /// The relationship carries properties like the offset of the data
2831 /// member, if applicable.
2832 class dm_context_rel : public context_rel
2833 {
2834 protected:
2835   struct priv;
2836   std::unique_ptr<priv> priv_;
2837 
2838 public:
2839   dm_context_rel();
2840 
2841   dm_context_rel(scope_decl* s,
2842 		 bool is_laid_out,
2843 		 size_t offset_in_bits,
2844 		 access_specifier a,
2845 		 bool is_static);
2846 
2847   dm_context_rel(scope_decl* s);
2848 
2849   bool
2850   get_is_laid_out() const;
2851 
2852   void
2853   set_is_laid_out(bool f);
2854 
2855   size_t
2856   get_offset_in_bits() const;
2857 
2858   void
2859   set_offset_in_bits(size_t o);
2860 
2861   const var_decl*
2862   get_anonymous_data_member() const;
2863 
2864   void
2865   set_anonymous_data_member(var_decl *);
2866 
2867   bool
2868   operator==(const dm_context_rel& o) const;
2869 
2870   bool
2871   operator!=(const dm_context_rel& o) const;
2872 
2873   virtual ~dm_context_rel();
2874 };// end class class_decl::dm_context_rel
2875 
2876 bool
2877 equals(const var_decl&, const var_decl&, change_kind*);
2878 
2879 bool
2880 equals_modulo_cv_qualifier(const array_type_def*, const array_type_def*);
2881 
2882 /// Abstracts a variable declaration.
2883 class var_decl : public virtual decl_base
2884 {
2885   struct priv;
2886   std::unique_ptr<priv> priv_;
2887 
2888   // Forbidden
2889   var_decl();
2890 
2891   virtual void
2892   set_scope(scope_decl*);
2893 
2894 public:
2895 
2896   /// Hasher for a var_decl type.
2897   struct hash;
2898 
2899   /// Equality functor to compare pointers to variable_decl.
2900   struct ptr_equal;
2901 
2902   var_decl(const string&	name,
2903 	   type_base_sptr	type,
2904 	   const location&	locus,
2905 	   const string&	mangled_name,
2906 	   visibility		vis = VISIBILITY_DEFAULT,
2907 	   binding		bind = BINDING_NONE);
2908 
2909   virtual bool
2910   operator==(const decl_base&) const;
2911 
2912   const type_base_sptr
2913   get_type() const;
2914 
2915   const type_base*
2916   get_naked_type() const;
2917 
2918   binding
2919   get_binding() const;
2920 
2921   void
2922   set_binding(binding b);
2923 
2924   void
2925   set_symbol(const elf_symbol_sptr& sym);
2926 
2927   const elf_symbol_sptr&
2928   get_symbol() const;
2929 
2930   var_decl_sptr
2931   clone() const;
2932 
2933   interned_string
2934   get_id() const;
2935 
2936   virtual const interned_string&
2937   get_qualified_name(bool internal = false) const;
2938 
2939   virtual size_t
2940   get_hash() const;
2941 
2942   virtual string
2943   get_pretty_representation(bool internal = false,
2944 			    bool qualified_name = true) const;
2945 
2946   string
2947   get_anon_dm_reliable_name(bool qualified = true) const;
2948 
2949   virtual bool
2950   traverse(ir_node_visitor& v);
2951 
2952   virtual ~var_decl();
2953 
2954   friend void
2955   set_data_member_offset(var_decl_sptr m, uint64_t o);
2956 
2957   friend uint64_t
2958   get_data_member_offset(const var_decl_sptr m);
2959 
2960   friend uint64_t
2961   get_data_member_offset(const var_decl& m);
2962 
2963   friend uint64_t
2964   get_absolute_data_member_offset(const var_decl& m);
2965 
2966   friend uint64_t
2967   get_absolute_data_member_offset(const var_decl_sptr& m);
2968 
2969   friend void
2970   set_data_member_is_laid_out(var_decl_sptr m, bool l);
2971 
2972   friend bool
2973   get_data_member_is_laid_out(const var_decl& m);
2974 
2975   friend bool
2976   get_data_member_is_laid_out(const var_decl_sptr m);
2977 }; // end class var_decl
2978 
2979 bool
2980 equals(const function_decl&, const function_decl&, change_kind*);
2981 
2982 /// Abstraction for a function declaration.
2983 class function_decl : public virtual decl_base
2984 {
2985   struct priv;
2986   // This priv pointer is not handled by a shared_ptr because
2987   // accessing the data members of the priv struct for this
2988   // function_decl shows up on performance profiles when dealing with
2989   // big binaries with a lot of types; dereferencing the shared_ptr
2990   // involves locking of some sort and that is slower than just
2991   // dereferencing a pointer likere here.  There are other types for
2992   // which the priv pointer is managed using shared_ptr just fine,
2993   // because those didn't show up during our performance profiling.
2994   priv* priv_;
2995 
2996 public:
2997   /// Hasher for function_decl
2998   struct hash;
2999 
3000   /// Equality functor to compare pointers to function_decl
3001   struct ptr_equal;
3002 
3003   /// Abstraction for the parameter of a function.
3004   class parameter;
3005 
3006   /// Convenience typedef for a shared pointer on a @ref
3007   /// function_decl::parameter
3008   typedef shared_ptr<parameter> parameter_sptr;
3009 
3010   /// Convenience typedef for a vector of @ref parameter_sptr
3011   typedef std::vector<parameter_sptr> parameters;
3012 
3013   function_decl(const string& name,
3014 		function_type_sptr function_type,
3015 		bool declared_inline,
3016 		const location& locus,
3017 		const string& mangled_name,
3018 		visibility vis,
3019 		binding bind);
3020 
3021   function_decl(const string& name,
3022 		type_base_sptr fn_type,
3023 		bool declared_inline,
3024 		const location& locus,
3025 		const string& mangled_name = "",
3026 		visibility vis = VISIBILITY_DEFAULT,
3027 		binding bind = BINDING_GLOBAL);
3028 
3029   virtual string
3030   get_pretty_representation(bool internal = false,
3031 			    bool qualified_name = true) const;
3032 
3033   string
3034   get_pretty_representation_of_declarator (bool internal = false) const;
3035 
3036   const std::vector<parameter_sptr >&
3037   get_parameters() const;
3038 
3039   void
3040   append_parameter(parameter_sptr parm);
3041 
3042   void
3043   append_parameters(std::vector<parameter_sptr >& parms);
3044 
3045   parameters::const_iterator
3046   get_first_non_implicit_parm() const;
3047 
3048   const function_type_sptr
3049   get_type() const;
3050 
3051   const function_type*
3052   get_naked_type() const;
3053 
3054   const type_base_sptr
3055   get_return_type() const;
3056 
3057   void
3058   set_type(const function_type_sptr& fn_type);
3059 
3060   void
3061   set_symbol(const elf_symbol_sptr& sym);
3062 
3063   const elf_symbol_sptr&
3064   get_symbol() const;
3065 
3066   bool
3067   is_declared_inline() const;
3068 
3069   binding
3070   get_binding() const;
3071 
3072   function_decl_sptr
3073   clone() const;
3074 
3075   virtual bool
3076   operator==(const decl_base& o) const;
3077 
3078   /// Return true iff the function takes a variable number of
3079   /// parameters.
3080   ///
3081   /// @return true if the function taks a variable number
3082   /// of parameters.
3083   bool
3084   is_variadic() const;
3085 
3086   virtual size_t
3087   get_hash() const;
3088 
3089   interned_string
3090   get_id() const;
3091 
3092   virtual bool
3093   traverse(ir_node_visitor&);
3094 
3095   virtual ~function_decl();
3096 }; // end class function_decl
3097 
3098 bool
3099 operator==(const function_decl_sptr& l, const function_decl_sptr& r);
3100 
3101 bool
3102 operator!=(const function_decl_sptr& l, const function_decl_sptr& r);
3103 
3104 bool
3105 function_decls_alias(const function_decl& f1, const function_decl& f2);
3106 
3107 bool
3108 equals(const function_decl::parameter&,
3109        const function_decl::parameter&,
3110        change_kind*);
3111 
3112 /// A comparison functor to compare pointer to instances of @ref
3113 /// type_or_decl_base.
3114 struct type_or_decl_base_comp
3115 {
3116   /// Comparison operator for ABI artifacts.
3117   ///
3118   /// @param f the first ABI artifact to consider for the comparison.
3119   ///
3120   /// @param s the second  ABI artifact to consider for the comparison.
3121   ///
3122   /// @return true iff @p f is lexicographically less than than @p s.
3123   bool
operatortype_or_decl_base_comp3124   operator()(const type_or_decl_base *f,
3125 	     const type_or_decl_base *s)
3126   {
3127     function_decl *f_fn = is_function_decl(f), *s_fn = is_function_decl(s);
3128     if (f_fn && s_fn)
3129       return function_decl_is_less_than(*f_fn, *s_fn);
3130 
3131     var_decl *f_var = is_var_decl(f), *s_var = is_var_decl(s);
3132     if (f_var && s_var)
3133       return get_name(f_var) < get_name(s_var);
3134 
3135     string l_repr = get_pretty_representation(f),
3136       r_repr = get_pretty_representation(s);
3137 
3138     return l_repr < r_repr;
3139   }
3140 
3141   /// Comparison operator for ABI artifacts.
3142   ///
3143   /// @param f the first ABI artifact to consider for the comparison.
3144   ///
3145   /// @param s the second  ABI artifact to consider for the comparison.
3146   ///
3147   /// @return true iff @p f is lexicographically less than than @p s.
3148   bool
operatortype_or_decl_base_comp3149   operator()(const type_or_decl_base_sptr& f,
3150 	     const type_or_decl_base_sptr& s)
3151   {return operator()(f.get(), s.get());}
3152 }; // end struct type_or_decl_base_comp
3153 
3154 /// Abstraction of a function parameter.
3155 class function_decl::parameter : public decl_base
3156 {
3157   struct priv;
3158   std::unique_ptr<priv> priv_;
3159 
3160 public:
3161 
3162   /// Hasher for an instance of function::parameter
3163   struct hash;
3164 
3165   parameter(const type_base_sptr	type,
3166 	    unsigned			index,
3167 	    const string&		name,
3168 	    const location&		loc,
3169 	    bool			variadic_marker = false);
3170 
3171   parameter(const type_base_sptr	type,
3172 	    unsigned			index,
3173 	    const string&		name,
3174 	    const location&		loc,
3175 	    bool			variadic_marker,
3176 	    bool			is_artificial);
3177 
3178   parameter(const type_base_sptr	type,
3179 	    const string&		name,
3180 	    const location&		loc,
3181 	    bool			variadic_marker = false,
3182 	    bool			is_artificial	= false);
3183 
3184   parameter(const type_base_sptr	type,
3185 	    unsigned			index = 0,
3186 	    bool			variadic_marker = false);
3187 
3188   virtual ~parameter();
3189 
3190   const type_base_sptr
3191   get_type()const;
3192 
3193   interned_string
3194   get_type_name() const;
3195 
3196   const string
3197   get_type_pretty_representation() const;
3198 
3199   interned_string
3200   get_name_id() const;
3201 
3202   unsigned
3203   get_index() const;
3204 
3205   void
3206   set_index(unsigned i);
3207 
3208   bool
3209   get_variadic_marker() const;
3210 
3211   bool
3212   operator==(const parameter& o) const;
3213 
3214   virtual bool
3215   operator==(const decl_base&) const;
3216 
3217   virtual bool
3218   traverse(ir_node_visitor& v);
3219 
3220   virtual size_t
3221   get_hash() const;
3222 
3223   virtual void
3224   get_qualified_name(interned_string& qualified_name,
3225 		     bool internal = false) const;
3226 
3227   virtual string
3228   get_pretty_representation(bool internal = false,
3229 			    bool qualified_name = true) const;
3230 }; // end class function_decl::parameter
3231 
3232 bool
3233 operator==(const function_decl::parameter_sptr&,
3234 	   const function_decl::parameter_sptr&);
3235 
3236 /// A hashing functor for a function_decl::parameter.
3237 struct function_decl::parameter::hash
3238 {
3239   size_t
3240   operator()(const function_decl::parameter&) const;
3241 
3242   size_t
3243   operator()(const function_decl::parameter*) const;
3244 
3245   size_t
3246   operator()(const function_decl::parameter_sptr) const;
3247 }; // end struct function_decl::parameter::hash
3248 
3249 function_decl::parameter*
3250 is_function_parameter(const type_or_decl_base*);
3251 
3252 function_decl::parameter_sptr
3253 is_function_parameter(const type_or_decl_base_sptr tod);
3254 
3255 bool
3256 equals(const function_type&, const function_type&, change_kind*);
3257 
3258 /// Abstraction of a function type.
3259 class function_type : public virtual type_base
3260 {
3261 protected:
3262   virtual void on_canonical_type_set();
3263 
3264 public:
3265   /// Hasher for an instance of function_type
3266   struct hash;
3267 
3268   /// Convenience typedef for a shared pointer on a @ref
3269   /// function_decl::parameter
3270   typedef shared_ptr<function_decl::parameter>	parameter_sptr;
3271   /// Convenience typedef for a vector of @ref parameter_sptr
3272   typedef std::vector<parameter_sptr>		parameters;
3273 
3274   struct priv;
3275   std::unique_ptr<priv> priv_;
3276 
3277 private:
3278   function_type();
3279 
3280 public:
3281 
3282   function_type(type_base_sptr		return_type,
3283 		const parameters&	parms,
3284 		size_t			size_in_bits,
3285 		size_t			alignment_in_bits);
3286 
3287   function_type(type_base_sptr	return_type,
3288 		size_t		size_in_bits,
3289 		size_t		alignment_in_bits);
3290 
3291   function_type(const environment&	env,
3292 		size_t		size_in_bits,
3293 		size_t		alignment_in_bits);
3294 
3295   type_base_sptr
3296   get_return_type() const;
3297 
3298   void
3299   set_return_type(type_base_sptr t);
3300 
3301   const parameters&
3302   get_parameters() const;
3303 
3304   const parameter_sptr
3305   get_parm_at_index_from_first_non_implicit_parm(size_t) const;
3306 
3307   void
3308   set_parameters(const parameters &p);
3309 
3310   void
3311   append_parameter(parameter_sptr parm);
3312 
3313   bool
3314   is_variadic() const;
3315 
3316   parameters::const_iterator
3317   get_first_non_implicit_parm() const;
3318 
3319   parameters::const_iterator
3320   get_first_parm() const;
3321 
3322   const interned_string&
3323   get_cached_name(bool internal = false) const;
3324 
3325   virtual bool
3326   operator==(const type_base&) const;
3327 
3328   virtual string
3329   get_pretty_representation(bool internal = false,
3330 			    bool qualified_name = true) const;
3331 
3332   virtual bool
3333   traverse(ir_node_visitor&);
3334 
3335   virtual ~function_type();
3336 
3337   friend bool
3338   equals(const function_type&, const function_type&, change_kind*);
3339 };//end class function_type
3340 
3341 /// The hashing functor for @ref function_type.
3342 struct function_type::hash
3343 {
3344   size_t
3345   operator()(const function_type& t) const;
3346 
3347   size_t
3348   operator()(const function_type* t) const;
3349 
3350   size_t
3351   operator()(const function_type_sptr t) const;
3352 };// end struct function_type::hash
3353 
3354 /// Abstracts the type of a class member function.
3355 class method_type : public function_type
3356 {
3357   struct priv;
3358   std::unique_ptr<priv> priv_;
3359 
3360   method_type();
3361 
3362 public:
3363 
3364   /// Hasher for intances of method_type
3365   struct hash;
3366 
3367   method_type(type_base_sptr return_type,
3368 	      class_or_union_sptr class_type,
3369 	      const std::vector<function_decl::parameter_sptr>& parms,
3370 	      bool is_const,
3371 	      size_t size_in_bits,
3372 	      size_t alignment_in_bits);
3373 
3374   method_type(type_base_sptr return_type,
3375 	      type_base_sptr class_type,
3376 	      const std::vector<function_decl::parameter_sptr>& parms,
3377 	      bool is_const,
3378 	      size_t size_in_bits,
3379 	      size_t alignment_in_bits);
3380 
3381   method_type(class_or_union_sptr class_type,
3382 	      bool is_const,
3383 	      size_t size_in_bits,
3384 	      size_t alignment_in_bits);
3385 
3386   method_type(const environment& env,
3387 	      size_t size_in_bits,
3388 	      size_t alignment_in_bits);
3389 
3390   class_or_union_sptr
3391   get_class_type() const;
3392 
3393   void
3394   set_class_type(const class_or_union_sptr& t);
3395 
3396   void set_is_const(bool);
3397 
3398   bool get_is_const() const;
3399 
3400   virtual ~method_type();
3401 
3402   virtual string
3403   get_pretty_representation(bool internal = false,
3404 			    bool qualified_name = true) const;
3405 
3406   friend interned_string
3407   get_method_type_name(const method_type& fn_type, bool internal);
3408 };// end class method_type.
3409 
3410 /// The base class of templates.
3411 class template_decl : public virtual decl_base
3412 {
3413   class priv;
3414   std::unique_ptr<priv> priv_;
3415 
3416   template_decl();
3417 
3418 public:
3419 
3420   /// Hasher.
3421   struct hash;
3422 
3423   template_decl(const environment&	env,
3424 		const string&		name,
3425 		const location&	locus,
3426 		visibility		vis = VISIBILITY_DEFAULT);
3427 
3428   void
3429   add_template_parameter(const template_parameter_sptr p);
3430 
3431   const std::list<template_parameter_sptr>&
3432   get_template_parameters() const;
3433 
3434   virtual bool
3435   operator==(const template_decl& o) const;
3436 
3437   virtual ~template_decl();
3438 };//end class template_decl
3439 
3440 /// Base class for a template parameter.  Client code should use the
3441 /// more specialized type_template_parameter,
3442 /// non_type_template_parameter and template_template_parameter below.
3443 class template_parameter
3444 {
3445   class priv;
3446   std::unique_ptr<priv> priv_;
3447 
3448   // Forbidden
3449   template_parameter();
3450 
3451  public:
3452 
3453   /// Hashers.
3454   struct hash;
3455   struct dynamic_hash;
3456   struct shared_ptr_hash;
3457 
3458   template_parameter(unsigned			index,
3459 		     template_decl_sptr	enclosing_tdecl);
3460 
3461   virtual bool
3462   operator==(const template_parameter&) const;
3463 
3464   bool
3465   operator!=(const template_parameter&) const;
3466 
3467   unsigned
3468   get_index() const;
3469 
3470   const template_decl_sptr
3471   get_enclosing_template_decl() const;
3472 
3473   bool
3474   get_hashing_has_started() const;
3475 
3476   void
3477   set_hashing_has_started(bool f) const;
3478 
3479   virtual ~template_parameter();
3480 };//end class template_parameter
3481 
3482 struct template_decl::hash
3483 {
3484     size_t
3485     operator()(const template_decl& t) const;
3486 };// end struct template_decl::hash
3487 
3488 /// Abstracts a type template parameter.
3489 class type_tparameter : public template_parameter, public virtual type_decl
3490 {
3491   class priv;
3492   std::unique_ptr<priv> priv_;
3493 
3494   // Forbidden
3495   type_tparameter();
3496 
3497 public:
3498 
3499   /// Hasher.
3500   struct hash;
3501 
3502   type_tparameter(unsigned		index,
3503 		  template_decl_sptr	enclosing_tdecl,
3504 		  const string&	name,
3505 		  const location&	locus);
3506 
3507   virtual bool
3508   operator==(const type_base&) const;
3509 
3510   virtual bool
3511   operator==(const template_parameter&) const;
3512 
3513   virtual bool
3514   operator==(const type_tparameter&) const;
3515 
3516   virtual ~type_tparameter();
3517 };// end class type_tparameter.
3518 
3519 /// Abstracts non type template parameters.
3520 class non_type_tparameter : public template_parameter, public virtual decl_base
3521 {
3522   class priv;
3523   std::unique_ptr<priv> priv_;
3524 
3525   type_base_wptr type_;
3526 
3527   // Forbidden
3528   non_type_tparameter();
3529 
3530 public:
3531   /// Hasher.
3532   struct hash;
3533 
3534   non_type_tparameter(unsigned			index,
3535 		      template_decl_sptr	enclosing_tdecl,
3536 		      const string&		name,
3537 		      type_base_sptr		type,
3538 		      const location&		locus);
3539   virtual size_t
3540   get_hash() const;
3541 
3542   virtual bool
3543   operator==(const decl_base&) const;
3544 
3545   virtual bool
3546   operator==(const template_parameter&) const;
3547 
3548   const type_base_sptr
3549   get_type() const;
3550 
3551   virtual ~non_type_tparameter();
3552 };// end class non_type_tparameter
3553 
3554 /// Hasher for the @ref non_type_tparameter type.
3555 struct non_type_tparameter::hash
3556 {
3557   size_t
3558   operator()(const non_type_tparameter& t) const;
3559 
3560   size_t
3561   operator()(const non_type_tparameter* t) const;
3562 };
3563 
3564 class template_tparameter;
3565 
3566 /// Abstracts a template template parameter.
3567 class template_tparameter : public type_tparameter, public template_decl
3568 {
3569   class priv;
3570   std::unique_ptr<priv> priv_;
3571 
3572   // Forbidden
3573   template_tparameter();
3574 
3575 public:
3576 
3577   /// A hasher for instances of template_tparameter
3578   struct hash;
3579 
3580   template_tparameter(unsigned			index,
3581 		      template_decl_sptr	enclosing_tdecl,
3582 		      const string&		name,
3583 		      const location&		locus);
3584 
3585   virtual bool
3586   operator==(const type_base&) const;
3587 
3588   virtual bool
3589   operator==(const template_parameter&) const;
3590 
3591   virtual bool
3592   operator==(const template_decl&) const;
3593 
3594   virtual ~template_tparameter();
3595 };
3596 
3597 /// This abstracts a composition of types based on template type
3598 /// parameters.  The result of the composition is a type that can be
3599 /// referred to by a template non-type parameter.  Instances of this
3600 /// type can appear at the same level as template parameters, in the
3601 /// scope of a template_decl.
3602 class type_composition : public template_parameter, public virtual decl_base
3603 {
3604   class priv;
3605   std::unique_ptr<priv> priv_;
3606 
3607   type_composition();
3608 
3609 public:
3610   struct hash;
3611 
3612   type_composition(unsigned		index,
3613 		   template_decl_sptr	tdecl,
3614 		   type_base_sptr	composed_type);
3615 
3616   const type_base_sptr
3617   get_composed_type() const;
3618 
3619   void
3620   set_composed_type(type_base_sptr t);
3621 
3622   virtual size_t
3623   get_hash() const;
3624 
3625   virtual ~type_composition();
3626 };
3627 
3628 /// Hasher for the @ref type_composition type.
3629 struct type_composition::hash
3630 {
3631   size_t
3632   operator()(const type_composition& t) const;
3633 
3634   size_t
3635   operator()(const type_composition* t) const;
3636 
3637 }; //struct type_composition::hash
3638 
3639 /// Abstract a function template declaration.
3640 class function_tdecl : public template_decl, public scope_decl
3641 {
3642   class priv;
3643   std::unique_ptr<priv> priv_;
3644 
3645   // Forbidden
3646   function_tdecl();
3647 
3648 public:
3649 
3650   /// Hash functor for function templates.
3651   struct hash;
3652   struct shared_ptr_hash;
3653 
3654   function_tdecl(const environment&	env,
3655 		 const location&	locus,
3656 		 visibility		vis = VISIBILITY_DEFAULT,
3657 		 binding		bind = BINDING_NONE);
3658 
3659   function_tdecl(function_decl_sptr	pattern,
3660 		 const location&	locus,
3661 		 visibility		vis = VISIBILITY_DEFAULT,
3662 		 binding		bind = BINDING_NONE);
3663 
3664   virtual bool
3665   operator==(const decl_base&) const;
3666 
3667   virtual bool
3668   operator==(const template_decl&) const;
3669 
3670   virtual bool
3671   operator==(const function_tdecl&) const;
3672 
3673   void
3674   set_pattern(shared_ptr<function_decl> p);
3675 
3676   shared_ptr<function_decl>
3677   get_pattern() const;
3678 
3679   binding
3680   get_binding() const;
3681 
3682   virtual bool
3683   traverse(ir_node_visitor& v);
3684 
3685   virtual ~function_tdecl();
3686 }; // end class function_tdecl.
3687 
3688 /// Abstract a class template.
3689 class class_tdecl : public template_decl, public scope_decl
3690 {
3691   class priv;
3692   std::unique_ptr<priv> priv_;
3693 
3694   // Forbidden
3695   class_tdecl();
3696 
3697 public:
3698 
3699   /// Hashers.
3700   struct hash;
3701   struct shared_ptr_hash;
3702 
3703   class_tdecl(const environment& env, const location& locus,
3704 	      visibility vis = VISIBILITY_DEFAULT);
3705 
3706   class_tdecl(class_decl_sptr	pattern,
3707 	      const location&	locus,
3708 	      visibility	vis = VISIBILITY_DEFAULT);
3709 
3710   virtual bool
3711   operator==(const decl_base&) const;
3712 
3713   virtual bool
3714   operator==(const template_decl&) const;
3715 
3716   virtual bool
3717   operator==(const class_tdecl&) const;
3718 
3719   void
3720   set_pattern(class_decl_sptr p);
3721 
3722   shared_ptr<class_decl>
3723   get_pattern() const;
3724 
3725   virtual bool
3726   traverse(ir_node_visitor& v);
3727 
3728   virtual ~class_tdecl();
3729 };// end class class_tdecl
3730 
3731 /// The base class for member types, data members and member
3732 /// functions.  Its purpose is mainly to carry the access specifier
3733 /// (and possibly other properties that might be shared by all class
3734 /// members) for the member.
3735 class member_base
3736 {
3737 protected:
3738   enum access_specifier access_;
3739   bool			is_static_;
3740 
3741 private:
3742   // Forbidden
3743   member_base();
3744 
3745 public:
3746   /// Hasher.
3747   struct hash;
3748 
3749   member_base(access_specifier a, bool is_static = false)
access_(a)3750     : access_(a), is_static_(is_static)
3751   {}
3752 
3753   /// Getter for the access specifier of this member.
3754   ///
3755   /// @return the access specifier for this member.
3756   access_specifier
get_access_specifier()3757   get_access_specifier() const
3758   {return access_;}
3759 
3760   /// Setter for the access specifier of this member.
3761   ///
3762   /// @param a the new access specifier.
3763   void
set_access_specifier(access_specifier a)3764   set_access_specifier(access_specifier a)
3765   {access_ = a;}
3766 
3767   /// @return true if the member is static, false otherwise.
3768   bool
get_is_static()3769   get_is_static() const
3770   {return is_static_;}
3771 
3772   /// Set a flag saying if the parameter is static or not.
3773   ///
3774   /// @param f set to true if the member is static, false otherwise.
3775   void
set_is_static(bool f)3776   set_is_static(bool f)
3777   {is_static_ = f;}
3778 
3779   virtual bool
3780   operator==(const member_base& o) const;
3781 };// end class member_base
3782 
3783 /// Abstraction of the declaration of a method.
3784 class method_decl : public function_decl
3785 {
3786   method_decl();
3787 
3788   virtual void
3789   set_scope(scope_decl*);
3790 
3791 public:
3792 
3793   method_decl(const string& name, method_type_sptr type,
3794 	      bool declared_inline, const location& locus,
3795 	      const string& mangled_name = "",
3796 	      visibility vis = VISIBILITY_DEFAULT,
3797 	      binding	bind = BINDING_GLOBAL);
3798 
3799   method_decl(const string& name,
3800 	      function_type_sptr type,
3801 	      bool declared_inline,
3802 	      const location& locus,
3803 	      const string& mangled_name = "",
3804 	      visibility vis  = VISIBILITY_DEFAULT,
3805 	      binding	bind = BINDING_GLOBAL);
3806 
3807   method_decl(const string& name, type_base_sptr type,
3808 	      bool declared_inline, const location& locus,
3809 	      const string& mangled_name = "",
3810 	      visibility vis = VISIBILITY_DEFAULT,
3811 	      binding bind = BINDING_GLOBAL);
3812 
3813   virtual void
3814   set_linkage_name(const string&);
3815 
3816   /// @return the type of the current instance of the
3817   /// method_decl.
3818   const method_type_sptr
3819   get_type() const;
3820 
3821   void
set_type(const method_type_sptr fn_type)3822   set_type(const method_type_sptr fn_type)
3823   {function_decl::set_type(fn_type);}
3824 
3825   friend bool
3826   get_member_function_is_ctor(const function_decl&);
3827 
3828   friend void
3829   set_member_function_is_ctor(function_decl&, bool);
3830 
3831   friend void
3832   set_member_function_is_ctor(const function_decl_sptr&, bool);
3833 
3834   friend bool
3835   get_member_function_is_dtor(const function_decl&);
3836 
3837   friend void
3838   set_member_function_is_dtor(function_decl&, bool);
3839 
3840   friend void
3841   set_member_function_is_dtor(const function_decl_sptr&, bool);
3842 
3843   friend bool
3844   get_member_function_is_static(const function_decl&);
3845 
3846   friend void
3847   set_member_function_is_static(const function_decl&, bool);
3848 
3849   friend bool
3850   get_member_function_is_const(const function_decl&);
3851 
3852   friend void
3853   set_member_function_is_const(function_decl&, bool);
3854 
3855   friend void
3856   set_member_function_is_const(const function_decl_sptr&, bool);
3857 
3858   friend bool
3859   member_function_has_vtable_offset(const function_decl&);
3860 
3861   friend ssize_t
3862   get_member_function_vtable_offset(const function_decl&);
3863 
3864   friend void
3865   set_member_function_vtable_offset(function_decl&, ssize_t);
3866 
3867   friend void
3868   set_member_function_vtable_offset(const function_decl_sptr&, ssize_t);
3869 
3870   friend bool
3871   get_member_function_is_virtual(const function_decl&);
3872 
3873   friend void
3874   set_member_function_is_virtual(function_decl&, bool);
3875 
3876   virtual ~method_decl();
3877 };// end class method_decl
3878 
3879 bool
3880 operator==(const method_decl_sptr& l, const method_decl_sptr& r);
3881 
3882 bool
3883 operator!=(const method_decl_sptr& l, const method_decl_sptr& r);
3884 
3885 /// The base type of @ref class_decl and @ref union_decl
3886 class class_or_union : public scope_type_decl
3887 {
3888 public:
3889   struct priv;
3890   priv *priv_;
3891 
3892 private:
3893   // Forbidden
3894   class_or_union();
3895 
3896 protected:
3897 
3898   virtual decl_base_sptr
3899   add_member_decl(const decl_base_sptr&);
3900 
3901   decl_base_sptr
3902   insert_member_decl(decl_base_sptr member);
3903 
3904   virtual void
3905   remove_member_decl(decl_base_sptr);
3906 
3907   void
3908   maybe_fixup_members_of_anon_data_member(var_decl_sptr& anon_dm);
3909 
3910 public:
3911   /// Hasher.
3912   struct hash;
3913 
3914   /// Convenience typedef
3915   /// @{
3916   typedef vector<type_base_sptr>		member_types;
3917   typedef vector<var_decl_sptr>		data_members;
3918   typedef vector<method_decl_sptr>		member_functions;
3919   typedef unordered_map<ssize_t, member_functions> virtual_mem_fn_map_type;
3920   typedef unordered_map<string, method_decl*> string_mem_fn_ptr_map_type;
3921   typedef unordered_map<string, method_decl_sptr> string_mem_fn_sptr_map_type;
3922   /// @}
3923 
3924   class_or_union(const environment& env, const string& name,
3925 		 size_t size_in_bits, size_t align_in_bits,
3926 		 const location& locus, visibility vis,
3927 		 member_types& mbrs, data_members& data_mbrs,
3928 		 member_functions& member_fns);
3929 
3930   class_or_union(const environment& env, const string& name,
3931 		 size_t size_in_bits, size_t align_in_bits,
3932 		 const location& locus, visibility vis);
3933 
3934   class_or_union(const environment& env, const string& name,
3935 		 bool is_declaration_only = true);
3936 
3937   virtual void
3938   set_size_in_bits(size_t);
3939 
3940   virtual size_t
3941   get_size_in_bits() const;
3942 
3943   virtual size_t
3944   get_alignment_in_bits() const;
3945 
3946   virtual void
3947   set_alignment_in_bits(size_t);
3948 
3949   virtual size_t
3950   get_num_anonymous_member_classes() const;
3951 
3952   virtual size_t
3953   get_num_anonymous_member_unions() const;
3954 
3955   virtual size_t
3956   get_num_anonymous_member_enums() const;
3957 
3958   void
3959   add_data_member(var_decl_sptr v, access_specifier a,
3960 		  bool is_laid_out, bool is_static,
3961 		  size_t offset_in_bits);
3962 
3963   const data_members&
3964   get_data_members() const;
3965 
3966   const var_decl_sptr
3967   find_data_member(const string&) const;
3968 
3969   const var_decl_sptr
3970   find_data_member(const var_decl_sptr&) const;
3971 
3972   const var_decl_sptr
3973   find_anonymous_data_member(const var_decl_sptr&) const;
3974 
3975   const data_members&
3976   get_non_static_data_members() const;
3977 
3978   void
3979   add_member_function(method_decl_sptr f,
3980 		      access_specifier a,
3981 		      bool is_static, bool is_ctor,
3982 		      bool is_dtor, bool is_const);
3983 
3984   void
3985   add_member_function(method_decl_sptr f,
3986 		      access_specifier a,
3987 		      bool is_virtual,
3988 		      size_t vtable_offset,
3989 		      bool is_static, bool is_ctor,
3990 		      bool is_dtor, bool is_const);
3991 
3992   const member_functions&
3993   get_member_functions() const;
3994 
3995   const method_decl*
3996   find_member_function(const string& mangled_name) const;
3997 
3998   method_decl*
3999   find_member_function(const string& mangled_name);
4000 
4001   method_decl_sptr
4002   find_member_function_sptr(const string& mangled_name);
4003 
4004   const method_decl*
4005   find_member_function_from_signature(const string& s) const;
4006 
4007   method_decl*
4008   find_member_function_from_signature(const string& s);
4009 
4010   void
4011   add_member_function_template(member_function_template_sptr);
4012 
4013   const member_function_templates&
4014   get_member_function_templates() const;
4015 
4016   void
4017   add_member_class_template(member_class_template_sptr m);
4018 
4019   const member_class_templates&
4020   get_member_class_templates() const;
4021 
4022   bool
4023   has_no_member() const;
4024 
4025   virtual bool
4026   operator==(const decl_base&) const;
4027 
4028   virtual bool
4029   operator==(const type_base&) const;
4030 
4031   virtual bool
4032   operator==(const class_or_union&) const;
4033 
4034   virtual bool
4035   traverse(ir_node_visitor& v);
4036 
4037   virtual ~class_or_union();
4038 
4039   friend method_decl_sptr
4040   copy_member_function(class_or_union_sptr& t,
4041 		       const method_decl*m);
4042 
4043   friend method_decl_sptr
4044   copy_member_function(class_or_union_sptr& t,
4045 		       const method_decl_sptr& m);
4046 
4047   friend void
4048   fixup_virtual_member_function(method_decl_sptr method);
4049 
4050   friend void
4051   set_member_is_static(decl_base& d, bool s);
4052 
4053   friend bool
4054   equals(const class_or_union&, const class_or_union&, change_kind*);
4055 
4056   friend bool
4057   equals(const class_decl&, const class_decl&, change_kind*);
4058 
4059   friend class method_decl;
4060   friend class class_decl;
4061 }; // end class class_or_union
4062 
4063 method_decl_sptr
4064 copy_member_function(const class_or_union_sptr& clazz,
4065 		     const method_decl_sptr& f);
4066 
4067 method_decl_sptr
4068 copy_member_function(const class_or_union_sptr& clazz,
4069 		     const method_decl* f);
4070 
4071 bool
4072 operator==(const class_or_union_sptr& l, const class_or_union_sptr& r);
4073 
4074 bool
4075 operator!=(const class_or_union_sptr& l, const class_or_union_sptr& r);
4076 
4077 /// Hasher for the @ref class_or_union type
4078 struct class_or_union::hash
4079 {
4080   size_t
4081   operator()(const class_or_union& t) const;
4082 
4083   size_t
4084   operator()(const class_or_union* t) const;
4085 }; // end struct class_decl::hash
4086 
4087 /// Abstracts a class declaration.
4088 class class_decl : public class_or_union
4089 {
4090   // Forbidden
4091   class_decl();
4092 
4093 protected:
4094 
4095   decl_base_sptr
4096   insert_member_decl(decl_base_sptr member);
4097 
4098 public:
4099   /// Hasher.
4100   struct hash;
4101 
4102   /// Forward declarations.
4103   class base_spec;
4104 
4105   /// Convenience typedef
4106   /// @{
4107   typedef shared_ptr<base_spec>			base_spec_sptr;
4108   typedef vector<base_spec_sptr>			base_specs;
4109 
4110   /// @}
4111 
4112 protected:
4113   virtual void
4114   on_canonical_type_set();
4115 
4116 private:
4117   struct priv;
4118   // This priv it's not handled by a shared_ptr because accessing the
4119   // data members of the priv struct for this class_decl shows up on
4120   // performance profiles when dealing with big binaries with a lot of
4121   // types; dereferencing the shared_ptr involves locking of some sort
4122   // and that is slower than just dereferencing a pointer likere here.
4123   // There are other types for which the priv pointer is managed using
4124   // shared_ptr just fine, because those didn't show up during our
4125   // performance profiling.
4126   priv * priv_;
4127 
4128 public:
4129 
4130   class_decl(const environment& env, const string& name,
4131 	     size_t size_in_bits, size_t align_in_bits,
4132 	     bool is_struct, const location& locus,
4133 	     visibility vis, base_specs& bases,
4134 	     member_types& mbrs, data_members& data_mbrs,
4135 	     member_functions& member_fns);
4136 
4137   class_decl(const environment& env, const string& name,
4138 	     size_t size_in_bits, size_t align_in_bits,
4139 	     bool is_struct, const location& locus,
4140 	     visibility vis, base_specs& bases,
4141 	     member_types& mbrs, data_members& data_mbrs,
4142 	     member_functions& member_fns, bool is_anonymous);
4143 
4144   class_decl(const environment& env, const string& name,
4145 	     size_t size_in_bits, size_t align_in_bits,
4146 	     bool is_struct, const location& locus, visibility vis);
4147 
4148   class_decl(const environment& env, const string& name,
4149 	     size_t size_in_bits, size_t align_in_bits,
4150 	     bool is_struct, const location& locus,
4151 	     visibility vis, bool is_anonymous);
4152 
4153   class_decl(const environment& env, const string& name, bool is_struct,
4154 	     bool is_declaration_only = true);
4155 
4156   virtual string
4157   get_pretty_representation(bool internal = false,
4158 			    bool qualified_name = true) const;
4159 
4160   void
4161   is_struct(bool f);
4162 
4163   bool
4164   is_struct() const;
4165 
4166   void
4167   add_base_specifier(shared_ptr<base_spec> b);
4168 
4169   const base_specs&
4170   get_base_specifiers() const;
4171 
4172   class_decl_sptr
4173   find_base_class(const string&) const;
4174 
4175   const member_functions&
4176   get_virtual_mem_fns() const;
4177 
4178   const virtual_mem_fn_map_type&
4179   get_virtual_mem_fns_map() const;
4180 
4181   void
4182   sort_virtual_mem_fns();
4183 
4184   bool
4185   has_no_base_nor_member() const;
4186 
4187   bool
4188   has_virtual_member_functions() const;
4189 
4190   bool
4191   has_virtual_bases() const;
4192 
4193   bool
4194   has_vtable() const;
4195 
4196   ssize_t
4197   get_biggest_vtable_offset() const;
4198 
4199   virtual size_t
4200   get_hash() const;
4201 
4202   virtual bool
4203   operator==(const decl_base&) const;
4204 
4205   virtual bool
4206   operator==(const type_base&) const;
4207 
4208   virtual bool
4209   operator==(const class_decl&) const;
4210 
4211   virtual bool
4212   traverse(ir_node_visitor& v);
4213 
4214   virtual ~class_decl();
4215 
4216   friend void
4217   fixup_virtual_member_function(method_decl_sptr method);
4218 
4219   friend void
4220   set_member_is_static(decl_base& d, bool s);
4221 
4222   friend bool
4223   equals(const class_decl&, const class_decl&, change_kind*);
4224 
4225   friend class method_decl;
4226   friend class class_or_union;
4227 };// end class class_decl
4228 
4229 bool
4230 equals(const class_decl&, const class_decl&, change_kind*);
4231 
4232 method_decl_sptr
4233 copy_member_function(const class_decl_sptr& clazz,
4234 		     const method_decl_sptr& f);
4235 
4236 method_decl_sptr
4237 copy_member_function(const class_decl_sptr& clazz,
4238 		     const method_decl* f);
4239 void
4240 fixup_virtual_member_function(method_decl_sptr method);
4241 
4242 /// Hasher for the @ref class_decl type
4243 struct class_decl::hash
4244 {
4245   size_t
4246   operator()(const class_decl& t) const;
4247 
4248   size_t
4249   operator()(const class_decl* t) const;
4250 }; // end struct class_decl::hash
4251 
4252 enum access_specifier
4253 get_member_access_specifier(const decl_base&);
4254 
4255 enum access_specifier
4256 get_member_access_specifier(const decl_base_sptr&);
4257 
4258 void
4259 set_member_access_specifier(decl_base&,
4260 			    access_specifier);
4261 
4262 void
4263 set_member_access_specifier(const decl_base_sptr&,
4264 			    access_specifier);
4265 
4266 std::ostream&
4267 operator<<(std::ostream&, access_specifier);
4268 
4269 bool
4270 operator==(const class_decl_sptr& l, const class_decl_sptr& r);
4271 
4272 bool
4273 operator!=(const class_decl_sptr& l, const class_decl_sptr& r);
4274 
4275 bool
4276 equals(const class_decl::base_spec&,
4277        const class_decl::base_spec&,
4278        change_kind*);
4279 
4280 /// Abstraction of a base specifier in a class declaration.
4281 class class_decl::base_spec : public member_base,
4282 			      public virtual decl_base
4283 {
4284   struct priv;
4285   std::unique_ptr<priv> priv_;
4286 
4287   // Forbidden
4288   base_spec();
4289 
4290 public:
4291 
4292   /// Hasher.
4293   struct hash;
4294 
4295   base_spec(const class_decl_sptr& base, access_specifier a,
4296 	    long offset_in_bits = -1, bool is_virtual = false);
4297 
4298   base_spec(const type_base_sptr& base, access_specifier a,
4299 	    long offset_in_bits = -1, bool is_virtual = false);
4300 
4301   virtual ~base_spec();
4302 
4303   class_decl_sptr
4304   get_base_class() const;
4305 
4306   bool
4307   get_is_virtual() const;
4308 
4309   long
4310   get_offset_in_bits() const;
4311 
4312   virtual bool
4313   operator==(const decl_base&) const;
4314 
4315   virtual bool
4316   operator==(const member_base&) const;
4317 
4318   virtual size_t
4319   get_hash() const;
4320 
4321   virtual bool
4322   traverse(ir_node_visitor&);
4323 };// end class class_decl::base_spec
4324 
4325 bool
4326 operator==(const class_decl::base_spec_sptr& l,
4327 	   const class_decl::base_spec_sptr& r);
4328 
4329 bool
4330 operator!=(const class_decl::base_spec_sptr& l,
4331 	   const class_decl::base_spec_sptr& r);
4332 
4333 class_decl::base_spec*
4334 is_class_base_spec(type_or_decl_base*);
4335 
4336 class_decl::base_spec_sptr
4337 is_class_base_spec(type_or_decl_base_sptr);
4338 
4339 /// Abstracts a union type declaration.
4340 class union_decl : public class_or_union
4341 {
4342   // Forbid
4343   union_decl();
4344 
4345 public:
4346 
4347   union_decl(const environment& env, const string& name,
4348 	     size_t size_in_bits, const location& locus,
4349 	     visibility vis, member_types& mbrs,
4350 	     data_members& data_mbrs, member_functions& member_fns);
4351 
4352   union_decl(const environment& env, const string& name,
4353 	     size_t size_in_bits, const location& locus,
4354 	     visibility vis, member_types& mbrs,
4355 	     data_members& data_mbrs, member_functions& member_fns,
4356 	     bool is_anonymous);
4357 
4358   union_decl(const environment& env, const string& name,
4359 	     size_t size_in_bits, const location& locus,
4360 	     visibility vis);
4361 
4362   union_decl(const environment& env, const string& name,
4363 	     size_t size_in_bits, const location& locus,
4364 	     visibility vis, bool is_anonymous);
4365 
4366   union_decl(const environment& env, const string& name,
4367 	     bool is_declaration_only = true);
4368 
4369   virtual string
4370   get_pretty_representation(bool internal = false,
4371 			    bool qualified_name = true) const;
4372 
4373   virtual bool
4374   operator==(const decl_base&) const;
4375 
4376   virtual bool
4377   operator==(const type_base&) const;
4378 
4379   virtual bool
4380   operator==(const union_decl&) const;
4381 
4382   virtual bool
4383   traverse(ir_node_visitor& v);
4384 
4385   virtual ~union_decl();
4386 }; // union_decl
4387 
4388 bool
4389 equals(const union_decl&, const union_decl&, change_kind*);
4390 
4391 method_decl_sptr
4392 copy_member_function(const union_decl_sptr& union_type,
4393 		     const method_decl_sptr& f);
4394 
4395 method_decl_sptr
4396 copy_member_function(const union_decl_sptr& union_type,
4397 		     const method_decl* f);
4398 
4399 bool
4400 operator==(const union_decl_sptr& l, const union_decl_sptr& r);
4401 
4402 bool
4403 operator!=(const union_decl_sptr& l, const union_decl_sptr& r);
4404 
4405 /// Abstraction of a member function context relationship.  This
4406 /// relates a member function to its parent class.
4407 class mem_fn_context_rel : public context_rel
4408 {
4409 protected:
4410   bool		is_virtual_;
4411   ssize_t	vtable_offset_in_bits_;
4412   bool		is_constructor_;
4413   bool		is_destructor_;
4414   bool		is_const_;
4415 
4416 public:
mem_fn_context_rel()4417   mem_fn_context_rel()
4418     : context_rel(),
4419       is_virtual_(false),
4420       vtable_offset_in_bits_(-1),
4421       is_constructor_(false),
4422       is_destructor_(false),
4423       is_const_(false)
4424   {}
4425 
mem_fn_context_rel(scope_decl * s)4426   mem_fn_context_rel(scope_decl* s)
4427     : context_rel(s),
4428       is_virtual_(false),
4429       vtable_offset_in_bits_(-1),
4430       is_constructor_(false),
4431       is_destructor_(false),
4432       is_const_(false)
4433   {}
4434 
mem_fn_context_rel(scope_decl * s,bool is_constructor,bool is_destructor,bool is_const,bool is_virtual,size_t vtable_offset_in_bits,access_specifier access,bool is_static)4435   mem_fn_context_rel(scope_decl* s,
4436 		     bool is_constructor,
4437 		     bool is_destructor,
4438 		     bool is_const,
4439 		     bool is_virtual,
4440 		     size_t vtable_offset_in_bits,
4441 		     access_specifier access,
4442 		     bool is_static)
4443     : context_rel(s, access, is_static),
4444       is_virtual_(is_virtual),
4445       vtable_offset_in_bits_(vtable_offset_in_bits),
4446       is_constructor_(is_constructor),
4447       is_destructor_(is_destructor),
4448       is_const_(is_const)
4449   {}
4450 
4451   bool
is_virtual()4452   is_virtual() const
4453   {return is_virtual_;}
4454 
4455   void
is_virtual(bool is_virtual)4456   is_virtual(bool is_virtual)
4457   {is_virtual_ = is_virtual;}
4458 
4459   /// Getter for the vtable offset property.
4460   ///
4461   /// This is the vtable offset of the member function of this
4462   /// relation.
4463   ///
4464   /// @return the vtable offset property of the relation.
4465   size_t
vtable_offset()4466   vtable_offset() const
4467   {return vtable_offset_in_bits_;}
4468 
4469   /// Setter for the vtable offset property.
4470   ///
4471   /// This is the vtable offset of the member function of this
4472   /// relation.
4473   ///
4474   /// @partam s the new vtable offset.
4475   void
vtable_offset(size_t s)4476   vtable_offset(size_t s)
4477   {vtable_offset_in_bits_ = s;}
4478 
4479   /// Getter for the 'is-constructor' property.
4480   ///
4481   /// This tells if the member function of this relation is a
4482   /// constructor.
4483   ///
4484   /// @return the is-constructor property of the relation.
4485   bool
is_constructor()4486   is_constructor() const
4487   {return is_constructor_;}
4488 
4489   /// Setter for the 'is-constructor' property.
4490   ///
4491   /// @param f the new value of the the property.  Is true if this is
4492   /// for a constructor, false otherwise.
4493   void
is_constructor(bool f)4494   is_constructor(bool f)
4495   {is_constructor_ = f;}
4496 
4497   /// Getter for the 'is-destructor' property.
4498   ///
4499   /// Tells if the member function of this relation is a destructor.
4500   ///
4501   /// @return the is-destructor property of the relation;
4502   bool
is_destructor()4503   is_destructor() const
4504   {return is_destructor_;}
4505 
4506   /// Setter for the 'is-destructor' property.
4507   ///
4508   /// @param f the new value of the property.  Is true if this is for
4509   /// a destructor, false otherwise.
4510   void
is_destructor(bool f)4511   is_destructor(bool f)
4512   {is_destructor_ = f;}
4513 
4514   /// Getter for the 'is-const' property.
4515   ///
4516   /// Tells if the member function of this relation is a const member
4517   /// function.
4518   ///
4519   /// @return the 'is-const' property of the relation.
4520   bool
is_const()4521   is_const() const
4522   {return is_const_;}
4523 
4524   /// Setter for the 'is-const' property.
4525   ///
4526   /// @param f the new value of the property.  Is true if this is for
4527   /// a const entity, false otherwise.
4528   void
is_const(bool f)4529   is_const(bool f)
4530   {is_const_ = f;}
4531 
4532   virtual ~mem_fn_context_rel();
4533 }; // end class mem_fn_context_rel
4534 
4535 method_decl*
4536 is_method_decl(const type_or_decl_base*);
4537 
4538 method_decl*
4539 is_method_decl(const type_or_decl_base&);
4540 
4541 method_decl_sptr
4542 is_method_decl(const type_or_decl_base_sptr&);
4543 
4544 const var_decl*
4545 lookup_data_member(const type_base* type,
4546 		   const char* dm_name);
4547 
4548 const function_decl::parameter*
4549 get_function_parameter(const decl_base* fun,
4550 		       unsigned parm_num);
4551 
4552 /// Abstract a member function template.
4553 class member_function_template : public member_base, public virtual decl_base
4554 {
4555   bool is_constructor_;
4556   bool is_const_;
4557   shared_ptr<function_tdecl> fn_tmpl_;
4558 
4559   // Forbiden
4560   member_function_template();
4561 
4562 public:
4563   /// Hasher.
4564   struct hash;
4565 
member_function_template(function_tdecl_sptr f,access_specifier access,bool is_static,bool is_constructor,bool is_const)4566   member_function_template(function_tdecl_sptr f,
4567 			   access_specifier access, bool is_static,
4568 			   bool is_constructor, bool is_const)
4569     : type_or_decl_base(f->get_environment()),
4570       decl_base(f->get_environment(), f->get_name(), location()),
4571       member_base(access, is_static), is_constructor_(is_constructor),
4572       is_const_(is_const), fn_tmpl_(f)
4573   {}
4574 
4575   bool
is_constructor()4576   is_constructor() const
4577   {return is_constructor_;}
4578 
4579   bool
is_const()4580   is_const() const
4581   {return is_const_;}
4582 
4583   operator const function_tdecl& () const
4584   {return *fn_tmpl_;}
4585 
4586   function_tdecl_sptr
as_function_tdecl()4587   as_function_tdecl() const
4588   {return fn_tmpl_;}
4589 
4590   virtual bool
4591   operator==(const member_base& o) const;
4592 
4593   virtual bool
4594   traverse(ir_node_visitor&);
4595 };// end class member_function_template
4596 
4597 bool
4598 operator==(const member_function_template_sptr& l,
4599 	   const member_function_template_sptr& r);
4600 
4601 bool
4602 operator!=(const member_function_template_sptr& l,
4603 	   const member_function_template_sptr& r);
4604 
4605 /// Abstracts a member class template template
4606 class member_class_template
4607   : public member_base,
4608     public virtual decl_base
4609 {
4610   shared_ptr<class_tdecl> class_tmpl_;
4611 
4612   // Forbidden
4613   member_class_template();
4614 
4615 public:
4616 
4617   /// Hasher.
4618   struct hash;
4619 
member_class_template(class_tdecl_sptr c,access_specifier access,bool is_static)4620   member_class_template(class_tdecl_sptr c,
4621 			access_specifier access, bool is_static)
4622     : type_or_decl_base(c->get_environment()),
4623       decl_base(c->get_environment(), c->get_name(), location()),
4624       member_base(access, is_static),
4625       class_tmpl_(c)
4626   {}
4627 
4628   operator const class_tdecl& () const
4629   { return *class_tmpl_; }
4630 
4631   class_tdecl_sptr
as_class_tdecl()4632   as_class_tdecl() const
4633   {return class_tmpl_;}
4634 
4635   virtual bool
4636   operator==(const member_base& o) const;
4637 
4638   virtual bool
4639   operator==(const member_class_template&) const;
4640 
4641   virtual bool
4642   traverse(ir_node_visitor& v);
4643 };// end class member_class_template
4644 
4645 bool
4646 operator==(const member_class_template_sptr& l,
4647 	   const member_class_template_sptr& r);
4648 
4649 bool
4650 operator!=(const member_class_template_sptr& l,
4651 	   const member_class_template_sptr& r);
4652 
4653 // Forward declarations for select nested hashers.
4654 struct type_base::shared_ptr_hash
4655 {
4656   size_t
4657   operator()(const shared_ptr<type_base> t) const;
4658 };
4659 
4660 struct type_base::dynamic_hash
4661 {
4662   size_t
4663   operator()(const type_base* t) const;
4664 };
4665 
4666 /// A hashing functor for instances and pointers of @ref var_decl.
4667 struct var_decl::hash
4668 {
4669   size_t
4670   operator()(const var_decl& t) const;
4671 
4672   size_t
4673   operator()(const var_decl* t) const;
4674 }; //end struct var_decl::hash
4675 
4676 /// A comparison functor for pointers to @ref var_decl.
4677 struct var_decl::ptr_equal
4678 {
4679   /// Return true if the two instances of @ref var_decl are equal.
4680   ///
4681   /// @param l the first variable to compare.
4682   ///
4683   /// @param r the second variable to compare.
4684   ///
4685   /// @return true if @p l equals @p r.
4686   bool
operatorptr_equal4687   operator()(const var_decl* l, const var_decl* r) const
4688   {
4689     if (l == r)
4690       return true;
4691     if (!!l != !!r)
4692       return false;
4693     return (*l == *r);
4694   }
4695 };// end struct var_decl::ptr_equal
4696 
4697 /// A hashing functor fo instances and pointers of @ref function_decl.
4698 struct function_decl::hash
4699 {
4700   size_t
4701   operator()(const function_decl& t) const;
4702 
4703   size_t
4704   operator()(const function_decl* t) const;
4705 };//end struct function_decl::hash
4706 
4707 /// Equality functor for instances of @ref function_decl
4708 struct function_decl::ptr_equal
4709 {
4710   /// Tests if two pointers to @ref function_decl are equal.
4711   ///
4712   /// @param l the first pointer to @ref function_decl to consider in
4713   /// the comparison.
4714   ///
4715   /// @param r the second pointer to @ref function_decl to consider in
4716   /// the comparison.
4717   ///
4718   /// @return true if the two functions @p l and @p r are equal, false
4719   /// otherwise.
4720   bool
operatorptr_equal4721   operator()(const function_decl* l, const function_decl* r) const
4722   {
4723     if (l == r)
4724       return true;
4725     if (!!l != !!r)
4726       return false;
4727     return (*l == *r);
4728   }
4729 };// function_decl::ptr_equal
4730 
4731 /// The hashing functor for class_decl::base_spec.
4732 struct class_decl::base_spec::hash
4733 {
4734   size_t
4735   operator()(const base_spec& t) const;
4736 };
4737 
4738 /// The hashing functor for member_base.
4739 struct member_base::hash
4740 {
4741   size_t
4742   operator()(const member_base& m) const;
4743 };
4744 
4745 /// The hashing functor for member_function_template.
4746 struct member_function_template::hash
4747 {
4748   size_t
4749   operator()(const member_function_template& t) const;
4750 };
4751 
4752 /// The hashing functor for member_class_template
4753 struct member_class_template::hash
4754 {
4755   size_t
4756   operator()(const member_class_template& t) const;
4757 };
4758 
4759 struct function_tdecl::hash
4760 {
4761   size_t
4762   operator()(const function_tdecl& t) const;
4763 };
4764 
4765 struct function_tdecl::shared_ptr_hash
4766 {
4767   size_t
4768   operator()(const shared_ptr<function_tdecl> f) const;
4769 };
4770 
4771 struct class_tdecl::hash
4772 {
4773   size_t
4774   operator()(const class_tdecl& t) const;
4775 };
4776 
4777 struct class_tdecl::shared_ptr_hash
4778 {
4779   size_t
4780   operator()(const shared_ptr<class_tdecl> t) const;
4781 };
4782 
4783 /// The base class for the visitor type hierarchy used for traversing
4784 /// a translation unit.
4785 ///
4786 /// Client code willing to get notified for a certain kind of node
4787 /// during the IR traversal might want to define a visitor class that
4788 /// inherit ir_node_visitor, overload the ir_node_visitor::visit_begin()
4789 /// or ir_node_visitor::visit_end() method of its choice, and provide
4790 /// and implementation for it.  If either
4791 /// ir_node_visitor::visit_begin() or ir_node_visitor::visit_end()
4792 /// return false, it means the traversal has to stop immediately after
4793 /// the methods' return.  If the methods return true, it means the
4794 /// traversal keeps going.
4795 ///
4796 /// That new visitor class would then be passed to e.g,
4797 /// translation_unit::traverse or to the traverse method of any type
4798 /// where the traversal is supposed to start from.
4799 class ir_node_visitor : public node_visitor_base
4800 {
4801   struct priv;
4802   std::unique_ptr<priv> priv_;
4803 
4804 public:
4805 
4806   ir_node_visitor();
4807 
4808   virtual ~ir_node_visitor();
4809 
4810   void allow_visiting_already_visited_type_node(bool);
4811   bool allow_visiting_already_visited_type_node() const;
4812   void mark_type_node_as_visited(type_base *);
4813   void forget_visited_type_nodes();
4814   bool type_node_has_been_visited(type_base*) const;
4815 
4816   virtual bool visit_begin(decl_base*);
4817   virtual bool visit_end(decl_base*);
4818 
4819   virtual bool visit_begin(scope_decl*);
4820   virtual bool visit_end(scope_decl*);
4821 
4822   virtual bool visit_begin(type_base*);
4823   virtual bool visit_end(type_base*);
4824 
4825   virtual bool visit_begin(scope_type_decl*);
4826   virtual bool visit_end(scope_type_decl*);
4827 
4828   virtual bool visit_begin(type_decl*);
4829   virtual bool visit_end(type_decl*);
4830 
4831   virtual bool visit_begin(namespace_decl*);
4832   virtual bool visit_end(namespace_decl*);
4833 
4834   virtual bool visit_begin(qualified_type_def*);
4835   virtual bool visit_end(qualified_type_def*);
4836 
4837   virtual bool visit_begin(pointer_type_def*);
4838   virtual bool visit_end(pointer_type_def*);
4839 
4840   virtual bool visit_begin(reference_type_def*);
4841   virtual bool visit_end(reference_type_def*);
4842 
4843   virtual bool visit_begin(array_type_def*);
4844   virtual bool visit_end(array_type_def*);
4845 
4846   virtual bool visit_begin(array_type_def::subrange_type*);
4847   virtual bool visit_end(array_type_def::subrange_type*);
4848 
4849   virtual bool visit_begin(enum_type_decl*);
4850   virtual bool visit_end(enum_type_decl*);
4851 
4852   virtual bool visit_begin(typedef_decl*);
4853   virtual bool visit_end(typedef_decl*);
4854 
4855   virtual bool visit_begin(function_type*);
4856   virtual bool visit_end(function_type*);
4857 
4858   virtual bool visit_begin(var_decl*);
4859   virtual bool visit_end(var_decl*);
4860 
4861   virtual bool visit_begin(function_decl*);
4862   virtual bool visit_end(function_decl*);
4863 
4864   virtual bool visit_begin(function_decl::parameter*);
4865   virtual bool visit_end(function_decl::parameter*);
4866 
4867   virtual bool visit_begin(function_tdecl*);
4868   virtual bool visit_end(function_tdecl*);
4869 
4870   virtual bool visit_begin(class_tdecl*);
4871   virtual bool visit_end(class_tdecl*);
4872 
4873   virtual bool visit_begin(class_or_union *);
4874   virtual bool visit_end(class_or_union *);
4875 
4876   virtual bool visit_begin(class_decl*);
4877   virtual bool visit_end(class_decl*);
4878 
4879   virtual bool visit_begin(union_decl*);
4880   virtual bool visit_end(union_decl*);
4881 
4882   virtual bool visit_begin(class_decl::base_spec*);
4883   virtual bool visit_end(class_decl::base_spec*);
4884 
4885   virtual bool visit_begin(member_function_template*);
4886   virtual bool visit_end(member_function_template*);
4887 
4888   virtual bool visit_begin(member_class_template*);
4889   virtual bool visit_end(member_class_template*);
4890 }; // end struct ir_node_visitor
4891 
4892 // Debugging facility
4893 void
4894 fns_to_str(vector<function_decl*>::const_iterator a_begin,
4895 	   vector<function_decl*>::const_iterator a_end,
4896 	   vector<function_decl*>::const_iterator b_begin,
4897 	   vector<function_decl*>::const_iterator b_end,
4898 	   std::ostream& o);
4899 
4900 }// end namespace ir
4901 } // end namespace abigail
4902 #endif // __ABG_IR_H__
4903