This is an archive of the discontinued LLVM Phabricator instance.

[Doc] Guideline on adding exception handling support for a target
ClosedPublic

Authored by chenwj on Jan 17 2018, 6:28 AM.

Details

Summary

This is the first attempt to write down a guideline on adding exception handling support for a target. The content basically bases on the discussion on [1]. If you guys know who is exception handling expert, please add him as the reviewer. Thanks.

[1] http://lists.llvm.org/pipermail/llvm-dev/2018-January/120405.html

Diff Detail

Repository
rL LLVM

Event Timeline

chenwj created this revision.Jan 17 2018, 6:28 AM

Thank you very much for making a start on this!

docs/ExceptionHandling.rst
853 ↗(On Diff #130166)

Most of this is generic code. The important thing for the back end is to make sure that every register has a unique DWARF number.

In your TargetFrameLowering's emitPrologue method, you must add the .cfi_def_cfa_offset directive for the frame and then the .cfi_def_cfa_register or similar to tell the unwinder the base address for all subsequent offsets.

860 ↗(On Diff #130166)

Perhaps note that the first of these contains a pointer and the second an integer. On most platforms, they will be GPRs, but on any architecture with distinct address and integer registers the first will likely be an address.

865 ↗(On Diff #130166)

Perhaps document what this does? I believe that it's an undocumented GCC extension that is used only in the GNU unwinder (LLVM's libUnwind doesn't use it). According to comments in the MIPS back end, it is of the form __builtin_eh_return (offset, handler) and adjusts the stack by offset and then jumps to the handler.

870 ↗(On Diff #130166)

It would be good to enumerate the things that are needed to get this working. This diff adds 64-bit MIPS support (soft-float only):

https://github.com/CTSRD-CHERI/libunwind/commit/7b3c8ca32786b7b63975f3c5f93f41d69578416b

It contains a bug where a couple of registers that should have been saved weren't, but it provides an example of all of the things that you need to add to support a new architecture.

The only difficult thing is correctly setting _LIBUNWIND_CONTEXT_SIZE and _LIBUNWIND_CURSOR_SIZE - you get a compile error that tells you if you got them wrong, but it doesn't tell you what the correct size should be. I did this by temporarily replacing the static_assert with a template that invoked static_assert and gave me the arguments in the failure backtrace.

chenwj updated this revision to Diff 130414.EditedJan 18 2018, 7:54 AM

@theraven For `libunwind` part, I am not sure if it's okay to include your link there. I just skim through the patch and list the key points I thought.

theraven accepted this revision.Jan 22 2018, 5:28 AM

I'm inclined to recommend that you commit this. It's not perfect, but it's a *lot* better than what was there before, and hopefully having something there will encourage other people to improve it.

This revision is now accepted and ready to land.Jan 22 2018, 5:28 AM

@theraven Could you commit this for me? I will be happy to update the context if I have more experience on this.

I appear to have lost my credentials for LLVM svn. I've asked Chris to reset them, but someone else should feel free to commit this before then if they want to.

This revision was automatically updated to reflect the committed changes.