[llvm-dev] Catching exceptions while unwinding through -fno-exceptions code

Everett Maus via llvm-dev llvm-dev at lists.llvm.org
Mon Dec 7 12:46:54 PST 2020


Hey all:

I wanted to bring up something that was discussed a few years ago around
the behavior of exceptions when interacting with code compiled with
-fno-exceptions. (In
https://lists.llvm.org/pipermail/llvm-dev/2017-February/109992.html and
https://lists.llvm.org/pipermail/llvm-dev/2017-February/109995.html)

It's possible to compile (and link/etc.) code with -fexceptions for some
compilation units and -fno-exceptions for others.  Unlike the behavior of
noexcept (which requires termination), this doesn't have a specified
behavior in the C++ standard as far as I can tell.  However, it can lead to
memory leaks & other issues (e.x. with TSAN, it messes up the tracking of
the current stack frame).

I'd be interested in looking into potentially doing the work to add an
option to clang/etc. to terminate when an exception traverses code compiled
with -fno-exceptions, instead of simply allowing the unwinder to walk
through the stack frame & leak memory/etc. (possibly behind a flag?).  This
particular issue bit a team I work closely with, and I'd imagine it could
be causing subtle issues for other clang users.

I'm mostly concerned with solving this on Linux/x86_64, although if there's
a way to solve it more generally I'm open to looking into doing that
instead.

I /think/ the right place to change this (from the discussions I linked)
would be in the LLVM -> assembly layer, adding an appropriate
.gcc_except_table for functions that are determined to be unable to throw
exceptions (either due to noexcept or due to -fno-exceptions). Then the
unwinder would find .eh_frame but no entry in the .gcc_except_table and
should terminate (via  __gxx_personality_v0).

Am I understanding that correctly?  What's the best way to propose this
sort of change to clang? (document/just try to look at putting together a
PR/other?)

Alternatively--one other thing that occurred to me is that it could be
reasonably cheap to simply add try/catch blocks that report an UBSAN error
in all methods that shouldn't be able to throw an exception.  This
obviously doesn't fix the code-generation problem and would lead to larger
binary sizes, but that seems less bad for an UBSAN build in particular.
That would likely meet my needs around wanting a way to automatically
detect this behavior/problem, but might not address the more generic issue.

Thanks,
-- 
--EJM
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/llvm-dev/attachments/20201207/f3e905f4/attachment.html>


More information about the llvm-dev mailing list