1 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 2 // -*- Mode: C++ -*- 3 // 4 // Copyright (C) 2013-2022 Red Hat, Inc. 5 // 6 // Author: Dodji Seketeli 7 8 #ifndef __ABG_COMPARISON_H__ 9 #define __ABG_COMPARISON_H__ 10 11 /// @file 12 13 #include <memory> 14 #include <ostream> 15 #include <unordered_map> 16 #include <unordered_set> 17 #include "abg-corpus.h" 18 #include "abg-diff-utils.h" 19 #include "abg-reporter.h" 20 21 namespace abigail 22 { 23 24 /// @brief utilities to compare abi artifacts 25 /// 26 /// The main entry points of the namespace are the compute_diff() 27 /// overloads used to compute the difference between two abi artifacts. 28 namespace comparison 29 { 30 31 namespace filtering 32 { 33 struct filter_base; 34 typedef shared_ptr<filter_base> filter_base_sptr; 35 typedef std::vector<filter_base_sptr> filters; 36 } 37 38 // Inject types we need into this namespace. 39 using std::ostream; 40 using std::vector; 41 using std::unordered_map; 42 using std::unordered_set; 43 using std::pair; 44 45 using diff_utils::insertion; 46 using diff_utils::deletion; 47 using diff_utils::edit_script; 48 49 class diff; 50 51 /// Convenience typedef for a shared_ptr for the @ref diff class 52 typedef shared_ptr<diff> diff_sptr; 53 54 /// Convenience typedef for a weak_ptr for the @ref diff class 55 typedef weak_ptr<diff> diff_wptr; 56 57 /// Hasher for @ref diff_sptr. 58 struct diff_sptr_hasher 59 { 60 /// The actual hashing functor. 61 size_t operatordiff_sptr_hasher62 operator()(const diff_sptr& t) const 63 {return reinterpret_cast<size_t>(t.get());} 64 }; // end struct diff_sptr_hasher 65 66 /// Convenience typedef for a vector of @ref diff_sptr. 67 typedef vector<diff_sptr> diff_sptrs_type; 68 69 /// Convenience typedef for a vector of @ref diff*. 70 typedef vector<diff*> diff_ptrs_type; 71 72 /// Convenience typedef for an unoredered set of @ref diff_sptr 73 typedef unordered_set<diff_sptr, diff_sptr_hasher> unordered_diff_sptr_set; 74 75 class decl_diff_base; 76 77 /// Convenience typedef for a shared_ptr of @ref decl_diff_base. 78 typedef shared_ptr<decl_diff_base> decl_diff_base_sptr; 79 80 /// Convenience typedef for a vector of @ref decl_diff_base_sptr. 81 typedef vector<decl_diff_base_sptr> decl_diff_base_sptrs_type; 82 83 class type_diff_base; 84 /// Convenience pointer for a shared pointer to a type_diff_base 85 typedef shared_ptr<type_diff_base> type_diff_base_sptr; 86 87 /// Convenience typedef for a vector of @ref type_diff_base_sptr 88 typedef vector<type_diff_base_sptr> type_diff_base_sptrs_type; 89 90 class function_decl_diff; 91 92 /// Convenience typedef for a shared pointer to a @ref function_decl type. 93 typedef shared_ptr<function_decl_diff> function_decl_diff_sptr; 94 95 /// Convenience typedef for a vector of @ref function_decl_diff_sptr 96 typedef vector<function_decl_diff_sptr> function_decl_diff_sptrs_type; 97 98 class fn_parm_diff; 99 100 /// Convenience typedef for a shared pointer to a @ref fn_parm_diff 101 /// type. 102 typedef shared_ptr<fn_parm_diff> fn_parm_diff_sptr; 103 104 class var_diff; 105 106 /// Convenience typedef for a shared pointer to a @ref var_diff type. 107 typedef shared_ptr<var_diff> var_diff_sptr; 108 109 /// Convenience typedef for a vector of @ref var_diff_sptr. 110 typedef vector<var_diff_sptr> var_diff_sptrs_type; 111 112 class base_diff; 113 114 /// Convenience typedef for a shared pointer to a @ref base_diff type. 115 typedef shared_ptr<base_diff> base_diff_sptr; 116 117 /// Convenience typedef for a vector of @ref base_diff_sptr. 118 typedef vector<base_diff_sptr> base_diff_sptrs_type; 119 120 class class_diff; 121 122 /// Convenience typedef for a shared pointer on a @ref class_diff type. 123 typedef shared_ptr<class_diff> class_diff_sptr; 124 125 /// Convenience typedef for a map of pointer values. The Key is a 126 /// pointer value and the value is potentially another pointer value 127 /// associated to the first one. 128 typedef unordered_map<size_t, size_t> pointer_map; 129 130 /// Convenience typedef for a map which key is a string and which 131 /// value is a @ref decl_base_sptr. 132 typedef unordered_map<string, decl_base_sptr> string_decl_base_sptr_map; 133 134 /// Convenience typedef for a map which key is a string and which 135 /// value is a @ref type_base_sptr. 136 typedef unordered_map<string, type_base_sptr> string_type_base_sptr_map; 137 138 /// Convenience typedef for a map which key is an unsigned integer and 139 /// which value is a @ref decl_base_sptr 140 typedef unordered_map<unsigned, decl_base_sptr> unsigned_decl_base_sptr_map; 141 142 /// Convenience typedef for a map of string and class_decl::basse_spec_sptr. 143 typedef unordered_map<string, class_decl::base_spec_sptr> string_base_sptr_map; 144 145 /// Convenience typedef for a map of string and @ref base_diff_sptr. 146 typedef unordered_map<string, base_diff_sptr> string_base_diff_sptr_map; 147 148 /// Convenience typedef for a map which value is a changed function 149 /// parameter and which key is the name of the function parameter. 150 typedef unordered_map<string, fn_parm_diff_sptr> string_fn_parm_diff_sptr_map; 151 152 /// Convenience typedef for a map which key is an integer and which 153 /// value is a changed parameter. 154 typedef unordered_map<unsigned, fn_parm_diff_sptr> 155 unsigned_fn_parm_diff_sptr_map; 156 157 /// Convenience typedef for a map which key is an integer and which 158 /// value is a parameter. 159 typedef unordered_map<unsigned, 160 function_decl::parameter_sptr> unsigned_parm_map; 161 162 /// Convenience typedef for a map which value is a 163 /// type_diff_base_sptr. The key of the map is the qualified name of 164 /// the changed type. 165 typedef unordered_map<string, 166 type_diff_base_sptr> string_type_diff_base_sptr_map; 167 168 /// Convenience typedef for a map which value is a 169 /// decl_diff_base_sptr. The key of the map is the qualified name of 170 /// the changed type. 171 typedef unordered_map<string, 172 decl_diff_base_sptr> string_decl_diff_base_sptr_map; 173 174 /// Convenience typedef for a map which value is a diff_sptr. The key 175 /// of the map is the qualified name of the changed type. 176 typedef unordered_map<string, diff_sptr> string_diff_sptr_map; 177 178 /// Convenience typedef for a map which value is a diff*. The key of 179 /// the map is the qualified name of the changed type. 180 typedef unordered_map<string, diff*> string_diff_ptr_map; 181 182 /// Convenience typedef for a map whose key is a string and whose 183 /// value is a changed variable of type @ref var_diff_sptr. 184 typedef unordered_map<string, 185 var_diff_sptr> string_var_diff_sptr_map; 186 187 188 /// Convenience typedef for a map whose key is an unsigned int and 189 /// whose value is a changed variable of type @ref var_diff_sptr. 190 typedef unordered_map<unsigned, var_diff_sptr> unsigned_var_diff_sptr_map; 191 192 /// Convenience typedef for a map which value is a function 193 /// parameter. The key is the name of the function parm. 194 typedef unordered_map<string, function_decl::parameter_sptr> string_parm_map; 195 196 /// Convenience typedef for a map which value is an enumerator. The 197 /// key is the name of the enumerator. 198 typedef unordered_map<string, enum_type_decl::enumerator> string_enumerator_map; 199 200 /// Convenience typedef for a changed enumerator. The first element 201 /// of the pair is the old enumerator and the second one is the new enumerator. 202 typedef std::pair<enum_type_decl::enumerator, 203 enum_type_decl::enumerator> changed_enumerator; 204 205 /// Convenience typedef for a vector of changed enumerators. 206 typedef vector<changed_enumerator> changed_enumerators_type; 207 208 /// Convenience typedef for a map which value is a changed enumerator. 209 /// The key is the name of the changed enumerator. 210 typedef unordered_map<string, changed_enumerator> string_changed_enumerator_map; 211 212 /// Convenience typedef for a map which key is a string and which 213 /// value is a pointer to @ref decl_base. 214 typedef unordered_map<string, function_decl*> string_function_ptr_map; 215 216 /// Convenience typedef for a map which key is a string and which 217 /// value is a @ref function_decl_diff_sptr. 218 typedef unordered_map<string, 219 function_decl_diff_sptr> 220 string_function_decl_diff_sptr_map; 221 222 /// Convenience typedef for a pair of class_decl::member_function_sptr 223 /// representing a changed member function. The first element of the 224 /// pair is the initial member function and the second element is the 225 /// changed one. 226 typedef pair<method_decl_sptr, 227 method_decl_sptr> changed_member_function_sptr; 228 229 /// Convenience typedef for a hash map of strings and changed member functions. 230 typedef unordered_map<string, 231 changed_member_function_sptr> 232 string_changed_member_function_sptr_map; 233 234 /// Convenience typedef for a hash map of strings and member functions. 235 typedef unordered_map<string, method_decl_sptr> string_member_function_sptr_map; 236 237 /// Convenience typedef for a map which key is a string and which 238 /// value is a point to @ref var_decl. 239 typedef unordered_map<string, var_decl*> string_var_ptr_map; 240 241 /// Convenience typedef for a pair of pointer to @ref var_decl 242 /// representing a @ref var_decl change. The first member of the pair 243 /// represents the initial variable and the second member represents 244 /// the changed variable. 245 typedef std::pair<var_decl*, var_decl*> changed_var_ptr; 246 247 /// Convenience typedef for a pair of @ref var_decl_sptr representing 248 /// a @ref var_decl change. The first member of the pair represents 249 /// the initial variable and the second member represents the changed 250 /// variable. 251 typedef std::pair<var_decl_sptr, var_decl_sptr> changed_var_sptr; 252 253 /// Convenience typedef for a vector of @changed_var_sptr.gg381 254 typedef vector<changed_var_sptr> changed_var_sptrs_type; 255 256 /// Convenience typedef for a map whose key is a string and whose 257 /// value is an @ref elf_symbol_sptr. 258 typedef unordered_map<string, elf_symbol_sptr> string_elf_symbol_map; 259 260 /// Convenience typedef for a map which key is a string and which 261 /// value is a @ref var_diff_sptr. 262 typedef unordered_map<string, var_diff_sptr> string_var_diff_ptr_map; 263 264 class diff_context; 265 266 /// Convenience typedef for a shared pointer of @ref diff_context. 267 typedef shared_ptr<diff_context> diff_context_sptr; 268 269 /// Convenience typedef for a weak pointer of @ref diff_context. 270 typedef weak_ptr<diff_context> diff_context_wptr; 271 272 class diff_node_visitor; 273 274 class diff_traversable_base; 275 276 /// Convenience typedef for shared_ptr on diff_traversable_base. 277 typedef shared_ptr<diff_traversable_base> diff_traversable_base_sptr; 278 279 /// An enum for the different ways to visit a diff tree node. 280 /// 281 /// This is used by the node traversing code, to know when to avoid 282 /// visiting children nodes, for instance. 283 enum visiting_kind 284 { 285 /// The default enumerator value of this enum. It doesn't have any 286 /// particular meaning yet. 287 DEFAULT_VISITING_KIND = 0, 288 289 /// This says that the traversing code should avoid visiting the 290 /// children nodes of the current node being visited. 291 SKIP_CHILDREN_VISITING_KIND = 1, 292 293 /// This says that the traversing code should not mark visited nodes 294 /// as having been traversed. This is useful, for instance, for 295 /// visitors which have debugging purposes. 296 DO_NOT_MARK_VISITED_NODES_AS_VISITED = 1 << 1 297 }; 298 299 visiting_kind 300 operator|(visiting_kind l, visiting_kind r); 301 302 visiting_kind 303 operator&(visiting_kind l, visiting_kind r); 304 305 visiting_kind 306 operator~(visiting_kind l); 307 308 /// The base class for the diff classes that are to be traversed. 309 class diff_traversable_base : public traversable_base 310 { 311 public: 312 virtual bool 313 traverse(diff_node_visitor& v); 314 }; // end struct diff_traversable_base 315 316 /// An enum for the different categories that a diff tree node falls 317 /// into, regarding the kind of changes it represents. 318 /// 319 /// Note that if you add an enumerator to this enum, you need to 320 /// update a few spots accordingly: 321 /// 322 /// * update the ACCESS_CHANGE_CATEGORY enumerator (which is the 323 /// last enumerator of this enum by OR-ing its initializer with 324 /// the new enumerator. 325 /// 326 /// * update the categorize_harmless_diff_node or 327 /// categorize_harmful_diff_node function depending on if the new 328 /// enumerator classifies diff nodes as harmless or harmful. 329 /// 330 /// * update the get_default_harmless_categories_bitmap or 331 /// get_default_harmful_categories_bitmap function as well, just 332 /// like above. 333 /// 334 /// * update the "operator<<(ostream& o, diff_category c)" streaming 335 /// operator so that it can stream the new enumerator to a textual 336 /// output stream. 337 enum diff_category 338 { 339 /// This means the diff node does not carry any (meaningful) change, 340 /// or that it carries changes that have not yet been categorized. 341 NO_CHANGE_CATEGORY = 0, 342 343 /// This means the diff node (or at least one of its descendant 344 /// nodes) carries access related changes, e.g, a private member 345 /// that becomes public. 346 ACCESS_CHANGE_CATEGORY = 1, 347 348 /// This means the diff node (or at least one of its descendant 349 /// nodes) carries a change involving two compatible types. For 350 /// instance a type and its typedefs. 351 COMPATIBLE_TYPE_CHANGE_CATEGORY = 1 << 1, 352 353 /// This means that a diff node in the sub-tree carries a harmless 354 /// declaration name change. This is set only for name changes for 355 /// data members and typedefs. 356 HARMLESS_DECL_NAME_CHANGE_CATEGORY = 1 << 2, 357 358 /// This means that a diff node in the sub-tree carries an addition 359 /// or removal of a non-virtual member function. 360 NON_VIRT_MEM_FUN_CHANGE_CATEGORY = 1 << 3, 361 362 /// This means that a diff node in the sub-tree carries an addition 363 /// or removal of a static data member. 364 STATIC_DATA_MEMBER_CHANGE_CATEGORY = 1 << 4, 365 366 /// This means that a diff node in the sub-tree carries an addition 367 /// of enumerator to an enum type. 368 HARMLESS_ENUM_CHANGE_CATEGORY = 1 << 5, 369 370 /// This means that a diff node in the sub-tree carries an a symbol 371 /// alias change that is harmless. 372 HARMLESS_SYMBOL_ALIAS_CHANGE_CATEGORY = 1 << 6, 373 374 /// This means that a diff node in the sub-tree carries a harmless 375 /// union change. 376 HARMLESS_UNION_CHANGE_CATEGORY = 1 << 7, 377 378 /// This means that a diff node in the sub-tree carries a harmless 379 /// data member change. An example of harmless data member change 380 /// is an anonymous data member that replaces a given data member 381 /// without locally changing the layout. 382 HARMLESS_DATA_MEMBER_CHANGE_CATEGORY = 1 << 8, 383 384 /// This means that a diff node was marked as suppressed by a 385 /// user-provided suppression specification. 386 SUPPRESSED_CATEGORY = 1 << 9, 387 388 /// This means that a diff node was warked as being for a private 389 /// type. That is, the diff node is meant to be suppressed by a 390 /// suppression specification that was auto-generated to filter out 391 /// changes to private types. 392 PRIVATE_TYPE_CATEGORY = 1 << 10, 393 394 /// This means the diff node (or at least one of its descendant 395 /// nodes) carries a change that modifies the size of a type or an 396 /// offset of a type member. Removal or changes of enumerators in a 397 /// enum fall in this category too. 398 SIZE_OR_OFFSET_CHANGE_CATEGORY = 1 << 11, 399 400 /// This means that a diff node in the sub-tree carries an 401 /// incompatible change to a vtable. 402 VIRTUAL_MEMBER_CHANGE_CATEGORY = 1 << 12, 403 404 /// A diff node in this category is redundant. That means it's 405 /// present as a child of a other nodes in the diff tree. 406 REDUNDANT_CATEGORY = 1 << 13, 407 408 /// This means that a diff node in the sub-tree carries a type that 409 /// was declaration-only and that is now defined, or vice versa. 410 TYPE_DECL_ONLY_DEF_CHANGE_CATEGORY = 1 << 14, 411 412 /// A diff node in this category is a function parameter type which 413 /// top cv-qualifiers change. 414 FN_PARM_TYPE_TOP_CV_CHANGE_CATEGORY = 1 << 15, 415 416 /// A diff node in this category has a function parameter type with a 417 /// cv-qualifiers change. 418 FN_PARM_TYPE_CV_CHANGE_CATEGORY = 1 << 16, 419 420 /// A diff node in this category is a function return type with a 421 /// cv-qualifier change. 422 FN_RETURN_TYPE_CV_CHANGE_CATEGORY = 1 << 17, 423 424 /// A diff node in this category is a function (or function type) 425 /// with at least one parameter added or removed. 426 FN_PARM_ADD_REMOVE_CHANGE_CATEGORY = 1 << 18, 427 428 /// A diff node in this category is for a variable which type holds 429 /// a cv-qualifier change. 430 VAR_TYPE_CV_CHANGE_CATEGORY = 1 << 19, 431 432 /// A diff node in this category carries a change from void pointer 433 /// to non-void pointer. 434 VOID_PTR_TO_PTR_CHANGE_CATEGORY = 1 << 20, 435 436 /// A diff node in this category carries a change in the size of the 437 /// array type of a global variable, but the ELF size of the 438 /// variable didn't change. 439 BENIGN_INFINITE_ARRAY_CHANGE_CATEGORY = 1 << 21, 440 441 /// A special enumerator that is the logical 'or' all the 442 /// enumerators above. 443 /// 444 /// This one must stay the last enumerator. Please update it each 445 /// time you add a new enumerator above. 446 EVERYTHING_CATEGORY = 447 ACCESS_CHANGE_CATEGORY 448 | COMPATIBLE_TYPE_CHANGE_CATEGORY 449 | HARMLESS_DECL_NAME_CHANGE_CATEGORY 450 | NON_VIRT_MEM_FUN_CHANGE_CATEGORY 451 | STATIC_DATA_MEMBER_CHANGE_CATEGORY 452 | HARMLESS_ENUM_CHANGE_CATEGORY 453 | HARMLESS_SYMBOL_ALIAS_CHANGE_CATEGORY 454 | HARMLESS_UNION_CHANGE_CATEGORY 455 | HARMLESS_DATA_MEMBER_CHANGE_CATEGORY 456 | SUPPRESSED_CATEGORY 457 | PRIVATE_TYPE_CATEGORY 458 | SIZE_OR_OFFSET_CHANGE_CATEGORY 459 | VIRTUAL_MEMBER_CHANGE_CATEGORY 460 | REDUNDANT_CATEGORY 461 | TYPE_DECL_ONLY_DEF_CHANGE_CATEGORY 462 | FN_PARM_TYPE_TOP_CV_CHANGE_CATEGORY 463 | FN_PARM_TYPE_CV_CHANGE_CATEGORY 464 | FN_RETURN_TYPE_CV_CHANGE_CATEGORY 465 | FN_PARM_ADD_REMOVE_CHANGE_CATEGORY 466 | VAR_TYPE_CV_CHANGE_CATEGORY 467 | VOID_PTR_TO_PTR_CHANGE_CATEGORY 468 | BENIGN_INFINITE_ARRAY_CHANGE_CATEGORY 469 }; // enum diff_category 470 471 diff_category 472 operator|(diff_category c1, diff_category c2); 473 474 diff_category& 475 operator|=(diff_category& c1, diff_category c2); 476 477 diff_category& 478 operator&=(diff_category& c1, diff_category c2); 479 480 diff_category 481 operator^(diff_category c1, diff_category c2); 482 483 diff_category 484 operator&(diff_category c1, diff_category c2); 485 486 diff_category 487 operator~(diff_category c); 488 489 diff_category 490 get_default_harmless_categories_bitmap(); 491 492 diff_category 493 get_default_harmful_categories_bitmap(); 494 495 ostream& 496 operator<<(ostream& o, diff_category); 497 498 class corpus_diff; 499 500 /// This type contains maps. Each map associates a type name to a 501 /// diff of that type. Not all kinds of diffs are present; only those 502 /// that carry leaf changes are, for now. 503 class diff_maps 504 { 505 struct priv; 506 std::unique_ptr<priv> priv_; 507 508 public: 509 510 diff_maps(); 511 512 ~diff_maps(); 513 514 const string_diff_ptr_map& 515 get_type_decl_diff_map() const; 516 517 string_diff_ptr_map& 518 get_type_decl_diff_map(); 519 520 const string_diff_ptr_map& 521 get_enum_diff_map() const; 522 523 string_diff_ptr_map& 524 get_enum_diff_map(); 525 526 const string_diff_ptr_map& 527 get_class_diff_map() const; 528 529 string_diff_ptr_map& 530 get_class_diff_map(); 531 532 const string_diff_ptr_map& 533 get_union_diff_map() const; 534 535 string_diff_ptr_map& 536 get_union_diff_map(); 537 538 const string_diff_ptr_map& 539 get_typedef_diff_map() const; 540 541 string_diff_ptr_map& 542 get_typedef_diff_map(); 543 544 const string_diff_ptr_map& 545 get_array_diff_map() const; 546 547 string_diff_ptr_map& 548 get_array_diff_map(); 549 550 const string_diff_ptr_map& 551 get_reference_diff_map() const; 552 553 string_diff_ptr_map& 554 get_reference_diff_map(); 555 556 const string_diff_ptr_map& 557 get_fn_parm_diff_map() const; 558 559 string_diff_ptr_map& 560 get_fn_parm_diff_map(); 561 562 const string_diff_ptr_map& 563 get_function_type_diff_map() const; 564 565 string_diff_ptr_map& 566 get_function_type_diff_map(); 567 568 const string_diff_ptr_map& 569 get_function_decl_diff_map() const; 570 571 string_diff_ptr_map& 572 get_function_decl_diff_map(); 573 574 const string_diff_ptr_map& 575 get_var_decl_diff_map() const; 576 577 string_diff_ptr_map& 578 get_var_decl_diff_map(); 579 580 const string_diff_ptr_map& 581 get_distinct_diff_map() const; 582 583 string_diff_ptr_map& 584 get_distinct_diff_map(); 585 586 bool 587 insert_diff_node(const diff *d, 588 const type_or_decl_base_sptr& impacted_iface); 589 590 artifact_sptr_set_type* 591 lookup_impacted_interfaces(const diff *d) const; 592 }; // end class diff_maps 593 594 /// A convenience typedef for a shared pointer to @ref corpus_diff. 595 typedef shared_ptr<corpus_diff> corpus_diff_sptr; 596 597 /// The context of the diff. This type holds various bits of 598 /// information that is going to be used throughout the diffing of two 599 /// entities and the reporting that follows. 600 class diff_context 601 { 602 struct priv; 603 std::unique_ptr<priv> priv_; 604 605 diff_sptr 606 has_diff_for(const type_or_decl_base_sptr first, 607 const type_or_decl_base_sptr second) const; 608 609 diff_sptr 610 has_diff_for_types(const type_base_sptr first, 611 const type_base_sptr second) const; 612 613 const diff* 614 has_diff_for(const diff* d) const; 615 616 diff_sptr 617 has_diff_for(const diff_sptr d) const; 618 619 void 620 add_diff(const type_or_decl_base_sptr first, 621 const type_or_decl_base_sptr second, 622 const diff_sptr d); 623 624 void 625 add_diff(const diff_sptr d); 626 627 void 628 add_diff(const diff* d); 629 630 void 631 set_canonical_diff_for(const type_or_decl_base_sptr first, 632 const type_or_decl_base_sptr second, 633 const diff_sptr); 634 635 diff_sptr 636 set_or_get_canonical_diff_for(const type_or_decl_base_sptr first, 637 const type_or_decl_base_sptr second, 638 const diff_sptr canonical_diff); 639 640 public: 641 diff_context(); 642 643 ~diff_context(); 644 645 void 646 set_corpus_diff(const corpus_diff_sptr&); 647 648 const corpus_diff_sptr& 649 get_corpus_diff() const; 650 651 corpus_sptr 652 get_first_corpus() const; 653 654 corpus_sptr 655 get_second_corpus() const; 656 657 reporter_base_sptr 658 get_reporter() const; 659 660 void 661 set_reporter(reporter_base_sptr&); 662 663 diff_sptr 664 get_canonical_diff_for(const type_or_decl_base_sptr first, 665 const type_or_decl_base_sptr second) const; 666 667 diff_sptr 668 get_canonical_diff_for(const diff_sptr d) const; 669 670 void 671 initialize_canonical_diff(const diff_sptr diff); 672 673 void 674 keep_diff_alive(diff_sptr&); 675 676 diff* 677 diff_has_been_visited(const diff*) const; 678 679 diff_sptr 680 diff_has_been_visited(const diff_sptr) const; 681 682 void 683 mark_diff_as_visited(const diff*); 684 685 void 686 forget_visited_diffs(); 687 688 void 689 mark_last_diff_visited_per_class_of_equivalence(const diff*); 690 691 void 692 clear_last_diffs_visited_per_class_of_equivalence(); 693 694 const diff* 695 get_last_visited_diff_of_class_of_equivalence(const diff*); 696 697 void 698 forbid_visiting_a_node_twice(bool f); 699 700 bool 701 visiting_a_node_twice_is_forbidden() const; 702 703 void 704 forbid_visiting_a_node_twice_per_interface(bool); 705 706 bool 707 visiting_a_node_twice_is_forbidden_per_interface() const; 708 709 diff_category 710 get_allowed_category() const; 711 712 void 713 set_allowed_category(diff_category c); 714 715 void 716 switch_categories_on(diff_category c); 717 718 void 719 switch_categories_off(diff_category c); 720 721 const filtering::filters& 722 diff_filters() const; 723 724 void 725 add_diff_filter(filtering::filter_base_sptr); 726 727 void 728 maybe_apply_filters(diff_sptr diff); 729 730 void 731 maybe_apply_filters(corpus_diff_sptr diff); 732 733 suppr::suppressions_type& 734 suppressions() const; 735 736 void 737 add_suppression(const suppr::suppression_sptr suppr); 738 739 void 740 add_suppressions(const suppr::suppressions_type& supprs); 741 742 void 743 show_leaf_changes_only(bool f); 744 745 bool 746 show_leaf_changes_only() const; 747 748 bool 749 show_hex_values() const; 750 751 void 752 show_hex_values(bool f); 753 754 bool 755 show_offsets_sizes_in_bits() const; 756 757 void 758 show_offsets_sizes_in_bits(bool f); 759 760 void 761 show_relative_offset_changes(bool f); 762 763 bool 764 show_relative_offset_changes(void); 765 766 void 767 show_stats_only(bool f); 768 769 bool 770 show_stats_only() const; 771 772 void 773 show_soname_change(bool f); 774 775 bool 776 show_soname_change() const; 777 778 void 779 show_architecture_change(bool f); 780 781 bool 782 show_architecture_change() const; 783 784 void 785 show_deleted_fns(bool f); 786 787 bool 788 show_deleted_fns() const; 789 790 void 791 show_changed_fns(bool f); 792 793 bool 794 show_changed_fns() const; 795 796 void 797 show_added_fns(bool f); 798 799 bool 800 show_added_fns() const; 801 802 void 803 show_deleted_vars(bool f); 804 805 bool 806 show_deleted_vars() const; 807 808 void 809 show_changed_vars(bool f); 810 811 bool 812 show_changed_vars() const; 813 814 void 815 show_added_vars(bool f); 816 817 bool 818 show_added_vars() const; 819 820 bool 821 show_linkage_names() const; 822 823 void 824 show_linkage_names(bool f); 825 826 bool 827 show_locs() const; 828 829 void 830 show_locs(bool f); 831 832 bool 833 show_redundant_changes() const; 834 835 void 836 show_redundant_changes(bool f); 837 838 bool 839 show_symbols_unreferenced_by_debug_info() const; 840 841 void 842 show_symbols_unreferenced_by_debug_info(bool f); 843 844 bool 845 show_added_symbols_unreferenced_by_debug_info() const; 846 847 void 848 show_added_symbols_unreferenced_by_debug_info(bool f); 849 850 void show_unreachable_types(bool f); 851 852 bool show_unreachable_types(); 853 854 bool 855 show_impacted_interfaces() const; 856 857 void 858 show_impacted_interfaces(bool f); 859 860 void 861 default_output_stream(ostream*); 862 863 ostream* 864 default_output_stream(); 865 866 void 867 error_output_stream(ostream*); 868 869 ostream* 870 error_output_stream() const; 871 872 bool 873 dump_diff_tree() const; 874 875 void 876 dump_diff_tree(bool f); 877 878 void 879 do_dump_diff_tree(const diff_sptr) const; 880 881 void 882 do_dump_diff_tree(const corpus_diff_sptr) const; 883 884 friend class_diff_sptr 885 compute_diff(const class_decl_sptr first, 886 const class_decl_sptr second, 887 diff_context_sptr ctxt); 888 };//end struct diff_context. 889 890 /// The abstraction of a change between two ABI artifacts, a.k.a an 891 /// artifact change. 892 /// 893 /// In the grand scheme of things, a diff is strongly typed; for 894 /// instance, a change between two enums is represented by an 895 /// enum_diff type. A change between two function_type is represented 896 /// by a function_type_diff type and a change between two class_decl 897 /// is represented by a class_diff type. All of these types derive 898 /// from the @ref diff parent class. 899 /// 900 /// An artifact change D can have one (or more) details named D'. A 901 /// detail is an artifact change that "belongs" to another one. Here, 902 /// D' belongs to D. Or said otherwise, D' is a child change of D. 903 /// Said otherwise, D and D' are related, and the relation is a 904 /// "child relation". 905 /// 906 /// For instance, if we consider a change carried by a class_diff, the 907 /// detail change might be a change on one data member of the class. 908 /// In other word, the class_diff change might have a child diff node 909 /// that would be a var_diff node. 910 /// 911 /// There are two ways to get the child var_diff node (for the data 912 /// member change detail) of the class_diff. 913 /// 914 /// The first way is through the typed API, that is, through the 915 /// class_diff::sorted_changed_data_members() member function which 916 /// returns var_diff nodes. 917 /// 918 /// The second way is through the generic API, that is, through the 919 /// diff::children_nodes() member function which returns generic diff 920 /// nodes. This second way enables us to walk the diff nodes graph in 921 /// a generic way, regardless of the types of the diff nodes. 922 /// 923 /// Said otherwise, there are two views for a given diff node. There 924 /// is typed view, and there is the generic view. In the typed view, 925 /// the details are accessed through the typed API. In the generic 926 /// view, the details are gathered through the generic view. 927 /// 928 /// 929 /// Please read more about the @ref DiffNode "IR" of the comparison 930 /// engine to learn more about this. 931 /// 932 /// This type encapsulates an edit script (a set of insertions and 933 /// deletions) for two constructs that are to be diff'ed. The two 934 /// constructs are called the "subjects" of the diff. 935 class diff : public diff_traversable_base 936 { 937 friend class diff_context; 938 939 // Forbidden 940 diff(); 941 942 protected: 943 struct priv; 944 std::unique_ptr<priv> priv_; 945 946 diff(type_or_decl_base_sptr first_subject, 947 type_or_decl_base_sptr second_subject); 948 949 diff(type_or_decl_base_sptr first_subject, 950 type_or_decl_base_sptr second_subject, 951 diff_context_sptr ctxt); 952 953 void 954 begin_traversing(); 955 956 void 957 end_traversing(); 958 959 virtual void 960 finish_diff_type(); 961 962 void 963 set_canonical_diff(diff *); 964 965 public: 966 type_or_decl_base_sptr 967 first_subject() const; 968 969 type_or_decl_base_sptr 970 second_subject() const; 971 972 const vector<diff*>& 973 children_nodes() const; 974 975 const diff* 976 parent_node() const; 977 978 diff* get_canonical_diff() const; 979 980 bool 981 is_traversing() const; 982 983 void 984 append_child_node(diff_sptr); 985 986 const diff_context_sptr 987 context() const; 988 989 void 990 context(diff_context_sptr c); 991 992 bool 993 currently_reporting() const; 994 995 void 996 currently_reporting(bool f) const; 997 998 bool 999 reported_once() const; 1000 1001 void 1002 reported_once(bool f) const; 1003 1004 diff_category 1005 get_category() const; 1006 1007 diff_category 1008 get_local_category() const; 1009 1010 diff_category 1011 get_class_of_equiv_category() const; 1012 1013 diff_category 1014 add_to_category(diff_category c); 1015 1016 diff_category 1017 add_to_local_category(diff_category c); 1018 1019 void 1020 add_to_local_and_inherited_categories(diff_category c); 1021 1022 diff_category 1023 remove_from_category(diff_category c); 1024 1025 diff_category 1026 remove_from_local_category(diff_category c); 1027 1028 void 1029 set_category(diff_category c); 1030 1031 void 1032 set_local_category(diff_category c); 1033 1034 bool 1035 is_filtered_out() const; 1036 1037 bool 1038 is_filtered_out_wrt_non_inherited_categories() const; 1039 1040 bool 1041 is_suppressed() const; 1042 1043 bool 1044 is_suppressed(bool &is_private_type) const; 1045 1046 bool 1047 to_be_reported() const; 1048 1049 bool 1050 has_local_changes_to_be_reported() const; 1051 1052 virtual const string& 1053 get_pretty_representation() const; 1054 1055 /// This constructs the relation between this diff node and its 1056 /// detail diff nodes, in the generic view of the diff node. 1057 /// 1058 /// Each specific typed diff node should implement how the typed 1059 /// view "links" itself to its detail nodes in the generic sense. 1060 virtual void 1061 chain_into_hierarchy(); 1062 1063 /// Pure interface to get the length of the changes encapsulated by 1064 /// this diff. A length of zero means that the current instance of 1065 /// @ref diff doesn't carry any change. 1066 /// 1067 /// This is to be implemented by all descendants of this type. 1068 virtual bool 1069 has_changes() const = 0; 1070 1071 /// Pure interface to know if the current instance of @diff carries 1072 /// a local change. A local change is a change that is on the @ref 1073 /// diff object itself, as opposed to a change that is carried by 1074 /// some of its children nodes. 1075 /// 1076 /// This is to be implemented by all descendants of this type. 1077 virtual enum change_kind 1078 has_local_changes() const = 0; 1079 1080 /// Pure interface to report the diff in a serialized form that is 1081 /// legible for the user. 1082 /// 1083 /// Note that the serializd report has to leave one empty line at 1084 /// the end of its content. 1085 /// 1086 /// @param out the output stream to serialize the report to. 1087 /// 1088 /// @param indent the indentation string to use. 1089 virtual void 1090 report(ostream& out, const string& indent = "") const = 0; 1091 1092 virtual bool 1093 traverse(diff_node_visitor& v); 1094 };// end class diff 1095 1096 diff_sptr 1097 compute_diff(const decl_base_sptr, 1098 const decl_base_sptr, 1099 diff_context_sptr ctxt); 1100 1101 diff_sptr 1102 compute_diff(const type_base_sptr, 1103 const type_base_sptr, 1104 diff_context_sptr ctxt); 1105 1106 /// The base class of diff between types. 1107 class type_diff_base : public diff 1108 { 1109 struct priv; 1110 std::unique_ptr<priv> priv_; 1111 1112 type_diff_base(); 1113 1114 protected: 1115 type_diff_base(type_base_sptr first_subject, 1116 type_base_sptr second_subject, 1117 diff_context_sptr ctxt); 1118 1119 public: 1120 1121 virtual enum change_kind 1122 has_local_changes() const = 0; 1123 1124 virtual ~type_diff_base(); 1125 };// end class type_diff_base 1126 1127 /// The base class of diff between decls. 1128 class decl_diff_base : public diff 1129 { 1130 struct priv; 1131 std::unique_ptr<priv> priv_; 1132 1133 protected: 1134 decl_diff_base(decl_base_sptr first_subject, 1135 decl_base_sptr second_subject, 1136 diff_context_sptr ctxt); 1137 1138 public: 1139 1140 virtual enum change_kind 1141 has_local_changes() const = 0; 1142 1143 virtual ~decl_diff_base(); 1144 };// end class decl_diff_base 1145 1146 string 1147 get_pretty_representation(diff*); 1148 1149 class distinct_diff; 1150 1151 /// Convenience typedef for a shared pointer to distinct_types_diff 1152 typedef shared_ptr<distinct_diff> distinct_diff_sptr; 1153 1154 /// An abstraction of a diff between entities that are of a different 1155 /// kind (disctinct). 1156 class distinct_diff : public diff 1157 { 1158 struct priv; 1159 std::unique_ptr<priv> priv_; 1160 1161 protected: 1162 distinct_diff(type_or_decl_base_sptr first, 1163 type_or_decl_base_sptr second, 1164 diff_context_sptr ctxt = diff_context_sptr()); 1165 1166 public: 1167 1168 const type_or_decl_base_sptr 1169 first() const; 1170 1171 const type_or_decl_base_sptr 1172 second() const; 1173 1174 const diff_sptr 1175 compatible_child_diff() const; 1176 1177 virtual const string& 1178 get_pretty_representation() const; 1179 1180 virtual bool 1181 has_changes() const; 1182 1183 virtual enum change_kind 1184 has_local_changes() const; 1185 1186 virtual void 1187 report(ostream& out, const string& indent = "") const; 1188 1189 virtual void 1190 chain_into_hierarchy(); 1191 1192 static bool 1193 entities_are_of_distinct_kinds(type_or_decl_base_sptr first, 1194 type_or_decl_base_sptr second); 1195 1196 friend distinct_diff_sptr 1197 compute_diff_for_distinct_kinds(const type_or_decl_base_sptr first, 1198 const type_or_decl_base_sptr second, 1199 diff_context_sptr ctxt); 1200 };// end class distinct_types_diff 1201 1202 distinct_diff_sptr 1203 compute_diff_for_distinct_kinds(const type_or_decl_base_sptr, 1204 const type_or_decl_base_sptr, 1205 diff_context_sptr ctxt); 1206 1207 /// Abstracts a diff between two instances of @ref var_decl 1208 class var_diff : public decl_diff_base 1209 { 1210 struct priv; 1211 std::unique_ptr<priv> priv_; 1212 1213 protected: 1214 var_diff(var_decl_sptr first, 1215 var_decl_sptr second, 1216 diff_sptr type_diff, 1217 diff_context_sptr ctxt = diff_context_sptr()); 1218 1219 public: 1220 var_decl_sptr 1221 first_var() const; 1222 1223 var_decl_sptr 1224 second_var() const; 1225 1226 diff_sptr 1227 type_diff() const; 1228 1229 virtual void 1230 chain_into_hierarchy(); 1231 1232 virtual bool 1233 has_changes() const; 1234 1235 virtual enum change_kind 1236 has_local_changes() const; 1237 1238 virtual void 1239 report(ostream& out, const string& indent = "") const; 1240 1241 virtual const string& 1242 get_pretty_representation() const; 1243 1244 friend var_diff_sptr 1245 compute_diff(const var_decl_sptr first, 1246 const var_decl_sptr second, 1247 diff_context_sptr ctxt); 1248 };// end class var_diff 1249 1250 var_diff_sptr 1251 compute_diff(const var_decl_sptr, const var_decl_sptr, diff_context_sptr); 1252 1253 class pointer_diff; 1254 /// Convenience typedef for a shared pointer on a @ref 1255 /// pointer_diff type. 1256 typedef shared_ptr<pointer_diff> pointer_diff_sptr; 1257 1258 /// The abstraction of a diff between two pointers. 1259 class pointer_diff : public type_diff_base 1260 { 1261 struct priv; 1262 std::unique_ptr<priv> priv_; 1263 1264 protected: 1265 pointer_diff(pointer_type_def_sptr first, 1266 pointer_type_def_sptr second, 1267 diff_sptr underlying_type_diff, 1268 diff_context_sptr ctxt = diff_context_sptr()); 1269 1270 public: 1271 const pointer_type_def_sptr 1272 first_pointer() const; 1273 1274 const pointer_type_def_sptr 1275 second_pointer() const; 1276 1277 diff_sptr 1278 underlying_type_diff() const; 1279 1280 void 1281 underlying_type_diff(const diff_sptr); 1282 1283 virtual const string& 1284 get_pretty_representation() const; 1285 1286 virtual bool 1287 has_changes() const; 1288 1289 virtual enum change_kind 1290 has_local_changes() const; 1291 1292 virtual void 1293 report(ostream&, const string& indent = "") const; 1294 1295 virtual void 1296 chain_into_hierarchy(); 1297 1298 friend pointer_diff_sptr 1299 compute_diff(pointer_type_def_sptr first, 1300 pointer_type_def_sptr second, 1301 diff_context_sptr ctxt); 1302 };// end class pointer_diff 1303 1304 pointer_diff_sptr 1305 compute_diff(pointer_type_def_sptr first, 1306 pointer_type_def_sptr second, 1307 diff_context_sptr ctxt); 1308 1309 class reference_diff; 1310 1311 /// Convenience typedef for a shared pointer on a @ref 1312 /// reference_diff type. 1313 typedef shared_ptr<reference_diff> reference_diff_sptr; 1314 1315 /// The abstraction of a diff between two references. 1316 class reference_diff : public type_diff_base 1317 { 1318 struct priv; 1319 std::unique_ptr<priv> priv_; 1320 1321 protected: 1322 reference_diff(const reference_type_def_sptr first, 1323 const reference_type_def_sptr second, 1324 diff_sptr underlying, 1325 diff_context_sptr ctxt = diff_context_sptr()); 1326 1327 public: 1328 reference_type_def_sptr 1329 first_reference() const; 1330 1331 reference_type_def_sptr 1332 second_reference() const; 1333 1334 const diff_sptr& 1335 underlying_type_diff() const; 1336 1337 diff_sptr& 1338 underlying_type_diff(diff_sptr); 1339 1340 virtual const string& 1341 get_pretty_representation() const; 1342 1343 virtual bool 1344 has_changes() const; 1345 1346 virtual enum change_kind 1347 has_local_changes() const; 1348 1349 virtual void 1350 report(ostream&, const string& indent = "") const; 1351 1352 virtual void 1353 chain_into_hierarchy(); 1354 1355 friend reference_diff_sptr 1356 compute_diff(reference_type_def_sptr first, 1357 reference_type_def_sptr second, 1358 diff_context_sptr ctxt); 1359 };// end class reference_diff 1360 1361 reference_diff_sptr 1362 compute_diff(reference_type_def_sptr first, 1363 reference_type_def_sptr second, 1364 diff_context_sptr ctxt); 1365 1366 class array_diff; 1367 1368 /// Convenience typedef for a shared pointer on a @ref 1369 /// array_diff type. 1370 typedef shared_ptr<array_diff> array_diff_sptr; 1371 1372 /// The abstraction of a diff between two arrays. 1373 class array_diff : public type_diff_base 1374 { 1375 struct priv; 1376 std::unique_ptr<priv> priv_; 1377 1378 protected: 1379 array_diff(const array_type_def_sptr first, 1380 const array_type_def_sptr second, 1381 diff_sptr element_type_diff, 1382 diff_context_sptr ctxt = diff_context_sptr()); 1383 1384 public: 1385 const array_type_def_sptr 1386 first_array() const; 1387 1388 const array_type_def_sptr 1389 second_array() const; 1390 1391 const diff_sptr& 1392 element_type_diff() const; 1393 1394 void 1395 element_type_diff(diff_sptr); 1396 1397 virtual const string& 1398 get_pretty_representation() const; 1399 1400 virtual bool 1401 has_changes() const; 1402 1403 virtual enum change_kind 1404 has_local_changes() const; 1405 1406 virtual void 1407 report(ostream&, const string& indent = "") const; 1408 1409 virtual void 1410 chain_into_hierarchy(); 1411 1412 friend array_diff_sptr 1413 compute_diff(array_type_def_sptr first, 1414 array_type_def_sptr second, 1415 diff_context_sptr ctxt); 1416 };// end class array_diff 1417 1418 array_diff_sptr 1419 compute_diff(array_type_def_sptr first, 1420 array_type_def_sptr second, 1421 diff_context_sptr ctxt); 1422 1423 class qualified_type_diff; 1424 typedef class shared_ptr<qualified_type_diff> qualified_type_diff_sptr; 1425 1426 /// Abstraction of a diff between two qualified types. 1427 class qualified_type_diff : public type_diff_base 1428 { 1429 struct priv; 1430 std::unique_ptr<priv> priv_; 1431 1432 protected: 1433 qualified_type_diff(qualified_type_def_sptr first, 1434 qualified_type_def_sptr second, 1435 diff_sptr underling, 1436 diff_context_sptr ctxt = diff_context_sptr()); 1437 1438 public: 1439 const qualified_type_def_sptr 1440 first_qualified_type() const; 1441 1442 const qualified_type_def_sptr 1443 second_qualified_type() const; 1444 1445 diff_sptr 1446 underlying_type_diff() const; 1447 1448 void 1449 underlying_type_diff(const diff_sptr); 1450 1451 diff_sptr 1452 leaf_underlying_type_diff() const; 1453 1454 virtual const string& 1455 get_pretty_representation() const; 1456 1457 virtual bool 1458 has_changes() const; 1459 1460 virtual enum change_kind 1461 has_local_changes() const; 1462 1463 virtual void 1464 report(ostream&, const string& indent = "") const; 1465 1466 virtual void 1467 chain_into_hierarchy(); 1468 1469 friend qualified_type_diff_sptr 1470 compute_diff(const qualified_type_def_sptr first, 1471 const qualified_type_def_sptr second, 1472 diff_context_sptr ctxt); 1473 };// end class qualified_type_diff. 1474 1475 qualified_type_diff_sptr 1476 compute_diff(const qualified_type_def_sptr first, 1477 const qualified_type_def_sptr second, 1478 diff_context_sptr ctxt); 1479 1480 class enum_diff; 1481 typedef shared_ptr<enum_diff> enum_diff_sptr; 1482 1483 /// Abstraction of a diff between two enums. 1484 class enum_diff : public type_diff_base 1485 { 1486 struct priv; 1487 std::unique_ptr<priv> priv_; 1488 1489 void 1490 clear_lookup_tables(); 1491 1492 bool 1493 lookup_tables_empty() const; 1494 1495 void 1496 ensure_lookup_tables_populated(); 1497 1498 protected: 1499 enum_diff(const enum_type_decl_sptr, 1500 const enum_type_decl_sptr, 1501 const diff_sptr, 1502 diff_context_sptr ctxt = diff_context_sptr()); 1503 1504 public: 1505 const enum_type_decl_sptr 1506 first_enum() const; 1507 1508 const enum_type_decl_sptr 1509 second_enum() const; 1510 1511 diff_sptr 1512 underlying_type_diff() const; 1513 1514 const string_enumerator_map& 1515 deleted_enumerators() const; 1516 1517 const string_enumerator_map& 1518 inserted_enumerators() const; 1519 1520 const string_changed_enumerator_map& 1521 changed_enumerators() const; 1522 1523 virtual const string& 1524 get_pretty_representation() const; 1525 1526 virtual bool 1527 has_changes() const; 1528 1529 virtual enum change_kind 1530 has_local_changes() const; 1531 1532 virtual void 1533 report(ostream&, const string& indent = "") const; 1534 1535 virtual void 1536 chain_into_hierarchy(); 1537 1538 friend enum_diff_sptr 1539 compute_diff(const enum_type_decl_sptr first, 1540 const enum_type_decl_sptr second, 1541 diff_context_sptr ctxt); 1542 };//end class enum_diff; 1543 1544 enum_diff_sptr 1545 compute_diff(const enum_type_decl_sptr, 1546 const enum_type_decl_sptr, 1547 diff_context_sptr); 1548 1549 /// This is the base class of @ref class_diff and @ref union_diff. 1550 class class_or_union_diff : public type_diff_base 1551 { 1552 protected: 1553 struct priv; 1554 typedef std::unique_ptr<priv> priv_ptr; 1555 priv_ptr priv_; 1556 1557 void 1558 clear_lookup_tables(void); 1559 1560 bool 1561 lookup_tables_empty(void) const; 1562 1563 void 1564 ensure_lookup_tables_populated(void) const; 1565 1566 void 1567 allocate_priv_data(); 1568 1569 protected: 1570 class_or_union_diff(class_or_union_sptr first_scope, 1571 class_or_union_sptr second_scope, 1572 diff_context_sptr ctxt = diff_context_sptr()); 1573 1574 public: 1575 1576 const class_or_union_diff::priv_ptr& 1577 get_priv() const; 1578 1579 //TODO: add change of the name of the type. 1580 1581 virtual ~class_or_union_diff(); 1582 1583 class_or_union_sptr 1584 first_class_or_union() const; 1585 1586 class_or_union_sptr 1587 second_class_or_union() const; 1588 1589 const edit_script& 1590 member_types_changes() const; 1591 1592 edit_script& 1593 member_types_changes(); 1594 1595 const edit_script& 1596 data_members_changes() const; 1597 1598 edit_script& 1599 data_members_changes(); 1600 1601 const string_decl_base_sptr_map& 1602 inserted_data_members() const; 1603 1604 const string_decl_base_sptr_map& 1605 deleted_data_members() const; 1606 1607 const edit_script& 1608 member_fns_changes() const; 1609 1610 edit_script& 1611 member_fns_changes(); 1612 1613 const function_decl_diff_sptrs_type& 1614 changed_member_fns() const; 1615 1616 const string_member_function_sptr_map& 1617 deleted_member_fns() const; 1618 1619 const string_member_function_sptr_map& 1620 inserted_member_fns() const; 1621 1622 const var_diff_sptrs_type& 1623 sorted_changed_data_members() const; 1624 1625 size_t 1626 count_filtered_changed_data_members(bool local_only = false) const; 1627 1628 const var_diff_sptrs_type& 1629 sorted_subtype_changed_data_members() const; 1630 1631 size_t 1632 count_filtered_subtype_changed_data_members(bool local_only = false) const; 1633 1634 const string_decl_base_sptr_map& 1635 data_members_replaced_by_adms() const; 1636 1637 const changed_var_sptrs_type& 1638 ordered_data_members_replaced_by_adms() const; 1639 1640 const edit_script& 1641 member_fn_tmpls_changes() const; 1642 1643 edit_script& 1644 member_fn_tmpls_changes(); 1645 1646 const edit_script& 1647 member_class_tmpls_changes() const; 1648 1649 edit_script& 1650 member_class_tmpls_changes(); 1651 1652 virtual bool 1653 has_changes() const; 1654 1655 virtual enum change_kind 1656 has_local_changes() const; 1657 1658 virtual void 1659 report(ostream&, const string& indent = "") const; 1660 1661 virtual void 1662 chain_into_hierarchy(); 1663 1664 friend class default_reporter; 1665 }; // end class_or_union_diff; 1666 1667 /// This type abstracts changes for a class_decl. 1668 class class_diff : public class_or_union_diff 1669 { 1670 struct priv; 1671 typedef std::unique_ptr<priv> priv_ptr; 1672 priv_ptr priv_; 1673 1674 const priv_ptr& get_priv()const; 1675 1676 void 1677 clear_lookup_tables(void); 1678 1679 bool 1680 lookup_tables_empty(void) const; 1681 1682 void 1683 ensure_lookup_tables_populated(void) const; 1684 1685 void 1686 allocate_priv_data(); 1687 1688 protected: 1689 class_diff(class_decl_sptr first_scope, 1690 class_decl_sptr second_scope, 1691 diff_context_sptr ctxt = diff_context_sptr()); 1692 1693 public: 1694 //TODO: add change of the name of the type. 1695 1696 virtual ~class_diff(); 1697 1698 class_decl_sptr 1699 first_class_decl() const; 1700 1701 class_decl_sptr 1702 second_class_decl() const; 1703 1704 const edit_script& 1705 base_changes() const; 1706 1707 edit_script& 1708 base_changes(); 1709 1710 const string_base_sptr_map& 1711 deleted_bases() const; 1712 1713 const string_base_sptr_map& 1714 inserted_bases() const; 1715 1716 const base_diff_sptrs_type& 1717 changed_bases(); 1718 1719 const vector<class_decl::base_spec_sptr>& 1720 moved_bases() const; 1721 1722 virtual bool 1723 has_changes() const; 1724 1725 virtual enum change_kind 1726 has_local_changes() const; 1727 1728 virtual const string& 1729 get_pretty_representation() const; 1730 1731 virtual void 1732 report(ostream&, const string& indent = "") const; 1733 1734 virtual void 1735 chain_into_hierarchy(); 1736 1737 friend class_diff_sptr 1738 compute_diff(const class_decl_sptr first, 1739 const class_decl_sptr second, 1740 diff_context_sptr ctxt); 1741 1742 friend class default_reporter; 1743 };// end class_diff 1744 1745 class_diff_sptr 1746 compute_diff(const class_decl_sptr first, 1747 const class_decl_sptr second, 1748 diff_context_sptr ctxt); 1749 1750 class union_diff; 1751 typedef shared_ptr<union_diff> union_diff_sptr; 1752 1753 class union_diff : public class_or_union_diff 1754 { 1755 void 1756 clear_lookup_tables(void); 1757 1758 bool 1759 lookup_tables_empty(void) const; 1760 1761 void 1762 ensure_lookup_tables_populated(void) const; 1763 1764 void 1765 allocate_priv_data(); 1766 1767 protected: 1768 union_diff(union_decl_sptr first_union, 1769 union_decl_sptr second_union, 1770 diff_context_sptr ctxt = diff_context_sptr()); 1771 1772 public: 1773 1774 virtual ~union_diff(); 1775 1776 union_decl_sptr 1777 first_union_decl() const; 1778 1779 union_decl_sptr 1780 second_union_decl() const; 1781 1782 virtual const string& 1783 get_pretty_representation() const; 1784 1785 virtual void 1786 report(ostream&, const string& indent = "") const; 1787 1788 friend union_diff_sptr 1789 compute_diff(const union_decl_sptr first, 1790 const union_decl_sptr second, 1791 diff_context_sptr ctxt); 1792 }; // end class union_diff 1793 1794 union_diff_sptr 1795 compute_diff(const union_decl_sptr first, 1796 const union_decl_sptr second, 1797 diff_context_sptr ctxt); 1798 1799 /// An abstraction of a diff between two instances of class_decl::base_spec. 1800 class base_diff : public diff 1801 { 1802 struct priv; 1803 std::unique_ptr<priv> priv_; 1804 1805 protected: 1806 base_diff(class_decl::base_spec_sptr first, 1807 class_decl::base_spec_sptr second, 1808 class_diff_sptr underlying, 1809 diff_context_sptr ctxt = diff_context_sptr()); 1810 1811 public: 1812 class_decl::base_spec_sptr 1813 first_base() const; 1814 1815 class_decl::base_spec_sptr 1816 second_base() const; 1817 1818 const class_diff_sptr 1819 get_underlying_class_diff() const; 1820 1821 void 1822 set_underlying_class_diff(class_diff_sptr d); 1823 1824 virtual const string& 1825 get_pretty_representation() const; 1826 1827 virtual bool 1828 has_changes() const; 1829 1830 virtual enum change_kind 1831 has_local_changes() const; 1832 1833 virtual void 1834 report(ostream&, const string& indent = "") const; 1835 1836 virtual void 1837 chain_into_hierarchy(); 1838 1839 friend base_diff_sptr 1840 compute_diff(const class_decl::base_spec_sptr first, 1841 const class_decl::base_spec_sptr second, 1842 diff_context_sptr ctxt); 1843 };// end class base_diff 1844 1845 base_diff_sptr 1846 compute_diff(const class_decl::base_spec_sptr first, 1847 const class_decl::base_spec_sptr second, 1848 diff_context_sptr ctxt); 1849 1850 class scope_diff; 1851 1852 /// Convenience typedef for a shared pointer on a @ref scope_diff. 1853 typedef shared_ptr<scope_diff> scope_diff_sptr; 1854 1855 /// An abstractions of the changes between two scopes. 1856 class scope_diff : public diff 1857 { 1858 struct priv; 1859 std::unique_ptr<priv> priv_; 1860 1861 bool 1862 lookup_tables_empty() const; 1863 1864 void 1865 clear_lookup_tables(); 1866 1867 void 1868 ensure_lookup_tables_populated(); 1869 1870 protected: 1871 scope_diff(scope_decl_sptr first_scope, 1872 scope_decl_sptr second_scope, 1873 diff_context_sptr ctxt = diff_context_sptr()); 1874 1875 public: 1876 1877 friend scope_diff_sptr 1878 compute_diff(const scope_decl_sptr first, 1879 const scope_decl_sptr second, 1880 scope_diff_sptr d, 1881 diff_context_sptr ctxt); 1882 1883 friend scope_diff_sptr 1884 compute_diff(const scope_decl_sptr first_scope, 1885 const scope_decl_sptr second_scope, 1886 diff_context_sptr ctxt); 1887 1888 const scope_decl_sptr 1889 first_scope() const; 1890 1891 const scope_decl_sptr 1892 second_scope() const; 1893 1894 const edit_script& 1895 member_changes() const; 1896 1897 edit_script& 1898 member_changes(); 1899 1900 const decl_base_sptr 1901 deleted_member_at(unsigned index) const; 1902 1903 const decl_base_sptr 1904 deleted_member_at(vector<deletion>::const_iterator) const; 1905 1906 const decl_base_sptr 1907 inserted_member_at(unsigned i); 1908 1909 const decl_base_sptr 1910 inserted_member_at(vector<unsigned>::const_iterator i); 1911 1912 const diff_sptrs_type& 1913 changed_types() const; 1914 1915 const diff_sptrs_type& 1916 changed_decls() const; 1917 1918 const string_decl_base_sptr_map& 1919 removed_types() const; 1920 1921 const string_decl_base_sptr_map& 1922 removed_decls() const; 1923 1924 const string_decl_base_sptr_map& 1925 added_types() const; 1926 1927 const string_decl_base_sptr_map& 1928 added_decls() const; 1929 1930 virtual const string& 1931 get_pretty_representation() const; 1932 1933 virtual bool 1934 has_changes() const; 1935 1936 virtual enum change_kind 1937 has_local_changes() const; 1938 1939 virtual void 1940 report(ostream& out, const string& indent = "") const; 1941 1942 virtual void 1943 chain_into_hierarchy(); 1944 1945 friend class default_reporter; 1946 friend class leaf_reporter; 1947 };// end class scope_diff 1948 1949 scope_diff_sptr 1950 compute_diff(const scope_decl_sptr first, 1951 const scope_decl_sptr second, 1952 scope_diff_sptr d, 1953 diff_context_sptr ctxt); 1954 1955 scope_diff_sptr 1956 compute_diff(const scope_decl_sptr first_scope, 1957 const scope_decl_sptr second_scope, 1958 diff_context_sptr ctxt); 1959 1960 /// Abstraction of a diff between two function parameters. 1961 class fn_parm_diff : public decl_diff_base 1962 { 1963 struct priv; 1964 std::unique_ptr<priv> priv_; 1965 1966 fn_parm_diff(const function_decl::parameter_sptr first, 1967 const function_decl::parameter_sptr second, 1968 diff_context_sptr ctxt); 1969 1970 public: 1971 friend fn_parm_diff_sptr 1972 compute_diff(const function_decl::parameter_sptr first, 1973 const function_decl::parameter_sptr second, 1974 diff_context_sptr ctxt); 1975 1976 const function_decl::parameter_sptr 1977 first_parameter() const; 1978 1979 const function_decl::parameter_sptr 1980 second_parameter() const; 1981 1982 diff_sptr 1983 type_diff() const; 1984 1985 virtual const string& 1986 get_pretty_representation() const; 1987 1988 virtual bool 1989 has_changes() const; 1990 1991 virtual enum change_kind 1992 has_local_changes() const; 1993 1994 virtual void 1995 report(ostream&, const string& indent = "") const; 1996 1997 virtual void 1998 chain_into_hierarchy(); 1999 }; // end class fn_parm_diff 2000 2001 fn_parm_diff_sptr 2002 compute_diff(const function_decl::parameter_sptr first, 2003 const function_decl::parameter_sptr second, 2004 diff_context_sptr ctxt); 2005 2006 class function_type_diff; 2007 2008 /// A convenience typedef for a shared pointer to @ref 2009 /// function_type_type_diff 2010 typedef shared_ptr<function_type_diff> function_type_diff_sptr; 2011 2012 /// Abstraction of a diff between two function types. 2013 class function_type_diff: public type_diff_base 2014 { 2015 struct priv; 2016 std::unique_ptr<priv> priv_; 2017 2018 void 2019 ensure_lookup_tables_populated(); 2020 2021 const function_decl::parameter_sptr 2022 deleted_parameter_at(int i) const; 2023 2024 const function_decl::parameter_sptr 2025 inserted_parameter_at(int i) const; 2026 2027 protected: 2028 function_type_diff(const function_type_sptr first, 2029 const function_type_sptr second, 2030 diff_context_sptr ctxt); 2031 2032 public: 2033 friend function_type_diff_sptr 2034 compute_diff(const function_type_sptr first, 2035 const function_type_sptr second, 2036 diff_context_sptr ctxt); 2037 2038 const function_type_sptr 2039 first_function_type() const; 2040 2041 const function_type_sptr 2042 second_function_type() const; 2043 2044 const diff_sptr 2045 return_type_diff() const; 2046 2047 const string_fn_parm_diff_sptr_map& 2048 subtype_changed_parms() const; 2049 2050 const string_parm_map& 2051 removed_parms() const; 2052 2053 const string_parm_map& 2054 added_parms() const; 2055 2056 const vector<function_decl::parameter_sptr>& 2057 sorted_deleted_parms() const; 2058 2059 const vector<function_decl::parameter_sptr>& 2060 sorted_added_parms() const; 2061 2062 virtual const string& 2063 get_pretty_representation() const; 2064 2065 virtual bool 2066 has_changes() const; 2067 2068 virtual enum change_kind 2069 has_local_changes() const; 2070 2071 virtual void 2072 report(ostream&, const string& indent = "") const; 2073 2074 virtual void 2075 chain_into_hierarchy(); 2076 2077 friend class default_reporter; 2078 friend class leaf_reporter; 2079 };// end class function_type_diff 2080 2081 function_type_diff_sptr 2082 compute_diff(const function_type_sptr first, 2083 const function_type_sptr second, 2084 diff_context_sptr ctxt); 2085 2086 /// Abstraction of a diff between two function_decl. 2087 class function_decl_diff : public decl_diff_base 2088 { 2089 struct priv; 2090 std::unique_ptr<priv> priv_; 2091 2092 void 2093 ensure_lookup_tables_populated(); 2094 2095 2096 protected: 2097 function_decl_diff(const function_decl_sptr first, 2098 const function_decl_sptr second, 2099 diff_context_sptr ctxt); 2100 2101 public: 2102 2103 friend function_decl_diff_sptr 2104 compute_diff(const function_decl_sptr first, 2105 const function_decl_sptr second, 2106 diff_context_sptr ctxt); 2107 2108 const function_decl_sptr 2109 first_function_decl() const; 2110 2111 const function_decl_sptr 2112 second_function_decl() const; 2113 2114 const function_type_diff_sptr 2115 type_diff() const; 2116 2117 virtual const string& 2118 get_pretty_representation() const; 2119 2120 virtual bool 2121 has_changes() const; 2122 2123 virtual enum change_kind 2124 has_local_changes() const; 2125 2126 virtual void 2127 report(ostream&, const string& indent = "") const; 2128 2129 virtual void 2130 chain_into_hierarchy(); 2131 }; // end class function_decl_diff 2132 2133 function_decl_diff_sptr 2134 compute_diff(const function_decl_sptr first, 2135 const function_decl_sptr second, 2136 diff_context_sptr ctxt); 2137 2138 class type_decl_diff; 2139 2140 /// Convenience typedef for a shared pointer on a @ref type_decl_diff type. 2141 typedef shared_ptr<type_decl_diff> type_decl_diff_sptr; 2142 2143 /// Abstraction of a diff between two basic type declarations. 2144 class type_decl_diff : public type_diff_base 2145 { 2146 type_decl_diff(); 2147 2148 protected: 2149 type_decl_diff(const type_decl_sptr first, 2150 const type_decl_sptr second, 2151 diff_context_sptr ctxt = diff_context_sptr()); 2152 2153 public: 2154 friend type_decl_diff_sptr 2155 compute_diff(const type_decl_sptr first, 2156 const type_decl_sptr second, 2157 diff_context_sptr ctxt); 2158 2159 const type_decl_sptr 2160 first_type_decl() const; 2161 2162 const type_decl_sptr 2163 second_type_decl() const; 2164 2165 virtual const string& 2166 get_pretty_representation() const; 2167 2168 virtual bool 2169 has_changes() const; 2170 2171 virtual enum change_kind 2172 has_local_changes() const; 2173 2174 virtual void 2175 report(ostream& out, const string& indent = "") const; 2176 };// end type_decl_diff 2177 2178 type_decl_diff_sptr 2179 compute_diff(const type_decl_sptr, 2180 const type_decl_sptr, 2181 diff_context_sptr); 2182 2183 class typedef_diff; 2184 2185 /// Convenience typedef for a shared pointer on a typedef_diff type. 2186 typedef shared_ptr<typedef_diff> typedef_diff_sptr; 2187 2188 /// Abstraction of a diff between two typedef_decl. 2189 class typedef_diff : public type_diff_base 2190 { 2191 struct priv; 2192 std::unique_ptr<priv> priv_; 2193 2194 typedef_diff(); 2195 2196 protected: 2197 typedef_diff(const typedef_decl_sptr first, 2198 const typedef_decl_sptr second, 2199 const diff_sptr underlying_type_diff, 2200 diff_context_sptr ctxt = diff_context_sptr()); 2201 2202 public: 2203 friend typedef_diff_sptr 2204 compute_diff(const typedef_decl_sptr first, 2205 const typedef_decl_sptr second, 2206 diff_context_sptr ctxt); 2207 2208 const typedef_decl_sptr 2209 first_typedef_decl() const; 2210 2211 const typedef_decl_sptr 2212 second_typedef_decl() const; 2213 2214 const diff_sptr 2215 underlying_type_diff() const; 2216 2217 void 2218 underlying_type_diff(const diff_sptr); 2219 2220 virtual const string& 2221 get_pretty_representation() const; 2222 2223 virtual bool 2224 has_changes() const; 2225 2226 virtual enum change_kind 2227 has_local_changes() const; 2228 2229 virtual void 2230 report(ostream&, const string& indent = "") const; 2231 2232 virtual void 2233 chain_into_hierarchy(); 2234 };// end class typedef_diff 2235 2236 typedef_diff_sptr 2237 compute_diff(const typedef_decl_sptr, 2238 const typedef_decl_sptr, 2239 diff_context_sptr ctxt); 2240 2241 const diff* 2242 get_typedef_diff_underlying_type_diff(const diff* diff); 2243 2244 class translation_unit_diff; 2245 2246 /// Convenience typedef for a shared pointer on a 2247 /// @ref translation_unit_diff type. 2248 typedef shared_ptr<translation_unit_diff> translation_unit_diff_sptr; 2249 2250 /// An abstraction of a diff between two translation units. 2251 class translation_unit_diff : public scope_diff 2252 { 2253 struct priv; 2254 std::unique_ptr<priv> priv_; 2255 2256 protected: 2257 translation_unit_diff(translation_unit_sptr first, 2258 translation_unit_sptr second, 2259 diff_context_sptr ctxt = diff_context_sptr()); 2260 2261 public: 2262 2263 const translation_unit_sptr 2264 first_translation_unit() const; 2265 2266 const translation_unit_sptr 2267 second_translation_unit() const; 2268 2269 friend translation_unit_diff_sptr 2270 compute_diff(const translation_unit_sptr first, 2271 const translation_unit_sptr second, 2272 diff_context_sptr ctxt); 2273 2274 virtual bool 2275 has_changes() const; 2276 2277 virtual enum change_kind 2278 has_local_changes() const; 2279 2280 virtual void 2281 report(ostream& out, const string& indent = "") const; 2282 };//end class translation_unit_diff 2283 2284 translation_unit_diff_sptr 2285 compute_diff(const translation_unit_sptr first, 2286 const translation_unit_sptr second, 2287 diff_context_sptr ctxt = diff_context_sptr()); 2288 2289 /// An abstraction of a diff between between two abi corpus. 2290 class corpus_diff 2291 { 2292 struct priv; 2293 std::unique_ptr<priv> priv_; 2294 2295 protected: 2296 corpus_diff(corpus_sptr first, 2297 corpus_sptr second, 2298 diff_context_sptr ctxt = diff_context_sptr()); 2299 2300 void 2301 finish_diff_type(); 2302 2303 public: 2304 2305 class diff_stats; 2306 2307 virtual ~corpus_diff(); 2308 2309 /// A convenience typedef for a shared pointer to @ref diff_stats 2310 typedef shared_ptr<diff_stats> diff_stats_sptr; 2311 2312 corpus_sptr 2313 first_corpus() const; 2314 2315 corpus_sptr 2316 second_corpus() const; 2317 2318 const vector<diff*>& 2319 children_nodes() const; 2320 2321 void 2322 append_child_node(diff_sptr); 2323 2324 edit_script& 2325 function_changes() const; 2326 2327 edit_script& 2328 variable_changes() const; 2329 2330 bool 2331 soname_changed() const; 2332 2333 bool 2334 architecture_changed() const; 2335 2336 const string_function_ptr_map& 2337 deleted_functions() const; 2338 2339 const string_function_ptr_map& 2340 added_functions(); 2341 2342 const string_function_decl_diff_sptr_map& 2343 changed_functions(); 2344 2345 const function_decl_diff_sptrs_type& 2346 changed_functions_sorted(); 2347 2348 const string_var_ptr_map& 2349 deleted_variables() const; 2350 2351 const string_var_ptr_map& 2352 added_variables() const; 2353 2354 const string_var_diff_sptr_map& 2355 changed_variables(); 2356 2357 const var_diff_sptrs_type& 2358 changed_variables_sorted(); 2359 2360 const string_elf_symbol_map& 2361 deleted_unrefed_function_symbols() const; 2362 2363 const string_elf_symbol_map& 2364 added_unrefed_function_symbols() const; 2365 2366 const string_elf_symbol_map& 2367 deleted_unrefed_variable_symbols() const; 2368 2369 const string_elf_symbol_map& 2370 added_unrefed_variable_symbols() const; 2371 2372 const string_type_base_sptr_map& 2373 deleted_unreachable_types() const; 2374 2375 const vector<type_base_sptr>& 2376 deleted_unreachable_types_sorted() const; 2377 2378 const string_type_base_sptr_map& 2379 added_unreachable_types() const; 2380 2381 const vector<type_base_sptr>& 2382 added_unreachable_types_sorted() const; 2383 2384 const string_diff_sptr_map& 2385 changed_unreachable_types() const; 2386 2387 const vector<diff_sptr>& 2388 changed_unreachable_types_sorted() const; 2389 2390 const diff_context_sptr 2391 context() const; 2392 2393 const string& 2394 get_pretty_representation() const; 2395 2396 bool 2397 has_changes() const; 2398 2399 bool 2400 has_incompatible_changes() const; 2401 2402 bool 2403 has_net_subtype_changes() const; 2404 2405 bool 2406 has_net_changes() const; 2407 2408 const diff_stats& 2409 apply_filters_and_suppressions_before_reporting(); 2410 2411 void 2412 mark_leaf_diff_nodes(); 2413 2414 diff_maps& 2415 get_leaf_diffs(); 2416 2417 const diff_maps& 2418 get_leaf_diffs() const; 2419 2420 virtual void 2421 report(ostream& out, const string& indent = "") const; 2422 2423 virtual bool 2424 traverse(diff_node_visitor& v); 2425 2426 virtual void 2427 chain_into_hierarchy(); 2428 2429 friend corpus_diff_sptr 2430 compute_diff(const corpus_sptr f, 2431 const corpus_sptr s, 2432 diff_context_sptr ctxt); 2433 2434 friend void 2435 apply_suppressions(const corpus_diff* diff_tree); 2436 2437 friend void 2438 maybe_report_unreachable_type_changes(const corpus_diff& d, 2439 const corpus_diff::diff_stats &s, 2440 const string& indent, 2441 ostream& out); 2442 2443 friend class default_reporter; 2444 friend class leaf_reporter; 2445 }; // end class corpus_diff 2446 2447 corpus_diff_sptr 2448 compute_diff(const corpus_sptr, 2449 const corpus_sptr, 2450 diff_context_sptr = diff_context_sptr()); 2451 2452 corpus_diff_sptr 2453 compute_diff(const corpus_group_sptr&, 2454 const corpus_group_sptr&, 2455 diff_context_sptr ctxt); 2456 2457 /// This is a document class that aims to capture statistics about the 2458 /// changes carried by a @ref corpus_diff type. 2459 /// 2460 /// Its values are populated by the member function 2461 /// corpus_diff::apply_filters_and_suppressions_before_reporting() 2462 class corpus_diff::diff_stats 2463 { 2464 struct priv; 2465 std::unique_ptr<priv> priv_; 2466 2467 diff_stats(); 2468 2469 public: 2470 2471 diff_stats(diff_context_sptr); 2472 2473 size_t num_func_removed() const; 2474 void num_func_removed(size_t); 2475 2476 size_t num_removed_func_filtered_out() const; 2477 void num_removed_func_filtered_out(size_t); 2478 2479 size_t net_num_func_removed() const; 2480 2481 size_t num_func_added() const; 2482 void num_func_added(size_t); 2483 2484 size_t num_added_func_filtered_out() const; 2485 void num_added_func_filtered_out(size_t); 2486 2487 size_t net_num_func_added() const; 2488 2489 size_t num_func_changed() const; 2490 void num_func_changed(size_t); 2491 2492 size_t num_changed_func_filtered_out() const; 2493 void num_changed_func_filtered_out(size_t); 2494 2495 size_t num_func_with_virtual_offset_changes() const; 2496 void num_func_with_virtual_offset_changes(size_t); 2497 2498 size_t net_num_func_changed() const; 2499 2500 size_t num_vars_removed() const; 2501 void num_vars_removed(size_t); 2502 2503 size_t num_removed_vars_filtered_out() const; 2504 void num_removed_vars_filtered_out(size_t) const; 2505 2506 size_t net_num_vars_removed() const; 2507 2508 size_t num_vars_added() const; 2509 void num_vars_added(size_t); 2510 2511 size_t num_added_vars_filtered_out() const; 2512 void num_added_vars_filtered_out(size_t); 2513 2514 size_t net_num_vars_added() const; 2515 2516 size_t num_vars_changed() const; 2517 void num_vars_changed(size_t); 2518 2519 size_t num_changed_vars_filtered_out() const; 2520 void num_changed_vars_filtered_out(size_t); 2521 2522 size_t net_num_vars_changed() const; 2523 2524 size_t num_func_syms_removed() const; 2525 void num_func_syms_removed(size_t); 2526 2527 size_t num_removed_func_syms_filtered_out() const; 2528 void num_removed_func_syms_filtered_out(size_t); 2529 2530 size_t num_func_syms_added() const; 2531 void num_func_syms_added(size_t); 2532 2533 size_t num_added_func_syms_filtered_out() const; 2534 void num_added_func_syms_filtered_out(size_t); 2535 2536 size_t net_num_removed_func_syms() const; 2537 size_t net_num_added_func_syms() const; 2538 2539 size_t num_var_syms_removed() const; 2540 void num_var_syms_removed(size_t); 2541 2542 size_t num_removed_var_syms_filtered_out() const; 2543 void num_removed_var_syms_filtered_out(size_t); 2544 2545 size_t num_var_syms_added() const; 2546 void num_var_syms_added(size_t); 2547 2548 size_t num_added_var_syms_filtered_out() const; 2549 void num_added_var_syms_filtered_out(size_t); 2550 2551 size_t net_num_removed_var_syms() const; 2552 size_t net_num_added_var_syms() const; 2553 2554 size_t num_leaf_changes() const; 2555 void num_leaf_changes(size_t); 2556 2557 size_t num_leaf_changes_filtered_out() const; 2558 void num_leaf_changes_filtered_out(size_t); 2559 2560 size_t net_num_leaf_changes() const; 2561 2562 size_t num_leaf_type_changes() const; 2563 void num_leaf_type_changes(size_t); 2564 2565 size_t num_leaf_type_changes_filtered_out() const; 2566 void num_leaf_type_changes_filtered_out(size_t); 2567 size_t net_num_leaf_type_changes() const; 2568 2569 size_t num_leaf_func_changes() const; 2570 void num_leaf_func_changes(size_t); 2571 2572 size_t num_leaf_func_changes_filtered_out() const; 2573 void num_leaf_func_changes_filtered_out(size_t); 2574 size_t net_num_leaf_func_changes() const; 2575 2576 size_t num_leaf_var_changes() const; 2577 void num_leaf_var_changes(size_t); 2578 2579 size_t num_leaf_var_changes_filtered_out() const; 2580 void num_leaf_var_changes_filtered_out(size_t); 2581 size_t net_num_leaf_var_changes() const; 2582 2583 size_t num_added_unreachable_types() const; 2584 void num_added_unreachable_types(size_t); 2585 2586 size_t num_added_unreachable_types_filtered_out() const; 2587 void num_added_unreachable_types_filtered_out(size_t); 2588 size_t net_num_added_unreachable_types() const; 2589 2590 size_t num_removed_unreachable_types() const; 2591 void num_removed_unreachable_types(size_t); 2592 2593 size_t num_removed_unreachable_types_filtered_out() const; 2594 void num_removed_unreachable_types_filtered_out(size_t); 2595 size_t net_num_removed_unreachable_types() const; 2596 2597 size_t num_changed_unreachable_types() const; 2598 void num_changed_unreachable_types(size_t); 2599 2600 size_t num_changed_unreachable_types_filtered_out() const; 2601 void num_changed_unreachable_types_filtered_out(size_t); 2602 size_t net_num_changed_unreachable_types() const; 2603 2604 }; // end class corpus_diff::diff_stats 2605 2606 /// The base class for the node visitors. These are the types used to 2607 /// visit each node traversed by the diff_traversable_base::traverse() method. 2608 class diff_node_visitor : public node_visitor_base 2609 { 2610 protected: 2611 struct priv; 2612 std::unique_ptr<priv> priv_; 2613 2614 public: 2615 2616 diff_node_visitor(); 2617 2618 virtual ~diff_node_visitor(); 2619 2620 diff_node_visitor(visiting_kind k); 2621 2622 visiting_kind 2623 get_visiting_kind() const; 2624 2625 void 2626 set_visiting_kind(visiting_kind v); 2627 2628 void 2629 or_visiting_kind(visiting_kind v); 2630 2631 void 2632 set_current_topmost_iface_diff(diff*); 2633 2634 diff* 2635 get_current_topmost_iface_diff() const; 2636 2637 virtual void 2638 visit_begin(diff*); 2639 2640 virtual void 2641 visit_begin(corpus_diff*); 2642 2643 virtual void 2644 visit_end(diff*); 2645 2646 virtual void 2647 visit_end(corpus_diff*); 2648 2649 virtual bool 2650 visit(diff*, bool); 2651 2652 virtual bool 2653 visit(distinct_diff*, bool); 2654 2655 virtual bool 2656 visit(var_diff*, bool); 2657 2658 virtual bool 2659 visit(pointer_diff*, bool); 2660 2661 virtual bool 2662 visit(reference_diff*, bool); 2663 2664 virtual bool 2665 visit(qualified_type_diff*, bool); 2666 2667 virtual bool 2668 visit(enum_diff*, bool); 2669 2670 virtual bool 2671 visit(class_diff*, bool); 2672 2673 virtual bool 2674 visit(base_diff*, bool); 2675 2676 virtual bool 2677 visit(scope_diff*, bool); 2678 2679 virtual bool 2680 visit(function_decl_diff*, bool); 2681 2682 virtual bool 2683 visit(type_decl_diff*, bool); 2684 2685 virtual bool 2686 visit(typedef_diff*, bool); 2687 2688 virtual bool 2689 visit(translation_unit_diff*, bool); 2690 2691 virtual bool 2692 visit(corpus_diff*, bool); 2693 }; // end struct diff_node_visitor 2694 2695 void 2696 propagate_categories(diff* diff_tree); 2697 2698 void 2699 propagate_categories(diff_sptr diff_tree); 2700 2701 void 2702 propagate_categories(corpus_diff* diff_tree); 2703 2704 void 2705 propagate_categories(corpus_diff_sptr diff_tree); 2706 2707 void 2708 apply_suppressions(diff* diff_tree); 2709 2710 void 2711 apply_suppressions(const corpus_diff* diff_tree); 2712 2713 void 2714 apply_suppressions(diff_sptr diff_tree); 2715 2716 void 2717 apply_suppressions(corpus_diff_sptr diff_tree); 2718 2719 void 2720 print_diff_tree(diff* diff_tree, std::ostream&); 2721 2722 void 2723 print_diff_tree(corpus_diff* diff_tree, 2724 std::ostream&); 2725 2726 void 2727 print_diff_tree(diff_sptr diff_tree, 2728 std::ostream&); 2729 2730 void 2731 print_diff_tree(corpus_diff_sptr diff_tree, 2732 std::ostream&); 2733 2734 void 2735 categorize_redundancy(diff* diff_tree); 2736 2737 void 2738 categorize_redundancy(diff_sptr diff_tree); 2739 2740 void 2741 categorize_redundancy(corpus_diff* diff_tree); 2742 2743 void 2744 categorize_redundancy(corpus_diff_sptr diff_tree); 2745 2746 void 2747 clear_redundancy_categorization(diff* diff_tree); 2748 2749 void 2750 clear_redundancy_categorization(diff_sptr diff_tree); 2751 2752 void 2753 clear_redundancy_categorization(corpus_diff* diff_tree); 2754 2755 void 2756 clear_redundancy_categorization(corpus_diff_sptr diff_tree); 2757 2758 void 2759 apply_filters(corpus_diff_sptr diff_tree); 2760 2761 bool 2762 is_diff_of_variadic_parameter_type(const diff*); 2763 2764 bool 2765 is_diff_of_variadic_parameter_type(const diff_sptr&); 2766 2767 bool 2768 is_diff_of_variadic_parameter(const diff*); 2769 2770 bool 2771 is_diff_of_variadic_parameter(const diff_sptr&); 2772 2773 const type_diff_base* 2774 is_type_diff(const diff* diff); 2775 2776 const decl_diff_base* 2777 is_decl_diff(const diff* diff); 2778 2779 const type_decl_diff* 2780 is_diff_of_basic_type(const diff* diff); 2781 2782 const type_decl_diff* 2783 is_diff_of_basic_type(const diff* diff, bool); 2784 2785 const class_or_union_diff* 2786 is_diff_of_class_or_union_type(const diff *d); 2787 2788 bool 2789 has_basic_type_change_only(const diff* diff); 2790 2791 const enum_diff* 2792 is_enum_diff(const diff *diff); 2793 2794 const class_diff* 2795 is_class_diff(const diff* diff); 2796 2797 const union_diff* 2798 is_union_diff(const diff* diff); 2799 2800 const class_or_union_diff* 2801 is_class_or_union_diff(const diff* d); 2802 2803 const class_or_union_diff* 2804 is_anonymous_class_or_union_diff(const diff* d); 2805 2806 const array_diff* 2807 is_array_diff(const diff* diff); 2808 2809 const function_type_diff* 2810 is_function_type_diff(const diff* diff); 2811 2812 const function_type_diff* 2813 is_function_type_diff_with_local_changes(const diff* diff); 2814 2815 const typedef_diff* 2816 is_typedef_diff(const diff *diff); 2817 2818 const var_diff* 2819 is_var_diff(const diff* diff); 2820 2821 const function_decl_diff* 2822 is_function_decl_diff(const diff* diff); 2823 2824 const pointer_diff* 2825 is_pointer_diff(const diff* diff); 2826 2827 const reference_diff* 2828 is_reference_diff(const diff* diff); 2829 2830 const qualified_type_diff* 2831 is_qualified_type_diff(const diff* diff); 2832 2833 const fn_parm_diff* 2834 is_fn_parm_diff(const diff* diff); 2835 2836 const base_diff* 2837 is_base_diff(const diff* diff); 2838 2839 const distinct_diff* 2840 is_distinct_diff(const diff *diff); 2841 2842 bool 2843 is_child_node_of_function_parm_diff(const diff* diff); 2844 2845 bool 2846 is_child_node_of_base_diff(const diff* diff); 2847 2848 const corpus_diff* 2849 is_corpus_diff(const diff* diff); 2850 2851 const diff* 2852 peel_typedef_diff(const diff* dif); 2853 2854 const diff* 2855 peel_pointer_diff(const diff* dif); 2856 2857 const diff* 2858 peel_reference_diff(const diff* dif); 2859 2860 const diff* 2861 peel_qualified_diff(const diff* dif); 2862 2863 const diff* 2864 peel_fn_parm_diff(const diff* dif); 2865 2866 const diff* 2867 peel_pointer_or_qualified_type_diff(const diff* dif); 2868 2869 const diff* 2870 peel_typedef_or_qualified_type_diff(const diff* dif); 2871 2872 const diff* 2873 peel_typedef_qualified_type_or_parameter_diff(const diff *dif); 2874 }// end namespace comparison 2875 2876 }// end namespace abigail 2877 2878 #endif //__ABG_COMPARISON_H__ 2879