Mark Wielaard [Thu, 5 May 2022 21:59:57 +0000 (23:59 +0200)]
debuginfod: Try without MHD_USE_DUAL_STACK if MHD_start_daemon fails
On a systems that have ipv6 disabled debuginfod doesn't start up
anymore because libhttpd MHD_USE_DUAL_STACK only works if it can
open an ipv6 socket. If MHD_start_daemon with MHD_USE_DUAL_STACK
fails try again without that flag set.
Mark Wielaard [Mon, 2 May 2022 23:35:53 +0000 (01:35 +0200)]
configure: Don't use valgrind and sanitize-undefined for make distcheck
make distcheck would always run with --enable-valgrind and
--enable-sanitize-undefined. Assuming the maintainer would run this just
before doing a release. But this makes distcheck really, really, really
slow. And we have various buildbots now that run various combinations
of valgrind, undefined and/or address sanitizer over every commit now.
Aaron Merey [Wed, 12 Jan 2022 03:07:55 +0000 (22:07 -0500)]
debuginfod: Use the debuginfod-size response header
In some cases the content-length header may not be available in order
to pass to a progressfn. If content-length isn't available then attempt
to get the size of the download from the debuginfod-size header instead.
It should be mentioned that if a compressed file (ex. gzip) is being
transferred, the actual transfer length will be less than debuginfod-size.
In this case debuginfod-size is a best-guess upper bound on the size of
the transfer.
Mark Wielaard [Fri, 22 Apr 2022 21:36:30 +0000 (23:36 +0200)]
debuginfod, libdwfl: Initialize libcurl and dlopen debuginfod-client lazily
We used to go out of our way to initialize libcurl early before any other
thread/code was running. But this meant that we might pay startup cost,
which under FIPS is significant, even for code that never uses libdebuginfod
or TLS libcurl connections. Although curl_global_init itself isn't thread-safe
we can use pthread_once to make sure we don't race against ourselves. This
still means we might race against any application code that might use
libcurl. But we can assume they will have called curl_global_init before
calling dwfl_begin or debuginfod_begin.
Mark Wielaard [Sun, 24 Apr 2022 17:42:29 +0000 (19:42 +0200)]
libelf: Check for mremap, elf_update needs it for ELF_C_RDWR_MMAP
Add a AC_CHECK_FUNCS configure check for mremap. Some systems like
KFreeBSD and the Hurd don't have it. Also add a configure warning
because without mremap elf_update will often fail when ELF_C_RDWR_MMAP
is used. ELF_C_RDWR_MMAP is an elfutils extension to libelf.
Mark Wielaard [Sun, 24 Apr 2022 10:16:58 +0000 (12:16 +0200)]
debuginfod: Use MHD_USE_ITC in MHD_start_daemon flags
This prevents the "Server reached connection limit. Closing inbound
connection." issue we have been seeing in the
run-debuginfod-webapi-concurrency.sh testcase. From the manual:
If the connection limit is reached, MHD’s behavior depends a bit
on other options. If MHD_USE_ITC was given, MHD will stop
accepting connections on the listen socket. This will cause the
operating system to queue connections (up to the listen() limit)
above the connection limit. Those connections will be held until
MHD is done processing at least one of the active connections. If
MHD_USE_ITC is not set, then MHD will continue to accept() and
immediately close() these connections.
1. Simplify needless sh -c "cat glob 2>/dev/null"
into cat glob 2>/dev/null under sh
and fix re-expansion/-e protection under csh
2. Use $( instead of ` under sh
3. Assign to DEBUGINFOD_URLS directly and either export it or unset it
Di Chen [Tue, 1 Mar 2022 12:44:38 +0000 (20:44 +0800)]
readelf: Don't consider padding DT_NULL as dynamic section entry
when using `$ eu-readelf -d {FILE}` to get the number of dynamic
section entris, it wrongly counts the padding DT_NULLs as dynamic
section entries. However, DT_NULL Marks end of dynamic section.
They should not be considered as dynamic section entries.
Mark Wielaard [Thu, 14 Apr 2022 11:26:57 +0000 (13:26 +0200)]
tests: Don't try to corrupt sqlite database during test.
In run-debuginfod-federation-sqlite.sh we used to try to corrupt
the sqlite database while the debuginfod server was running and
check it detected errors, but that was unreliably and slightly
dangerous since part of the database was already mapped into memory.
Instead trigger some some random activity, then trigger a shutdown.
PR29022: 000-permissions files cause problems for backups
000-permission files currently used for negative caching can cause
permission problems for some backup software and disk usage checkers.
Fix this by using empty files for negative caching instead.
Also use each empty file's mtime to determine the time since
last download attempt instead of the cache_miss_s file's mtime.
Mark Wielaard [Thu, 7 Apr 2022 13:16:41 +0000 (15:16 +0200)]
config: Add versioned requires on libs/libelf for debuginfod-client
elfutils-debuginfod-client contains the debuginfod-client binary
which is uses libelf and libdw. Add explicit versioned requires
on elfutils-libs and elfutils-libelf so they will always be in sync
like done with all other inter sub package dependencies.
debuginfod: Include "IPv4 IPv6" in server startup message
At startup debuginfod prints a message indicating the port which the
server is listening to. Prior to commit 4e4082be03 this message would
include "IPv4" and/or "IPv6"
[...] (48671/48671): started http server on IPv4 IPv6 port=8002
As of commit 4e4082be03 the IP versions have been removed from this
message. This change can cause issues in any applications that
parse the message for this information. Fix this by adding
"IPv4 IPv6" back to the message.
Mark Wielaard [Fri, 1 Apr 2022 10:19:20 +0000 (12:19 +0200)]
libelf: Return already gotten Elf_Data from elf_getdata_rawchunk
elf_getdata_rawchunk keeps a list of Elf_Data_Chunk to track which
Elf_Data structures have already been requested. This allows elf_end
to clean up all internal data structures and the Elf_Data d_buf if
it was malloced.
But it didn't check if a chunk was already requested earlier. This
meant that if for example dwelf_elf_gnu_build_id was called multiple
times to lookup a build-id from the phdrs a new Elf_Data_Chunk was
created. This could slowly leak memory.
So also keep track of the offset from which the size and type of
the rawdata was requested so we can return existing data if it is
requested multiple times.
Note that the current cache is a simple linked list but the chain
is normally not that long. It is normally used to get chunks from
the phdrs, and there are normally less than 10.
debuginfod: use single ipv4+ipv6 microhttpd daemon configuration
Use a single MHD_USE_DUAL_STACK mhd daemon. This way, the thread
connection pool is not doubled, saving memory and better matching user
expectations. A slight tweak to logging is required to pull IPv4
remote addresses back out, and also to allow IPv6 ::-laden address
forwarding through federation links.
PR28708: debuginfod: use MHD_USE_EPOLL for microhttpd threads
Testing on s390x and other architectures indicates that this
configuration reduces thundering-herd wakeups and saturation of a
small number of threads. The run-debuginfod-webapi-concurrency.sh
test appears solid now.
Mark Wielaard [Tue, 29 Mar 2022 22:17:08 +0000 (00:17 +0200)]
libelf: Also copy/convert partial datastructures in xlate functions
The generated xlate functions can only convert full datastructures,
dropping any trailing partial data on the floor. That means some of
the data might be undefined. Just copy over the trailing bytes as
is. That data isn't really usable. But at least it is defined data.
Mark Wielaard [Sun, 27 Mar 2022 19:08:36 +0000 (21:08 +0200)]
Introduce error_exit as a noreturn variant of error (EXIT_FAILURE, ...)
error (EXIT_FAILURE, ...) should be noreturn but on some systems it
isn't. This may cause warnings about code that should not be
reachable. So have an explicit error_exit wrapper that is noreturn
(because it calls exit explicitly). Use error_exit in all tools under
the src directory.
Mark Wielaard [Thu, 24 Mar 2022 22:06:09 +0000 (23:06 +0100)]
libelf: Sync elf.h from glibc.
Adds EM_INTELGT, NT_ARM_TAGGED_ADDR_CTRL, NT_ARM_PAC_ENABLED_KEYS,
ELF_NOTE_FDO, NT_FDO_PACKAGING_METADATA and OpenRISC 1000 specific
relocs.
It also adds and renames some GNU_PROPERTY constants. But none of the
constants the elfutils code uses was renamed or given a different
constant value.
dwelf_elf_e_machine_string was updated to handle EM_INTELGT.
Mark Wielaard [Sun, 20 Mar 2022 23:34:24 +0000 (00:34 +0100)]
configure: Don't check whether -m64 works for 32bit host biarch check
Running a 32bit backtrace test against a 64bit binary doesn't work.
Only a 64bit binary can backtrace a 32bit binary. So disable the
biarch check that inserts -m64 for a 32bit host.
Mark Wielaard [Wed, 23 Mar 2022 00:20:56 +0000 (01:20 +0100)]
libelf: Correct alignment of ELF_T_GNUHASH data for ELFCLASS64
ELF_T_GNUHASH data is just 32bit words for ELFCLASS32. But for
ELFCLASS64 it is a mix of 32bit and 64bit words. In the
elf_cvt_gnuhash function we rely on the alignment of the whole to be
64bit word aligned, even though the first 4 words are
32bits. Otherwise we might try to convert an unaligned 64bit word.
Mark Wielaard [Sun, 20 Mar 2022 21:21:05 +0000 (22:21 +0100)]
libelf: Don't overflow offsets in elf_cvt_Verneed and elf_cvt_Verdef
The conversion functions for Verdef and Verneed keep offsets to the next
structure. Make sure that following vd_aux, vda_next, vd_next, vn_aux,
vna_next and vn_next don't overflow (and wrap around) the offsets.
Mark Wielaard [Fri, 18 Mar 2022 15:01:20 +0000 (16:01 +0100)]
libdwfl: Close ar members when they cannot be processed.
When reporting ar members they should be closed when they cannot
be processed. A comment in offline.c said that process_file called
elf_end if it returned NULL. But this is incorrect. And other places
that call process_file do call elf_end explicitly when it returns
NULL.
Mark Wielaard [Thu, 17 Mar 2022 23:59:38 +0000 (00:59 +0100)]
libelf: Check alignment of Verdef, Verdaux, Verneed and Vernaux offsets
The Verdef, Verdaux, Verneed and Vernaux structures contain fields
which point to the next structures. Make sure these offsets are
correctly aligned for the structures they point to.
Mark Wielaard [Thu, 17 Mar 2022 13:03:06 +0000 (14:03 +0100)]
libelf: Make sure ar_size starts with a digit before calling atol.
The ar_size field is a 10 character string, not zero terminated, of
decimal digits right padded with spaces. Make sure it actually starts
with a digit before calling atol on it. We already make sure it is
zero terminated. Otherwise atol might produce unexpected results.
Mark Wielaard [Thu, 17 Mar 2022 12:58:56 +0000 (13:58 +0100)]
libelf: Take map offset into account for Shdr alignment check in elf_begin
The sh_num function tries to get at the zero section Shdr directly.
When the file is mmapped it has to make sure the offset into the file
to the start of the Elf structure is taken into account when trying to
cast the address to make sure the alignment is correct.
Mark Wielaard [Mon, 14 Mar 2022 12:13:34 +0000 (13:13 +0100)]
configure: Use AS_HELP_STRING instead of AC_HELP_STRING.
In most places we already used AS_HELP_STRING. A few places used
AC_HELP_STRING. Which has been deprecated for a long time. Use
AS_HELP_STRING instead of AC_HELP_STRING everywhere.
Mark Wielaard [Thu, 10 Mar 2022 16:03:36 +0000 (17:03 +0100)]
configure: Test for _FORTIFY_SOURCE=3 support.
_FORTIFY_SOURCE=3 adds extra glibc (dynamic) fortification checks
when using GCC 12.
This adds a configure check to see if -D_FORTIFY_SOURCE=3 can be used.
If not, configure will fall back to -D_FORTIFY_SOURCE=2.
On some older glibc versions (glibc 2.17) using -D_FORTIFY_SOURCE=3
provides the same fortification as _FORTIFY_SOURCE=2. On some newer
glibc versions and older GCC (glibc 2.34 amd gcc 11) using
-D_FORTIFY_SOURCE=3 produces a not supported warning (and we fall
back to -D_FORTIFY_SOURCE=2). With newer glibc and newer GCC versions
(glibc 2.35 and gcc 12) -D_FORTIFY_SOURCE=3 will use the newer dynamic
fortification checks.
This patch also makes sure that AC_PROG_CXX is used earlier so that
CXXFLAGS is always setup correctly (even if we then don't use it).
And it outputs both the CFLAGS and CXXFLAGS as used at the end.
Mark Wielaard [Wed, 16 Feb 2022 13:47:46 +0000 (14:47 +0100)]
backends: Use PTRACE_GETREGSET for ppc_set_initial_registers_tid
The code in ppc_initreg.c used PTRACE_PEEKUSER to fetch all registers
one by one. Which is slightly inefficient. It did this because it wanted
things to work on linux 2.6.18 which didn't support PTRACE_GETREGSET.
PTRACE_GETREGSET was only officially since 2.6.34 (but backported
to some earlier versions). It seems ok to require a linux kernel that
supports PTRACE_GETREGSET now. This is much more efficient since it
takes just one ptrace call instead of 44 calls to fetch each register
individually.
For some really old versions we need to include <linux/ptrace.h> to
get PTRACE_GETREGSET defined. And on ppc64 there is no 32bit version
of struct pt_regs available, so we define that ourselves and check
how much data is returned to know whether this is a full pt_regs or
one for a 32bit process. An alternative would be to use the raw
iov_base bytes with 64bit or 32bit offset constants to get at the
registers instead of using a struct with names.
The code works for inspecting a 32bit process from a 64bit build,
but not the other way around (the previous code also didn't). This
could work if we also defined and used a 64bit pt_regs struct on
ppc32. But it seems a use case that is not really used (it was hard
enough finding ppc32 setups to test this on).
Tested against ppc and ppc64 on linux 2.6.32 and glibc 2.12 and
ppc and ppc64 on linux 3.10.0 with glibc 2.17.
Frank Ch. Eigler [Mon, 31 Jan 2022 23:13:40 +0000 (18:13 -0500)]
man debuginfod-client-config.7: Elaborate $DEBUGINFOD_URLS
Add reference to /etc/profile.d and /etc/debuginfod/*.urls as possible
source of default. (No need to autoconf @prefix@ it, these paths are
customarily distro standard rather than elfutils configurables.)
Drop warning about federation loops, due to protection via PR27917 (0.186).
Mark Wielaard [Thu, 6 Jan 2022 16:58:59 +0000 (17:58 +0100)]
libdwfl: Declare possible zero sized arrays only when non-zero
The gcc undefined sanitizer complains when seeing a zero sized array
declaration. Move the declaration to the point in the code where we
know they aren't zero sized.
Mark Wielaard [Thu, 6 Jan 2022 16:35:13 +0000 (17:35 +0100)]
libdwfl: Handle unaligned Dyns in dwfl_segment_report_module
The xlate functions only handle correctly aligned buffers. But they do
handle src == dest. So if the source buffer isn't aligned correctly
just copy it first into the destination (which is already correctly
aligned).
Mark Wielaard [Fri, 24 Dec 2021 01:01:32 +0000 (02:01 +0100)]
libdwfl: Calculate addr to read by hand in link_map.c read_addrs.
The gcc undefined sanitizer doesn't like the trick we use to calculate
the (possibly) unaligned addresses to read. So calculate them by hand
as unsigned char pointers.
Mark Wielaard [Fri, 24 Dec 2021 00:44:57 +0000 (01:44 +0100)]
libdwfl: Call xlatetom on aligned buffers in dwfl_link_map_report
Make sure that when calling xlatetom for Phdrs and Dyns in
dwfl_link_map_report the input buffer is correctly aligned by calling
memcpy and setting in.d_buf to out.d_buf.
Mark Wielaard [Thu, 23 Dec 2021 22:16:25 +0000 (23:16 +0100)]
libdwfl: Make sure dwfl_elf_phdr_memory_callback returns at least minread
The callers of dwfl_elf_phdr_memory_callback assume at least minread
bytes are read and available. Make sure to check start is smaller than
elf->maximum_size before reading more. Return false if end - start is
smaller than minread.
Mark Wielaard [Mon, 20 Dec 2021 23:55:27 +0000 (00:55 +0100)]
libdwfl: Always clean up build_id.memory
There was a small memory leak if an error was detected in some places
in dwfl_segment_report_module after the build_id.memory was alredy
allocated. Fix this by moving initialization of struct elf_build_id
early and always free the memory, if not NULL, at exit.
Mark Wielaard [Mon, 20 Dec 2021 00:39:21 +0000 (01:39 +0100)]
libdwfl: Handle unaligned Nhdr in dwfl_segment_report_module
The xlate functions only handle correctly aligned buffers. But they do
handle src == dest. So if the source buffer isn't aligned correctly
just copy it first into the destination (which is already correctly
aligned).
Mark Wielaard [Sun, 19 Dec 2021 23:31:33 +0000 (00:31 +0100)]
libdwfl: Handle unaligned Phdr in dwfl_segment_report_module
The xlate functions only handle correctly aligned buffers. But they do
handle src == dest. So if the source buffer isn't aligned correctly
just copy it first into the destination (which is already correctly
aligned).
Mark Wielaard [Sun, 19 Dec 2021 22:58:32 +0000 (23:58 +0100)]
libdwfl: Handle unaligned Ehdr in dwfl_segment_report_module
The xlate functions only handle correctly aligned buffers. But they do
handle src == dest. So if the source buffer isn't aligned correctly
just copy it first into the destination (which is already correctly
aligned).
Mark Wielaard [Sun, 19 Dec 2021 20:11:13 +0000 (21:11 +0100)]
libdwfl: Rewrite GElf_Nhdr reading in dwfl_segment_report_module
Make sure that the notes filesz is not too big. Rewrite reading of the
notes to check for overflow at every step. Also limit the size of the
buildid bytes.
Mark Wielaard [Sun, 19 Dec 2021 14:52:32 +0000 (15:52 +0100)]
libelf: Only set shdr state when there is at least one shdr
The elf shdr state only needs to be set when scncnt is at least
one. Otherwise e_shoff can be bogus. Also use unsigned arithmetic for
checking e_shoff alignment.
Mark Wielaard [Fri, 17 Dec 2021 17:09:31 +0000 (18:09 +0100)]
libdwfl: Make sure the note len increases each iteration
In dwfl_segment_report_module we have an overflow check when reading
notes, but we could still not make any progress if the number of bytes
read (len) didn't increase at all. Check len > last_len.
Mark Wielaard [Fri, 17 Dec 2021 16:43:19 +0000 (17:43 +0100)]
libdwfl: Make dwfl_segment_report_module aware of maximum Elf size
At the end of dwfl_segment_report_module we might try to read in
the whole contents described by a core file. To do this we first
allocate a zeroed block of memory that is as big as possible. The
core file however may describe much more loaded data than is actually
available in the Elf image. So pass the maximum size so we can
limit the amount of memory we reserve.
Mark Wielaard [Sat, 18 Dec 2021 01:01:37 +0000 (02:01 +0100)]
libdwfl: Make sure note data is properly aligned.
In dwfl_segment_report_module the note data might not be properly
aligned. Check that it is before accessing the data directly.
Otherwise convert data so it is properly aligned.
Also fix NOTE_ALIGN4 and NOTE_ALIGN8 to work correctly with long
types.
Mark Wielaard [Wed, 8 Dec 2021 17:02:27 +0000 (18:02 +0100)]
libdwfl: Add overflow check while iterating in dwfl_segment_report_module
While iterating the notes we could overflow the len variable if the
note name or description was too big. Fix this by adding an (unsigned)
overflow check.
Mark Wielaard [Wed, 15 Dec 2021 23:29:22 +0000 (00:29 +0100)]
libdwfl: Make sure phent is sane and there is at least one phdr
dwfl_link_map_report can only handle program headers that are the
correct (32 or 64 bit) size. The buffer read in needs to contain room
for at least one Phdr.
Mark Wielaard [Tue, 14 Dec 2021 15:12:31 +0000 (16:12 +0100)]
libelf: Use offsetof to get field of unaligned
gcc undefined sanitizer flags:
elf_begin.c:230:18: runtime error: member access within misaligned
address 0xf796400a for type 'struct Elf64_Shdr', which requires 4 byte
alignment struct.
We aren't actually accessing the field member of the struct, but are
taking the address of it. Which the compiler can take as a hint that
the address is correctly aligned. But we can do the same by adding
the field offsetof to the base address. Which doesn't trigger a
runtime error.
debuginfod/debuginfod-client.c: use long for cache time configurations
time_t is platform dependent and some of architectures e.g.
x32, riscv32, arc use 64bit time_t even while they are 32bit
architectures, therefore directly using integer printf formats will not
work portably.
Use a plain long everywhere as the intervals are small enough
that it will not be problematic.
Signed-off-by: Alexander Kanavin <alex@linutronix.de>
Mark Wielaard [Sun, 12 Dec 2021 22:26:18 +0000 (23:26 +0100)]
libdwfl: Don't allocate more than SIZE_MAX in dwfl_segment_report_module.
The code in dwfl_segment_report_module tries to allocate and fill in
memory as described in a core file. Normally all memory in filled in
through the (phdrs) memory_callback or the read_eagerly callback. If
the last callback doesn't work we try to calloc file_trimmed_end bytes
and then try to fill in the parts of memory we can from the core file
at the correct offsets.
file_trimmed_end is a GElf_Off which is an unsigned 64bit type. On
32bit systems this means when cast to a size_t to do an allocation
might allocate truncated (much smaller) value. So make sure to not
allocate more than SIZE_MAX bytes.
It would be nice to have a better way to limit the amount of memory
allocated here. A core file might describe really big memory areas for
which it doesn't provide any data. In that case we really shouldn't
calloc mega- or giga-bytes of zeroed out memory.
Reported-by: Evgeny Vereshchagin <evvers@ya.ru> Signed-off-by: Mark Wielaard <mark@klomp.org>
Add an option -C, which activates libmicrohttpd's thread-pool mode for
handling incoming http connections. Add libmicrohttpd error-logging
callback function so as to receive indication of its internal errors,
and relay counts to our metrics. Some of these internal errors tipped
us off to a microhttpd bug that thread pooling works around. Document
in debuginfod.8 page. Hand-tested against "ulimit -u NNN" shells, and
with a less strenuous new test case.
Mark Wielaard [Thu, 9 Dec 2021 20:24:18 +0000 (21:24 +0100)]
libdwfl: Don't try to convert too many dyns in dwfl_link_map_report
When trying to read (corrupt) dynamic entries from a core file we only
want to read and convert the entries we could read. Also make sure we
don't try to allocate too bug a buffer.
Mark Wielaard [Wed, 8 Dec 2021 22:44:34 +0000 (23:44 +0100)]
libdwfl: Don't install an Elf handle in a Dwfl_Module twice
dwfl_segment_report_module can be called with the same module
name, start and end address twice (probably because of a corrupt
core file). In that case don't override the main.elf handle if
it already exists.
Mark Wielaard [Wed, 8 Dec 2021 21:20:17 +0000 (22:20 +0100)]
libdwfl: Don't trust e_shentsize in dwfl_segment_report_module
When calulating the possible section header table end us the actual size
of the section headers (sizeof (Elf32_Shdr) or sizeof (Elf64_Shdr)),
not the ELF header e_shentsize value, which can be corrupted. This
prevents a posssible overflow, but we check the shdrs_end is sane
later anyway.
Mark Wielaard [Wed, 8 Dec 2021 12:39:47 +0000 (13:39 +0100)]
libdwfl: Don't try to convert too many bytes in dwfl_link_map_report
When trying to read (corrupt) phdrs from a core file we only want
to read and convert the bytes we could read. Also make sure we don't
try to allocate too big buffers.
Mark Wielaard [Sat, 4 Dec 2021 01:57:24 +0000 (02:57 +0100)]
debuginfod: Fix debuginfod_pool leak
gcc address sanitizer detected a dangling debuginfod_client handler
when debuginfod exits. Make sure to groom the debuginfod client pool
before exit after all threads are done.
Mark Wielaard [Sat, 4 Dec 2021 00:18:42 +0000 (01:18 +0100)]
tests: varlocs workaround format-overflow errors
In function ‘printf’,
inlined from ‘handle_attr’ at varlocs.c:932:3:
error: ‘%s’ directive argument is null [-Werror=format-overflow=]
The warning is technically correct. A %s argument should not be
NULL. Although in practice all implementations will print it as
"(null)". Workaround this by simply changing the dwarf string
functions to return an "<unknown>" string. The test is for the correct
names, either "(null)" or "<unknown>" would make it fail (also remove
a now unnecessary assert, the switch statement will check for unknown
opcodes anyway).
Mark Wielaard [Sat, 4 Dec 2021 00:08:48 +0000 (01:08 +0100)]
readelf: Workaround stringop-truncation error
In function ‘strncpy’,
inlined from ‘print_ehdr’ at readelf.c:1175:4:
error: ‘__builtin_strncpy’ specified bound 512 equals destination size
[-Werror=stringop-truncation]
strncpy doesn't terminate the copied string if there is not enough
room. We compensate later by explicitly adding a zero terminator at
buf[sizeof (buf) - 1]. Normally gcc does see this, but with
-fsanitize=address there is too much (checking) code in between. But
it is actually better to not let strncpy do too much work, so
substract one from the size.
Mark Wielaard [Wed, 1 Dec 2021 11:32:27 +0000 (12:32 +0100)]
debuginfod: Check result of calling MHD_add_response_header.
Although unlikely the MHD_add_response_header can fail for
various reasons. If it fails something odd is going on.
So check we can actually add a response header and log an
error if we cannot.
Mark Wielaard [Sat, 4 Dec 2021 19:21:16 +0000 (20:21 +0100)]
debuginfod: Clear and reset debuginfod_client winning_headers on reuse
gcc address sanitizer detected a leak of the debuginfod_client
winning_headers when the handle was reused. Make sure to free and
reset the winning_headers field before reuse.
Mark Wielaard [Wed, 1 Dec 2021 12:12:49 +0000 (13:12 +0100)]
debuginfod: Fix some memory leaks on debuginfod-client error paths.
In a couple of places we might leak some memory when we encounter
an error. tmp_url might leak if realloc failed. escaped_string might
leak when setting up the data handle fails and we don't use it.
And one of the goto out1 should have been goto out2 to make sure
we release all allocated resources on exit (also updated a wrong
comment about that).
Mark Wielaard [Sat, 4 Dec 2021 12:07:04 +0000 (13:07 +0100)]
debuginfod: sqlite3_sharedprefix_fn should not compare past end of string
gcc address sanitizer detected a read after the end of string in
sqlite3_sharedprefix_fn. Make sure to stop comparing the strings when
seeing the zero terminator.
Mark Wielaard [Wed, 1 Dec 2021 12:42:50 +0000 (13:42 +0100)]
debuginfod: Use gmtime_r instead of gmtime to avoid data race
Since we are multi-threaded using gmtime might cause a data race
because gmtime reuses a global struct to write data into. Make
sure that each thread uses their own struct tm and use gmtime_r
instead.
Mark Wielaard [Thu, 18 Nov 2021 20:34:57 +0000 (21:34 +0100)]
tests: Add -rdynamic to dwfl_proc_attach_LDFLAGS
dwfl-proc-attach uses (overrides) dlopen (so it does nothing). This
seems to cause a versioned dlopen symbol to be pulled in when building
with LTO. Resulting in a link failure (when dlopen isn't integrated
into libc):
/usr/bin/ld: dwfl-proc-attach.o (symbol from plugin): undefined
reference to symbol 'dlopen@@GLIBC_2.2.5'
/usr/bin/ld: /usr/lib64/libdl.so.2: error adding symbols: DSO missing
from command line collect2: error: ld returned 1 exit status
Add -rdynamic to the LDFLAGS to add all symbols to the dynamic symbol
table for dwfl-proc-attach.
dwfl: fix potential overflow when reporting on kernel modules
dwfl_linux_kernel_report_modules_ has an outstanding ancient bug when
reading kernel module information from a modules list file. The target
buffer for the module name was sized too small to hold potential values.
Fix that by increasing the value to account for the null termination.
In practice, this unlikely ever happened, but it now got diagnosed by
LLVM as part of a stricter -Wfortify-source implementation [1]:
libdwfl/linux-kernel-modules.c:1019:7: error: 'sscanf' may overflow; destination buffer in argument 3 has size 128, but the corresponding specifier may require size 129 [-Werror,-Wfortify-source]
modname, &modsz, &modaddr) == 3)
Add support for a limited mode for debuginfod that uses a pure
read-only sqlite index. This mode is useful for load spreading based
on naively shared or replicated databases.
libdw, readelf: Read inlining info in NVIDIA extended line map
As of CUDA 11.2, NVIDIA added extensions to the line map section
of CUDA binaries to represent inlined functions. These extensions
include
- two new fields in a line table row to represent inline
information: context, and functionname,
- two new DWARF extended opcodes: DW_LNE_NVIDIA_inlined_call,
DW_LNE_NVIDIA_set_function_name,
- an additional word in the line table header that indicates
the offset in the .debug_str function where the function
names for this line table begin, and
A line table row for an inlined function contains a non-zero "context"
value. The “context” field indicates the index of the line table row
that serves as the call site for an inlined context.
The "functionname" field in a line table row is only meaningful if the
"context" field of the row is non-zero. A meaningful "functionname"
field contains an index into the .debug_str section relative to the
base offset established in the line table header; the position in the
.debug_str section indicates the name of the inlined function.
These extensions resemble the proposed DWARF extensions
(http://dwarfstd.org/ShowIssue.php?issue=140906.1) by Cary Coutant,
but are not identical.
This commit integrates support for handling NVIDIA's extended line
maps into elfutil's libdw library, by adding two functions
dwarf_linecontext and dwarf_linefunctionname, and the readelf
--debug-dump=line command line utility.
Signed-off-by: John M Mellor-Crummey <johnmc@rice.edu> Signed-off-by: Mark Wielaard <mark@klomp.org>
Mark Wielaard [Mon, 8 Nov 2021 08:27:51 +0000 (09:27 +0100)]
libdw: dwarf_elf_begin should use either plain, dwo or lto DWARF sections.
When opening an ELF file that contained a mix of plain, dwo or lto .debug
sections the result could be confusing. Add a check to pick just the plain
.debug sections, or the .dwo sections or the .gnu.debuglto_.debug sections
(in that order of preference). That way there is always a consistent set.
Alexander Miller [Thu, 18 Feb 2021 02:38:56 +0000 (03:38 +0100)]
Improve building with LTO
Use symver attribute for symbol versioning instead of .symver
assembler directive when available. Convert to use double @ syntax
for default version in all cases (required when using the attribute).
Add the attributes externally_visible, no_reorder if available when
using assembler directives to improve the situation for < gcc-10.
This is not 100% reliable, though; -flto-partition=none may still be
needed in some cases.
Bug: https://sourceware.org/bugzilla/show_bug.cgi?id=24498 Signed-off-by: Alexander Miller <alex.miller@gmx.de>
For large databases and many stale files, it was possible to starve
rescan operations by numerous groom "nuke" (database delete ops).
Under the theory that including new data is at least as important as
aging old, we now impose a rough deadline on groom queries.
In the process, we discovered that we were commiting some
undefined-behaviour sqlite ops (deleting rows while iterating), which
may explain some previous heisenbug occurrences. So the groom nuke
operations are split into decision & action phases, with associated
progress-tracking metrics.
Testing the timeout facility requires hand-testing beyond the
testsuite (since it requires LARGE databases to show measurable query
times). So confirmed this part by hand.