summaryrefslogtreecommitdiffstats
path: root/clang/lib/Frontend/CompilerInvocation.cpp
diff options
context:
space:
mode:
authorOliver Stannard <oliver.stannard@arm.com>2016-10-11 10:12:25 +0000
committerOliver Stannard <oliver.stannard@arm.com>2016-10-11 10:12:25 +0000
commitd2083fb356889360237c8899d085987ab7efb36b (patch)
tree5a73c8a20487d985599134de40dddeda4f0a7593 /clang/lib/Frontend/CompilerInvocation.cpp
parent50a74393c2c49ccf726977e84ce52c66d43fc010 (diff)
downloadbcm5719-llvm-d2083fb356889360237c8899d085987ab7efb36b.tar.gz
bcm5719-llvm-d2083fb356889360237c8899d085987ab7efb36b.zip
[Thumb] Save/restore high registers in Thumb1 pro/epilogues
The high registers are not allocatable in Thumb1 functions, but they could still be used by inline assembly, so we need to save and restore the callee-saved high registers (r8-r11) in the prologue and epilogue. This is complicated by the fact that the Thumb1 push and pop instructions cannot access these registers. Therefore, we have to move them down into low registers before pushing, and move them back after popping into low registers. In most functions, we will have low registers that are also being pushed/popped, which we can use as the temporary registers for saving/restoring the high registers. However, this is not guaranteed, so we may need to push some extra low registers to ensure that the high registers can be saved/restored. For correctness, it would be sufficient to use just one low register, but if we have enough low registers available then we only need one push/pop instruction, rather than one per high register. We can also use the argument/return registers when they are not live, and the link register when saving (but not restoring), reducing the number of extra registers we need to push. There are still a few extreme edge cases where we need two push/pop instructions, because not enough low registers can be made live in the prologue or epilogue. In addition to the regression tests included here, I've also tested this using a script to generate functions which clobber different combinations of registers, have different numbers of argument and return registers (including variadic arguments), allocate different fixed sized objects on the stack, and do or don't use variable sized allocas and the __builtin_return_address intrinsic (all of which affect the available registers in the prologue and epilogue). I ran these functions in a test harness which verifies that all of the callee-saved registers are correctly preserved. Differential Revision: https://reviews.llvm.org/D24228 llvm-svn: 283867
Diffstat (limited to 'clang/lib/Frontend/CompilerInvocation.cpp')
0 files changed, 0 insertions, 0 deletions
OpenPOWER on IntegriCloud