Add options for constructor intializers, using declarations and
consecutive declarations.
Even though sorting using declarations could be useful, it changes too
much existing code as of now.
* .clang-format: Add options for ConstructorInitializers
Set SortUsingDeclarations=false
Set AlignConsecutiveDeclarations=true
Signed-off-by: Matthias Maennich <maennich@google.com>
- Artifacts produced by `make dist` should be ignored.
- Artifacts produced by git merge resolution should be ignored.
* .gitignore: add entries for distribution artifacts
* .gitignore: add *.orig files
Signed-off-by: Matthias Maennich <maennich@google.com>
Drop the deprecated overloads for write_translation_unit, write_corpus,
write_corpus_group. Also remove the deprecation facilities as they are
not used anymore.
* include/abg-fwd.h (ABG_DEPRECATED): Remove this macro.
* include/abg-writer.h (write_translation_unit, write_corpus)
(write_corpus_group): Drop the deprecated overloads of these
declarations.
* src/abg-writer.cc (write_translation_unit, write_corpus)
(write_corpus_group): Drop the deprecated overloads of these
definitions.
Signed-off-by: Matthias Maennich <maennich@google.com>
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
Various emitted directories contain machine specific information and
therefore break reproducibility of abidw's output across different
build paths.
Hence introduce --short-locs to only emit file names.
Thanks to earlier changes, adding an option boils down to adding it to
set_opts and to the write_context along with some auxiliary functions
for setting and getting.
* include/abg-writer.h (set_short_locs): Declare new function.
(set_common_options): Use it.
set_opts
* src/abg-writer.cc (write_context::m_short_locs): New data
member.
(write_context::write_context): Initialize it.
(write_context::{g,s}et_short_locs): Define new accessors.
(write_location, write_translation_unit, write_corpus): Honour the
new write_context::get_short_locs property.
(set_short_locs): Define new function.
* tools/abidw.cc (options::short_locs): New data member.
(display_usage): Help string for the new --no-show-locs option.
(parse_command_line): Parse the new --no-show-locs option.
Signed-off-by: Matthias Maennich <maennich@google.com>
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
The compilation directory contains machine specific information
therefore breaks reproducibility of abidw's output across different
build paths. Hence introduce --no-comp-dir-path (as in the xml
attribute). Internally I decided to not carry on the duplication of
'dir' and 'path' and used 'comp_dir'.
Thanks to earlier changes, adding an option boils down to adding it to
set_common_options and to the write_context along with some auxiliary
functions for setting and getting.
write_translation_unit uses the flag in the write_context and omits the
comp-dir-path if asked for.
* include/abg-writer.h (set_write_comp_dir): Declare new function.
(set_common_options): Use it.
* src/abg-writer.cc (write_context::m_write_comp_dir): Define new
data member.
(write_context::write_context): Initialize it.
(write_context::{g,s}et_write_comp_dir): Define new member
accessors.
(set_write_comp_dir): Define new free-form getter.
(write_translation_unit): Teach to respect write_comp_dir flag of
write_context.
* tools/abidw.cc (options::write_corpus_path): Define new data
member.
(options::options): Initialize it.
(display_usage): Add doc string for a new command line option: --no-comp-dir-path.
(parse_command_line): Parse the new command line option --no-comp-dir-path.
Signed-off-by: Matthias Maennich <maennich@google.com>
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
Having write_context carry corresponding flags for output sensitive
command line options, is useful to ensure these options are not lost in
chains for write_* calls. In particular, these options can have various
meanings depending on the context (corpus, corpus_group, etc.)
Hence add them to the write_context along with getters and setters and
make the writers aware of their existence. We do not need to modify the
corpus or corpus group's path or architecture any longer as they get
ignored for a different reason now.
Finally, drop the flag handling in abidw as it is already done via
set_opts, which learned about these new flags.
* include/abg-writer.h (set_write_architecture)
(set_write_corpus_path): Declare new getter functions.
(write_corpus): Take a new "member_of_group" argument.
(set_common_options): Use set_write_{architecture, corpus_path}
here.
* src/abg-writer.cc (write_context::m_write_{architecture,
corpus_path}}): Add new data members.
(write_context::write_context): Initialize the new data members.
(write_context::{s,g}et_write_{architecture, corpus}): Define new
accessors.
(set_write_{architecture, corpus}): Define new free-form getter
functions.
(write_corpus): Add flag to make aware if written as part of a
group.
* tools/abidw.cc (load_corpus_and_write_abixml)
(load_kernel_corpus_group_and_write_abixml): Drop obsolete option
handling as xml_writer::set_common_options now takes care of it.
Signed-off-by: Matthias Maennich <maennich@google.com>
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
ldiff --git a/include/abg-writer.h b/include/abg-writer.h
index 200b5f7..729b455 100644
--- a/include/abg-writer.h
+++ b/include/abg-writer.h
@@ -53,6 +53,11 @@ set_show_locs(write_context& ctxt, bool flag);
void
set_annotate(write_context& ctxt, bool flag);
+void
+set_write_architecture(write_context& ctxt, bool flag);
+
+void
+set_write_corpus_path(write_context& ctxt, bool flag);
/// A convenience generic function to set common options (usually used
/// by Libabigail tools) from a generic options carrying-object, into
@@ -69,6 +74,8 @@ set_common_options(write_context& ctxt, const OPTS& opts)
{
set_annotate(ctxt, opts.annotate);
set_show_locs(ctxt, opts.show_locs);
+ set_write_architecture(ctxt, opts.write_architecture);
+ set_write_corpus_path(ctxt, opts.write_corpus_path);
}
void
@@ -105,7 +112,10 @@ write_corpus_to_archive(const corpus_sptr corp,
const bool annotate = false);
bool
-write_corpus(write_context& ctxt, const corpus_sptr& corpus, unsigned indent);
+write_corpus(write_context& ctxt,
+ const corpus_sptr& corpus,
+ unsigned indent,
+ bool member_of_group = false);
bool ABG_DEPRECATED
write_corpus(const corpus_sptr& corpus, unsigned indent, write_context& ctxt);
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
When setting options meant to be used for the write_context, it is easy
to forget to change all relavant locations. In order to consolidate
that, introduce a set_opts function that sets various known options.
We benefit from earlier refactoring as now the write_context is passed
around to carry options for writers. Hence we can be sure, that if we
set up the context correctly (and do not use deprecated functionality),
the respective write_* function will see the options set in the context.
* include/abg-writer.h (set_common_option): Declare new function.
* tools/abidw.cc (load_corpus_and_write_abixml)
(load_kernel_corpus_group_and_write_abixml): Use the newly
introduced set_common_option.
Signed-off-by: Matthias Maennich <maennich@google.com>
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
Allowing the mutation of the ostream, allows heavy reuse of the
write_context as this is the distinction in most places where
write_context is used.
Hence, fixup various users of write_context and use common objects where
applicable.
* include/abg-writer.h (set_ostream): Declare new function.
* src/abg-writer.cc (write_context::m_ostream): Make this data
member be a pointer rather than a reference.
(write_context::{write_context, get_ostream): Adjust. member.
(write_context::set_ostream): Define new member function.
(set_ostream): Define new free-form function.
* tools/abidw.cc (load_corpus_and_write_abixml)
(load_kernel_corpus_group_and_write_abixml): Use the feature of
mutating the ostream and reuse the write_context in most cases.
Signed-off-by: Matthias Maennich <maennich@google.com>
Introduce a new call overload for write_corpus_group that follows the
parameter order context, object (i.e. corpus_group), indent.
Deprecate all other overloads that were part of the API and mostly
forward them to the new overload. That effort is made to ensure
write_context is always provided. write_context allows access to all
options that influence the output format.
* include/abg-writer.h (write_corpus_group): Introduce new
overload write_corpus_group(ctxt, corpus_group, indent) and
deprecate all others.
* src/abg-writer.cc (write_corpus_group): Likewise for the
definitions and adjust.
* tools/abidw.cc (load_kernel_corpus_group_and_write_abixml):
Migrate to new API of write_corpus_group()
Signed-off-by: Matthias Maennich <maennich@google.com>
Introduce a new overload for write_corpus that follows the parameter
order context, object (i.e. corpus), indent.
Deprecate all other overloads that were part of the API and mostly
forward them to the new overload. That effort is made to ensure
write_context is always provided. write_context allows access to all
options that influence the output format.
* include/abg-writer.h (write_corpus): Introduce new overload
write_corpus(ctxt, corpus, indent) and deprecate all others.
* src/abg-writer.cc (write_corpus): Likewise for the definitions
and adjust.
* tests/test-read-dwarf.cc (test_task::perform): Use the new
write_corpus which requires a write_context.
* tools/abidw.cc (load_corpus_and_write_abixml, ): Likewise.
* tools/abilint.cc (main): Likewise. Also simplify logic around the
locations as they now can be expressed with less code.
Signed-off-by: Matthias Maennich <maennich@google.com>
Introduce a new overload for write_translation_unit that follows the
parameter order context, object (i.e. translation unit), indent.
Deprecate all other overloads that were part of the API and mostly
forward them to the new one. That effort is made to ensure write_context
is always provided. write_context allows access to all options that
influence the output format.
* include/abg-writer.h (write_translation_unit): Declare a new
overload write_translation_unit(ctxt, tu, indent) and deprecate
all others.
* src/abg-writer.cc (write_translation_unit): Likewise in the
definitions.
(write_corpus, dump, write_translation_unit): Adjust.
* tools/abilint.cc (main): use new write_translation_unit() API
Signed-off-by: Matthias Maennich <maennich@google.com>
Add the macro 'ABG_DEPRECATED' to mark APIs as to be removed in a next
major release. APIs marked with that flag are supposed to work as
before, but might come with downsides. E.g. they could perform worse or
provide only limited functionality. All deprecated functions shall come
with a hint to equivalent functionality within the non-deprecated part
of the API.
* include/abg-fwd.h: Introduce deprecation macro ABG_DEPRECATED
Signed-off-by: Matthias Maennich <maennich@google.com>
'annotate' is one of many flags that could potentially influence the
way, output is written. Remove the default parameter from
write_context's constructor and let users explicitely set that flag on
the context.
* src/abg-writer.cc (write_context::write_context): remove
'annotate' parameter.
(write_translation_unit, write_corpus, write_corpus_group, dump): Adjust.
Signed-off-by: Matthias Maennich <maennich@google.com>
Add .clang-format definitions that are an approximation of the current
coding style. As I understand it, the current style is based on what GNU
Emacs implements for C++. Hence these rules might not be entirely
accurate, but a good-enough approximation to allow contributers to
follow the coding style more easily.
I expect modifications for specific cases and when clang-format itself
evolves over time.
As of now, this definition is most useful in partial code formatting,
such as executed by `git clang-format` on staged files or
clang-format.py as a means of integration into various editors.
* .clang-format: New File.
Signed-off-by: Matthias Maennich <maennich@google.com>
In this problem report, the issue is that when comparing two corpus
groups, especially when looking up function/variable symbols, the
get_fun_symbol_map() and get_var_symbol_map() member functions used
are corpus::get_{fun,var}_symbol_map, rather than
corpus_group::get_{fun, var}_symbol_map. Note that the type
corpus_group inherits from the type corpus. That leads to unexpected
comparison results, especially for symbols.
This patch fixes this by making the corpus::get_{fun, var}_symbol_map
member function be virtual and by using it during the lookup of
function/variable symbols. That way, the right symbol map gets used.
* include/abg-corpus.h (corpus{_group}::get_{fun,
var}_symbol_map): Make these member functions virtual.
* src/abg-corpus.cc (corpus::lookup_{function, variable}_symbol):
Use the virtual corpus::get_{fun, var}_symbol_map() member
function to get the symbols of the current corpus or corpus_group.
* tests/data/Makefile.am: Add the new test input material below to
source distribution.
* tests/data/test-abidiff/test-PR24552-report0.txt: New test input.
* tests/data/test-abidiff/test-PR24552-v0.abi: Likewise.
* tests/data/test-abidiff/test-PR24552-v1.abi: Likewise.
* tests/test-abidiff.cc (main): Support comparing corpus groups.
(specs): Add the new test inputs to the harness.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
When reading an abixml file, we should not try to re-use an anonymous
class, union or enum because by construction two anonymous unions of
the same (internal) name don't necessarily designate the same type.
We already do that in the ELF/DWARF reader so we need to update the
abixml reader too.
Fixed thus.
* src/abg-reader.cc (read_context::maybe_canonicalize_type): Delay
canonicalization of union types too.
(build_class_decl, build_union_decl): Do not try to re-use
anonymous types.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
Some Linux kernel binaries can have no __ksymtab section. It's
possible that only have a __ksymtab_gpl section or no __ksymtab_gpl
either. And apparently they can also have a __ksymtab* section full
of zeroes.
This patch gets the ELF/DWARF reader prepared to handle these cases.
* src/abg-dwarf-reader.cc (find_section): Use elf_getshdrstrndx
rather than poking at the elf header on our own.
(read_context::find_any_ksymtab_section): Define new member
function.
(read_context::{get_symtab_format,
try_reading_first_ksymtab_entry_using_pre_v4_19_format}): Use the
new find_any_ksymtab_section rather than find_ksymtab_section.
(read_context::get_nb_ksymtab_entries): Handle the absence of
__ksymtab.
(read_context::get_nb_ksymtab_gpl_entries): Handle the absence of
__ksymtab_gpl.
(read_context::load_kernel_symbol_table): Handle the case of zero
ksymtab entries.
(read_context::{maybe_adjust_address_for_exec_or_dyn,
maybe_adjust_fn_sym_address, load_kernel_symbol_table}): Handle an
address that is zero.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
The value of the of the pointer to program header returned by
gelf_getphdr is always the same, assuming the value of the last
parameter to gelf_getphdr stays the same. What changes is what is
pointed to by that pointer. So rather than storing the the program
header (to determine the lowest load address among several program
headers returned by gelf_getphdr) we need to store the load address
pointed to by the pointer to the program header.
Thanks to Matthias Männich for spotting this and discussing it at
https://sourceware.org/ml/libabigail/2019-q2/msg00064.html.
Testing this is a bit annoying as we'd need to consider a prelinked binary which has
split debuginfo. I should probably add such a binary to the regression
test suite at some point.
* src/abg-dwarf-reader.cc (get_binary_load_address): Consider the
load address pointed to by the program header pointer returned by
gelf_getphdr rather than the program header itself.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
Calculating the relocation for values in __ksymtab with GElf_Addr (i.e.
uint64_t), makes the calculation rely on overflows for negative offsets.
Address that by treating these as 32bit signed values for the v4.19+
__ksymtabs and calculate the offset with them. This also allows, similar
an earlier commit, to drop the distinction between 64bit and 32bit
kernels.
* src/abg-dwarf-reader.cc (maybe_adjust_sym_address_from_v4_19_ksymtab):
treat passed addr as 32bit signed offset in case of v4.19+ __ksymtabs
Signed-off-by: Matthias Maennich <maennich@google.com>
Reading into uint64_t when reading the symbol table values drops the
sign and subsequently offset calculations will only be correct if either
the offset is positive or if the calculation overflows.
Read the relative value as signed int32_t (indepently of the target's
bitness) to allow negative offsets. That also allows to drop the code
that formerly handled the overflow.
That change fixes an assertion raised when dealing with aarch64 kernel
binaries that have a __ksymtab with 32bit relocations. i.e. Bug #24431
* src/abg-dwarf-reader.cc
(try_reading_first_ksymtab_entry_using_v4_19_format): attempt to
read first __ksymtab entry into int32_t to preserve sign
Signed-off-by: Matthias Maennich <maennich@google.com>
Making the return value type a template type allows for signed types to
be passed and successfully interpreted.
* src/abg-dwarf-reader.cc (read_int_from_array_of_bytes):
templatize return type to allow passing of signed integer references
Signed-off-by: Matthias Maennich <maennich@google.com>
Swap the descriptive comments for the two functions.
* src/abg-dwarf-reader.cc: swap the comments of
try_reading_first_ksymtab_entry_using_{pre_,}v4_19_format
Signed-off-by: Matthias Maennich <maennich@google.com>
This is a follow-up patch for the commit:
43d56de Handle several member anonymous types of the same kind
It allows support for severan anonymous types even when these are not
members of a class/unions.
The patch introduces the concept of a scoped name. It's a qualified
name for a decl made of the name of the decl appended to the
*unqualified* name of its scope. Unlike for qualified names, the
scoped name won't have a "__anonymous_*__" string in its name if its
directly containing scope is not anonymous; a qualified name might
still have that string in its name because the decl has a parent scope
(not necessarily its directly containing scope though) that is
anonymous.
The patch goes on to update the logic for comparison of decls that are
anonymous. For a decl which direct scope is *NOT* anonymous, the
scoped name is what's used in the comparison. Otherwise, only the
name of the decl is used.
The patch also updates how we detect changes in data members and
member types, in the comparison engine. It now uses the names of the
data members, rather than their qualified name. This is in the scope
of the current class/union anyway. The improvement is that the fact
that the class/union itself is anonymous (even if its anonymous name
changes to another anonymous name) won't have any spurious impact on
the detection of name change of the members.
The patch considers the change of an anonymous decl name which
anonymous name changes to another anonymous name as being harmless.
The patch updates the logic of category propagation in the comparison
engine. Although a public typedef to private underlying type needs to
stay public and thus not propagate the PRIVATE_TYPE_CATEGORY from its
child diff node to himself, it still needs to suppress the changes to
the private underlying diff node that were suppressed (because of the
private-ness), unless that typedef has local changes.
* include/abg-ir.h (decl_base::get_scoped_name): Declare new
member function.
(scope_decl::get_num_anonymous_member_{classes, unions, enums}):
Declare new virtual member functions.
(class_decl::get_num_anonymous_member_{classes, unions, enums}):
Adjust to make these virtual. It's not necessary but I feel
redundancy is a kind of self-documentation here.
* src/abg-comp-filter.cc (has_harmless_name_change): Consider
anonymous name changes as harmless.
* src/abg-comparison.cc
(class_or_union_diff::ensure_lookup_tables_populated): Consider
the names of the members rather than their qualified names.
(suppression_categorization_visitor::visit_end): Suppress the
changes to the private underlying diff node that were suppressed
because of the private-ness, unless that typedef has local
changes.
* src/abg-dwarf-reader.cc (build_enum_type)
(add_or_update_class_type, add_or_update_union_type): Handle
anonymous types in namespaces as well, not just in class/unions.
* src/abg-ir.cc (decl_base::priv::scoped_name_): Define new data
member.
(decl_base::get_scoped_name): Define new member function.
(equals): For the decl_base overload, use scoped name in the
comparison, unless the decl belongs to an anonymous type. For the
class_or_union_diff, only consider scoped_name during comparison.
Avoid name comparison between anonymous types.
(scope_decl::get_num_anonymous_member_{classes, unions, enums}):
Define new member functions.
(types_have_similar_structure): Do not compare names between
anonymous types.
(qualified_name_setter::do_update): Update scoped names too.
* tests/data/test-abidiff/test-PR18791-report0.txt: Adjust.
* tests/data/test-annotate/libtest23.so.abi: Likewise.
* tests/data/test-annotate/test13-pr18894.so.abi: Likewise.
* tests/data/test-annotate/test14-pr18893.so.abi: Likewise.
* tests/data/test-annotate/test15-pr18892.so.abi: Likewise.
* tests/data/test-annotate/test21-pr19092.so.abi: Likewise.
* tests/data/test-diff-dwarf/test43-PR22913-report-0.txt:
Likewise.
* tests/data/test-diff-dwarf/test46-rust-report-0.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/test30-pr18904-rvalueref-report2.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-filter/test33-report-0.txt: Likewise.
* tests/data/test-diff-filter/test35-pr18754-no-added-syms-report-0.txt:
Likewise.
* tests/data/test-diff-filter/test44-anonymous-data-member-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/nss-3.23.0-1.0.fc23.x86_64-report-0.txt:
Likewise.
* tests/data/test-diff-pkg/spice-server-0.12.4-19.el7.x86_64-0.12.8-1.el7.x86_64-report-0.txt:
Likewise.
* tests/data/test-diff-pkg/spice-server-0.12.4-19.el7.x86_64-0.12.8-1.el7.x86_64-report-1.txt:
Likewise.
* tests/data/test-diff-pkg/spice-server-0.12.4-19.el7.x86_64-0.12.8-1.el7.x86_64-report-2.txt:
Likewise.
* tests/data/test-diff-pkg/spice-server-0.12.4-19.el7.x86_64-0.12.8-1.el7.x86_64-report-3.txt:
Likewise.
* tests/data/test-read-dwarf/PR22015-libboost_iostreams.so.abi:
Likewise.
* tests/data/test-read-dwarf/PR22122-libftdc.so.abi: Likewise.
* tests/data/test-read-dwarf/libtest23.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.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
When there are several anonymous types (e.g, anonymous classes, unions
or enums) in a given class or union, libabigail's internals do
struggle.
An anonymous class, for instance, is named __anonymous_struct__. When
there are more than one of these inside a given class, then we can't
name and look them up, because they all have the same name.
Incidentally, when add_or_update_class_type completes a class type
that was initially constructed before, it fails to determine that an
anonymous member type of that class was already present in that
context. It thus wrongly duplicates anonymous structs/unions/enums in
there and that leads to spurious textual (abixml) representation
differences later, where duplicated anonymous member types would
appear intermittently, depending on the order in which the class was
built.
This patch addresses this general issue by naming anonymous member
types in a way that allows several of them to exist. That is, if there
are two anonymous structs in a class, they are going to be named
__anonymous_struct__ and __anonymous_struct__1. We do follow a
similar scheme for anonymous unions and enums. This is handled by the
DWARF reader that builds the internal representation.
While looking at this issue, I also fixed a tangent bug; some DWARF
emitters wrongly *define* types in the scope of a
DW_TAG_subroutine_type or DW_TAG_array_type. We handle that by
actually defining those types in the scope of that subroutine or
array. But then it appears that if that scope itself a class and if
the type defined is an anonymous type, then putting that anonymous
type in the class scope might interfere with the *naming* of the
existing legit anonymous types of that scope. I decided to put those
anonymous types in the containing namespace instead. We'll see how
that goes in real time use.
The patch also updates lots of existing tests and adds a new one.
* include/abg-ir.h
(class_or_union::get_num_anonymous_member_{classes, unions,
enums}): Declare new member functions.
* src/abg-dwarf-reader.cc (get_internal_anonynous_die_base_name)
(build_internal_anonymous_die_name)
(get_internal_anonymous_die_name, is_anonymous_type_die): Define
new static functions.
(die_qualified_type_name): Use the new
get_internal_anonymous_die_name.
(get_scope_for_die): Fix this to put anonymous types that were
wrongly emitted into the scope of DW_TAG_subroutine_type or
DW_TAG_array_type by buggy DWARF emitters into the enclosing
namespace, rather than into the enclosing class/union.
(build_enum_type): Take the scope of the enum to have a chance to
properly name potential anonymous enums.
(lookup_class_typedef_or_enum_type_from_corpus): Take an anonymous
member type index for when the DIE we are lookup up represents an
anonymous type. Support proper building of the internal anonymous
name of the anonymous type we are lookup up.
(add_or_update_class_type): Use the new
get_internal_anonynous_die_base_name and
build_internal_anonymous_die_name functions. Support making sure
that the anonymous member type we are adding to the class wasn't
already there, especially for cases where we are updating a class
type.
(add_or_update_union_type): Use the new
get_internal_anonynous_die_base_name and
build_internal_anonymous_die_name functions.
(build_ir_node_from_die): Adjust the use of build_enum_type to
pass it the scope of the enum type we are building.
* src/abg-ir.cc (lookup_union_type): Add a new overload.
(lookup_class_or_typedef_type): Use the new overload of
lookup_union_type above to support looking up union types too.
(class_or_union::get_num_anonymous_member_{classes, unions,
enums}): Define new member functions.
* src/abg-reporter-priv.cc (represent): Detect when anonymous
types of anonymous data members have their internal names change,
probably because anonymous member types were inserted in the scope.
* tests/data/Makefile.am: Add the new test-anonymous-members-0.*
test input files to the source distribution.
* tests/data/test-annotate/test-anonymous-members-0.cc: New test
input file.
* tests/data/test-annotate/test-anonymous-members-0.o: Likewise.
* tests/data/test-annotate/test-anonymous-members-0.o.abi: Likewise.
* tests/data/test-annotate/test17-pr19027.so.abi: Adjust.
* tests/data/test-annotate/test18-pr19037-libvtkRenderingLIC-6.1.so.abi:
Likewise.
* tests/data/test-annotate/test19-pr19023-libtcmalloc_and_profiler.so.abi:
Likewise.
* tests/data/test-annotate/test21-pr19092.so.abi: Likewise.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report0.txt:
Likewise.
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report1.txt
* tests/data/test-diff-filter/test30-pr18904-rvalueref-report2.txt:
Likewise.
* tests/data/test-diff-filter/test35-pr18754-no-added-syms-report-0.txt:
Likewise.
* tests/data/test-read-dwarf/PR22122-libftdc.so.abi: Likewise.
* tests/data/test-read-dwarf/test12-pr18844.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/test21-pr19092.so.abi: Likewise.
* tests/data/test-read-dwarf/test22-pr19097-libstdc++.so.6.0.17.so.abi:
Likewise.
* tests/test-annotate.cc (int_out_specs): Add the new test inputs
to this test harness.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
This patch stores canonical types in the hash maps that are used in
the abixml writer to compute the type IDs. This limits the
possibility that two types that are equivalent (especially when one is
a declaration-only class) end-up in the same abixml.
* src/abg-writer.cc (write_context::{type_has_existing_id,
get_id_for_type}): Save the canonical type of the type in the map,
not the type itself.
(write_context::{type_is_emitted}): Use the canonical type rather
than the type itself.
* tests/data/test-read-dwarf/test9-pr18818-clang.so.abi: Adjust.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
Trying to de-duplicate anonymous struct DIEs can lead to subtle
issues, because there can be two different naming typedefs designating
two anonymous structs that are equivalent, in the same translation
unit. In that case, de-duplicating the two leaf anonymous structs
DIEs leads to non-resolvable conflict.
This patch avoids de-duplicating anonymous structs DIEs and rather
de-duplicates (naming) typedefs.
* include/abg-fwd.h (is_typedef): Remove the overloads for
type_base_sptr and decl_base_sptr. Replace those with an overload
for type_or_decl_base_sptr.
* src/abg-ir.cc (is_typedef): Do the same for the definitions.
* src/abg-dwarf-reader.cc (add_or_update_class_type)
(add_or_update_union_type): Do not de-duplicate anonymous
struct/union DIEs.
(build_typedef_type): Try to de-duplicate typedefs DIEs.
* tests/data/test-annotate/test17-pr19027.so.abi: Adjust.
* tests/data/test-annotate/test19-pr19023-libtcmalloc_and_profiler.so.abi:
Likewise
* tests/data/test-annotate/test21-pr19092.so.abi: Likewise.
* tests/data/test-read-dwarf/PR22015-libboost_iostreams.so.abi: Likewise.
* tests/data/test-read-dwarf/PR22122-libftdc.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/test19-pr19023-libtcmalloc_and_profiler.so.abi:
Likewise.
* tests/data/test-read-dwarf/test21-pr19092.so.abi: Likewise.
* tests/data/test-read-dwarf/test9-pr18818-clang.so.abi: Likewise.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
During DWARF reading, it can happen that some types are created that
are not tied to a given DIE. This happens for instance when editing
the internal representation of types to better reflect the intent of
the code rather than the letter of the code; more precisely this
happens when a qualified array is edited to represent an array of
qualified elements, for instance. In that case, the qualified element
type is created by the DWARF analyser. And in the present incarnation
of the code, we forget to canonicalize that type.
The fact that that type is not canonicalized leads to cases where two
equivalent types can still be present in a translation unit in the
resulting abixml representation, without the abixml writer noticing
it. That duplication can lead to unnecessary cycles in the type graph
where passes can either take one side or the other of the cycle; and
that leads to subtle heisen-changes in the emitted abixml representation.
This patch thus canonicalizes those newly created types.
* src/abg-dwarf-reader.cc
(read_context::extra_types_to_canonicalize_): Add new data member.
(read_context::{initialize, clear_types_to_canonicalize}): Adjust.
(read_context::extra_types_to_canonicalize): Create new accessor.
(read_context::schedule_type_for_late_canonicalization): Add new
overload for type_base_sptr.
(read_context::perform_late_type_canonicalizing): Perform the
canonicalization of the types created by the DWARF analyzer, but
that are not tied to any DIE.
(maybe_strip_qualification): Take a read_context&. Schedule newly
created types (during type edition) for late canonicalization.
(build_ir_node_from_die): Adjust the call to
maybe_strip_qualification to pass a read_context.
* tests/data/test-annotate/test15-pr18892.so.abi: Adjust.
* tests/data/test-annotate/test17-pr19027.so.abi: Likewise.
* tests/data/test-annotate/test21-pr19092.so.abi: Likewise.
* tests/data/test-read-dwarf/PR22122-libftdc.so.abi: Likewise.
* tests/data/test-read-dwarf/test12-pr18844.so.abi: Likewise.
* tests/data/test-read-dwarf/test15-pr18892.so.abi: Likewise.
* tests/data/test-read-dwarf/test17-pr19027.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.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
The GCC8 address sanitizer found an issue in find_alt_debug_info_link.
It tried to convert a build-id byte sequence into a string. But the
build-id byte sequence is not a zero terminated sequence of chars.
So it could run off way past the section data.
The code never actually uses the build-id. It could use it to verify
the referenced alt-file is the correct one. But since it uses elfutils
to actually load the alt file it doesn't have to, since elfutils will
already check the build-id matches.
So just remove the build_id argument from find_alt_debug_info_link
and don't try to convert and return it as a string.
* src/abg-dwarf-reader.cc (find_alt_debug_info_link): Remove
build_id argument. Don't try to read the buildid chars as a
string.
(find_alt_debug_info): Don't call find_alt_debug_info_link
with a build_id string argument.
Signed-off-by: Mark Wielaard <mark@klomp.org>
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
* src/abg-comp-filter.cc: (has_var_type_cv_qual_change):
Initialize the ch_kind variable before using it.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
Add options to enable building with -fsanitize=address or
-fsanitize=undefined.
* configure.ac: Add configure options for -fsanitize=address and
-fsanitize=undefined.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
We were forgetting to call fts_close on a file hierarchy returned by
fts_open. Plugged thus.
* src/abg-tools-utils.cc (find_file_under_dir): Call fts_close
before return.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
Within the loop, the call `gelf_getphdr(elf_handle, i, &ph_mem)` is
returning a pointer to `ph_mem` that is only valid in this loop
iteration. The later assignment to *lowest_program_header and its
eventual use to assign load_address leads to undefined behaviour.
* src/abg-dwarf-reader.cc (get_binary_load_address): Move the
ph_mem and program_header variables out of the inner for-loop.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
Array and qualified types can be edited after they are built, e.g, to
fold the qualifiers of the array as those should always apply to the
element types of the array, at least in C and C++. So we need to
delay the canonicalization of these types until *after* all that type
editing is done. We were not doing that properly and I suspect this
is the cause of some "heisenregressions" we are seeing on some
platforms intermittently.
This patch does delay the type canonicalization and insures that we
don't edit types that are canonicalized already.
* src/abg-dwarf-reader.cc (maybe_canonicalize_type): Delay the
canonicalization of array and qualified types, just like what we
do for classes and function types already.
(maybe_strip_qualification): Do not
re-canonicalize array and qualified types here because it should
not be necessary anymore.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
Running the testsuite with AddressSanitizer turned on flagged a memory
leak in real_path, in abg-tools-utils.cc.
Fixed thus.
* src/abg-tools-utils.cc (real_path): Fee the returned pointer of
realpath.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
With this patch, configuring the project with the environment variables
ABIGAIL_DEVEL=on and ABIGAIL_DEVEL_ASAN=on will turn on
AddressSanitizer.
* configure.ac: If ABIGAIL_DEVEL_ASAN=on (in addition to
ABIGAIL_DEVEL=on), then turn on AddressSanitizer in the build.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
This is a fallout from this commit:
ad8c253 Bug 24431 - ELF reader can't interpret ksymtab with Kernel 4.19+
The problem is that the method used to determine if the format of the
__ksymtab section is pre or post v4.19. In that commit, we assumed
that a kernel without relocations for the __ksymtab section implies a
v4.19 format, because in that format, we don't need relocations for
that section. But then it can happen that the entire kernel be built
without relocations, in the case a non relocatable kernels. So just
looking a the presence of relocations is not a good enough
discriminant to determine the format of the __ksymtab section.
This patch rather tries to read the first entry of the __ksymtab
section assuming a pre v4.19 format, comes up with an address, and
then looks the .symtab section up with that address. If the lookup
succeeds and we find a symbol, then we can reasonably assume that the
__ksymtab section is in the v4.19 format. Otherwise, we do the same
assuming a v4.19 format, etc.
Tested on v4.9, v4.16 and v4.16 kernels in 32 and 64 bits.
* src/abg-dwarf-reader.cc
(read_context::{try_reading_first_ksymtab_entry_using_pre_v4_19_format,
try_reading_first_ksymtab_entry_using_v4_19_format}): Define new
member functions.
(read_context::maybe_adjust_sym_address_from_v4_19_ksymtab): Make
member function this const.
(read_context::get_ksymtab_format): Implement the new heuristic
here, using try_reading_first_ksymtab_entry_using_pre_v4_19_format
and try_reading_first_ksymtab_entry_using_v4_19_format, rather
than assuming that if we have no relocations, then we are in the
v4.19 format.
(maybe_adjust_sym_address_from_v4_19_ksymtab): When on a 64 bits
architecture, ensure the 32 bits address read from the v4.19
format __ksymtab section is converted into a 64 bits address.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
Add / update .gitignore files for tests/ and tools to ignore
binaries, logs, traces typically produced during development.
* tests/.gitignore: exclude tests binaries and test results
* tools/.gitignore: update to ignore produced binaries
Signed-off-by: Matthias Maennich <maennich@google.com>
operator& was implemented in terms of itself, leading to infinite
recursion. Fix that by implementing it in terms of &='ing the const
value. That is consistent with all other ?= operators.
* src/abg-dwarf-reader.cc: fix expr_result::operator&
Signed-off-by: Matthias Maennich <maennich@google.com>
When compiling with clang, the following warning is emitted:
abg-comparison.cc:2674:17: warning: expression with side effects will be
evaluated despite being used as an operand to 'typeid' [-Wpotentially-evaluated-expression]
return typeid(*first.get()) != typeid(*second.get());
^
Mitigate that warning by moving potential side effects out of typeid.
* src/abg-comparison.cc: fix clang warning "potentially-evaluated-expression"
Signed-off-by: Matthias Maennich <maennich@google.com>
The data members environment_setter::artifact_ and
qualified_name_setter::node_ are not used and can therefore be dropped
along with all their references.
* src/abg-ir.cc: drop unused data members
Signed-off-by: Matthias Maennich <maennich@google.com>
Drop 'require_drop_property' as it is not used at all.
That fixes a clang warning.
* include/abg-suppression-priv.h: drop unused argument from type_is_suppressed
Signed-off-by: Matthias Maennich <maennich@google.com>
_M_canvas and _M_typo are unused within "dot". Remove them and all
references.
* include/abg-viz-dot.h: remove unused data members from 'dot'
Signed-off-by: Matthias Maennich <maennich@google.com>
Several virtual desctructors were missing. Even though there might not
have been actual leaks or similar bugs, it is worth fixing these
locations as they might lead to bugs in the future.
Clang also warns at these locations:
warning: delete called on non-final 'abigail::ir::corpus' that has virtual
functions but non-virtual destructor [-Wdelete-non-virtual-dtor]
* include/abg-comparison.h: add virtual destructor for corpus_diff and diff_node_visitor
* include/abg-corpus.h: add virtual destructor for corpus
* include/abg-reporter.h: add virtual destructor for reporter_base
* include/abg-traverse.h: add virtual destructor for traversable_base
Signed-off-by: Matthias Maennich <maennich@google.com>
The postfix increment / decrement operators were implemented by calling
themselves recursively. Fix that by implementing these in terms of their
prefix counter parts.
* include/abg-diff-utils.h: fix postfix dec/inc operator
Signed-off-by: Matthias Maennich <maennich@google.com>
When compiling with clang, the following warning is emitted:
abg-reader.cc:1981:15: warning: using the result of an assignment as a condition without parentheses [-Wparentheses]
while (corp = read_corpus_from_input(ctxt))
~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
That is certainly a common pitfall and can be mitigated by placing
parentheses around the assignment.
* src/abg-reader.cc: clarify boolean use of assignment
Signed-off-by: Matthias Maennich <maennich@google.com>
Returning bool literals from main can be misleading. Returning booleans
maps to (by convention):
return false -> converted to 0 -> rc=0 considered SUCCESS
return true -> converted to 1 -> rc=1 considered FAILURE
Compiling with clang also emits:
abilint.cc:258:7: warning: bool literal returned from 'main' [-Wmain]
return true;
^ ~~~~
The issues can be addressed by consistently returning integers as also
done in all other mains across the project.
Same issue applies to print-diff-tree.cc.
* tools/abilint.cc: return int in main rather than bool.
* tests/print-diff-tree.cc: Likewise.
Signed-off-by: Matthias Maennich <maennich@google.com>
ir_node_visitor is defined as `class` in include/abg-ir.h:4429 and
should therefore also be forward-declared as such.
* include/abg-fwd.h: forward-declare ir_node_visitor as class
Signed-off-by: Matthias Maennich <maennich@google.com>
Since the commit
7290d58095
of the kernel, the format of the ksymtab section changed, so the ELF
reader of Libabigail cannot get the list of kernel symbols that are
meaningful to analyze.
In the new format, each ksymtab entry is now 32 bits length,
independently of if the kernel was built in 32 or 64 bits mode. This
way, 64 bit kernels save 32 bits per entry, from the ksymtab section
alone.
Also, note that the symbol address in the ksymtab entry is stored in a
"place-relative address" format. That means for a given symbol value
'Sym_Addr', the value which is stored at a given offset 'Off' of the
ksymtab secthion which address is Ksymtab_Addr is:
Sym_Addr - Ksymtab_Addr - Off.
This is what is meant by storing Sym_Addr in a "place-relative" manner.
One advantage, of course, is to make Sym_Addr take 32 bits, even on a
64 bits arch. Another advantage is that the resulting value doesn't
need to be relocated! So we don't need any relocation section either!
So lots of space saving.
This patch teaches the ELF reader into this new format.
* src/abg-dwarf-reader.cc (enum kernel_symbol_table_kind): Move this
enum at the top.
(enum ksymtab_format): Define new enum.
(read_context::{ksymtab_format_, ksymtab_entry_size_,
nb_ksymtab_entries_, nb_ksymtab_gpl_entries_}): Define new data
members.
(read_context::initiliaze): Initialize the new data members above.
(read_context::{get_ksymtab_format, get_ksymtab_symbol_value_size,
get_ksymtab_entry_size, get_nb_ksymtab_entries,
get_nb_ksymtab_gpl_entries,
maybe_adjust_sym_address_from_v4_19_ksymtab}): Define new member
functions.
(read_context::load_kernel_symbol_table): Support loading from
both pre and post v4.19 linux kernels with their different ksymtab
formats. Add more comments.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>
In C and C++ the qualifiers of a qualified array type apply to the
element type of said array.
In this particular problem report, GCC and Clang emit DWARF that
represent the qualifiers either on the array type, or on the element
type. Quoting the test of the bug:
Given the following example:
struct test {
const char asdf[4];
};
void func(struct test arg) {}
abidiff says:
1 function with some indirect sub-type change:
[C]'function void func(test)' at test.c:5:1 has some indirect sub-type
changes:
parameter 1 of type 'struct test' has sub-type changes:
type size hasn't changed
1 data member change:
type of 'const char test::asdf[4]' changed:
entity changed from 'const char[4]' to 'const char[4] const'
This is because GCC represents the array as const array of const
signed char, whereas clang represents it as an array of const signed
char.
In this patch, libabigail's DWARF reader detects qualified array types
and appropriately qualifies the array element type, instead of
qualifying the array type. The patch accordingly adjusts the various
regression tests and adds a new test which comes from the problem
report.
* include/abg-fwd.h (is_array_of_qualified_element): Declare 2
overloads of this function.
(re_canonicalize): Declare a new function.
* include/abg-ir.h (class {decl_base, type_base}): Declare
re_canonicalize as a friend of these classes.
* src/abg-dwarf-reader.cc (maybe_strip_qualification): Detect
qualified array types and appropriately qualifies the array
element type, instead of qualifying the array type itself.
Re-canonicalize the resulting type if necessary.
* src/abg-ir.cc (is_array_of_qualified_element): Define 2
overloads of this function.
(re_canonicalize): Define new function.
* tests/data/Makefile.am: The two new test binary input files
PR24430-fold-qualified-array-clang and
PR24430-fold-qualified-array-gcc to source distribution, as well
as the expected reference output.
* tests/data/test-annotate/test15-pr18892.so.abi: Adjust.
* tests/data/test-annotate/test17-pr19027.so.abi: Likewise.
* tests/data/test-annotate/test19-pr19023-libtcmalloc_and_profiler.so.abi:
Likewise.
* tests/data/test-annotate/test21-pr19092.so.abi: Likewise.
* tests/data/test-diff-filter/PR24430-fold-qualified-array-clang:
New binary test input coming from the bug report.
* tests/data/test-diff-filter/PR24430-fold-qualified-array-gcc:
Likewise.
* tests/data/test-diff-filter/PR24430-fold-qualified-array-report-0.txt:
Expected reference abi difference.
* tests/data/test-diff-filter/test33-report-0.txt: Adjust.
* tests/data/test-diff-pkg/nss-3.23.0-1.0.fc23.x86_64-report-0.txt:
Likewise.
* tests/data/test-read-dwarf/PR22122-libftdc.so.abi: Likewise.
* tests/data/test-read-dwarf/test12-pr18844.so.abi: Likewise.
* tests/data/test-read-dwarf/test15-pr18892.so.abi: Likewise.
* tests/data/test-read-dwarf/test17-pr19027.so.abi: Likewise.
* tests/data/test-read-dwarf/test19-pr19023-libtcmalloc_and_profiler.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/test-diff-filter.cc: Add the new binary test input to this
test harness.
Signed-off-by: Dodji Seketeli <dodji@redhat.com>