Chenxiong Qi [Mon, 19 Dec 2016 11:09:53 +0000 (12:09 +0100)]
Read Koji config via Koji API
Besides reading Koji config via Koji API read_config, option --topdir is
also renamed to --topurl that is the correct one should be used.
* tools/fedabipkgdiff: Read DEFAULT_KOJI_TOPURL and
DEFAULT_KOJI_SERVER from Koji config via Koji API read_config.
(build_commandline_args_parser): --topdir is renamed to
--topurl.
* doc/manuals/fedabipkgdiff.rst: Rename --topdir to --topurl.
Ondrej Oprala [Thu, 15 Dec 2016 19:15:38 +0000 (20:15 +0100)]
Properly report missing files for abipkgdiff
Currently, if abipkgdiff is given a path to a nonexistent file,
it propagates all the way until package classification
and ends up being reported as "PKG should be a valid package file",
which doesn't hint it's not there at all.
* tools/abipkgdiff.cc: (class options): Add the "nonexistent_file" flag
(parse_command_line): Check if the files given exist.
(main): Check the nonexistent_file flag. If any of the input
files don't exist, report it and exit. Also, for present and future test
uniformity, only show the base names of the packages when using their
names in error output.
* tests/test-diff-pkg.cc: Add a new regression test.
* tests/data/test-diff-pkg/test-nonexistent-report-0.txt: The
expected output of the above regression test.
* tests/data/Makefile.am: Add the above file to the list.
Signed-off-by: Ondrej Oprala <ondrej.oprala@gmail.com>
Dodji Seketeli [Thu, 15 Dec 2016 13:29:38 +0000 (14:29 +0100)]
Naming typedefs of classes are not read properly from abixml
When loading a class from abixml and when that class has a naming
typedef, build_class_decl fails to build the naming typedef from its
ID because it calls read_context::get_type_decl() instead of
read_context::build_or_get_type_decl().
This patch fixes that issue by using
read_context::build_or_get_type_decl rather than
read_context::get_type_decl.
Also, as read_context::build_or_get_type_decl can trigger the creation
of a class (and recursively call build_class_decl), it needs to be
called after the class type being built is marked as work-in-progress
(aka WIP). So the handling of the naming typedef is moved to after
the class type being built is marked as WIP.
* src/abg-reader.cc (build_class_decl): Use
read_context::build_or_get_type_decl rather than
read_context::get_type_decl to build the naming typedef referred
to by the class being built. Move the handling of naming typedefs
after the class is marked as WIP and keyed.
Dodji Seketeli [Thu, 15 Dec 2016 13:12:57 +0000 (14:12 +0100)]
Don't early-canonicalize function types when reading abixml
When reading from an abixml file, we sometimes canonicalize function
types before the entire abixml file is read. This can lead to, e.g, a
function type that is not yet fully built being canonicalized too
early and so its canonical type being wrong because it reflects the
state of the function type at canonicalization time -- but then that
state changed later.
This patch fixes that by forcing us to late-canonicalize function
types, just like we do for all aggregate types.
* src/abg-reader.cc (read_context::maybe_canonicalize_type):
late-canonicalize function types too.
Ondrej Oprala [Mon, 12 Dec 2016 15:37:54 +0000 (16:37 +0100)]
Check --enable-rpm dependencies more rigorously
If a user has explicitly specified --enable-rpm when running
"configure", it will now fail unless both rpm2cpio and cpio
are present on the system.
* configure.ac: Check if both rpm2cpio and cpio
exist on the system. If not, disable the option and fail the
configuration if --enable-rpm was specified explicitly.
Signed-off-by: Ondrej Oprala <ondrej.oprala@gmail.com>
Ondrej Oprala [Mon, 12 Dec 2016 14:44:29 +0000 (15:44 +0100)]
Fix a few remarks made by cppcheck
* src/abg-comparison.cc (types_or_decls_equal::operator()): Pass
arguments by reference.
(class_diff::ensure_lookup_tables_populated): Expression
!A || (A && B) can be reduced to !A || B.
* src/abg-suppression.cc (suppression_matches_type_no_name):
Likewise.
Signed-off-by: Ondrej Oprala <ondrej.oprala@gmail.com>
Ondrej Oprala [Fri, 9 Dec 2016 22:01:58 +0000 (23:01 +0100)]
Bug 19272 - abipkgdiff doesn't report arch change
Previously, architecture change wasn't included in the incompatible
changes check.
This patch makes corpus_diff::has_incompatible_changes take
architecture change into account.
It turns out corpus_diff::has_net_changes wasn't taking architecture
or soname change into account either. This patch fixes that as well.
The patch also updates abicompat.cc to make it use
corpus_diff::has_net_changes() and
corpus_diff::has_incompatible_changes(), instead of open-coding these
member functions.
* src/abg-comparison.cc (corpus_diff::has_incompatible_changes):
The architecture change into account.
(corpus_diff::has_net_changes): Take architecture and soname
changes into account.
* tools/abicompat.cc (perform_compat_check_in_normal_mode): Use
corpus_diff::{has_net_changes, has_incompatible_changes}.
* tests/data/test-diff-pkg/dbus-glib-0.104-3.fc23.armv7hl.rpm: New
test input.
* tests/data/test-diff-pkg/dbus-glib-0.104-3.fc23.x86_64--dbus-glib-0.104-3.fc23.armv7hl-report-0.txt:
New test reference output.
* tests/data/Makefile.am: Add the new test material above to
source distribution.
* tests/test-diff-pkg.cc (in_out_spec): Compare the new package
above against an x86_64 one.
This patch also introduces new terms for libabigail, that is the
subject, ancillary package, and comparison half. Subject represents a
package that is subject of the ABI comparison, a subject could be a RPM
and maybe it would be a DEB or some other kind of "package". A subject
may have several ancillary packages that are used to compare the
subject. Generally, a subject may have devel, debuginfo, or both.
* configure.ac: add dependent mimetype module.
* doc/manuals/fedabipkgdiff.rst: Update to add document for the
new use case of comparing two local RPMs.
* tests/data/Makefile.am: Include new RPMs for tests.
* tests/data/test-fedabipkgdiff/dbus-glib/dbus-glib-0.100.2-2.fc20.x86_64.rpm:
New RPM for running test.
* tests/data/test-fedabipkgdiff/dbus-glib/dbus-glib-0.106-1.fc23.x86_64.rpm:
Likewise.
* tests/data/test-fedabipkgdiff/nss-util/nss-util-3.12.6-1.fc14.x86_64.rpm:
Likewise.
* tests/data/test-fedabipkgdiff/nss-util/nss-util-3.24.0-2.0.fc25.x86_64.rpm:
Likewise.
* tests/data/test-fedabipkgdiff/nss-util/nss-util-devel-3.24.0-2.0.fc25.x86_64.rpm:
Likewise.
* tests/data/test-fedabipkgdiff/test4-glib-0.100.2-2.fc20.x86_64.rpm-glib-0.106-1.fc23.x86_64.rpm-report-0.txt:
Rename filename by adding .rpm extension.
* tests/data/test-fedabipkgdiff/test5-same-dir-dbus-glib-0.100.2-2.fc20.x86_64--dbus-glib-0.106-1.fc23.x86_64-report-0.txt:
New reference output for testing comparing local RPMs.
* tests/data/test-fedabipkgdiff/test6-missing-devel-debuginfo-nss-util-3.12.6-1.fc14.x86_64--nss-util-3.24.0-2.0.fc25.x86_64-report-0.txt:
New reference output for testing comparison without non-existent
debuginfo or development package.
* tests/runtestfedabipkgdiff.py.in (FEDABIPKGDIFF_TEST_SPECS):
Rename filename for test4. Add two new test cases.
(run_fedabipkgdiff_tests): Remove semicolon and trailing
whitespaces.
(main): Likewise.
(ensure_output_dir_created): Likewise.
* tools/fedabipkgdiff: Require some new modules.
Fix of return code.
(PkgInfo): Renamed to ComparisonHalf.
(match_nvr): New method to determine if a string matches format
of N-V-R.
(match_nvra): New method to determine if a string matches format
of N-V-R.A.
(is_rpm_file): New method to guess if a file is a RPM file.
(RPM.is_peer): New method to determine if current RPM is a peer
of another.
(RPM.filename): Use Koji module API to construct the filename.
(RPM.nvra): Get nvra from filename instead of constructing
manually that is duplicated with Koji module API.
(RPMCollection): New class to represent a set of RPMs.
(generate_pkg_info_pair_for_abipkgdiff): New method working as a
generator to yeild comparison halves for running abipkgdiff.
(Brew.getRPM): Fix string format with incorrect argument.
(Brew.select_rpms_from_a_build): Return instance of
RPMCollection.
(abipkgdiff): If there is no debuginfo or development package,
just ignore it and leave a warning. If --error-on-warning is
specified, raise an exception instead. Arguments are modified
to represent the new name ComparisonHalf, and relative docstring
is also updated.
(magic_construct): Removed.
(run_abipkgdiff): Rewrite.
(make_rpms_usable_for_abipkgdiff): Removed.
(diff_local_rpm_with_latest_rpm_from_koji): Rewrite by using
RPMCollection.
(diff_latest_rpms_based_on_distros): Likewise.
(diff_two_nvras_from_koji): Likewise.
(diff_from_two_rpm_files): New method to compare two local RPMs.
(build_commandline_args_parser): Add new option
--error-on-warning.
(main): Add support to compare local RPMs.
Dodji Seketeli [Thu, 8 Dec 2016 23:37:43 +0000 (00:37 +0100)]
Fix aborting when reading .foo symbols from a ppc64 binary
On ppc64, the value of a function symbol is *usually* the pointer to
the function. That function pointer value refers to an index inside
the ".opd" (Official Procedure Descriptor) section. That section is a
record of tripplets values. One of these values is the address of the
entry point of the function. A debug information entry for a
function, in DWARF, refers to the entry point of the function; not to
the function pointer address.
So libabigail builds a table that associates a function entry point
address to its function pointer address.
So, if a function is named "foo", it has an entry in the symbol table
for the symbol name "foo"; the value of that symbol is the function
pointer address of foo, which refers to an offset in the ".opd"
section.
But then it turns out that there is also going to be an entry in the
symbol table for an artificial symbol named ".foo". Pleast note the
dot before the suffix "foo". The value of the ".foo" symbol is the
address of the entry point of the function "foo"; it's an address in
the ".text" section this time.
Libabigail's ELF symbols reading code was (wrongly) expecting all
entries in the symbol table that refer to function to have values that
are offset in the ".opd" section. It wasn't expecting the ".foo"
symbols whose value are an address in the ".text" section.
This patch fixes the ELF symbol reading code to make it be aware of
the ".foo" symbols too.
* abg-dwarf-reader.cc (read_context::find_opd_section): Fix
comment.
(read_context::load_symbol_maps): If for a given function entry
point (that we got by looking at the ".opd" section for a given
function pointer value) we already had an entry in the
function_entry_address -> symbol, maybe it means that the previous
entry that we had was from an entry in the symbol table which
value was directly the entry point address of a function. In that
case, if the name of the symbol is "foo", the name of the symbol
which value is directly the entry point address is ".foo". What
we do in this case is that we just keep the reference to the "foo"
symbol in the function_entry_address -> symbol map.
(read_context::address_is_in_opd_section): Define new member
function.
* tests/data/test-diff-pkg/gmp-4.3.1-10.el6.ppc64.rpm: New test input.
* tests/data/test-diff-pkg/gmp-4.3.1-7.el6_2.2.ppc64.rpm: Likewise.
* tests/data/test-diff-pkg/gmp-debuginfo-4.3.1-10.el6.ppc64.rpm: Likewise.
* tests/data/test-diff-pkg/gmp-debuginfo-4.3.1-7.el6_2.2.ppc64.rpm: Likewise.
* tests/data/test-diff-pkg/gmp-4.3.1-7.el6_2.2.ppc64--gmp-4.3.1-10.el6.ppc64-report-0.txt:
New test reference output.
* tests/data/Makefile.am: Add the new test input and reference
output to source distribution.
* tests/test-diff-pkg.cc (in_out_specs): Add the new test inputs
and reference output to the set of inputs that are compared.
Dodji Seketeli [Mon, 5 Dec 2016 09:11:19 +0000 (10:11 +0100)]
Bug 20927 - Segfault when $HOME is not set
When comparing two binaries with abi{pkg}diff, if $HOME is not set, we
segfault at some places because we don't expect that. I ran "make
check" after doing "unset HOME" to help me catch most of those places.
This patch updates the code to handle that case.
* src/abg-tools-utils.cc
(get_default_user_suppression_file_path): Handle the case where
the HOME environment variable is not set.
* tools/abipkgdiff.cc (package::extracted_packages_parent_dir):
Likewise. When $HOME is empty set then use $TMPDIR. If it's
empty too then use "/tmp".
Dodji Seketeli [Fri, 2 Dec 2016 13:41:07 +0000 (14:41 +0100)]
Bug 20887 - Show relative change of offsets
Until now, an offset change is reported by showing the old and new
offsets of the data member that changed.
This patch adds the string "(by +N bits)" with 'N' being the number of
bits by which the offset of the data member was increased, or "(by -N
bits) if the offset of the data member was decreased of N bits.
The patch also emits a string that says "size hasn't changed" if the
size of the structure did not change.
This can be disabled by a new --no-show-relative-offset-changes
option.
* doc/manuals/abidiff.rst: Document the new
--no-show-relative-offset-changes.
* doc/manuals/abipkgdiff.rst: Likewise.
* include/abg-comparison.h
(diff_context::show_relative_offset_changes): New accessors.
* include/abg-ir.h ({set,get}_data_member_offset): Return uint64_t
instead of the less portable size_t.
* src/abg-comparison.cc
(diff_context::priv::show_relative_offset_changes_): New data
member.
(dif_context::show_relative_offset_changes): Define accessor.
(maybe_show_relative_offset_change): Define new function.
(represent): In the overload for var_diff, call the new
maybe_show_relative_offset_change.
(report_size_and_alignment_changes): If the size of the type
didn't change then say it now.
* src/abg-ir.cc (set_data_member_offset, get_data_member_offset):
Take or return a uint64_t instead of a size_t.
* tools/abidiff.cc (options::show_relative_offset_changes): New
data member.
(options::options): Initialize it.
(display_usage): Display help string for the new
--no-show-relative-offset-changes.
(parse_command_line): Parse the new
--no-show-relative-offset-changes options.
(set_diff_context_from_opts): Set the
"show-relative-offset-changes" flag according to the new option.n
* tools/abipkgdiff.cc (options::show_relative_offset_changes): New
data member.
(options::options): Initialize it.
(display_usage): Add help string for the new
--no-show-relative-offset-changes option.
(set_diff_context_from_opts): Set the
"show-relative-offset-changes" flag according to the new option.
(parse_command_line): Parse the new command line option.
* tests/data/test-diff-dwarf/test40-report-0.txt: Add new
reference output.
* tests/data/test-diff-dwarf/test40-v0.c: Source code of the first
test binary.
* tests/data/test-diff-dwarf/test40-v1.c: Source code of the
second test binay.
* tests/data/test-diff-dwarf/libtest40-v0.so: New first test binary.
* tests/data/test-diff-dwarf/libtest40-v1.so: New second test binary.
* tests/test-diff-dwarf.cc (in_out_spec): Add the new test
binaries above to the set of binaries that are compared.
* tests/data/Makefile.am: Add the new test material to source
distribution.
* tests/data/test-abicompat/test7-fn-changed-report-0.txt: Adjust.
* tests/data/test-abidiff/test-PR18791-report0.txt: Likewise.
* tests/data/test-abidiff/test-enum0-report.txt: Likewise.
* tests/data/test-abidiff/test-enum1-report.txt: Likewise.
* tests/data/test-abidiff/test-struct1-report.txt: Likewise.
* tests/data/test-diff-dwarf/test0-report.txt: Likewise.
* tests/data/test-diff-dwarf/test1-report.txt: Likewise.
* tests/data/test-diff-dwarf/test10-report.txt: Likewise.
* tests/data/test-diff-dwarf/test11-report.txt: Likewise.
* tests/data/test-diff-dwarf/test13-report.txt: Likewise.
* tests/data/test-diff-dwarf/test15-enum-report.txt: Likewise.
* tests/data/test-diff-dwarf/test27-local-base-diff-report.txt: Likewise.
* tests/data/test-diff-dwarf/test32-fnptr-changes-report-0.txt: Likewise.
* tests/data/test-diff-dwarf/test33-fnref-changes-report-0.txt: Likewise.
* tests/data/test-diff-dwarf/test38-union-report-0.txt: Likewise.
* tests/data/test-diff-dwarf/test4-report.txt: Likewise.
* tests/data/test-diff-dwarf/test5-report.txt: Likewise.
* tests/data/test-diff-dwarf/test6-report.txt: Likewise.
* tests/data/test-diff-dwarf/test8-report.txt: Likewise.
* tests/data/test-diff-filter/test0-report.txt: Likewise.
* tests/data/test-diff-filter/test01-report.txt: Likewise.
* tests/data/test-diff-filter/test1-report.txt: Likewise.
* tests/data/test-diff-filter/test13-report.txt: Likewise.
* tests/data/test-diff-filter/test16-report-2.txt: Likewise.
* tests/data/test-diff-filter/test16-report.txt: Likewise.
* tests/data/test-diff-filter/test17-0-report.txt: Likewise.
* tests/data/test-diff-filter/test17-1-report.txt: Likewise.
* tests/data/test-diff-filter/test18-report.txt: Likewise.
* tests/data/test-diff-filter/test19-enum-report-1.txt: Likewise.
* tests/data/test-diff-filter/test2-report.txt: Likewise.
* tests/data/test-diff-filter/test23-redundant-fn-parm-change-report-0.txt:
Likewise.
* tests/data/test-diff-filter/test24-compatible-vars-report-1.txt:
Likewise.
* tests/data/test-diff-filter/test25-cyclic-type-report-0.txt:
Likewise.
* tests/data/test-diff-filter/test25-cyclic-type-report-1.txt:
Likewise.
* tests/data/test-diff-filter/test26-qualified-redundant-node-report-0.t:
Likewise.xt
* tests/data/test-diff-filter/test26-qualified-redundant-node-report-1.txt:
Likewise.
* tests/data/test-diff-filter/test27-redundant-and-filtered-children-nodes-report-1.txt:
Likewise.
* tests/data/test-diff-filter/test27-redundant-and-filtered-children-nodes-report-2.txt:
Likewise.
* tests/data/test-diff-filter/test29-finer-redundancy-marking-report-0.txt:
Likewise.
* tests/data/test-diff-filter/test3-report.txt: Likewise.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report0.txt:
Likewise.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report1.txt:
Likewise.
* tests/data/test-diff-filter/test31-pr18535-libstdc++-report-0.txt:
Likewise.
* tests/data/test-diff-filter/test31-pr18535-libstdc++-report-1.txt:
Likewise.
* tests/data/test-diff-pkg/libICE-1.0.6-1.el6.x86_64.rpm--libICE-1.0.9-2.el7.x86_64.rpm-report-0.txt: Likewise.
* tests/data/test-diff-pkg/libsigc++-2.0-0c2a_2.4.0-1_amd64--libsigc++-2.0-0v5_2.4.1-1ubuntu2_amd64-report-0.txt: Likewise.
* tests/data/test-diff-pkg/tbb-4.1-9.20130314.fc22.x86_64--tbb-4.3-3.20141204.fc23.x86_64-report-0.txt: Likewise.
* tests/data/test-diff-pkg/tbb-4.1-9.20130314.fc22.x86_64--tbb-4.3-3.20141204.fc23.x86_64-report-1.txt: Likewise.
* tests/data/test-diff-suppr/test0-type-suppr-report-0.txt: Likewise.
* tests/data/test-diff-suppr/test0-type-suppr-report-3.txt: Likewise.
* tests/data/test-diff-suppr/test0-type-suppr-report-5.txt: Likewise.
* tests/data/test-diff-suppr/test0-type-suppr-report-7.txt: Likewise.
* tests/data/test-diff-suppr/test1-typedef-suppr-report-0.txt: Likewise.
* tests/data/test-diff-suppr/test1-typedef-suppr-report-2.txt: Likewise.
* tests/data/test-diff-suppr/test10-changed-parm-c-report-0.txt: Likewise.
* tests/data/test-diff-suppr/test2-struct-suppr-report-0.txt: Likewise.
* tests/data/test-diff-suppr/test23-alias-filter-report-0.txt: Likewise.
* tests/data/test-diff-suppr/test23-alias-filter-report-2.txt: Likewise.
* tests/data/test-diff-suppr/test3-struct-suppr-report-0.txt: Likewise.
* tests/data/test-diff-suppr/test3-struct-suppr-report-1.txt: Likewise.
* tests/data/test-diff-suppr/test3-struct-suppr-report-2.txt: Likewise.
* tests/data/test-diff-suppr/test30-report-0.txt: Likewise.
* tests/data/test-diff-suppr/test4-local-suppr-report-0.txt: Likewise.
* tests/data/test-diff-suppr/test4-local-suppr-report-1.txt: Likewise.
* tests/data/test-diff-suppr/test5-fn-suppr-report-0.txt: Likewise.
* tests/data/test-diff-suppr/test5-fn-suppr-report-1.txt: Likewise.
* tests/data/test-diff-suppr/test5-fn-suppr-report-2.txt: Likewise.
* tests/data/test-diff-suppr/test5-fn-suppr-report-3.txt: Likewise.
* tests/data/test-diff-suppr/test5-fn-suppr-report-4.txt: Likewise.
* tests/data/test-diff-suppr/test5-fn-suppr-report-5.txt: Likewise.
* tests/data/test-diff-suppr/test6-fn-suppr-report-0-1.txt: Likewise.
* tests/data/test-diff-suppr/test6-fn-suppr-report-0.txt: Likewise.
* tests/data/test-diff-suppr/test6-fn-suppr-report-1.txt: Likewise.
* tests/data/test-diff-suppr/test6-fn-suppr-report-2.txt: Likewise.
* tests/data/test-diff-suppr/test6-fn-suppr-report-3.txt: Likewise.
* tests/data/test-diff-suppr/test7-var-suppr-report-0.txt: Likewise.
* tests/data/test-diff-suppr/test7-var-suppr-report-1.txt: Likewise.
* tests/data/test-diff-suppr/test7-var-suppr-report-2.txt: Likewise.
* tests/data/test-diff-suppr/test7-var-suppr-report-3.txt: Likewise.
* tests/data/test-diff-suppr/test7-var-suppr-report-4.txt: Likewise.
* tests/data/test-diff-suppr/test7-var-suppr-report-7.txt: Likewise.
* tests/data/test-diff-suppr/test7-var-suppr-report-8.txt: Likewise.
Dodji Seketeli [Fri, 2 Dec 2016 11:54:49 +0000 (12:54 +0100)]
Rename tests/update-test-read-dwarf-output.py
Renamed tests/update-test-read-dwarf-output.py into
tests/update-test-output.py as it can be used for all tests that emit
an output and compare it against a reference output.
* tests/update-test-output.py: renamed
tests/update-test-read-dwarf-output.py into this. Update its
comments. Make this script executable.
Dodji Seketeli [Wed, 30 Nov 2016 10:01:38 +0000 (11:01 +0100)]
Add tests/data/test-diff-suppr/test33-report-0.txt to tarball
I forgot to add the file testing file
tests/data/test-diff-suppr/test33-report-0.txt to
tests/data/Makefile.am. This makes the test runtestdiffsupp fail
under 'make distcheck'.
Dodji Seketeli [Wed, 30 Nov 2016 08:28:34 +0000 (09:28 +0100)]
Bug 20670 - abipkgdiff aborts if $XDG_CACHE_HOME does not exist
This patch creates $XDG_CACHE_HOME if it doesn't exist, rather than
just aborting.
* tools/abipkgdiff.cc (package::extracted_packages_parent_dir):
Ensure that the cache directory is created, even when
XDG_CACHE_HOME is set. Also, remove the now useless "using
abigail::tools_utils::get_random_number_as_string" statement.
Dodji Seketeli [Wed, 9 Nov 2016 14:10:27 +0000 (15:10 +0100)]
Very light speed improvements
When comparing of two kernel trees showed that for huge changesets
involving highly recursive types, leaf functions used by the
categorization code dominate the performance profile.
This patch introduces some changes that help gain around 30 seconds
(out of 14 minutes) on a non-optimized build, when comparing 4.7 nd
4.8 fedora kernels (between fedora 24 and 26).
* include/abg-comp-filter.h (has_harmless_name_change): Pass smart
pointers by reference.
* src/abg-comp-filter.cc (access_changed)
(function_name_changed_but_not_symbol)
(non_static_data_member_type_size_changed)
(static_data_member_type_size_changed, is_compatible_change)
(decl_name_changed, has_harmless_name_change): Pass smart
pointers by reference.
* include/abg-ir.h (decl_base::set_context_rel): Take a bare
pointer, not a smart pointer.
* src/abg-ir.cc (decl_base::priv::context_): Make this data member
be a naked pointer, not a smart pointer.
(decl_base::priv::priv): Initialize it.
(decl_base::priv::~priv): New constructor.
(decl_base::{get_context_rel, set_scope}): Adjust.
(class_decl::method_decl::{method_decl, set_scope}): Likewise.
(equals): In the overload for var_decl, compare the type of the
var first as that might be faster (to detect var_decls with
different types) in the general case where types are
canonicalized.
Dodji Seketeli [Tue, 8 Nov 2016 10:48:58 +0000 (11:48 +0100)]
Introduce on-the-fly type canonicalization
During canonicalization of a type T, when T is structurally compared
to an already canonicalized type C, it can happen that
non-canonicalized sub-types of T are structurally compared again and
again to canonicalized sub-types of C.
This patch introduces a new optimization or those cases: on-the-fly
type canonicalized.
That means, if a not-yet-canonicalized sub-type S of the type T being
canonicalized structurally compares equal to a canonicalized sub-type,
then the canonical type of S is said to be the canonical type of the
canonicalized sub-type. So sub-type S is canonicalized, on-the-fly,
during canonicalization of type T.
This considerably speeds up the canonicalization process while doing
"abidiff vmlinux vmlinux". It goes from taking forever to taking 45
seconds on a non-optimized build.
* include/abg-ir.h (environment::do_on_the_fly_canonicalization):
Declare new member functions.
({type_base, function_type}::priv_): Make this public so that
static non-member functions defined in abg-ir.cc can access it.
* src/abg-ir.cc
(environment::priv::do_on_the_fly_canonicalization_): New data
member.
(environment::priv::priv): Initialize it.
(environment::do_on_the_fly_canonicalization): Define new member
functions.
(type_base::get_canonical_type_for): Trigger on-the-fly
canonicalization during comparison of the type being canonicalized
and an already canonicalized type.
(types_are_being_compared, maybe_propagate_canonical_type): Define
new static functions.
(equals): In overloads for class_decl and function_type, call
maybe_propagate_canonical_type when the two types compare equal.
* tests/data/test-diff-pkg/tbb-4.1-9.20130314.fc22.x86_64--tbb-4.3-3.20141204.fc23.x86_64-report-0.txt:
Adjust.
* tests/data/test-read-dwarf/test9-pr18818-clang.so.abi: Likewise.
Dodji Seketeli [Sun, 6 Nov 2016 11:15:41 +0000 (12:15 +0100)]
Fix pretty representation of array types
It turned out we were wrongly emitting the pretty representation of
array types in two cases:
1/ in case of qualified array types: a const array of string type
was being pretty-represented as: "const string[]" instead of
"string[] const".
2/ in case of array with an empty sub-range DIE; that is a sub-range
DIE with no attribute at all. For instance an array of char with an
empty sub-range DIE was being represented as: "char", instead of
"char[]".
This patch fixes 1 and 2. It also updates numerous test reference
output files.
* include/abg-ir.h (array_type_def::is_infinite): Fix indentation.
* src/abg-ir.cc (qualified_type_def::build_name): An empty set of
sub-ranges for a vector is represented by "[]".
(array_type_def::is_infinite): If a vector has no sub-range, that
means it has an infinite size. Adjust comment.
* tests/data/test-diff-filter/test33-report-0.txt: Adjust.
* tests/data/test-read-dwarf/libtest23.so.abi: Adjust.
* tests/data/test-read-dwarf/libtest24-drop-fns-2.so.abi: Adjust.
* tests/data/test-read-dwarf/libtest24-drop-fns.so.abi: Adjust.
* tests/data/test-read-dwarf/test10-pr18818-gcc.so.abi: Adjust.
* tests/data/test-read-dwarf/test11-pr18828.so.abi: Adjust.
* tests/data/test-read-dwarf/test14-pr18893.so.abi: Adjust.
* tests/data/test-read-dwarf/test19-pr19023-libtcmalloc_and_profiler.so.abi:
Adjust.
* tests/data/test-read-dwarf/test22-pr19097-libstdc++.so.6.0.17.so.abi:
Adjust.
* tests/data/test-read-dwarf/test9-pr18818-clang.so.abi: Adjust.
The typedef name "anonymous_struct_type" becomes the name of the
otherwise anonymous struct. That is what a naming typedef is.
So, the nice thing about naming typedefs is that an anonymous class
type suddenly becomes non anymous. So that type becomes eligible to
the ODR-based optimization during type canonicalization. That speeds
up type canonicalization, at least for 'abidw'.
This patch represents naming typedefs for class_decl types in the
internal representation. The patch also changes the meaning of an
anonymous class. Whenever such a class becomes named by a typedef,
the class is not considered anonymous anymore, at least for the
purpose of type canonicalization.
* include/abg-ir.h (typedef_decl_wptr): New typedef.
(class_decl::{g,s}et_naming_typedef): Declare new member
functions.
* src/abg-dwarf-reader.cc (build_typedef_type): When the
underlying type of a typedef is an anonymous class, the class type
is said to have a naming typedef.
* src/abg-ir.cc (is_anonymous_type): An anonymous class that has
a naming typedef is said to not be anonymous anymore.
(class_decl::priv::naming_typedef): New data member.
(class_decl::{g,s}et_naming_typedef): Define new member functions.
(class_decl::get_pretty_representation): When called for internal
purposes (e.g, for type canonicalization) compute the pretty
representation of the class by using its typedef name, when class
is anonymous and has a naming typedef.
* src/abg-reader.cc (build_class_decl): Read the new
"naming-typedef-id" attribute.
* src/abg-writer.cc (write_naming_typedef): New function.
(write_class_decl_opening_tag): Use the new write_naming_typedef
function.
* tests/data/test-read-dwarf/libtest23.so.abi: Adjust.
* tests/data/test-read-dwarf/libtest24-drop-fns-2.so.abi:
Likewise.
* tests/data/test-read-dwarf/libtest24-drop-fns.so.abi: Likewise.
* tests/data/test-read-dwarf/test10-pr18818-gcc.so.abi: Likewise.
* tests/data/test-read-dwarf/test11-pr18828.so.abi: Likewise.
* tests/data/test-read-dwarf/test12-pr18844.so.abi: Likewise.
* tests/data/test-read-dwarf/test13-pr18894.so.abi: Likewise.
* tests/data/test-read-dwarf/test14-pr18893.so.abi: Likewise.
* tests/data/test-read-dwarf/test15-pr18892.so.abi: Likewise.
* tests/data/test-read-dwarf/test16-pr18904.so.abi: Likewise.
* tests/data/test-read-dwarf/test21-pr19092.so.abi: Likewise.
* tests/data/test-read-dwarf/test22-pr19097-libstdc++.so.6.0.17.so.abi:
Likewise.
* tests/data/test-read-dwarf/test9-pr18818-clang.so.abi: Likewise.
Dodji Seketeli [Wed, 2 Nov 2016 11:33:35 +0000 (12:33 +0100)]
Implement de-duplication for types and decls at DWARF loading time
Many types and decls are redefined in every translation unit that make
up an ELF binary. This patch detects that a DIE represents a type or
decl that has already been defined in the current corpus and so will
not create a new internal representation for it.
The patch defines facilities to build the pretty representation of a
type or decl. It's by looking at the pretty representation of a DIE
that the patch detects that a different DIE has already defined the
same type or decl.
The patch also fixes detection of the const-ness of member functions
as there were many cases where const member functions were not
recognized as const. This fix makes it so that the pretty
representation of the DIE of said member functions match the pretty
representation of their internal representation, as far as the
const-ness is concerned.
One bit of infrastructure change that is used by the const-ness fix is
that method_type now carries const-ness. So a method_decl that has a
const method_type is going to be const itself.
* include/abg-ir.h (method_type::priv_): Introduce new pimpl
pointer here.
(method_type::class_type_): Move this into the pimpl idiom.
(method_type::method_type): Take a new is_const flag.
(method_type::get_class_type): Make this method out-of-line.
(method_type::{s,g}et_is_const): Declare new member functions.
(get_method_type_name): Declare this function as a friend of
the method_type type.
* src/abg-dwarf-reader.cc: Include the new abg-ir-priv.h and
abg-corpus-priv.h.
(typedef die_tu_map_type): Fix comment.
(typedef die_istring_map_type): New typedef.
(class read_context::die_source_dependant_container_set): New
class template.
(read_context::{die_qualified_name_maps_, die_pretty_repr_maps_,
die_pretty_type_repr_maps_}): Define new data members.
(read_context::{get_die_qualified_name, get_die_qualified_name,
get_die_qualified_type_name, get_die_pretty_type_representation,
get_die_pretty_representation, lookup_type_artifact_from_die,
lookup_artifact_from_die, lookup_artifact_from_die_representation,
associate_die_to_artifact_by_repr,
associate_die_to_artifact_by_repr_internal,
lookup_type_from_die}): Define new member functions.
(read_context::lookup_type_from_die_offset): Fix comment.
(get_parent_die, get_scope_die, die_is_decl)
(die_is_namespace, die_is_unspecified, die_is_void_type)
(die_is_pointer_type, die_is_reference_type)
(die_is_pointer_or_reference_type, die_is_class_type)
(die_has_object_pointer, die_this_pointer_from_object_pointer)
(die_this_pointer_is_const, is_decl_tag)
(die_object_pointer_is_for_const_method, die_is_at_class_scope)
(die_name, die_qualified_type_name, die_qualified_decl_name)
(die_qualified_name, die_qualified_type_name_empty)
(die_return_and_parm_names_from_fn_type_die)
(die_function_signature, die_peel_qual_ptr)
(die_function_type_is_method_type, die_pretty_print_type)
(die_pretty_print_decl, die_pretty_print)
(build_subranges_from_array_type_die)
(build_or_get_fn_decl_if_not_suppressed)
(lookup_class_or_typedef_type)
(lookup_class_typedef_or_enum_type_from_corpus)
(is_function_for_die_a_member_of_class)
(add_or_update_member_function): Define new static functions.
(read_context::associate_die_to_decl): Call
associate_die_to_artifact_by_repr.
(read_context::{associate_die_to_type,
schedule_type_for_late_canonicalization}): Take just one "die"
parameter rather than taking a die offset and a die source; adjust
accordingly.
(maybe_canonicalize_type): Likewise.
(finish_member_function_reading): Take a const reference to
function_decl_sptr.
(die_loc_and_name): Use the new die_name function.
(die_is_type): Rename is_type_die into this.
(build_type_decl): Take a new "where_offset" parameter. Adjust.
If a type of the same name as the one for the current DIE is is
already present, do not create a new type; just return the
already-existing one.
(build_enum_type): Take a new "where_offset" parameter. Adjust.
(finish_member_function_reading): Pass two smart pointers by const
reference. Assert that the type of the member function is a
method_type. Some light cleanups.
(add_or_update_class_type): Rename build_class_type_and_add_to_ir.
If a DIE defining the same class has already been seen, then
return that class; don't construct any other internal
representation for the same class. Better handle the updating of
member data and functions. Do not duplicate member types.
(build_qualified_type, build_pointer_type_def)
(build_reference_type): Support de-duplication here.
(build_function_type): Likewise. Support detection and building
of method type. This also supports *const* method type building.
(build_array_type): Use the new
build_subranges_from_array_type_die.
(build_type_decl): Cleanup logic.
(build_or_get_var_decl_if_not_suppressed): Renamed
build_var_decl_if_not_suppressed into this. Perform
de-duplication for data members.
(build_function_decl): Don't set an empty source location. If the
function type cannot be constructed, do not construct the function
decl either. Adjust.
(build_ir_node_from_die): Adjust. When building a function for a
DW_TAG_subroutine_type DIE, use the new
build_or_get_fn_decl_if_not_suppressed.
* src/abg-ir.cc (translation_unit::bind_function_type_life_time):
Fix comment.
(strip_typedef): Adjust.
(qualified_type_def::build_name): Set the prefix name of a the
name of a noop qualifier to "noop-qual", just like what is done in
the new die_qualified_name function.
(struct method_type::priv): New priv type for the method_type
class.
(method_type::method_type): Take a new 'is_const' parameter.
Adjust as the method_type is now pimpl'ed.
(method_type::{get_class_type, set_is_const, get_is_const}):
Define new member functions.
(function_decl::get_pretty_representation_of_declarator): Better
detecter of const-ness.
(class_decl::insert_member_decl): Better setting of the
const-ness.
(class_decl::method_decl::method_decl): Adjust. Deduce the
const-ness of the method_decl from the const-ness of its
method_type.
(copy_member_function): Adjust.
(set_member_is_static): Do not assume a non-nil scope anymore
because member_decl can now be scope-less, at least for a little
while.
* src/abg-reader.cc (push_decl_to_current_scope): Adjust.
(build_function_decl): Style adjustment. Adjust for method_type
const-ness changes.
(build_function_type): Likewise. Also, support the new
"method-class-id" property that flags a function type as being a
method type.
* src/abg-writer.cc (write_function_decl): Style fixes.
(write_function_type): Likewise. Emit a new "method-class-id"
property for function type that is actually a method type. That
property's value is the id of the class of the method type.
* tests/data/test-diff-dwarf-abixml/test0-pr19026-libvtkIOSQL-6.1.so.1.abi: Adjust.
* tests/data/test-diff-dwarf/test0-report.txt: Adjust.
* tests/data/test-diff-filter/test0-report.txt: Adjust.
* tests/data/test-diff-filter/test01-report.txt: Adjust.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report0.txt: Adjust.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report1.txt: Adjust.
* tests/data/test-diff-filter/test31-pr18535-libstdc++-report-0.txt: Adjust.
* tests/data/test-diff-filter/test31-pr18535-libstdc++-report-1.txt: Adjust.
* tests/data/test-diff-pkg/libICE-1.0.6-1.el6.x86_64.rpm--libICE-1.0.9-2.el7.x86_64.rpm-report-0.txt: Adjust.
* tests/data/test-diff-pkg/libsigc++-2.0-0c2a_2.4.0-1_amd64--libsigc++-2.0-0v5_2.4.1-1ubuntu2_amd64-report-0.txt: Adjust.
* tests/data/test-diff-pkg/tbb-4.1-9.20130314.fc22.x86_64--tbb-4.3-3.20141204.fc23.x86_64-report-0.txt: Adjust.
* tests/data/test-diff-pkg/tbb-4.1-9.20130314.fc22.x86_64--tbb-4.3-3.20141204.fc23.x86_64-report-1.txt: Adjust.
* tests/data/test-read-dwarf/libtest23.so.abi: Adjust.
* tests/data/test-read-dwarf/libtest24-drop-fns-2.so.abi: Adjust.
* tests/data/test-read-dwarf/libtest24-drop-fns.so.abi: Adjust.
* tests/data/test-read-dwarf/test10-pr18818-gcc.so.abi: Adjust.
* tests/data/test-read-dwarf/test11-pr18828.so.abi: Adjust.
* tests/data/test-read-dwarf/test12-pr18844.so.abi: Adjust.
* tests/data/test-read-dwarf/test13-pr18894.so.abi: Adjust.
* tests/data/test-read-dwarf/test14-pr18893.so.abi: Adjust.
* tests/data/test-read-dwarf/test15-pr18892.so.abi: Adjust.
* tests/data/test-read-dwarf/test16-pr18904.so.abi: Adjust.
* tests/data/test-read-dwarf/test17-pr19027.so.abi: Adjust.
* tests/data/test-read-dwarf/test18-pr19037-libvtkRenderingLIC-6.1.so.abi: Adjust.
* tests/data/test-read-dwarf/test19-pr19023-libtcmalloc_and_profiler.so.abi: Adjust.
* tests/data/test-read-dwarf/test20-pr19025-libvtkParallelCore-6.1.so.abi: Adjust.
* tests/data/test-read-dwarf/test21-pr19092.so.abi: Adjust.
* tests/data/test-read-dwarf/test22-pr19097-libstdc++.so.6.0.17.so.abi: Adjust.
* tests/data/test-read-dwarf/test8-qualified-this-pointer.so.abi: Adjust.
* tests/data/test-read-dwarf/test9-pr18818-clang.so.abi: Adjust.
Dodji Seketeli [Tue, 1 Nov 2016 13:05:45 +0000 (14:05 +0100)]
Setup per-corpus type maps indexed by type names
This patch creates per-corpus maps that associate, for a certain kind
of type, the fully qualified name of the type to the type.
So there is a map for class_decl, one for enum_type_decl, one for
type_decl, etc.
These maps are populated when a new type is added to its scope.
The patch defines overloads of the function
maybe_update_types_lookup_map() that update the right map, depending
on the kind of type we are looking at.
Note that there also is a map in each class that associates a
signature string to a member functions. This is so that member
functions of a given class can be looked up by signature.
This is so that looking up a type becomes now much faster than having
to walk all the translation units of a corpus to find one.
Note that this patch is specifically part of the series of patches
that implements types and declarations de-duplication while reading
DWARF information.
The patch might slightly change the output of abi serialization or
comparison so it needs some adjustments of some test reference files.
That adjustment is not done here. Rather, it's done at once in
another patch of the set.
* include/abg-corpus.h (corpus::priv_): Make this public so that
functions from outside of the class can access it. These
functions are meant to be used only by code that is *inside*
libabigail.so, though.
* src/abg-corpus-priv.h: New file.
* src/abg-corpus.cc: Include the new abg-corpus-priv.h file.
(struct regex_t_deleter): Move this to abg-sptr-utils.h.
(build_sptr<regex_t>): Move the declaration of this function
template specialization to abg-sptr-utils.h and its definition to
abg-sptr-utils.cc.
(typedef regex_t_sptrs_type, typedef str_var_ptr_map_type)
(struct corpus::exported_decls_builder::priv, struct
corpus::priv): Move these declarations to the new
abg-corpus-priv.h.
(maybe_update_types_lookup_map): Define overloads of this (one per
kind of type).
(lookup_{basic, class, enum, typedef, class_or_typedef,
class_typedef_or_enum, qualified, pointer, reference, array,
function}_type): Define new functions.
* include/abg-ir.h (typedef istring_type_base_wptr_map_type)
(typedef istring_type_or_decl_base_sptr_map_type): Declare new
typedefs.
(class_decl::find_member_function_from_signature): Declare new
member function.
* src/abg-ir.cc: Include the new abg-corpus-priv.h file.
(maybe_update_types_lookup_map): Remove this initial function.
There are now new overloads in abg-corpus.cc for it.
(scope_decl::{add_member_decl, insert_member_decl}): Adjust.
(class_decl::{set_is_declaration_only, find_member_function,
add_member_function}): Adjust.
(class_decl::find_member_function_from_signature): Define new
member function.
* include/abg-sptr-utils.h (struct regex_t_deleter): Declare new
type.
(build_sptr<regex_t>): New build function template
specializations.
* src/abg-sptr-utils.cc: New file.
* src/Makefile.am: Add src/abg-sptr-utils.cc and
src/abg-corpus-priv.h to the build system.
Dodji Seketeli [Tue, 1 Nov 2016 12:25:05 +0000 (13:25 +0100)]
Allow pretty printing function decls for internal purposes
It appears that function_decl::get_pretty_representation doesn't make
the difference between internal and non-internal purposes. This patch
fixes that by making the helper
get_pretty_representation_of_declarator() take an "internal" flag and
calls that.
* include/abg-ir.h
(function_decl::get_pretty_representation_of_declarator): Take an
"internal" flag.
* src/abg-ir.cc
(function_decl::get_pretty_representation_of_declarator): Take an
"internal" flag.
(function_decl::get_pretty_representation): Pass the "internal"
flag to the function
function_decl::get_pretty_representation_of_declarator.
(function_decl::parameter::get_type_name): Better handle variadic
parameter type.
(function_decl::parameter::get_type_pretty_representation):
Likewise.
Dodji Seketeli [Sat, 26 Nov 2016 10:01:45 +0000 (11:01 +0100)]
A suppressed diff node implies suppressing all equivalent nodes too
When a diff node N is suppressed (for instance, using the
--headers-dir{1,2} option of abidiff}, it's only that diff node that
is suppressed. We forget to suppress diff nodes that are equivalent
to N.
Here is why we forget to suppress diff ndoes that are equivalent.
apply_suppressions walks the diff node graph to mark diff nodes as
suppressed. But it does the walking by making sure each diff node's
*class of equivalence* is visited once. This is not only a way to
prevent infinite loops while visiting the graph, but also an
optimization as it avoids walking two equivalent diff nodes.
But then it can happen that we forget to categorize some diff nodes
inside a given class of equivalence, even though we categorized some
others.
This patch makes it so that when a diff node inside a class of
equivalence is categorized as SUPPRESSED, the canonical diff node of
that class of equivalence is categorized as SUPPRESSED too. That way,
to know if a diff node is suppressed, we just need to look at its
canonical diff node.
While doing this, I noticed that abidiff and abipkgdiff are not
dropping private types from libabigail's internal representation, even
though the Library now has that capability. The patch fixes that.
But then the patch adds a --dont-drop-private-types option to abidiff
to avoid dropping those private types from the IR, so that regression
tests can make sure that a suppressed diff node implies suppression
all equivalent nodes too.
* doc/manuals/abidiff.rst b/doc/manuals/abidiff.rst: Document the
new --dont-drop-private-types option.
* src/abg-comparison.cc (diff::is_filtered_out): If the canonical
type was suppressed then the current diff node is filtered out.
(suppression_categorization_visitor::visit_{begin,end}):
Categorized the canonical node as SUPPRESSED if the current node
is suppressed.
* tools/abidiff.cc (options::drop_private_types): New data member.
(options::options): Initialize it.
(display_usage): Add new help string for the new
--dont-drop-private-types option.
(parse_command_line): Parse the new --dont-drop-private-types
option.
(set_suppressions): Generate suppression specification from header
directories given in parameter and stick them to the read context.
* tools/abipkgdiff.cc (compare): Likewise.
* tests/data/test-diff-suppr/libtest34-v0.so: New test input.
* tests/data/test-diff-suppr/libtest34-v1.so: Likewise.
* tests/data/test-diff-suppr/test34-report-0.txt: New reference
report.
* tests/data/test-diff-suppr/test34-v0.c: Source code for the new
test input.
* tests/data/test-diff-suppr/test34-v1.c: Likewise.
* tests/data/test-diff-suppr/test34-priv-include-dir-v0/test34-priv-include-v0.h:
Likewise.
* tests/data/test-diff-suppr/test34-priv-include-dir-v1/test34-priv-include-v1.h:
Likewise.
* tests/data/test-diff-suppr/test34-pub-include-dir-v0/test34-pub-include-v0.h:
Likewise.
* tests/data/test-diff-suppr/test34-pub-include-dir-v1/test34-pub-include-v1.h:
Likewise.
* tests/data/Makefile.am: Add new test input material above to
source distribution.
* tests/test-diff-suppr.cc (in_out_spec): Compare the two new test
library provided. Add --dont-drop-private-types to test30*.
Dodji Seketeli [Wed, 23 Nov 2016 09:54:44 +0000 (10:54 +0100)]
Update NEWS and ChangeLog for 1.0.rc6
* ChangeLog: Update this automatically using "make
update-changelog".
* NEWS: update this by editing the output of 'git shortlog
libabigail-1.0.rc5..HEAD'.
Dodji Seketeli [Thu, 24 Nov 2016 10:24:04 +0000 (11:24 +0100)]
Avoid using size_t to get DWARF data
This can cause issues on i686 compared to x86_64 as size_t has
different size on these two platforms. Rather, use int64_t which has
the same fixed size on both platforms.
* src/abg-dwarf-reader.cc (die_size_in_bits, die_location_expr):
Take uint64_t rather than size_t and adjust.
(expr_result::const_value_): Make this be int64_t rather than
ssize_t.
(expr_result::expr_result): Take int64_t rather than ssize_t.
(expr_result::const_value): Return int64_t rather than ssize_t.
(expr_result::{operator(), operator=, operator+=}): Make these
operators return or take int64_t.
too.
(op_pushes_constant_value, op_manipulates_stack)
(op_is_arith_logic, op_is_control_flow)
(eval_last_constant_dwarf_sub_expr, die_member_offset)
(die_virtual_function_index): Take
uint64_t rather than size_t, or int64_t rather than ssize_t.
(finish_member_function_reading, build_class_type_and_add_to_ir)
(build_union_type_and_add_to_ir): Adjust.
Dodji Seketeli [Wed, 23 Nov 2016 17:12:50 +0000 (18:12 +0100)]
Support reading data member offset from DW_AT_bit_offset
There are times where the DW_AT_data_member_location attribute is set
to zero and where the actual offset of the data member is the value of
the DW_AT_bit_offset. This seems to be happening when a union type is
involved.
To get the offset of a data member, this patch makes us read the
DW_AT_bit_offset when it's present. Otherwise, it gets the offset
from the DW_AT_data_member_location as we used to do.
In the passing the patch fixes the offset of base classes; the
nubmer of bytes value was what was being used, rather than the number
bits value.
* src/abg-dwarf-reader.cc (die_member_offset): Better comments.
Support reading the bit offset also from the DW_AT_bit_offset
attribute when it's present. Make sure this always returns a
value in bits.
(build_class_type_and_add_to_ir): No need to multiply (by 8) the
value returned by die_member_offset anymore because it's now in
bits directly.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report0.txt: Adjust.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report1.txt: Adjust.
* tests/data/test-read-dwarf/test1.abi: Adjust.
* tests/data/test-read-dwarf/test11-pr18828.so.abi: Adjust.
* tests/data/test-read-dwarf/test12-pr18844.so.abi: Adjust.
* tests/data/test-read-dwarf/test13-pr18894.so.abi: Adjust.
* tests/data/test-read-dwarf/test14-pr18893.so.abi: Adjust.
* tests/data/test-read-dwarf/test15-pr18892.so.abi: Adjust.
* tests/data/test-read-dwarf/test16-pr18904.so.abi: Adjust.
* tests/data/test-read-dwarf/test17-pr19027.so.abi: Adjust.
* tests/data/test-read-dwarf/test19-pr19023-libtcmalloc_and_profiler.so.abi:
Adjust.
* tests/data/test-read-dwarf/test21-pr19092.so.abi: Adjust.
* tests/data/test-read-dwarf/test22-pr19097-libstdc++.so.6.0.17.so.abi:
Adjust.
Dodji Seketeli [Wed, 23 Nov 2016 13:55:59 +0000 (14:55 +0100)]
Lexicographically sort union data members in change reports
Until now, when reporting about struct or union changes, data members
were sorted by using their offset; the data member with the smallest
offset coming first.
But then in unions, all data member have the same offset. In that
case, the patch sort them lexicographically, by taking their name into
account.
* src/abg-comparison.cc (data_member_comp::operator()): Data
members with the same offset are sorted lexicographically, by
taking their name into account.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report0.txt:
Adjust.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report1.txt:
Likewise.
Dodji Seketeli [Wed, 23 Nov 2016 12:13:19 +0000 (13:13 +0100)]
Better diagnostics when wget is missing
When wget is missing building the fedabipkgdiff tool is disabled.
This patch fixes diagnostics in that case.
* configure.ac: When wget is missing then make the disabling of
the building of the fedabipkgdiff tool show up in the
configuration summary and emit a notice.
Dodji Seketeli [Tue, 15 Nov 2016 00:16:46 +0000 (01:16 +0100)]
Support union types
This patch makes Libabigail understand C and C++ union types. It
defines a new class abigail::ir::union_decl to represent the
declaration of a union type. It also defines a new type
abigail::comparison::union_diff to represent the changes between two
union types. The patch then adds facilities to read union types from
DWARF and abixml and also to write union types into the abixml format.
As union types and class types have a lot in common, the patch tries
very hard to share code between the abigail::ir::class_decl and
abigail::ir::union_decl. To do so, a new class
abigail::ir::class_or_union is created. It's the base class for both
abigai::ir::class_decl and abigail::ir::union_decl. Its data members
and methods represent the set of data and behaviour that are common to
classes and unions. A lot of code and data that were initially in
abigail::ir::class_decl got moved into the new
abigail::ir::class_or_union class.
Similary, the patch creates a new class
abigail::comparison::class_or_union_diff that is a base class for both
the existing class abigail::comparison::class_diff and the newly
created class abigail::comparison::union_diff. The new class
abigail::comparison::class_or_union_diff contains data and behaviour
that are common to both union_diff and class_diff and that were
previously in class_diff.
The rest of the patch is mostly adjustment so that code that was
supposed to work with class class_decl only can now work with class
class_or_union when it makes sense. Similarly for class_diff and
class_or_union_diff.
The patch adds regression tests into the test suite and adjust many
existing tests involving binaries that contain union types; the
reference output of those tests now take union types into account.
* include/abg-fwd.h (class_or_union, union_decl): Forward-declare
new types.
(is_class_or_union_type, is_union_type): Declare new functions.
* include/abg-ir.h (method_type::class_type_): Make this be of
class_or_union_wptr type.
(method_type::method_type): Make the class_type parameter be of
class_or_union_wptr type.
(method_type::{g,s}et_class_type): Take or return a
class_or_union_sptr.
(member_base, method_decl, member_function_template)
(member_class_template, member_base::hash)
(member_function_template::hash, member_class_template::hash):
Take these class types out of the class_decl scope.
(is_method_decl): Adjust.
(operator==, opertor!=): Adjust overloads for
member_function_template_sptr and member_class_template_sptr.
(class class_or_union): Declare new type.
(class class_decl): Make this class inherit class_or_union class.
(class_decl::{add_member_decl, insert_member_decl,
remove_member_decl, set_size_in_bits, get_size_in_bits,
get_alignment_in_bits, set_alignment_in_bits,
get_is_declaration_only, set_is_declaration_only,
set_definition_of_declaration, get_definition_of_declaration,
get_earlier_declaration, set_earlier_declaration,
insert_member_type, add_member_type, remove_member_type,
get_member_type, find_member_type, add_data_member,
get_data_members, find_data_member, get_non_static_data_members,
add_member_function, get_member_functions, find_member_function,
add_member_function_template, get_member_function_templates,
add_member_class_template, get_member_class_templates): Move these
to the parent class class_or_union.
(copy_member_function, equals): Add overloads for class_or_union.
(struct class_or_union::hash): Declare new type.
(class union_decl): Declare new type.
(equals, copy_member_function): New overloads for class union_decl
type.
(ir_node_visitor::visit): Add new overloads for union_decl* and
class_or_union*.
* src/abg-ir.cc (get_member_function_is_ctor)
(set_member_function_is_ctor, get_member_function_is_dtor)
(set_member_function_is_dtor, get_member_function_is_const)
(set_member_function_is_const, get_member_function_vtable_offset)
(set_member_function_vtable_offset)
(get_member_function_is_virtual, set_member_function_is_virtual)
(maybe_update_types_lookup_map, get_location)
(get_method_type_name, is_at_global_scope, is_at_class_scope):
Adjust.
(is_class_or_union_type, is_union_type): Define new functions.
(type_base::get_canonical_type_for, maybe_adjust_canonical_type)
(method_type::method_type, method_type::set_class_type)
(function_decl::get_pretty_representation)
(function_decl::get_first_non_implicit_parm)
(function_decl::clone): Adjust.
(equals): Adjust the overload for function_type.
(struct class_or_union::priv): Define new type.
(class::priv::{declaration_, definition_of_declaration_,
member_types_, data_members_, non_static_data_members_,
member_functions_, mem_fns_map_, member_function_templates_,
member_class_templates_, is_declaration_only_}): Move these data
member into class_or_union::priv.
(class_priv::{mark_as_being_compared, unmark_as_being_compared,
comparison_started}): Moved these member functions to
class_or_union::priv.
(class_or_union::{class_or_union, traverse, ~class_or_union,
add_member_decl, remove_member_decl, insert_member_type,
add_member_type, get_size_in_bits, remove_member_type,
get_alignment_in_bits, set_alignment_in_bits, set_size_in_bits,
get_is_declaration_only, set_is_declaration_only,
set_definition_of_declaration, get_definition_of_declaration,
get_earlier_declaration, set_earlier_declaration,
get_member_types, find_member_type, add_data_member,
get_data_member, find_data_member, add_member_function,
get_member_functions, find_member_function,
add_member_function_template, get_member_function_templates,
add_member_class_template, get_member_class_templates,
has_no_member, insert_member_decl, operator==}): Define new member
functions.
(class_decl::{add_member_decl, remove_member_decl,
insert_member_type, add_member_type, get_size_in_bits,
remove_member_type, get_alignment_in_bits, set_alignment_in_bits,
set_size_in_bits, get_is_declaration_only,
set_is_declaration_only, set_definition_of_declaration,
get_earlier_declaration, set_earlier_declaration,
get_member_types, find_member_type, add_data_member,
get_data_member, find_data_member, add_member_function,
get_member_functions, find_member_function,
add_member_function_template, get_member_function_templates,
add_member_class_template, get_member_class_templates): Move these
member functions into class_or_union.
(class_decl::{class_decl, get_definition_of_declaration,
insert_member_decl, add_member_function, has_no_base_nor_member}):
Adjust.
(equals, copy_member_function): Define new overloads for
class_or_union.
(equals): Adjust the overload for class_decl.
(method_decl::{method_decl, set_linkage_name, ~method_decl,
get_type, set_scope}): Remove from the class_decl scope.
(member_base::operator==, member_function_template::operator==):
Likewise.
(member_function_template::traverse)
(member_class_template::operator==)
(member_class_template::traverse): Likewise.
(operator==, operator!=): Adjust the overlod for
member_function_template_sptr.
(is_method_decl, fixup_virtual_member_function)
(set_member_is_static): Adjust.
(virtual_member_function_less_than::operator()): Likewise.
(union_decl::{union_decl, get_pretty_representation, operator==,
traverse}): Define new member functions.
(equals, copy_member_function): Define new overloads for
union_decl.
(hash_type_or_decl): Adjust.
(ir_node_visitor::visit_{begin, end}): Adjust. Add new overloads
for class_or_union* and union_decl*.
* include/abg-comparison.h (changed_member_function_sptr)
(string_member_function_sptr_map): Adjust these typedefs.
(class class_or_union_diff): Declare new type.
(class_diff): Adjust to make this inherit the new
class_or_union_diff type.
(class_diff::{get_priv, member_types_changes,
data_members_changes, inserted_data_members, deleted_data_members,
member_fn_tmpls_changes, member_fn_tmpls_changes,
member_class_tmpls_changes}): These member functions got moved
into -- and shared with -- class_or_union_diff class.
(class union_diff): Declare new type.
(typedef union_diff_sptr): New typedef.
(compute_diff): New overload for union_diff
(is_class_diff, is_union_diff): Declare new functions.
* src/abg-comparison.cc (is_class_diff, is_union_diff): Define new
functions.
(compute_diff_for_types): Support union_decl.
(represent): Adjust.
(represent_data_member): Do not show offset information for data
members of unions as all union data members are at offset 0.
(struct class_or_union_diff::priv): New type.
(class_or_union_diff::priv::{member_type_has_changed,
subtype_changed_dm, member_class_tmpl_has_changed,
get_deleted_non_static_data_members_number,
get_inserted_non_static_data_members_number,
count_filtered_subtype_changed_dm, count_filtered_changed_dm,
count_filtered_changed_mem_fns, count_filtered_inserted_mem_fns,
count_filtered_deleted_mem_fns}): Define new member functions.
(class_or_union_diff::{class_or_union_diff, finish_diff_type,
lookup_tables_empty, lookup_tables_empty,
ensure_lookup_tables_populated, allocate_priv_data, get_priv,
~class_or_union_diff, first_class_or_union, second_class_or_union,
member_types_changes, member_types_changes, data_members_changes,
inserted_data_members, deleted_data_members, member_fns_changes,
changed_member_fns, member_fns_changes, inserted_member_fns,
member_fn_tmpls_changes, member_fn_tmpls_changes,
member_class_tmpls_changes, member_class_tmpls_changes,
has_changes, has_local_changes, report, chain_into_hierarchy}):
Define new member functions.
(class_diff::priv::{member_types_changes_, data_members_changes,
member_fn_tmpls_changes_, member_class_tmpls_changes_,
deleted_member_types_, inserted_member_types_,
changed_member_types_, sorted_changed_member_types_,
deleted_data_members_, deleted_dm_by_offset_,
inserted_data_members_, inserted_dm_by_offset_,
subtype_changed_dm_, sorted_subtype_changed_dm_, changed_dm_,
sorted_changed_dm_, deleted_member_functions_,
inserted_member_functions_, changed_member_functions_,
sorted_changed_member_functions_, deleted_member_class_tmpls_,
inserted_member_class_tmpls_, changed_member_class_tmpls_,
sorted_changed_member_class_tmpls_}): Move these data members into
class_or_union_diff::priv.
(class_diff::{clear_lookup_tables, lookup_tables_empty,
ensure_lookup_tables_populate}): Adjust.
(class_diff::allocate_priv_data): Define new function.
(class_diff::priv::{count_filtered_changed_mem_fns,
count_filtered_inserted_mem_fns, count_filtered_deleted_mem_fns,
chain_into_hierarchy, class_diff}): Likewise.
(class_diff::{member_types_changes, data_members_changes,
inserted_data_members, deleted_data_members,
member_fn_tmpls_changes, member_fn_tmpls_changes,
member_class_tmpls_changes}): These are deleted as they got moved
to class_or_union_diff.
(class_diff::report): Adjust.
(union_diff::{clear_lookup_tables, lookup_tables_empty,
ensure_lookup_tables_populated, allocate_priv_data, union_diff,
finish_diff_type, first_union_decl, second_union_decl,
get_pretty_representation, report}): Define new functions.
(compute_diff): Define an overload for union_decl_sptr.
(function_decl_diff::report): Adjust.
(corpus_diff::priv::apply_suppressions_to_added_removed_fns_vars):
Adjust.
(corpus_diff::report): Adjust.
* src/abg-hash.cc (member_base::hash::operator)
(member_function_template::hash::operator)
(member_class_template::hash::operator): Move these out of the
class_decl scope.
(class_or_union::hash::operator): Define new member function.
(class_decl::hash::operator): Adjust.
(type_base::dynamic_hash::operator): Support hashing of
union_decl. Adjust.
* src/abg-suppression.cc (type_suppression::suppresses_diff):
Adjust.
* src/abg-dwarf-reader.cc (typedef die_class_or_union_map_type):
Define new typedef.
(read_context::{die_wip_classes_map_,
alternate_die_wip_classes_map_, type_unit_die_wip_classes_map_):
Make these data member have type die_class_or_union_map_type.
(read_context::{lookup_type_from_die_offset, die_wip_classes_map,
is_wip_class_die_offset, resolve_declaration_only_classes}):
Adjust.
(finish_member_function_reading, build_class_type_and_add_to_ir)
(build_function_type, build_function_decl, build_reference_type)
(type_is_suppressed, build_function_decl)
(maybe_canonicalize_type, maybe_set_member_type_access_specifier):
Adjust.
(build_union_type_and_add_to_ir): Define new static function.
(build_ir_node_from_die): Support DW_TAG_union_type DIE tag.
* src/abg-reader.cc (handle_element_node): Handle union_decl.
(build_function_decl, build_function_decl_if_not_suppressed):
Adjust.
(build_union_decl_if_not_suppressed, build_union_decl)
(handle_union_decl): Define new functions.
(build_class_decl): Adjust.
* src/abg-writer.cc (record_decl_only_type_as_emitted): Adjust.
(write_decl): Adjust. Support writting union_decl type.
p (write_class_decl_opening_tag, write_class_decl): Adjust. Call
the new write_class_or_union_is_declaration_only.
(write_union_decl_opening_tag, write_union_decl): Define new
static functions.
(write_member_tpe): Support writting union decl.
* tests/test-diff-dwarf.cc (in_out_specs): Add new tests for this
union type support.
* tests/data/test-diff-dwarf/libtest37-union-v0.so: New test input.
* tests/data/test-diff-dwarf/libtest37-union-v1.so: Likewise.
* tests/data/test-diff-dwarf/libtest38-union-v0.so: Likewise.
* tests/data/test-diff-dwarf/libtest38-union-v1.so: Likewise.
* tests/data/test-diff-dwarf/libtest39-union-v0.so: Likewise.
* tests/data/test-diff-dwarf/libtest39-union-v1.so: Likewise.
* tests/data/test-diff-dwarf/test37-union-report-0.txt: Likewise.
* tests/data/test-diff-dwarf/test38-union-report-0.txt: Likewise.
* tests/data/test-diff-dwarf/test39-union-report-0.txt: Likewise.
* tests/data/test-diff-dwarf/test37-union-v0.cc: Source code for
new test input.
* tests/data/test-diff-dwarf/test37-union-v1.cc: Likewise.
* tests/data/test-diff-dwarf/test38-union-v0.cc: Likewise.
* tests/data/test-diff-dwarf/test38-union-v1.cc: Likewise.
* tests/data/test-diff-dwarf/test39-union-v0.cc: Likewise.
* tests/data/test-diff-dwarf/test39-union-v1.cc: Likewise.
* tests/data/test-diff-dwarf-abixml/test0-pr19026-libvtkIOSQL-6.1.so.1.abi:
Update test reference.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report0.txt:
Likewise.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report1.txt:
Likewise.
* tests/data/test-read-dwarf/libtest23.so.abi: Likewise.
* tests/data/test-read-dwarf/libtest24-drop-fns-2.so.abi:
Likewise.
* tests/data/test-read-dwarf/libtest24-drop-fns.so.abi: Likewise.
* tests/data/test-read-dwarf/test10-pr18818-gcc.so.abi: Likewise.
* tests/data/test-read-dwarf/test11-pr18828.so.abi: Likewise.
* tests/data/test-read-dwarf/test12-pr18844.so.abi: Likewise.
* tests/data/test-read-dwarf/test13-pr18894.so.abi: Likewise.
* tests/data/test-read-dwarf/test14-pr18893.so.abi: Likewise.
* tests/data/test-read-dwarf/test15-pr18892.so.abi: Likewise.
* tests/data/test-read-dwarf/test16-pr18904.so.abi: Likewise.
* tests/data/test-read-dwarf/test17-pr19027.so.abi: Likewise.
* tests/data/test-read-dwarf/test18-pr19037-libvtkRenderingLIC-6.1.so.abi:
Likewise.
* tests/data/test-read-dwarf/test19-pr19023-libtcmalloc_and_profiler.so.abi:
Likewise.
* tests/data/test-read-dwarf/test20-pr19025-libvtkParallelCore-6.1.so.abi:
Likewise.
* tests/data/test-read-dwarf/test21-pr19092.so.abi: Likewise.
* tests/data/test-read-dwarf/test22-pr19097-libstdc++.so.6.0.17.so.abi:
Likewise.
* tests/data/test-read-dwarf/test9-pr18818-clang.so.abi:
Likewise.
Dodji Seketeli [Thu, 10 Nov 2016 12:06:50 +0000 (13:06 +0100)]
Support empty properties in INI files
The ini file parser doesn't support parsing properties with no value.
This patch adds that feature, as it turned out to be a pre-requisite
for reading Linux Kernel ABI whitelist files.
* include/abg-ini.h (simple_property::simple_property): Add a new
constructor for empty values.
(simple_property::has_empty_value): Declare new member function.
* src/abg-ini.cc (simple_property::{simple_property,
has_empty_value}): Define new member functions.
(read_context::read_property): Support reading a property with no
value.
(write_property_value, write_property): Support writting a
property with empty value.
Dodji Seketeli [Wed, 9 Nov 2016 14:29:20 +0000 (15:29 +0100)]
Apply harmless and harmful filters in one pass
When comparing linux kernels with lots of changes, walking changes
twice just to apply harmless and harmful change filters was dominating
the performance profile.
This patch performs the harmless and harmful filtering in one pass.
This makes the overall comparison go from 15 minutes to 10 minutes
when comparing a 4.7 kernel from fedora24 and a 4.8 kernel from
fedora26.
* include/abg-comp-filter.h (class harmless_harmful_filter):
Decalre new class.
(typedef harmless_harmful_filter_sptr): Declare new typedef.
(class harmless_filter, class harmful_filter): Remove these class
declarations.
(typedef harmful_filter_sptr, harmless_filter_sptr): Remove these
typedefs.
* src/abg-comp-filter.cc (categorize_harmless_diff_node)
(categorize_harmful_diff_node): Define new static functions.
({harmless, harmful}_filter::{visit, visit_end}): Remove these
member functions.
(harmless_harmful_filter::{visit, visit_end}): Define new member
functions.
* src/abg-comparison.cc (diff_context::diff_context): Register the
new harmless_harmful_filter, and remove the premier
harmless_filter and harmful_filter.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
# Please enter the commit message for your changes. Lines starting
# with '#' will be ignored, and an empty message aborts the
commit. # On branch kabidiff-dedup # Changes to be committed: #
(use "git reset HEAD <file>..." to unstage) # # modified:
include/abg-comp-filter.h # modified: src/abg-comp-filter.cc #
modified: src/abg-comparison.cc # # Untracked files: # (use "git
add <file>..." to include in what will be committed) # # diff.txt
# prtests/ # tests/data/test-read-dwarf/libtest23.so.abi.conflict
Dodji Seketeli [Tue, 8 Nov 2016 11:22:50 +0000 (12:22 +0100)]
Avoid stripping typedefs too much
strip_typedef re-constructs entire type trees and canonicalize them.
Calling it a lot on very deep and recursive trees can be costly.
Unfortunately, categorization of changes uses strip_typedef quite a
bit to determine if the two types that are different are still
compatible. When used on changesets generating from comparing two
Linux Kernels, it makes changes categorization dominate CPU usage
profiles.
This patch avoids using strip_typedef to determine if two types are
compatible and thus speeds up type categorization of changes involving
lots of deep and recursive type trees.
* src/abg-ir.cc (types_are_compatible)
(is_compatible_with_class_type): Do not strip typedefs. Just get
their leaf types.
Dodji Seketeli [Tue, 8 Nov 2016 11:31:03 +0000 (12:31 +0100)]
Misc style cleanups in abg-ir.cc
* src/abg-ir.cc (equals): In overloads for function_type and
class_decl, avoid returning a constant when we can return a
variable like in the rest of the code.
Dodji Seketeli [Tue, 1 Nov 2016 10:37:41 +0000 (11:37 +0100)]
Factorize out string representation of array_type_def::subrange_type
As we are going to need to print names of array types from DIEs
directly, we'll need to represent names of subranges.
This patch factorizes the string representation of the
array_type_def::subrange_type type.
* src/abg-ir.cc (array_type_def::subrange_type::{as_string,
vector_as_string}): Define methods.
(array_type_def::get_subrange_representation): Use the new
vector_as_string method.
Dodji Seketeli [Tue, 1 Nov 2016 10:16:55 +0000 (11:16 +0100)]
Factorize out parsing of integral types
Until now, integral_type has been just a "private" helper type used in
the building of a type_decl.
Now it's going to be helpful in determining the name of an integral
type, directly from DIEs -- without having to build a type_decl.
This patch factorizes out the parsing and building of an integral_type
by introducing a src/abg-ir-priv.h file that is meant to declare
interfaces that are going to be private to libabigail.so but usable by
all of its modules.
* src/abg-ir-priv.h: New file.
* src/Makefile.am: Add abg-ir-priv.h to the build system.
* src/abg-ir.cc: Include the new abg-ir-priv.h header file.
(class_integral_type): Move this type
declaration to the new abg-ir-priv.h header.
(integral_type::modifiers_type): Make this non-static.
(parse_integral_type): This new overload is a factorized out of
...
(integral_type::integral_type): ... here.
Dodji Seketeli [Mon, 31 Oct 2016 15:31:38 +0000 (16:31 +0100)]
Consider a method_decl as always being a member decl
The is_member_decl() function considers that a decl is a member decl
only if it's at class scope.
In preparation for the support of incremental building of method
decls, a method decl, even before being added to its final class, must
always be considered as a member decl. This allows for instance, the
proper pretty printing of the method decl even before it's added to
its class.
This patch prepares the upcoming support of incremental building of
method decls by making is_member_decl() work on a method_decl that
hasn't yet been added to a class, so that is not, strictly-speaking,
at class scope yet.
* src/abg-ir.cc (is_member_decl): Consider a method decl as always
being a member decl.
(is_member_function): Use is_member_decl.
Dodji Seketeli [Mon, 31 Oct 2016 12:52:53 +0000 (13:52 +0100)]
Cleanup void and variadic parameter type interfaces
While working on something else, it appeared that renaming
abigail::environment::get_void_type_decl() to
abigail::environment::get_void_type() and
abigail::environment::get_variadic_parameter_type_decl() to
abigail::environment::get_variadic_parameter_type() would be an
improvement.
This patch implements that.
* include/abg-ir.h (environment::{get_void_type,
get_variadic_parameter_type}): Renamed get_void_type_decl and
get_variadic_parameter_type_decl to these.
(environment::is_void_type): Remove the overload that takes a bare
pointer.
(environment::is_variadic_parameter_type): Declare new member
function.
* src/abg-ir.cc (environment::void_type_): Renamed the data member
void_type_decl_ into this.
(environment::variadic_marker_type_): Renamed the data member
variadic_marker_type_decl_ into this.
(environment::{get_void_type, get_variadic_parameter_type}):
Renamed get_void_type_decl and get_variadic_parameter_type_decl to
these.
(environment::is_void_type): Take a smart pointer now.
(environment::is_variadic_parameter_type): Define new member
function.
(synthesize_function_type_from_translation_unit): Adjust.
(function_decl::parameter::get_pretty_representation): Likewise.
* src/abg-comparison.cc (is_diff_of_variadic_parameter_type):
Adjust.
* src/abg-dwarf-reader.cc (build_function_type)
(build_ir_node_for_void_type): Likewise.
* src/abg-reader.cc (build_function_parameter)
(build_function_decl, build_function_type): Likewise.
Dodji Seketeli [Mon, 31 Oct 2016 11:26:22 +0000 (12:26 +0100)]
Cleanup some entry points in abg-fwd.h
While looking at something else I came accross some interface cleanup
opportunities, as usual. This patch honours some of those
opportunities.
* include/abg-fwd.h (add_decl_to_scope): Pass the scope smart
pointer by reference.
(is_member_type): pass the type smart pointer by reference.
(is_function_decl, is_pointer_type, is_reference_type)
(is_qualified_type, is_function_type, is_method_type)
(is_array_type): Take a type_or_decl base pointer, rather than
either a decl_base or type_base pointer.
* include/abg-ir.h (translation_unit::set_corpus): Take a pointer
to non-const corpus.
(translation_unit::get_corpus): Add a non-const overload.
(type_or_decl_base::get_corpus): Likewise.
(type_or_decl_base::set_translation_unit): Take a pointer to
non-corpus translation_unit.
(type_or_decl_base::get_translation_unit): Add a non-const
overload.
(scope_decl::{add_member_decl, insert_member_decl}): Pass the
member smart pointer by reference.
(scope_decl::remove_member_decl): Take a non-const smart pointer.
(class_decl::add_member_decl): Pass the decl smart pointer by
reference.
(is_method_decl): Take pointer or reference to type_or_decl_base
rather than function_decl.
* src/abg-ir.cc (translation_unit::priv::corpus): Make this a
pointer to non-const corpus.
(translation_unit::set_corpus): Take a pointer to non-const
corpus.
(translation_unit::get_corpus): Add a non-const overload.
(translation_unit::get_global_scope): Adjust.
(translation_unit::bind_function_type_life_time): Adjust.
(type_or_decl_base::translation_unit): Make this a pointer to
non-const translation_unit.
(type_or_decl_base::get_corpus): Likewise.
(type_or_decl_base::set_translation_unit): Take a pointer to
non-corpus translation_unit.
(type_or_decl_base::get_translation_unit): Add a non-const
overload.
(is_member_type): pass the type smart pointer by reference.
(scope_decl::{add_member_decl, insert_member_decl}): Take a
reference to the member decl smart pointer. Adjust.
(class_decl::add_member_decl): Likewise.
(scope_decl::remove_member_decl): Take a non-const smart pointer.
(add_decl_to_scope): Pass the scope smart pointer by reference.
(is_decl, is_function_decl, is_pointer_type, is_reference_type)
(is_qualified_type, is_function_type, is_method_type)
(is_method_decl, is_array_type): Take a type_or_decl base pointer,
rather than either a decl_base or type_base pointer.
Dodji Seketeli [Tue, 11 Oct 2016 13:08:13 +0000 (15:08 +0200)]
Canonicalize function types when reading from DWARF
Up until now, only function types pointed to by a pointer to function
was canonicalized. This patch also canonicalizes function types that
are used as types for function declarations.
* src/abg-dwarf-reader.cc (build_function_decl): Canonicalize
function types.
Dodji Seketeli [Tue, 11 Oct 2016 11:08:25 +0000 (13:08 +0200)]
Misc cleanups here and there
While looking at something else, the usual cleanup spree came up.
* src/abg-dwarf-reader.cc (canonicalize_types_scheduled): Fix
identation.
* src/abg-reader.cc (build_class_decl): Use class_decl_sptr rather
than shared_ptr<class_decl>.
* src/abg-writer.cc (write_class_is_declaration_only)
(write_is_struct, write_decl, write_decl_in_scope)
(write_type_decl, write_qualified_type_def)
(write_pointer_type_def, write_reference_type_def)
(write_array_type_def, write_enum_type_decl, write_typedef_decl)
(write_elf_symbol, write_var_decl, write_function_decl)
(write_member_type_opening_tag, write_member_type)
(write_class_decl_opening_tag, write_class_decl): Cleanup
parameters to use the right typedef, rather than the long
shared_ptr<*> form. Pass the shared pointers by reference as
well.
Dodji Seketeli [Fri, 7 Oct 2016 13:46:02 +0000 (15:46 +0200)]
Cleanup functions to detect infinite comparison of class_decl
While looking around, I found some things in need of a cleanup. This
patch addresses those.
* src/abg-ir.cc (class_decl::priv::unmark_as_being_compared): In
the overload that takes a pointer to class_decl, re-use the
overload that takes a reference.
(class_decl::priv::comparison_started): Do not crash if the klass
pointer is nil.
(equals): In the overload for class_decl&, undef the RESULT macro
when it's not used anymore.
Dodji Seketeli [Fri, 7 Oct 2016 13:26:30 +0000 (15:26 +0200)]
Cleanup class_decl inifite comparison detection
We recently used a new type interned_string_set_type to detect
infinite comparison of function_type type. This patch uses the same
type for class_decl infinite comparison detection.
* src/abg-ir.cc (environment::priv::classes_being_compared_): Make
this use the new interned_string_set_type type.
(class_decl::priv::{mark_as_being_compared, comparison_started}):
Adjust.
Dodji Seketeli [Mon, 10 Oct 2016 09:20:04 +0000 (11:20 +0200)]
Apply ODR-based type comparison optimization to function types
Inside a given ABI corpus, during type canonicalization, function
types are compared structurally (member-wise). Note that on the other
hand, class, enums and basic types are compared using an ODR-based
optimization: only their type names are compared.
This makes function types comparison be *super slow* for ABI corpora
with a lot of function types.
This patch fixes that by enabling the ODR-based comparison
optimization for function types too, during type canonicalization.
* src/abg-ir.cc (type_eligible_for_odr_based_comparison):
Factorize this out of type_base::get_canonical_type_for. Also,
add function types to the set of types to use the ODR-based
comparison optimization on.
(type_base::get_canonical_type_for): Use the new
type_eligible_for_odr_based_comparison function.
Dodji Seketeli [Fri, 7 Oct 2016 10:38:27 +0000 (12:38 +0200)]
Prevent infinite loops while comparing two function_type
While comparing two function types a given sub-type can itself have a
sub-type that *is* the same function_type as the one we are looking
at. In that case, an infinite loop appears.
This patch detects those cases, similarly to what we do for class_decl
and avoids the eventual infinite loop.
* include/abg-ir.h (class environment): Make class function_type
be a friend of this class.
(class function_type): Make the equality function for
function_types be a friend of this class.
* src/abg-ir.cc (environment::priv::fn_types_being_compared_): New
data member.
(function_type::priv::{mark_as_being_compared,
unmark_as_being_compared, comparison_started}): Define new member
functions.
(equals): In the overload for function_types, if any of the the
function_type being compared is already being compared, return
early saying that the two function_types are equal. This avoids
Even when the configure script is executed without the
--enable-fedabipkgdiff switch, if one of the dependencies of
fedabipkgdiff is missing (e.g, python), it fails with a fatal error.
It should rather just disable fedabipkgdiff in that case.
This patch fixes this behaviour. It makes it so that it's only when
the --enable-fedabipkgdiff switch provided that a missing dependency
results in a fatal hard error.
* configure.ac: It's only when --enable-fedabipkgdiff is provided
that a missing dependency of the fedabipkgdiff program results in
a fatal error. Otherwise, building fedabipkgdiff is just
disabled.
Add default suppression specifications for C++ binaries
For C++ libraries that are not libstdc++ or boost, this patch defines
default suppression specifications that drop function or variables that
we know are from namespaces that are not meant to be part of the API.
By doing so, we also decrease the memory needed to process the
binaries.
* default.abignore: Add suppressions for non-libstdc++ and
non-boost C++ libraries.
Add default suppression specification for webkitgtk
This patch adds default suppression specifications for webkitgtk and
webkit2gtk so that unnecessary ABI artifacts are dropped from the
in-memory IR. This dramatically helps to lower the memory usage of
libabigail while analyzing the webkit2gtk libraries.
* default.abignore: New suppression specifications for webkitgtk.
This patch allows dropping suppressed ABI artifacts from the in-memory
internal representation right during the DWARF or abixml reading.
In practise, this means that abidw and abilint now have a
--suppressions options to give them suppression specifications. If a
suppression specification that has the "drop" property matches an ABI
artifact (type, function or variable) then that artifact is dropped
from the internal representation. This also applies to abidiff.
Note that now, by default, ABI artifacts (types) that are suppressed
due to the --headers-dir{1,2} option of abidiff are now also dropped
from the IR as well. Incidentally, abidw and abilint tools now have a
--header-dir option too.
* doc/manuals/abidw.rst: Document the new --suppressions and
--headers-dir options off the abidw tool.
* doc/manuals/abilint.rst: Document the new --suppressions and
--headers-dir options on the abilint tool.
* doc/manuals/libabigail-concepts.rst: Document the new "drop" and
"name_not_regexp" properties on suppression directives.
* include/abg-corpus.h (corpus::corpus): Add a default argument to
the path parameter.
* src/abg-suppression-priv.h: New private header file.
* src/Makefile.am: Add the new abg-suppression-priv.h file to
source distribution.
* include/abg-suppression.h ({suppression_base, type_suppression,
function_suppression, variable_suppression}::priv): Make these
public.
(suppression_base::{g,s}et_drops_artifact_from_ir): Declare new
member functions.
(type_suppression::{suppressed_type}): Likewise.
(suppression_base::{names,sonames}_of_binaries_match): Remove
member functions.
(function_suppression::{get_name, set_name, get_name_regex_str,
set_name_regex_str}): Renamed get_function_name,
set_function_name, get_function_name_regex_str,
set_function_name_regex_str into these.
({variable,function}_suppression::{g,s}et_name_not_regex_str):
Declare new member functions.
* src/abg-suppression.cc: Include the new abg-suppression-priv.h
private header.
(class suppression_base::priv, class type_suppression::priv, class
function_suppression::parameter_spec::priv, class
function_suppression::priv, class variable_suppression::priv):
Move these types to that new private header.
(suppression_base::{g,s}et_drops_artifact_from_ir)
(function_suppression::{g,s}et_name_not_regex_str)
(variable_suppression::{g,s}et_name_not_regex_str): New member
functions.
(sonames_of_binaries_match): New static function, taken from
suppression_base::sonames_of_binaries_match.
(names_of_binaries_match): New static function, taken from
suppression_base::names_of_binaries_match.
(suppression_matches_type_no_name): New static function.
(type_suppression::suppresses_type): Adjust
(function_suppression::suppresses_function)
(variable_suppression::suppresses_variable): Adjust. Evaluate the
new "name_not_regexp" property.
(suppression_matches_type_name)
(suppression_matches_type_location)
(suppression_matches_type_name_or_location)
(suppression_matches_function_name)
(suppression_matches_function_sym_name)
(suppression_matches_variable_name)
(suppression_matches_variable_sym_name, suppression_matches_type):
New functions.
(read_type_suppression): Support the new "drop_artifacts" and
"drop" properties.
(read_function_suppression, read_variable_suppression): Support
the new "drop_artifacts", "drop", and "name_not_regexp"
properties.
(function_suppression::{g,s}et_name): Renamed
{g,s}et_function_name into these.
(function_suppression::set_name_not_regex_str): Renamed
{g,s}et_name_regex_str into this.
(function_suppression::suppresses_function_symbol): Adjust.
* include/abg-dwarf-reader.h (add_read_context_suppressions):
Declare new function.
* src/abg-dwarf-reader.cc: Use the new private
abg-suppression-priv.h header file.
(read_context::supprs_): New data member.
(read_context::get_suppressions): New member function.
(read_context::get_die_source): Make this const.
(read_context::tu_die_imported_unit_points_map): Add a const
overload.
(read_context::cur_transl_unit): Renamed current_translation_unit
unit into this;
(read_context::cur_tu): Remove or rename into cur_transl_unit.
(get_scope_for_die, build_translation_unit_and_add_to_ir)
(build_enum_type, build_pointer_type_def, build_reference_type)
(build_function_type, build_array_type, build_function_decl):
Adjust.
(read_context::{suppression_can_match,
suppression_matches_function_sym_name,
suppression_matches_function_name,
suppression_matches_variable_sym_name,
suppression_matches_variable_name,
suppression_matches_type_name_or_location,
suppression_matches_type_name}): Add member functions.
(die_signed_constant_attribute): Remove this as dead code.
(die_location, die_loc_and_name)
(find_import_unit_point_between_dies)
(find_import_unit_point_before_die, get_parent_die): Make the
read_context& parameter be const and adjust as required.
(build_var_decl_if_not_suppressed, function_is_suppressed)
(variable_is_suppressed, type_is_suppressed): Define new static
functions.
(add_read_context_suppressions): Define new function.
(build_class_type_and_add_to_ir): Do not add suppressed static
data members to the IR.
(build_ir_node_from_die): Do not add suppressed enum types, class
types, variables or functions to the IR. Adjust for the
read_context::cur_tu -> read_context::cur_transl_unit rename.
* include/abg-reader.h (read_context_sptr): Declare new type.
(create_native_xml_read_context, read_corpus_from_input)
(add_read_context_suppressions): Declare new functions.
* src/abg-reader.cc: Include the new private
abg-suppression-priv.h header file.
(read_context::m_exported_decls_builder): Renamed
m_exported_decls_builder_ into this.
(read_context::get_exported_decls_builder): Adjust.
(read_context::get_cur_scope): Make this const.
(read_location): Take a const read_context and adjust.
(read_corpus_from_input): Make this non-static.
(build_namespace_decl): Don't abort if trying to add an artifact
to the IR doesn't succeed. It might be suppressed now.
(read_context::{m_path, m_supprs}): New data members.
(read_context::{g,s}et_path): New member functions.
(read_context::{get_suppressions,
suppression_matches_function_name, suppression_can_match,
suppression_matches_function_name,
suppression_matches_function_sym_name,
suppression_matches_variable_name,
suppression_matches_variable_sym_name,
suppression_matches_type_name_or_location}): Likewise.
(add_read_context_suppressions, create_native_xml_read_context)
(read_corpus_from_native_xml): New functions.
(build_function_decl_if_not_suppressed, function_is_suppressed)
(type_is_suppressed, build_var_decl_if_not_suppressed)
(variable_is_suppressed, build_enum_type_decl_if_not_suppressed)
(build_class_decl_if_not_suppressed): New static functions.
(build_class_decl): Add member types that are being built early,
so that their sub-types can be evaluated for suppression. Do not
add suppressed static data members or suppressed member functions
to the IR.
(build_type): Do not add an enum type or a class type to the IR if
they are suppressed.
(handle_enum_type_decl): Do not add an enum type to the IR if its
suppressed.
(handle_var_decl): Likewise for a variable decl.
(handle_function_decl): Likewise for a function decl.
(handle_class_decl): Likewise for a class decl.
* src/abg-tools-utils.cc (handle_fts_entry): Drop suppressed ABI
from the IR.
* tools/abidiff.cc (display_usage): Fix help strings for
--headers-dirs{1,2}.
(set_suppressions): New static function.
(main): Adjust. Release the memory used by read_context early.
* tools/abidw.cc (options::{headers_dir, suppression_paths}):
(display_usage): New help strings for the new --header-dir and
--suppressions options.
(parse_command_line): Parse the new --header-dir and
--suppressions options.
(maybe_check_suppression_files, set_suppressions): New static
functions.
(main): Use the two new functions above. Free the memory used by
the read context before working with the corpus.
* tools/abilint.cc (options::suppression_paths):
(display_usage): New help strings for the new --header-dir and
--suppressions options.
(parse_command_line): Parse the new --header-dir and
--suppressions options.
(maybe_check_suppression_files, set_suppressions): New static
functions.
(main): Use the two new functions above. Free the memory used by
the read context before working with the corpus.
* tests/data/test-diff-suppr/test24-soname-suppr-{2,3].txt:
Adjust.
* tests/data/test-diff-suppr/test29-suppr-6.txt: Likewise.
* tests/data/test-diff-suppr/test29-suppr-8.txt: Likewise.
* tests/data/test-diff-suppr/libtest31-v{0,1}.so: New test input.
* tests/data/test-diff-suppr/libtest31.suppr: Likewise
* tests/data/test-diff-suppr/libtest32-v{0,1}.so: Likewise.
* tests/data/test-diff-suppr/libtest32-0.suppr: Likewise.
* tests/data/test-diff-suppr/libtest33-v{0,1}.so: Likewise.
* tests/data/test-diff-suppr/test31-report-{0,1}.txt: Likewise.
* tests/data/test-diff-suppr/test31-v{0,1}.cc: Likewise.
* tests/data/test-diff-suppr/test32-report-{0,1}.txt: Likewise.
* tests/data/test-diff-suppr/test32-v{0,1}.c: Likewise.
* tests/data/test-diff-suppr/test33-suppr-1.txt: Likewise.
* tests/data/test-diff-suppr/test33-v{0,1}.cc: Likewise.
* tests/data/test-diff-suppr/test33-v{0,1}.h: Likewise.
* tests/data/test-read-dwarf/libtest24-drop-fns-2.so.abi:
Likewise.
* tests/data/test-read-dwarf/libtest24-drop-fns.so: Likewise.
* tests/data/test-read-dwarf/libtest24-drop-fns.so.abi: Likewise.
* tests/data/test-read-dwarf/test24-drop-fns-0.suppr: Likewise.
* tests/data/test-read-dwarf/test24-drop-fns.cc: Likewise.
* tests/data/test-read-write/test28-drop-std-fns.abignore:
Likewise.
* tests/data/test-read-write/test28-drop-std-vars.abignore:
Likewise.
* tests/data/test-read-write/test28-without-std-fns-ref.xml:
Likewise.
* tests/data/test-read-write/test28-without-std-fns.xml: Likewise.
* tests/data/test-read-write/test28-without-std-vars-ref.xml:
Likewise.
* tests/data/test-read-write/test28-without-std-vars.xml:
Likewise.
* tests/data/test-read-write/test28.xml: Likewise.
* tests/data/Makefile.am: Add the new test artifacts to source
distribution.
* tests/test-diff-suppr.cc (in_out_spec): Take the new test inputs
into account.
* tests/test-read-dwarf.cc (Inoutspec::in_suppr_spec_path): New
data member.
(in_out_spec): Adjust. The new test inputs into account.
(set_suppressions): New static function.
(handle_in_out_spec): Adjust.
* tests/test-read-write.cc (Inoutspec::{in_suppr_spec_path,
ref_out_path}): New data members.
(in_out_spec): Adjust. Take new test inputs into account.
(main): Adjust.
The abigail::ir::scope_decl still has its data member members be
visible from its header file. This patch hides those data member
using the pimpl idiom, just as what is done other types throughout the
project.
* include/abg-ir.h (scope_decl::{priv, priv_sptr}) Declare new types.
(scope_decl::priv_): New pimpl data member.
(scope_decl::{member_, member_scopes}): Move this as data member
of the new scope_decl::priv type in the abg-ir.cc file.
(scope_decl::{scope_decl, get_member_decls, get_member_scopes,
is_empty}): Make these inline member functions be out-of-line.
* src/abg-ir.cc (struct scope_decl::priv): Define new type.
(scope_decl::{scope_decl, get_member_decls, get_member_scopes,
is_empty}): Define these new member functions here. They were
inline in the include/abg-ir.h header files before.
(scope_decl::{add_member_decl, insert_member_decl,
remove_member_decl}): Adjust.
In preparation of dropping ABI artifacts from the IR, add new generic
helper functions.
* include/abg-fwd.h (get_location, build_qualified_name): Declare
new functions.
* include/abg-ir.h (is_method_decl): Declare two new overloads of
this function.
* src/abg-ir.cc (get_location, build_qualified_name)
(is_method_decl): Define these functions declared above.
Today The abixml writer emits namespaces even if they are empty or
contain empty namespaces. This leads to abixml files that are
unnecessarily big and verbose. This patch prevents that.
* include/abg-ir.h
(namespace_decl::is_empty_or_has_empty_sub_namespaces): Declare
new function ...
* src/abg-ir.cc
(namespace_decl::is_empty_or_has_empty_sub_namespaces): ... and
define it.
* src/abg-writer.cc (write_namespace_decl): Do not write empty
namespaces or namespaces containing empty namespaces.
* tests/data/test-read-dwarf/test9-pr18818-clang.so.abi: Adjust.
* tests/data/test-read-dwarf/test11-pr18828.so.abi: Adjust.
* tests/data/test-read-dwarf/test12-pr18844.so.abi: Adjust.
* tests/data/test-read-dwarf/test15-pr18892.so.abi: Adjust.
* tests/data/test-read-dwarf/test16-pr18904.so.abi: Adjust.
* tests/data/test-read-dwarf/test17-pr19027.so.abi: Adjust.
* tests/data/test-read-dwarf/test18-pr19037-libvtkRenderingLIC-6.1.so.abi: Adjust.
* tests/data/test-read-dwarf/test19-pr19023-libtcmalloc_and_profiler.so.abi: Adjust.
* tests/data/test-read-dwarf/test20-pr19025-libvtkParallelCore-6.1.so.abi: Adjust.
* tests/data/test-read-dwarf/test21-pr19092.so.abi: Adjust.
* tests/data/test-read-dwarf/test22-pr19097-libstdc++.so.6.0.17.so.abi: Adjust.
* tests/data/test-read-dwarf/libtest23.so.abi: Adjust.
Dodji Seketeli [Tue, 30 Aug 2016 07:41:01 +0000 (09:41 +0200)]
Bug 20534 - abipkgdiff wrongly displays the name of added binary files
abipkgdiff displays an address instead of displaying the name of the
added binary file. This patch, which is from a diff that Sinny Kumari
attached to the bugzilla entry, fixes the issue.
* tools/abipkgdiff.cc (compare): Show the name of the added
binary, rather than its address.
Dodji Seketeli [Wed, 24 Aug 2016 08:37:08 +0000 (10:37 +0200)]
Bug 20420 - Wrong ODR-based type comparison optimization on qualified type
During type canonicalizing, qualified types are being compared using
the ODR-based optimization. This is wrong because, for instance, it's
not because two types from the same ABI corpus are both const
anonymous structs that they are meant to be equivalent.
This patch fixes the issue by applying the ODR-based comparison
optimization only to built-in types and non-anonymous struct and
enums.
The reproducer is a glibc package that takes a while to compare so
it's not suitable for inclusion in the test suite.
Dodji Seketeli [Tue, 23 Aug 2016 10:38:36 +0000 (12:38 +0200)]
Don't walk diff trees indefinitely when applying suppressions
When applying suppressions to diff graphs, if the same diff node
appears twice in the graph in a way that creates a cycle, we can get
trapped in the cycle when walking the graph. That results in a an
infinite loop. Note that the infinite loop appears in the
diff::traverse member function, in the for-loop that walks the
children nodes of a given node.
This patch avoids walking the same node twice when applying
suppressions.
The test binaries that exhibit the issue come from the two following
packages:
rh-mariadb101-mariadb-10.1.14-2.el6 and rh-mariadb101-mariadb-10.1.16-1.el6.
The sub-packages compared are
rh-mariadb101-mariadb-server-10.1.14-2.el6.x86_64.rpm and
rh-mariadb101-mariadb-server-10.1.16-1.el6.x86_64.rpm.
The debug info packages are
rh-mariadb101-mariadb-debuginfo-10.1.16-1.el6.x86_64.rpm and
rh-mariadb101-mariadb-debuginfo-10.1.14-2.el6.x86_64.rpm.
Once the packages are properly extracted the command line that
exhibits the infinite loop is:
This patch has no test because of the cheer size of these packages;
the debug info packages alone take more than 100MB :-( I really hope
we set up a separate repository with big test packages to overcome
this. Maybe something using fedabipkgdiff ...
Symbols of pretty much all member functions of types that are meant to
be "private" to translation units that contribute to libabigail.so
were exported because we didn't do much to prevent that.
This patch starts controlling the set of symbols that are exported.
By default, symbols of any entity declared in a translation unit that
contributes to libabigail.so are hidden by default. Only symbols of
entities declared in public headers (headers in include/*.h) are
exported.
There are many ways to achieve that. This patch chooses to avoid
cluttering declarations of entities in the public header by adding
__attribute__((visibility="default")) to every declared type of
function in there.
Rather, the patch uses "#pragma GCC visibility push(default)" before
entities declared on those headers. By doing so, all those entities
have their symbol marked as "visible" by the compiler. Once the
header are #included, the #pragma GCC visibility pop" is used, so that
anything else has its symbol be hidden from that point on.
Note that for ease of maintenance the patch uses the macros
ABG_BEGIN_EXPORT_DECLARATIONS and ABG_END_EXPORT_DECLARATIONS rather
than using the pragma directive directly.
I believe this is a more elegant way of handling visibility, compared
to cluttering every single declaration in public headers with a
"__attribute__((visibility=("default")))" or with a macro which
expands to it.
This reduces the the set of symbols exported by libabigail.so from
20000+ to less than 5000.
* VISIBILITY: New documentation about this visiblity business.
* CONTRIBUTING: Update the "contributing guide" to refer to symbol
visibility issues.
* configure.ac: Define a variable VISIBILITY_FLAGS that is set to
the -fvisibility=hidden flag to pass to GCC, when its available.
* src/Makefile.am: Add VISIBILITY to source distribution. Also
add COMPILING and COMMIT-LOG-GUIDELINES that were missing.
* src/Makefile.am: Use the new $(VISIBILITY_FLAGS) when buiding
the library.
* tests/Makefile.am: Use the new $(VISIBILITY_FLAGS) when buiding
tests.
* tools/Makefile.am: Use the new $(VISIBILITY_FLAGS) when buiding
tools.
* src/abg-comp-filter.cc: Enclose inclusion of public headers in
ABG_BEGIN_EXPORT_DECLARATIONS and ABG_END_EXPORT_DECLARATIONS to
export the symbols of entities declared in there.
* src/abg-comparison.cc: Likewise.
* src/abg-config.cc: Likewise.
* src/abg-corpus.cc: Likewise.
* src/abg-diff-utils.cc: Likewise.
* src/abg-dwarf-reader.cc: Likewise.
* src/abg-hash.cc: Likewise.
* src/abg-ini.cc: Likewise.
* src/abg-ir.cc: Likewise.
* src/abg-libxml-utils.cc: Likewise.
* src/abg-libzip-utils.cc: Likewise.
* src/abg-reader.cc: Likewise.
* src/abg-suppression.cc: Likewise.
* src/abg-tools-utils.cc: Likewise.
* src/abg-traverse.cc: Likewise.
* src/abg-viz-common.cc: Likewise.
* src/abg-viz-dot.cc: Likewise.
* src/abg-viz-svg.cc: Likewise.
* src/abg-workers.cc: Likewise.
* src/abg-writer.cc: Likewise.
Type units sections are sections in which the compiler emits types
uniquely identified by a signature. This is so that the linker can
later discard redundant types (types having the same signature) from
the debug info and thus reduce the overall size of debug info.
These types are children DIEs of DW_TAG_type_unit.
Because DIEs coming from that .debug_types section can have the same
offset as DIEs coming from the .debug_info section, this patch defines
a new DIE source to identify DIEs coming from .debug_types section.
The name of that new source is the new TYPE_UNIT_DIE_SOURCE enumerator
of the die_source enum. The patch also creates the necessary maps
containing DIEs coming from this new source and adjusts the
accompanying accessors accordingly.
* src/abg-dwarf-reader.cc (TYPE_UNIT_DIE_SOURCE): New enumerator
in enum die_source.
(read_context::{type_unit_die_decl_map_, type_unit_die_type_map_,
type_unit_die_wip_classes_map_,
type_unit_die_wip_function_types_map_,
type_unit_types_to_canonicalize_,
type_units_tu_die_imported_unit_points_map_,
type_section_die_parent_map_}): New data members.
(read_context::{get_die_source, associate_die_to_decl,
lookup_decl_from_die_offset, die_type_map, clear_die_type_maps,
die_wip_classes_map, die_wip_function_types_map,
types_to_canonicalize, clear_types_to_canonicalize,
tu_die_imported_unit_points_map, die_parent_map}): Support
TYPE_UNIT_DIE_SOURCE.
(get_parent_die, get_scope_for_die): Likewise.
(read_context::{lookup_decl_from_type_unit_die_offset,
type_section_die_parent_map}): Define new member functions.
(read_context::build_die_parent_maps): Build a DIE -> parent map
for DIEs coming from the .debug_types section.
* tests/data/test-read-dwarf/libtest23.so: New test input.
* tests/data/test-read-dwarf/libtest23.so.abi: New reference output.
* tests/data/test-read-dwarf/test23-first-tu.cc: Source code of
the new binary above.
* tests/data/test-read-dwarf/test23-second-tu.cc: Likewise.
* tests/data/Makefile.am: Add the new test material above to
source distribution.
* tests/test-read-dwarf.cc (in_out_specs): Make this test harness
execute over the new test input and reference output.
There are many functions in the DWARF reader that need to know if a
DIE comes from the primary or alternate debug info file. Today, this
is conveyed by a boolean parameter.
This patch generalizes this idea of "source of DIE" by introducing a
new enum type named die_source that says where the DIE comes from.
This is to help later enable the introduction of a new kind of DIE
source.
The patch also introduces a new member function named
read_context::get_die_source to determine the source of a DIE. This
helps remove the need of a die_source parameter on functions that
already take a DIE. So this patch conceptually removes the die_source
parameter from many functions.
* src/abg-dwarf-reader.cc (enum die_source): Define new enum.
(operator++): Define new prefix increment operator for the
die_source enum.
(imported_unit_point::imported_unit_from_alt_di): Remove this
data member.
(imported_unit_point::imported_unit_die_source):
New data member of type die_source.
(read_context::primary_die_parent_map_): Renamed
die_parent_map_ data member into this.
(read_context::clear_per_corpus_data): Use the new
clear_die_type_maps function, not die_type_map. Also use the
new clear_types_to_canonicalize overload that takes no
parameter.
(read_context::{get_die_source, clear_die_type_maps,
clear_types_to_canonicalize}): New member functions.
(build_ir_node_from_die, die_die_attribute, get_parent_die)
(get_scope_for_die, build_namespace_decl_and_add_to_ir)
(build_type_decl, build_enum_type)
(build_class_type_and_add_to_ir, build_qualified_type)
(build_pointer_type_def, build_reference_type)
(build_function_type, build_array_type, build_typedef_type)
(build_var_decl, build_function_decl): Remove the boolean
parameter that was designating the source of the DIE. If
necessary, get the source of the DIE from inside the function
using the new read_context::get_die_source.
(read_debug_info_into_corpus): Adjust.
(maybe_canonicalize_type, find_import_unit_point_between_dies)
(maybe_canonicalize_type, read_context::{associate_die_to_decl,
lookup_decl_from_die_offset, die_type_map, associate_die_to_type,
lookup_type_from_die_offset, die_wip_classes_map,
die_wip_function_types_map, is_wip_class_die_offset,
is_wip_function_type_die_offset, types_to_canonicalize,
schedule_type_for_late_canonicalization,
canonicalize_types_scheduled, add_late_canonicalized_types_stats,
perform_late_type_canonicalizing}): Take a die_source as the
source of the DIE, not a boolean. Adjust the code of the function
accordingly.
(read_context::{tu_die_imported_unit_points_map}): Modified
this to make it take a die_source and return the appropriate
map depending on the source.
(read_context::build_die_parent_relations_under): Turn the
non-member static function build_die_parent_relations_under
into a member function.
(read_context::build_die_parent_maps): Turn the non-member
static function build_die_parent_maps into a member function.
Make this function build a DIE -> parent map also for type
DIEs that are in the .type_units section.
Cleanup is_class and is_compatible_with_class_type
There was two overloads of is_class, one for types and one for decls.
Now that we have type_or_decl_base which is a common base type for
both, having just one is_class function that takes a type_or_decl_base
is more compact and easier to maintain. This patch does that. It
also cleans up the declaration of the is_compatible_with_class_type
function.
* include/abg-fwd.h (is_class): Remove the overloads that take a
decl_base or a type_base. Add one that takes a type_or_decl_base.
(is_compatible_with_class_type): Make this take a reference to
smart pointer, not just the smart pointer.
* src/abg-ir.cc (is_class): Do the same as in the header file.
(is_compatible_with_class_type): Likewise.
Adding this macro to abort at places where the execution flow
shouldn't take us to. Using this is more explicit (self-documented)
than using abort.
This patch replaces the use of abort() in abg-dwarf-reader.cc.
* include/abg-tools-utils.h (ABG_ASSERT_NOT_REACHED): New macro.
* src/abg-dwarf-reader.cc (stt_to_elf_symbol_type)
(stb_to_elf_symbol_binding, get_elf_class_size_in_bytes)
(build_ir_node_from_die): Use the new ABG_ASSERT_NOT_REACHED macro
in lieu of just calling abort().
While working on something else, I started to prepare the support for
visibility control in the library. This patch detects that we are
using a compiler that supports GCC's visibility control attributes and
defines macros ABG_HIDDEN, ABG_EXPORTED,
ABG_{BEGIN,END}_EXPORT_DECLARATIONS to control the visibility of
declarations accordingly. These are not yet used but using them
should now be easy.
* configure.ac: Detect compiler support for
__attribute__((visibility("hidden")) and define the
HAS_GCC_VISIBILITY_ATTRIBUTE macro accordingly. Update the
configuration report.
* src/abg-internal.h: New internal header file that defines macros
to be used in the source code to control declaration visibility.
* src/Makefile.am: Add abg-internal.h to source distribution. Add
src/ to the include search path.
Make fedabipkgdiff consistent with Libabigail's other tests
In the libabigail project, almost all the tests for the tools follow a
similar pattern. The test contains a set of input files to compare.
The result of the comparison is thus compared to a set of reference
comparison result.
This approach is already documented in the CONTRIBUTING file.
There are several interesting properties with this scheme. First, it
capture the behaviour of the tools, including what is shown to the
user.
Second, it eases the job of a hacker who wants to add a new test for a
new behaviour of a given tool. The user just has to provide:
1/ A new reference output of the new use case of the tool (that is easily
constructed by using the tool itself and saving its output) and add an
entry to array of entries that describe what to compare
2/ A new set of inputs to the tool
And voila.
Unfortunately, fedabipkgdiff tests don't follow this scheme. That
make them surprising to hackers who read the source code of the
existing tests, at very least. Also, the fedabipkgdiff tests were
only unit tests. They were not testing the tool as used by users in
general.
This patch makes the fedabipkgdiff tests follow the general approach
of the tests of the other Libabigail tools.
The patch first craetes a program names tests/mockfedabipkgdiff. It's
a wrapper around tools/fedabipkgdiff. It overloads the Koji client of
fedabipkgdiff with a fake Koji client that gets the Fedora packages
locally, from tests/data/test-fedabipkgdiff/packages. In other words,
mockfedabipkgdiff is fedabipkgdiff without going to the network.
I believe that in the future, tests/mockfedabipkgdiff should be killed
when fedabipkgdiff is able to cache a local description of a local
partial view of a Koji repository, along with the build packages that
were already downloaded.
That way, calling fedabipkgdiff twice with the same set of option
should make the tool perform correctly without going to the netword on
the second invocation. We should be able to save the local partial
view of the Koji repository under e.g,
tests/data/test-fedabipkgdiff/local-koji and tell fedabipkgdiff to use
that, instead of using the network. But we are not there yet. So for
now, I am using mockfedabipkgdiff.
Then, tests/runtestfedabipkdiff.py.in has been re-written to use
tests/mockfedabipkgdiff and to look like what is described in
CONTRIBUTING as far as how Libabigail tools' tests are organized:
mockfedabipkgdiff is called to perform a comparison. The result of
the comparison is then compared (using GNU diff) to a reference
comparison result file.
Please note that tests/runtestfedabipkdiff.py is relatively fast for
the moment. But when it contains much more tests and start becoming
slow, then we'll need to change the code to run several comparisons in
parallel, just like we do today in tests/test-diff-filter.cc. At that
point, I believe I'll just re-write this in C++, just like
tests/test-diff-filter.cc because that will allow us to have true
concurrent code based on the abigail:workers API. For now, I am
keeping this in Python also because I think that keeps Chenxiong happy
;-)
To be sure that fedabipkgdiff (and its underlying abipkgdiff) are
really comparing all the packages they are supposed to compare and
also all the binaries in those packages, I have added a new
--show-identical-binaries to abipkgdiff and fedabipkgdiff. That
option shows the name of the binaries (and packages) that are
compared, *even if* the ABI of those binaries are identical. Because
otherwise, today, if two binaries (or packages) have the same ABI,
nothing is displayed.
For instance, here is the result of comparing a package against
itself, using this new --show-identical-binaries options:
dodji@adjoa:patches$ ./tools/fedabipkgdiff --abipkgdiff ./build/tools/abipkgdiff --show-identical-binaries dbus-glib-0.80-3.fc12.x86_64.rpm dbus-glib-0.80-3.fc12.x86_64.rpm
Comparing the ABI of binaries between dbus-glib-0.80-3.fc12.x86_64.rpm and dbus-glib-0.80-3.fc12.x86_64.rpm:
================ changes of 'dbus-binding-tool'===============
No ABI change detected
================ end of changes of 'dbus-binding-tool'===============
================ changes of 'libdbus-glib-1.so.2.1.0'===============
No ABI change detected
================ end of changes of 'libdbus-glib-1.so.2.1.0'===============
dodji@adjoa:patches$
And here is what this command before that patch would do:
dodji@adjoa:patches$ ./tools/fedabipkgdiff --abipkgdiff ../master/build/tools/abipkgdiff dbus-glib-0.80-3.fc12.x86_64.rpm dbus-glib-0.80-3.fc12.x86_64.rpm
Comparing the ABI of binaries between dbus-glib-0.80-3.fc12.x86_64.rpm and dbus-glib-0.80-3.fc12.x86_64.rpm:
dodji@adjoa:patches$
The rest of the patch is mostly new test inputs material and the
necessary adjustments following all the changes above.
* configure.ac: Do not require Python dependencies itertools,
unittest and StringIO anymore as they are not used anymore.
Require new module tempfile now. Generate new executable script
tests/mockfedabipkgdiff from tests/mockfedabipkgdiff.in.
* doc/manuals/abipkgdiff.rst: Add doc for new option
--show-identical-binaries to abipkgdiff
* doc/manuals/fedabipkgdiff.rst: Add doc for new options
--show-identical-binaries to fedabipkgdiff.
* tools/abipkgdiff.cc (options::show_identical_binaries): New data
member.
(options::options): Initialize new data member.
(display_usage): Add a new help string for the new
--show-identical-binaries option.
(parse_command_line): Parse the newq --show-identical-binaries
command line switch.
(pthread_routine_compare): When the comparison of two binaries is
empty, if --show-identical-binaries was provided, then emit some
output saying the comparison did yield the empty set.
* tools/fedabipkgdiff (DEFAULT_ABIPKGDIFF): Store the default path
to abipkgdiff in this new global variable. Naming this default
path is useful because it can then be cleanly overloaded when
using mock.patch.
(build_path_to_abipkgdiff): Return the new DEFAULT_ABIPKGDIFF
global variable.
(cmd): Parse the new --show-identical-binaries command line
switch.
* tests/data/test-diff-pkg/test-dbus-glib-0.80-3.fc12.x86_64-report-0.txt:
New reference output.
* tests/data/test-fedabipkgdiff/test0-from-fc20-to-fc23-dbus-glib-report-0.txt:
Likewise.
* tests/data/test-fedabipkgdiff/test1-from-fc20-to-dbus-glib-0.106-1.fc23.x86_64-report-0.txt:
Likewise.
* tests/data/test-fedabipkgdiff/test2-dbus-glib-0.100.2-2.fc20--dbus-glib-0.106-1.fc23-report-0.txt:
Likewise.
* tests/data/test-fedabipkgdiff/test3-dbus-glib-0.100.2-2.fc20.i686--dbus-glib-0.106-1.fc23.i686-report-0.txt:
Likewise.
* tests/mockfedabipkgdiff.in: New uninstalled script template.
* tests/runtestfedabipkgdiff.py.in (counter)
(temp_file_or_dir_prefix, UtilsTest, RPMTest, LocalRPMTest)
(RunAbipkgdiffTest, GetPackageLatestBuildTest, DownloadRPMTest)
(BrewListRPMsTest, AssertionHelper, MockGlobalConfig)
(BUILT_ABIPKGDIFF, CompareABIFromCommandLineTest): Remove these
classes, global variables and functions.
(FEDABIPKGDIFF, TEST_SRC_DIR, TEST_BUILD_DIR, INPUT_DIR)
(OUTPUT_DIR, FEDABIPKGDIFF_TEST_SPECS): New global variables.
(ensure_output_dir_created, run_fedabipkgdiff_tests, main): New
functions.
* tests/test-diff-pkg.cc (in_out_specs): Add
tests/data/test-diff-pkg/test-dbus-glib-0.80-3.fc12.x86_64-report-0.txt
to the set of reference outputs to consider.
* tests/Makefile.am: Add non-installed script mockfedabipkgdiff to
source distribution. Also added
tests/data/test-diff-pkg/test-dbus-glib-0.80-3.fc12.x86_64-report-0.txt,
tests/data/test-fedabipkgdiff/test0-from-fc20-to-fc23-dbus-glib-report-0.txt,
tests/data/test-fedabipkgdiff/test1-from-fc20-to-dbus-glib-0.106-1.fc23.x86_64-report-0.txt,
tests/data/test-fedabipkgdiff/test2-dbus-glib-0.100.2-2.fc20--dbus-glib-0.106-1.fc23-report-0.txt
and
tests/data/test-fedabipkgdiff/test3-dbus-glib-0.100.2-2.fc20.i686--dbus-glib-0.106-1.fc23.i686-report-0.txt
to source distribution.
Fix spurious type size change report for distinct_diff
When looking at diff of two distinct types it can happen that the
change report mentions a type size change even when the two type sizes
are equal.
This patch fixes that.
* src/abg-comparison.cc (report_size_and_alignment_changes):
Report size change only when the sizes are different.
* tests/data/test-diff-filter/test33-report-0.txt: Adjust.
Bug 20199 - Consider integral type synonyms as being equal
In this problem report, Abigail's type comparison engine considers
e.g, "unsigned short" and "short unsigned int" as being different
types because they have different name strings. This is wrong.
This patch canonicalize the names of integral types, so that e.g,
"short unsigned", "unsigned short" and "unsigned short int" all have
the same name which would be "unsigned short int".
* src/abg-ir.cc (class integral_type): New class declaration and
definition.
(operator|, operator&, operator&=): New non-member bitwise
operators for integral_type.
(parse_integral_type_modifier, parse_base_integral_type)
(parse_integral_type_modifier): New static function definitions.
(type_decl::type_decl): Use the parse_integral_type to parse an
integral type out of the current type_decl being built and
transform the current type name into a canonical form.
* tests/data/test-abidiff/test-PR18791-v0.so.abi: Adjust.
* tests/data/test-abidiff/test-PR18791-v1.so.abi: Likewise.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report0.txt: Likewise.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report1.txt: Likewise.
* tests/data/test-diff-filter/test33-report-0.txt: Likewise.
* tests/data/test-diff-filter/test34-report-0.txt: Likewise.
* tests/data/test-diff-pkg/libICE-1.0.6-1.el6.x86_64.rpm--libICE-1.0.9-2.el7.x86_64.rpm-report-0.txt: Likewise.
* tests/data/test-read-dwarf/test10-pr18818-gcc.so.abi: Likewise.
* tests/data/test-read-dwarf/test11-pr18828.so.abi: Likewise.
* tests/data/test-read-dwarf/test12-pr18844.so.abi: Likewise.
* tests/data/test-read-dwarf/test13-pr18894.so.abi: Likewise.
* tests/data/test-read-dwarf/test14-pr18893.so.abi: Likewise.
* tests/data/test-read-dwarf/test15-pr18892.so.abi: Likewise.
* tests/data/test-read-dwarf/test16-pr18904.so.abi: Likewise.
* tests/data/test-read-dwarf/test17-pr19027.so.abi: Likewise.
* tests/data/test-read-dwarf/test18-pr19037-libvtkRenderingLIC-6.1.so.abi: Likewise.
* tests/data/test-read-dwarf/test19-pr19023-libtcmalloc_and_profiler.so.abi: Likewise.
* tests/data/test-read-dwarf/test20-pr19025-libvtkParallelCore-6.1.so.abi: Likewise.
* tests/data/test-read-dwarf/test21-pr19092.so.abi: Likewise.
* tests/data/test-read-dwarf/test22-pr19097-libstdc++.so.6.0.17.so.abi: Likewise.
* tests/data/test-read-dwarf/test9-pr18818-clang.so.abi: Likewise.
GCC can generate several DW_TAG_unspecified_parameters for a given
function. Abigail's DWARF reader is recklessly creating a variadic
function parameter in its internal representation (IR) each time it
sees a DW_TAG_unspecified_parameters. This leads to functions having
several variadic parameters in the final IR. And this is wrong.
This patch fixes the problem by creating a variadic parameter only for
the first DW_TAG_unspecified_parameters encountered for a given
function DIE.
* src/abg-dwarf-reader.cc (build_function_type): Create a variadic
parameter just for the first DW_TAG_unspecified_parameters seen.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report0.txt: Adjust.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report1.txt: Adjust.
* tests/data/test-read-dwarf/test16-pr18904.so.abi: Adjust.
This fixes Bug 20329 - DW_TAG_const_type with no DW_AT_type not recognized as "const void".
It appears that GCC sometimes emits "const void" types by emitting a
const type DIE with no type attribute. The DWARF reader didn't
recognize that construct as a qualified void type.
This patch teaches the DWARF reader to recognize that construct.
It also appears that "const void" and "void" are equivalent and can be
emitted interchangeably by compilers (Intel and GCC) in their debug
info. That can lead to spurious ABI change reports saying that a type
"const void" was changed into a "void" type.
This patch transforms an occurrence of "const void" type into a "void"
type in the internal representation when reading DWARF. This does
away with the spurious change that appears when comparing selected
binaries emitted with the intel against binaries emitted with GCC.
* include/abg-ir.h (environment::is_void_type): Declare new member
function.
* src/abg-ir.cc (environment::is_void_type): Define new member
function.
* src/abg-dwarf-reader.cc (maybe_strip_qualification): Strip const
qualifier from const void.
* tests/data/test-diff-filter/test34-libjemalloc.so.2-gcc-6.1.0:
New test input.
* tests/data/test-diff-filter/test34-libjemalloc.so.2-intel-16.0.3: Likewise.
* tests/data/test-diff-filter/test34-report-0.txt: New reference output.
* tests/data/Makefile.am: Add the new files above to the source
distribution.
* tests/test-diff-filter.cc (in_out_specs): Compare the two new
binaries above.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report0.txt: Adjust.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report1.txt: Adjust.
* tests/data/test-diff-pkg/tbb-4.1-9.20130314.fc22.x86_64--tbb-4.3-3.20141204.fc23.x86_64-report-0.txt: Adjust.
* tests/data/test-diff-pkg/tbb-4.1-9.20130314.fc22.x86_64--tbb-4.3-3.20141204.fc23.x86_64-report-1.txt: Adjust.
* tests/data/test-read-dwarf/test1.abi: Adjust.
* tests/data/test-read-dwarf/test10-pr18818-gcc.so.abi: Adjust.
* tests/data/test-read-dwarf/test11-pr18828.so.abi: Adjust.
* tests/data/test-read-dwarf/test12-pr18844.so.abi: Adjust.
* tests/data/test-read-dwarf/test13-pr18894.so.abi: Adjust.
* tests/data/test-read-dwarf/test14-pr18893.so.abi: Adjust.
* tests/data/test-read-dwarf/test15-pr18892.so.abi: Adjust.
* tests/data/test-read-dwarf/test16-pr18904.so.abi: Adjust.
* tests/data/test-read-dwarf/test17-pr19027.so.abi: Adjust.
* tests/data/test-read-dwarf/test18-pr19037-libvtkRenderingLIC-6.1.so.abi: Adjust.
* tests/data/test-read-dwarf/test19-pr19023-libtcmalloc_and_profiler.so.abi: Adjust.
* tests/data/test-read-dwarf/test20-pr19025-libvtkParallelCore-6.1.so.abi: Adjust.
* tests/data/test-read-dwarf/test21-pr19092.so.abi: Adjust.
* tests/data/test-read-dwarf/test22-pr19097-libstdc++.so.6.0.17.so.abi: Adjust.
* tests/data/test-read-dwarf/test9-pr18818-clang.so.abi: Adjust.
Bug 20194 - Fail to recognize void type represented by DW_TAG_base_type
This patch makes the DWARF reader recognize a "void" type expressed as
a DW_TAG_base_type of size zero and named "void".
* src/abg-dwarf-reader.cc (build_type_decl): Recognize a
DW_TAG_base_type of size zero and of name "void" as a void
type.
* tests/data/test-diff-filter/test33-libelf.so.0.8.13-gcc: New
binary test input.
* tests/data/test-diff-filter/test33-libelf.so.0.8.13-intel16.0.3: Likewise.
* tests/data/test-diff-filter/test33-report-0.txt: New reference output.
* tests/data/Makefile.am: Add the new files above to source
distribution.
* tests/test-diff-filter.cc (in_out_specs): Make this test harness
run over the new test inputs above.
While working on something else, it appeared that I needed an overload
for is_type_decl that takes a shared pointer to decl_base. The
current is_type_decl takes a shared opinter to type_base.
This patch also updates some code that unnecessarily calls
is_type_decl.
* include/abg-fwd.h (is_type_decl): Declare a new overload
* src/abg-ir.cc (is_type_decl): Define a new overload.
(function_decl::parameter::get_pretty_representation): Adjust.
Dodji Seketeli [Fri, 24 Jun 2016 10:05:39 +0000 (12:05 +0200)]
Misc cleanup in abg-reader.cc
While looking at something else, I figured we should pass a smart
pointer parameter by reference in
read_context::push_decl_to_current_scope in the abixml reader.
* src/abg-reader.cc (read_context::push_decl_to_current_scope):
Pass the decl smart pointer by value.
Dodji Seketeli [Wed, 22 Jun 2016 07:56:27 +0000 (09:56 +0200)]
Use ODR-based optimization on C/C++ translation unit only
Looking at the debug info of the libgo library (written in Go) it
appears that there can be for instance a public type "int" which is a
4 bytes long in a translation unit, and another type named "int" as
well, and which is 8 bytes long. Having this in C++ is illegal as per
the One Definition Rule (ODR). And generally, in C, we don't have
this either even if C doesn't have an ODR.
Abigail uses the ODR to speed-up type canonicalization. So in cases
where two "int" types (of different sizes) are considered equal
because they have the same name and are in the same binary we end up
with inconsistencies that make comparison tools emit wrong reports.
This patch thus performs the ODR-based optimization only for C and C++
translation units.
Note that while working on this, I noticed that we were not setting
the translation unit of a certain number of ABI artifacts correctly.
This patch fixes that too. We need to set the translation unit of all
ABI artifacts because to get the language of the translation union of
an ABI artifact, we need to get its translation unit first.
* src/abg-ir.cc (strip_typedef): Set the translation unit of the
new ABI artifact.
(type_base::get_canonical_type_for): Perform the ODR-based
optimization only for ABI artifact in C and C++ language
translation units.
* src/abg-dwarf-reader.cc (build_ir_node_from_die): Assert that
the new ABI artifact has its translation unit set.
* src/abg-reader.cc (read_context::{push_decl_to_current_scope,
push_and_key_type_decl}): Set the translation unit of the current
decl, irrespective of if it was added to the current scope or not.
Assert that the decl that was newly pushed to the current scope is
added to the current translation unit.