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