This is an archive of the discontinued LLVM Phabricator instance.

Make libc++abi work with gcc's ARM unwind library
ClosedPublic

Authored by mclow.lists on Jan 18 2018, 7:12 AM.

Details

Summary

See https://bugs.llvm.org/show_bug.cgi?id=35945, which reports that libc++ doesn't build for the Raspberry PI.

The problem is that the exception class is defined as a char[8] in that library, rather than uint64_t, as in other libraries.
Same size, same values, different type.

Solution: Pull the code to check the exception class into a routine, and memcpy the field into a uint64_t and call the routine everywhere we were previously checking directly.

Diff Detail

Event Timeline

mclow.lists created this revision.Jan 18 2018, 7:12 AM
bebuch added a subscriber: bebuch.Jan 22 2018, 12:57 AM

Thanks for the amazing patch!

I get another error:

/home/pi/projects/llvm/llvm/projects/libcxxabi/src/cxa_default_handlers.cpp: In function ‘void demangling_terminate_handler()’:
/home/pi/projects/llvm/llvm/projects/libcxxabi/src/cxa_default_handlers.cpp:41:58: error: ISO C++ forbids comparison between pointer and integer [-fpermissive]
                     unwind_exception->exception_class == kOurDependentExceptionClass ?
                                                          ^

The comparison is still between uint8_t[8] and uint64_t. Please add a fix for this, then I will test again. :-)

BTW: Is the memcpy a better choice than a reinterpret_cast?

Find *all* the places that we are using exception_class and wrap them in helper routines.

compnerd accepted this revision.Jan 23 2018, 3:53 PM
This revision is now accepted and ready to land.Jan 23 2018, 3:53 PM
bebuch requested changes to this revision.Jan 24 2018, 4:16 AM

I get some new errors:

/home/pi/projects/llvm/llvm/projects/libcxxabi/src/cxa_personality.cpp: In function ‘void __cxxabiv1::scan_eh_tab(__cxxabiv1::{anonymous}::scan_results&, _Unwind_Action, bool, _Unwind_Control_Block*, _Unwind_Context*)’:
/home/pi/projects/llvm/llvm/projects/libcxxabi/src/cxa_personality.cpp:564:22: error: ‘_URC_FATAL_PHASE1_ERROR’ was not declared in this scope
     results.reason = _URC_FATAL_PHASE1_ERROR;
                      ^
/home/pi/projects/llvm/llvm/projects/libcxxabi/src/cxa_personality.cpp:584:30: error: ‘_URC_FATAL_PHASE2_ERROR’ was not declared in this scope
             results.reason = _URC_FATAL_PHASE2_ERROR;
                              ^
/home/pi/projects/llvm/llvm/projects/libcxxabi/src/cxa_personality.cpp: In function ‘_Unwind_Reason_Code __cxxabiv1::__gxx_personality_v0(_Unwind_State, _Unwind_Control_Block*, _Unwind_Context*)’:
/home/pi/projects/llvm/llvm/projects/libcxxabi/src/cxa_personality.cpp:1074:16: error: ‘_URC_FATAL_PHASE1_ERROR’ was not declared in this scope
         return _URC_FATAL_PHASE1_ERROR;
                ^
/home/pi/projects/llvm/llvm/projects/libcxxabi/src/cxa_personality.cpp:1087:11: error: invalid conversion from ‘int’ to ‘_Unwind_State’ [-fpermissive]
     state &= ~_US_FORCE_UNWIND;
           ^
/home/pi/projects/llvm/llvm/projects/libcxxabi/src/cxa_personality.cpp:1090:12: warning: enumeration value ‘_US_ACTION_MASK’ not handled in switch [-Wswitch]
     switch (state) {
            ^
/home/pi/projects/llvm/llvm/projects/libcxxabi/src/cxa_personality.cpp:1090:12: warning: enumeration value ‘_US_FORCE_UNWIND’ not handled in switch [-Wswitch]
/home/pi/projects/llvm/llvm/projects/libcxxabi/src/cxa_personality.cpp:1090:12: warning: enumeration value ‘_US_END_OF_STACK’ not handled in switch [-Wswitch]
/home/pi/projects/llvm/llvm/projects/libcxxabi/src/cxa_personality.cpp:1167:12: error: ‘_URC_FATAL_PHASE1_ERROR’ was not declared in this scope
     return _URC_FATAL_PHASE1_ERROR;
            ^
/home/pi/projects/llvm/llvm/projects/libcxxabi/src/cxa_personality.cpp:1168:1: error: control reaches end of non-void function [-Werror=return-type]
 }
 ^

_URC_FATAL_PHASE1_ERROR and _URC_FATAL_PHASE2_ERROR should be enum values of _Unwind_Reason_Code, but this is defined in unwind-arm-common.h as:

typedef enum
  {
    _URC_OK = 0,       /* operation completed successfully */
    _URC_FOREIGN_EXCEPTION_CAUGHT = 1,
    _URC_END_OF_STACK = 5,
    _URC_HANDLER_FOUND = 6,
    _URC_INSTALL_CONTEXT = 7,
    _URC_CONTINUE_UNWIND = 8,
    _URC_FAILURE = 9   /* unspecified failure of some kind */
  }
_Unwind_Reason_Code;

In other unwind libraries these values are defined: https://github.com/llvm-mirror/libunwind/blob/master/include/unwind.h
In the arm version it isn't: https://github.com/gcc-mirror/gcc/blob/gcc-4_9-branch/gcc/ginclude/unwind-arm-common.h

This revision now requires changes to proceed.Jan 24 2018, 4:16 AM
avsej added a subscriber: avsej.May 16 2018, 3:05 AM

A modified version of this patch (v8-6.7.17-fix-gcc-unwind-header.patch) has been integrated in Fedora Linux and will be accessible in v8-6.7.17-4.fc28

mgorny added a subscriber: mgorny.Oct 7 2018, 10:07 AM

@mclow.lists , ping. Any chance to get a proper version upstream? I'd rather not pull patches from Fedora when we can have something official.

mclow.lists added a comment.EditedOct 8 2018, 1:31 PM

@mclow.lists , ping. Any chance to get a proper version upstream? I'd rather not pull patches from Fedora when we can have something official.

I gave up on this patch several months ago, because no one would say how much work it was.
I fixed one place, and was told "here are several others".
I fixed those, and was told "I get some new errors:" (which were completely unrelated to the previous problems)

@bebuch, I agree with @mclow.lists here that the new errors are completely unrelated to the problem solved by this patch, and the fix to it belongs in a separate changeset. Can we get the original problem fixed first then?

bebuch accepted this revision.Oct 10 2018, 3:19 AM

Okay, sorry for the blockage!

This revision is now accepted and ready to land.Oct 10 2018, 3:19 AM
mclow.lists closed this revision.Oct 10 2018, 9:20 AM

Committed as revision 344152