Commit 006eeaa8 by Alexandre Oliva Committed by Alexandre Oliva

Initialize barrier_cache for ARM EH ABI compliance

The ARM Exception Handling ABI requires personality functions in
phase1 to initialize barrier_cache before returning
_URC_HANDLER_FOUND, and we don't.

Although our own ARM personality function does not use barrier_cache
at all, other languages' ARM personality functions, during phase2, are
allowed and expected to test barrier_cache.sp to check whether the
handler frame was reached, which implies that personality functions is
in charge of the frame, and the remaining fields of barrier_cache hold
whatever values it put there in phase1.

Since we did not set barrier_cache.sp, an earlier exception, already
handled by a non-Ada handler and then released, may have its storage
reused for a new exception, that phase1 matches to an Ada frame, but
if that leaves barrier_cache.sp alone, the phase2 personality function
that handled the earlier exception, upon reaching the frame that
handled the earlier exception, may believe the information in
barrier_cache applies to the current exception.  The C++ personality
function, for example, would take the information in the barrier_cache
and end up activating the handler that handled the earlier exception:

  try {
    throw 1;
  } catch (int i) {
    std::cout << "caught " << i << " by c++" << std::endl;
  }
  raise_ada_exception (); // might loop back to the handler above

for  gcc/ada/ChangeLog

	* raise-gcc.c (personality_body) [__ARM_EABI_UNWINDER__]:
	Initialize barrier_cache.sp when ending phase1.
parent 3774c0b9
2020-02-06 Alexandre Oliva <oliva@adacore.com>
* raise-gcc.c (personality_body) [__ARM_EABI_UNWINDER__]:
Initialize barrier_cache.sp when ending phase1.
2020-01-04 Eric Botcazou <ebotcazou@adacore.com> 2020-01-04 Eric Botcazou <ebotcazou@adacore.com>
* gnatvsn.ads: Bump copyright year. * gnatvsn.ads: Bump copyright year.
......
...@@ -1211,6 +1211,16 @@ personality_body (_Unwind_Action uw_phases, ...@@ -1211,6 +1211,16 @@ personality_body (_Unwind_Action uw_phases,
} }
else else
{ {
#ifdef __ARM_EABI_UNWINDER__
/* Though we do not use this field ourselves, initializing
it is required by the ARM EH ABI before a personality
function in phase1 returns _URC_HANDLER_FOUND, so that
any personality function can use it in phase2 to test
whether the handler frame was reached. */
uw_exception->barrier_cache.sp
= _Unwind_GetGR (uw_context, UNWIND_STACK_REG);
#endif
#ifndef CERT #ifndef CERT
/* Trigger the appropriate notification routines before the second /* Trigger the appropriate notification routines before the second
phase starts, when the stack is still intact. First install what phase starts, when the stack is still intact. First install what
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment