__nih_abort_msg symbol cannot be read any more

Bug #1580601 reported by Martin Pitt
6
This bug affects 1 person
Affects Status Importance Assigned to Milestone
gcc-5 (Ubuntu)
New
Undecided
Unassigned
libnih (Ubuntu)
Invalid
Undecided
Unassigned

Bug Description

libnih has a global symbol __nih_abort_msg that contains the message of the last failed nih_assert() (similar to glibc's own __abort_msg and glib's __glib_assert_msg). Apport uses these to produce a more meaningful crash report than just "/bin/foo crashed with SIGABRT", as in these case the thing you actually want to see is the assertion message.

This stopped working in yakkety/amd64. apport's report.test_add_gdb_info_abort_libnih() now fails:

ERROR: test_add_gdb_info_abort_libnih (__main__.T)
add_gdb_info() with libnih assertion
----------------------------------------------------------------------
Traceback (most recent call last):
  File "./test_report.py", line 886, in test_add_gdb_info_abort_libnih
    self.assertIn('Assertion failed in main: 1 < 0', pr['AssertionMessage'])
  File "/usr/lib/python3.5/collections/__init__.py", line 985, in __getitem__
    raise KeyError(key)
KeyError: 'AssertionMessage'

This can be reproduced with the attached script which compiles a trivial nih_assert() C program, runs it, and runs gdb on the produced core dump. Up until xenial it looks like:

$ ./nih-assert.sh
(null):<stdin>:2: Assertion failed in main: 1 < 0
Aborted (core dumped)
[New LWP 9838]
[Thread debugging using libthread_db enabled]
Using host libthread_db library "/lib/x86_64-linux-gnu/libthread_db.so.1".
Core was generated by `./nih-assert'.
Program terminated with signal SIGABRT, Aborted.
#0 0x00007f28c070d418 in __GI_raise (sig=sig@entry=6) at ../sysdeps/unix/sysv/linux/raise.c:54
54 ../sysdeps/unix/sysv/linux/raise.c: No such file or directory.
$1 = 0x25400f0 "<stdin>:2: Assertion failed in main: 1 < 0"

But in yakkety/amd64 it now looks like

$ ./nih-assert.sh
(null):<stdin>:2: Assertion failed in main: 1 < 0
Aborted (core dumped)
[New LWP 10489]
[Thread debugging using libthread_db enabled]
Using host libthread_db library "/lib/x86_64-linux-gnu/libthread_db.so.1".
Core was generated by `./nih-assert'.
Program terminated with signal SIGABRT, Aborted.
#0 0x00007fd303865418 in __GI_raise (sig=sig@entry=6) at ../sysdeps/unix/sysv/linux/raise.c:54
54 ../sysdeps/unix/sysv/linux/raise.c: No such file or directory.
$1 = 0xffffffff869400f0 <error: Cannot access memory at address 0xffffffff869400f0>

This can be reproduced easily in a schroot, you need to install "libnih-dev pkg-config gdb".

ProblemType: Bug
DistroRelease: Ubuntu 16.04
Package: libnih-dev 1.0.3-4.3ubuntu1
ProcVersionSignature: Ubuntu 4.4.0-22.39-generic 4.4.8
Uname: Linux 4.4.0-22-generic x86_64
ApportVersion: 2.20.1-0ubuntu2
Architecture: amd64
CurrentDesktop: i3
Date: Wed May 11 15:13:46 2016
Dependencies:
 gcc-6-base 6.0.1-0ubuntu1
 libc6 2.23-0ubuntu3
 libgcc1 1:6.0.1-0ubuntu1
 libnih1 1.0.3-4.3ubuntu1
EcryptfsInUse: Yes
SourcePackage: libnih
UpgradeStatus: No upgrade log present (probably fresh install)

Revision history for this message
Martin Pitt (pitti) wrote :
Revision history for this message
Martin Pitt (pitti) wrote :

Neither libnih nor glibc changed in yakkety, but what did change is that gcc now applies the PIE option by default. Maybe libnih needs to be adjusted for PIE on amd64, or this needs to be fixed in gcc, thus adding a task for both for now.

tags: added: regression-releasease yakkety
removed: xenial
Revision history for this message
Martin Pitt (pitti) wrote :

A no-change rebuild of libnih with yakkety's gcc does not fix this. Curiously, libnih's debian/rules already has

CFLAGS := -Wall -fstack-protector -fPIE $(shell dpkg-buildflags --get CFLAGS)
LDFLAGS := -Wl,--as-needed -Wl,-z,relro -Wl,-z,now -pie $(shell dpkg-buildflags --get LDFLAGS)

i. e. it should have built with PIE in xenial and before already.

Revision history for this message
Martin Pitt (pitti) wrote :

Downgrading the compiler to xenial in an otherwise identical yakkety environment fixes this again, so it's not a change in some other component. With some manual dpkg -i --force-depends I confirm it's the gcc-5 binary itself, not any lib*, -base, or -dev.

Revision history for this message
Martin Pitt (pitti) wrote :

gcc -E output is identical between xenial and yakkety, as expected (as neither glibc nor libnih changed).

__nih_abort_msg (nor any __nih symbol) does not appear anywhere in "objdump -x", but there are some differences in the objdump output other than addresses, like in the header:

-architecture: i386:x86-64, flags 0x00000112:
-EXEC_P, HAS_SYMS, D_PAGED
+architecture: i386:x86-64, flags 0x00000150:
+HAS_SYMS, DYNAMIC, D_PAGED

Full objdump -x diff attached, but I'm afraid I can't interpret this.

Revision history for this message
Dimitri John Ledkov (xnox) wrote :

If i recall correctly there was something funny with weak symbols / symbol overwriting with __nih_ things and i guess it's the bind now that links the no-op symbol, instead of the real one.

Revision history for this message
Martin Pitt (pitti) wrote :

> i guess it's the bind now that links the no-op symbol, instead of the real one.

But libnih has built with "-z now" for a long time already:

CFLAGS := -Wall -fstack-protector -fPIE $(shell dpkg-buildflags --get CFLAGS)
LDFLAGS := -Wl,--as-needed -Wl,-z,relro -Wl,-z,now -pie $(shell dpkg-buildflags --get LDFLAGS)

I tried to change that to "-z,lazy", but the debs produced by that behave the same. There's also no difference when using -Wl,-z,lazy in the reproducer script's gcc call.

Revision history for this message
Brian Murray (brian-murray) wrote :

There is now a similar issue with getting __glib_assert_msg see bug 1689344.

Revision history for this message
Julian Andres Klode (juliank) wrote :

libnih has been removed from the archive.

Changed in libnih (Ubuntu):
status: New → Invalid
To post a comment you must log in.
This report contains Public information  
Everyone can see this information.

Other bug subscribers

Remote bug watches

Bug watches keep track of this bug in other bug trackers.