The MUSL libc setjmp/longjmp handling differs from the GNU libc
setjmp/longjmp handling. It may not be possible to properly support
sigsetjmp/siglongjmp on MUSL libc.
1. Add a configure option, --enable-cet, to compile libunwind with
"-mshstk -fcf-protection" and link with -Wl,-z,cet-report=error.
CET is always enabled if -fcf-protection is on by default.
2. Add a frames field to struct cursor and update unw_step to cont stack
frames to pop.
3. Update x86_64_sigreturn to pop 4 shadow stack frames.
4. Update x86_64_local_resume to pop the same number of shadow stack
frames as the regular stack frames.
5. Update _Ux86_64_setcontext to pop 2 shadow stack frames.
There are no failures with
$ ./configure --enable-cet
$ make -j12
$ GLIBC_TUNABLES=glibc.cpu.hwcaps=SHSTK make check
on Linux when shadow stack is enabled.
Signed-off-by: H.J. Lu <hjl.tools@gmail.com>
Two tests were failing on QNX because they hard-code the syscall
function name for raising a signal and the hard-coded function name is
wrong for QNX OS.
Ran the relevant test code through clang-format and fixed additional
issues with Aarch64 scalable vector extension (SVE) on QNX.
Include <cet.h> when Intel Control-flow Enforcement Technology (CET)
is enabled. Both GCC and Clang provide <cet.h> which should be included
in assembly codes with .S suffix when -fcf-protection is used. It will
define _CET_ENDBR (endbr64) and the .note.gnu.property note section.
Fixes#644.
Signed-off-by: H.J. Lu <hjl.tools@gmail.com>
This test randomly fails on arm because depending on the place where the
signal is received, the backtrace can involve glibc functions such as
"__read", which do not have .EXIDX instructions.
The function in this source file was never used anywhere
(`unw_tdep_getcontext()` is a macro generating inline asm for arm). It
also fails to build from source for any OS other than Linux and FreeBSD.
Removed the file and checks for the symbol.
When using .EXIDX based unwinding, some functions are flagged with the
.cantunwind directive. That causes unw_step to stop unwinding and to return
-UNW_ESTOPUNWIND.
Do not consider that as an error in the tests.
A (new) unit test was failing at -O0 because it referenced functions
private to the implementation and not exposed through the shared library
ABI. To fix this, the shared library(ies) are now built using a
convenience library, which can also be directly linked to unit tests so
the private functions can be exposed.
This is the first step to greatly expanded unit testing (ie. testing at
unit seams instead of integration testing only at the public API level).
Only one single unit test for the AARCH64 architecture is fully enabled
at this point.
Fixes#841
The unit test Gtest-nomalloc.c had an incorrect prototype for malloc()
which caused newer compilers to fail compiling for newer C editions.
Corrected the prototype and corrected a few other errors. The unit now
compiles using GCC with `CFLAGS=-Wall -Wextra -pedantic -C11` with no
warnings, which is the minimum requirement.
Added the tests/unw_test.h header as a first step to cleaning up some
unit tests further.
`tdep_trace()` did not return the right count value when it did not
complete successfully.
Also rewrote tests/Gtest-trace to (a) add more tests of
`unw_backtrace2()`, (2) give more meaningful verbose output for the poor
humans trying to figure out why it's failing, and (iii) iterate the
signal callback several times to detect cache-related edge cases.
QNX does not put the signal context at a fixed offset in the signal
stack. Need to get the pointer to the context passed by the kernel to
the trampoline instead.
Added unit tests to detect this situation (`[GL]test-sig-context`).
Added `make -C src check-abi` target to leverage libabigail 2.0 tools to
check for ABI changes.
Add ABI baseline files for aarch64, i686, riscv, s390x, and x86_64 Linux
targets and aarch64 and x86_64 QNX SDP 7.1 targets.
Used the check-abi target in the CI-unix github workflow.
Enabling debug mode was convoluted and added cognitive load.
This change simplifies how the configuration option --enable-debug works
by simply adding -DUNW_DEBUG=1 to the preprocesor flags via a specific
confiuration variable, accomplishing the folowing goals.
- don't clobber the CPPFLAGS user variable
- don't mess with -DNDEBUG which has other meanings orthogonal
to libunwind debug mode
- don't hide the definition of the ABI-changing build-time option
behind an ifdef in an internal header file
In addition I added a warning to confogure --help to point out that
enabling the option changes the ABI. Caveat lector.
ISO C does not support omitting parameter names in function definitions
before C2X, so better add them.
fixes:
ppc64-test-plt.c: In function ‘unw_get_accessors_int’:
ppc64-test-plt.c:10:41: error: parameter name omitted
10 | unw_accessors_t *unw_get_accessors_int (unw_addr_space_t) { return NULL; }
| ^~~~~~~~~~~~~~~~
ppc64-test-plt.c: In function ‘_Uppc64_dwarf_step’:
ppc64-test-plt.c:11:17: error: parameter name omitted
11 | int dwarf_step (struct dwarf_cursor*) { return 0; }
| ^~~~~~~~~~~~~~~~~~~~
make[1]: *** [Makefile:1662: ppc64-test-plt.o] Error 1
seen on ppc64 with gcc 10.3.1
Tests will now always be built (unless configured with --disable-tests)
and installed by default in ${prefix}/libexec/libunwind. A new script,
test-runner, is supplied to run all of the tests and produce TAP output.
configure.ac: make tests/check-namespace.sh executable,
add license boilerplate
tests/Makefile.am: remove run-coredump-unwind, add test-runner,
add license boilerplate, remove XFAIL for riscv64
tests/README.md: new file
tests/check-namespace.sh.in: make LIBUNWIND and LIBUNWIND_GENERIC
externally settable, add license boilerplate
tests/run-check-namespace: remove file
test/run-ptrace-mapper: look for test-ptrace relative to script,
add license boilerplate
test/run-ptrace-misc: look for test-ptrace relative to script,
add license boilerplate
test/test-runner.in: new file
.github/workflows/CI-unix.yml: change run-check-namespace to
check-namespace.sh, use libtool to run in-tree binaries instead of
forcing static linking
If the compiler supports -march=armv8-a+sve then those options are used
to build this test, but all that needs is a sufficiently new compiler.
This then results in the __ARM_FEATURE_SVE check always passing, because
SVE is explicitly enabled.
However it's perfectly possible for the compiler to support +sve but the
machine running the code to not, which results with the test crashing
with "Illegal instruction".
Handle this case by checking HWCAP for SVE support, and skipping the
test unless we know it is available. This check is Linux-specific at
present, but the logic is easily extended.
Signed-off-by: Ross Burton <ross.burton@arm.com>
This test source had all kinds of bells and whistles added, requiring all kinds
of (non-portable) dependencies that were never really used. Removed the extra
stuff (logging through syslog, catching segfaults).
Also remove the build dependency on libbacktrace since it actually causes
conflicts with libunwind.
This header file was included in all the other coredump sources and pulled in a
slew of system headers, none of which were used anywhere. Some of those headers
did not even exist on all supported targets.
Fewer build dependencies, fewer build failures, no change in functionality.
Some of the unit test code was bringing an extern function prototype
into scoe in a function body. The idiomatic and expected way to do this
is by using a header file and not adhering to the idiom not only
increases the cognitive load of the reader but tgriggers warning from
static analysis tools.
This change just does it the right way instead. No functional change.
Frame pointer (FP) cannot always be relied upon if DWARF unwinding
fails. Depending on position in the function prologue/epilogue, the
frame record may be pointed to by the FP, SP, or at an offset to SP.
Detect which case it is by inspecting the function disassembly and
matching to known frame record store/load instructions.
Unittest added to verify different frame record store/load methods are
detected when given real function examples from a python2.7 binary.
This issue was found by static analysis. It makes comprehending what the
tests do a little more difficult. There is no functional change.
Verified on Ubuntu 20.04 x86_64.
Previous implementation could only handle cases where IP was at the
first instruction in the PLT. This change implements detecting PLT
entries regardless of where the current IP is within the entry.
Added AArch64-only unittest for is_plt_entry. Mock instructions are set
up for testing, using different offsets and non-PLT replacements.
glibc printf() needs using atomic instruction to acquire the stdout lock.
Under ARMv8.0 ISA, atomic instruction is realized using LL-SC routine, which
will keep retrying if other cpu accesses the target memory during the atomic
instruction.
In mapper testcase, parent process uses ptrace to single step mapper program,
thus if calling printf between SIGUSR1 and SIGUSR2, printf will be single-
step executed, and the atomic instruction will be stuck in deadloop.
Added function to detect when specified IP is within a PLT entry. This
is determined by reading surrounding instructions and matching them to
known PPC64 PLT procedure instructions.
Added PPC64-only unittest for is_plt_entry. Mock instructions are set up
for testing, using different offsets and non-PLT replacements.
This target is no longer supported by common toolchains or operating
systems. If support is required, it can still be found in libunwind
version 1.7 and earlier.
Adds OS-specific functionality to the x86_64 target for QNX OS.
Fixes some miscellaneous portability issues.
Disables the setjmp module build by default for QNX OS since it's not
supported at all.
Eliminated all build warnings coming from `make check` with
CFLAGS="-Wall -Wextra" (and some "-pedantic") for an x86_64 target (GCC
9 Ubuntu 16.04, GCC 10 Ubuntu 20.04). Except for the "Implement
get_list_addr(), please." beg.
This was mostly tagging various parameters as "maybe unused", but there
were a few other changes like assigning to the correct member of
sa_handler and casting things to the right type.
This will hopefully reduce the noise in builds.
Not all targets have a separate pthread library. Make it autodetected in
configure.
Refactored a number of the optionally enabled things in configure.ac for
the following reasons.
1. Their dependencies are only checked when the feature is enabled
2. reduce redundant checks
3. Add defaults to the --help message
4. Group related check and messages together
5. Improve user feedback
6. Make grammatic voice and style more consistent
There should be no functional changes to what gets built and when.