//===----------------------------------------------------------------------===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//
//  This file implements the personality and helper functions for the state
//  table based EH used by IBM legacy compilers xlC and xlclang++ on AIX.
//
//===----------------------------------------------------------------------===//

#include <new>
#include <stdio.h>
#include <sys/debug.h>

/*
  The legacy IBM xlC and xlclang++ compilers use the state table for EH
  instead of the range table. Destructors, or addresses of the possible catch
  sites or cleanup code are specified in the state table which is a finite
  state machine (FSM). Each function that has a state table also has an
  autolocal state variable. The state variable represents the current state
  of the function for EH and is found through the traceback table of the
  function during unwinding, which is located at the end of each function.
  The FSM is an array of state entries. Each state entry has the following
  fields:

  * offset/address/pointer - the offset used to locate the object, or the
    address of a global object, or the address of the next state if it is an
    old conditional state change entry;
  * dtor/landing pad - address of the destructor function to invoke,
    or address of the catch block or cleanup code in the user code to branch to;
  * element count/action flag - the number of elements or the flag for actions;
  * element size - if the object is an array this is the size of one element
    of the array;
  * flags - flags used to control how fields in the entry are interpreted;
  * next state - the state to execute next after the action for this state is
    performed. The value of zero indicates the end of the state for this
    function.

  The following is the description of 'element count/action flag' field.
+-----------------------------------------------------------------------------+
| value |      description       |                  action                    |
+-------+------------------------+--------------------------------------------+
| > 1   |   object is an array   | calls __cxa_vec_cleanup to run dtor for    |
|       |                        | each member of the array                   |
+-------+------------------------+--------------------------------------------+
| 1, 0  |   object is a scalar   | calls dtor for the object                  |
+-------+------------------------+--------------------------------------------+
|  -1   |      begin catch       | branches to the handler which performes    |
|       |                        | catch-match. If there is no catch that     |
|       |                        | matches the exception it will be rethrown  |
+-------+------------------------+--------------------------------------------+
|  -2   |       end catch        | ends current catch block and continues     |
|       |                        | attempting to catch the exception          |
+-------+------------------------+--------------------------------------------+
|  -3   |   delete the object    | calls the delete function of the object    |
+-------+------------------------+--------------------------------------------+
|  -4   |      cleanup label     | branches to the user code for cleaning up  |
+-------+------------------------+--------------------------------------------+
*/

namespace __cxxabiv1 {

extern "C" {

// Macros for debugging the state table parsing.
#ifdef NDEBUG
#  define _LIBCXXABI_TRACE_STATETAB(msg, ...)
#  define _LIBCXXABI_TRACE_STATETAB0(msg)
#  define _LIBCXXABI_TRACE_STATETAB1(msg)
#  define _LIBCXXABI_TRACING_STATETAB 0
#else
static bool state_tab_dbg() {
  static bool checked = false;
  static bool log = false;
  if (!checked) {
    log = (getenv("LIBCXXABI_PRINT_STATTAB") != NULL);
    checked = true;
  }
  return log;
}

#  define _LIBCXXABI_TRACE_STATETAB(msg, ...)                                  \
     do {                                                                      \
       if (state_tab_dbg())                                                    \
         fprintf(stderr, "libcxxabi: " msg, __VA_ARGS__);                      \
     } while (0)
#  define _LIBCXXABI_TRACE_STATETAB0(msg)                                      \
     do {                                                                      \
       if (state_tab_dbg())                                                    \
         fprintf(stderr, "libcxxabi: " msg);                                   \
     } while (0)
#  define _LIBCXXABI_TRACE_STATETAB1(msg)                                      \
     do {                                                                      \
       if (state_tab_dbg())                                                    \
         fprintf(stderr, msg);                                                 \
     } while (0)

#  define _LIBCXXABI_TRACING_STATETAB state_tab_dbg()
#endif // NDEBUG

namespace __state_table_eh {

using destruct_f = void (*)(void*);

// Definition of flags for the state table entry field 'action flag'.
enum FSMEntryCount : intptr_t { beginCatch = -1, endCatch = -2, deleteObject = -3, cleanupLabel = -4, terminate = -5 };

// Definition of flags for the state table entry field 'flags'.
enum FSMEntryFlag : int16_t {
  indirect = 0x100,                  // Object was thrown from a function where
                                     // the return value optimization was used.
  oldConditionalStateChange = 0x400, // State table entry is an indirect state
                                     // change, dereference the address in
                                     // offset as int for the target state.
                                     // This is deprecated. This indicates
                                     // the address is direct. (static local).
  conditionalStateChange = 0x800,    // State table entry is an indirect state
                                     // change, dereference the address in
                                     // offset as int for the target state.
                                     // The temporary is an automatic. State
                                     // change is used in cases such as
                                     // (b?(T1(),foo()):(T2(),foo())),throw 42;
                                     // which causes a conditional state change
                                     // so that we know if T1 or T2 need to be
                                     // destroyed.
  thisFlag = 0x01,                   // The address of the object for the
                                     // cleanup action is based on the
                                     // StateVariable::thisValue.
  vBaseFlag = 0x02,                  // The object is of a virtual base class.
  globalObj = 0x04                   // FSMEntry::address is the address of
                                     // a global object.
};

namespace {
// The finite state machine to be walked.
struct FSMEntry {
  union {
    // Offset of the object within its stack frame or containing object.
    intptr_t offset;
    // Address of a global object.
    intptr_t address;
    // Address of the next state if it is an old conditional state change entry.
    intptr_t nextStatePtr;
  };
  union {
    // Address of the destructor function.
    void (*destructor)(void*, size_t);
    // The address of the catch block or cleanup code.
    void* landingPad;
  };
  union {
    // The flag for actions (when the value is negative).
    FSMEntryCount actionFlag;
    // The element count (when the value is positive or zero).
    size_t elementCount;
  };
  size_t elemSize;
  FSMEntryFlag flags;
  uint16_t nextState;
};

struct FSM {
  uint32_t magic; // Magic number of the state table.
  int32_t numberOfStates;
  FSMEntry table[1]; // Actually table[numberOfStates].
};

// The state variable on the stack.
struct StateVariable {
  int32_t state;
  struct FSM* table;
  intptr_t thisValue;
  int32_t ignoreVBasePtrs;
};
} // namespace

// State table magic number
enum FSMMagic : uint32_t {
  number = 0xbeefdead,  // State table generated by xlC compiler.
  number2 = 0xbeeedead, // State table generated by early version xlC compiler.
  number3 = 0x1cedbeef  // State table generated by xlclang++ compiler.
};

constexpr uint32_t REG_EXCP_OBJ = 14; // Register to pass the address of the exception
                                      // object from the personality to xlclang++
                                      // compiled code.

constexpr size_t dtorArgument = 0x02; // Flag to destructor indicating to free
                                      // virtual bases, don't delete object.

static void invoke_destructor(FSMEntry* fsmEntry, void* addr) {
  _LIBCXXABI_TRACE_STATETAB("Destruct object=%p, fsmEntry=%p\n", addr, reinterpret_cast<void*>(fsmEntry));
  try {
    if (fsmEntry->elementCount == 1) {
      _LIBCXXABI_TRACE_STATETAB0("calling scalar destructor\n");
      (*fsmEntry->destructor)(addr, dtorArgument);
      _LIBCXXABI_TRACE_STATETAB0("returned from scalar destructor\n");
    } else {
      _LIBCXXABI_TRACE_STATETAB0("calling vector destructor\n");
      __cxa_vec_cleanup(addr, reinterpret_cast<size_t>(fsmEntry->elementCount), fsmEntry->elemSize,
                        reinterpret_cast<destruct_f>(fsmEntry->destructor));
      _LIBCXXABI_TRACE_STATETAB0("returned from vector destructor\n");
    }
  } catch (...) {
    _LIBCXXABI_TRACE_STATETAB0("Uncaught exception in destructor, terminating\n");
    std::terminate();
  }
}

static void invoke_delete(FSMEntry* fsmEntry, void* addr) {
  char* objectAddress = *reinterpret_cast<char**>(addr);

  _LIBCXXABI_TRACE_STATETAB("Delete object=%p, fsmEntry=%p\n", reinterpret_cast<void*>(objectAddress),
                            reinterpret_cast<void*>(fsmEntry));
  try {
    _LIBCXXABI_TRACE_STATETAB0("..calling delete()\n");
    // 'destructor' holds a function pointer to delete().
    (*fsmEntry->destructor)(objectAddress, fsmEntry->elemSize);
    _LIBCXXABI_TRACE_STATETAB0("..returned from delete()\n");
  } catch (...) {
    _LIBCXXABI_TRACE_STATETAB0("Uncaught exception in delete(), terminating\n");
    std::terminate();
  }
}

// Get the frame address of the current function from its traceback table
// which is at the end of each function.
static uintptr_t get_frame_addr(_Unwind_Context* context) {
  int framePointerReg = 1; // default frame pointer == SP.
  uint32_t* p = reinterpret_cast<uint32_t*>(_Unwind_GetIP(context));

  // Keep looking forward until a word of 0 is found. The traceback
  // table starts at the following word.
  while (*p)
    ++p;
  tbtable* TBTable = reinterpret_cast<tbtable*>(p + 1);

  p = reinterpret_cast<uint32_t*>(&TBTable->tb_ext);

  // Skip field parminfo if it exists.
  if (TBTable->tb.fixedparms || TBTable->tb.floatparms)
    ++p;

  // Skip field tb_offset if it exists.
  if (TBTable->tb.has_tboff)
    ++p;

  // Skip field hand_mask if it exists.
  if (TBTable->tb.int_hndl)
    ++p;

  // Skip fields ctl_info and ctl_info_disp if they exist.
  if (TBTable->tb.has_ctl)
    p += 1 + *p;

  // Skip fields name_len and name if exist.
  if (TBTable->tb.name_present) {
    const uint16_t name_len = *reinterpret_cast<uint16_t*>(p);
    p = reinterpret_cast<uint32_t*>(reinterpret_cast<char*>(p) + name_len + sizeof(uint16_t));
  }

  if (TBTable->tb.uses_alloca)
    framePointerReg = *reinterpret_cast<char*>(p);

  return _Unwind_GetGR(context, framePointerReg);
}

// Calculate the object address from the FSM entry.
static void* compute_addr_from_table(FSMEntry* fsmEntry, StateVariable* const state, _Unwind_Context* context) {
  void* addr;
  if (fsmEntry->flags & FSMEntryFlag::globalObj) {
    addr = reinterpret_cast<void*>(fsmEntry->address);
    _LIBCXXABI_TRACE_STATETAB("Address calculation (global obj) addr=fsmEntry->address=%p\n", addr);
  } else if (fsmEntry->flags & FSMEntryFlag::thisFlag) {
    addr = reinterpret_cast<void*>(state->thisValue + fsmEntry->offset);
    _LIBCXXABI_TRACE_STATETAB("Address calculation (this obj) fsmEntry->offset=%ld : "
                              "state->thisValue=%ld addr=(fsmEntry->offset+state->thisValue)=%p\n",
                              fsmEntry->offset, state->thisValue, addr);
  } else if (fsmEntry->flags & FSMEntryFlag::indirect) {
    addr = reinterpret_cast<void*>(
        *reinterpret_cast<char**>(get_frame_addr(context) + static_cast<uintptr_t>(fsmEntry->offset)));
    _LIBCXXABI_TRACE_STATETAB("Address calculation (indirect obj) addr=%p, fsmEntry->offset=%ld \n",
                              addr, fsmEntry->offset);
  } else {
    addr = reinterpret_cast<void*>(get_frame_addr(context) + static_cast<uintptr_t>(fsmEntry->offset));
    _LIBCXXABI_TRACE_STATETAB("Address calculation. (local obj) addr=fsmEntry->offset=%p\n",
                              addr);
  }
  return addr;
}

static void scan_state_tab(scan_results& results, _Unwind_Action actions, bool native_exception,
                           _Unwind_Exception* unwind_exception, _Unwind_Context* context) {
  // Initialize results to found nothing but an error.
  results.ttypeIndex = 0;
  results.actionRecord = 0;
  results.languageSpecificData = 0;
  results.landingPad = 0;
  results.adjustedPtr = 0;
  results.reason = _URC_FATAL_PHASE1_ERROR;

  // Check for consistent actions.
  if (actions & _UA_SEARCH_PHASE) {
    // Do Phase 1
    if (actions & (_UA_CLEANUP_PHASE | _UA_HANDLER_FRAME | _UA_FORCE_UNWIND)) {
      // None of these flags should be set during Phase 1.
      //   Client error
      results.reason = _URC_FATAL_PHASE1_ERROR;
      return;
    }
  } else if (actions & _UA_CLEANUP_PHASE) {
    if ((actions & _UA_HANDLER_FRAME) && (actions & _UA_FORCE_UNWIND)) {
      // _UA_HANDLER_FRAME should only be set if phase 1 found a handler.
      // If _UA_FORCE_UNWIND is set, phase 1 shouldn't have happened.
      //    Client error
      results.reason = _URC_FATAL_PHASE2_ERROR;
      return;
    }
  } else {
    // Neither _UA_SEARCH_PHASE nor _UA_CLEANUP_PHASE is set.
    //   Client error
    results.reason = _URC_FATAL_PHASE1_ERROR;
    return;
  }

  if (_LIBCXXABI_TRACING_STATETAB) {
    _LIBCXXABI_TRACE_STATETAB1("\n");
    _LIBCXXABI_TRACE_STATETAB("%s: actions=%d (", __func__, actions);

    if (_UA_SEARCH_PHASE & actions)
      _LIBCXXABI_TRACE_STATETAB1("_UA_SEARCH_PHASE ");
    if (_UA_CLEANUP_PHASE & actions)
      _LIBCXXABI_TRACE_STATETAB1("_UA_CLEANUP_PHASE ");
    if (_UA_HANDLER_FRAME & actions)
      _LIBCXXABI_TRACE_STATETAB1("_UA_HANDLER_FRAME ");
    if (_UA_FORCE_UNWIND & actions)
      _LIBCXXABI_TRACE_STATETAB1("_UA_FORCE_UNWIND ");
    _LIBCXXABI_TRACE_STATETAB1(")\n");
    _LIBCXXABI_TRACE_STATETAB("       unwind_exception=%p context=%p\n", reinterpret_cast<void*>(unwind_exception),
                              reinterpret_cast<void*>(context));
  }

  // Start scan by getting state table address.
  StateVariable* const state = reinterpret_cast<StateVariable* const>(_Unwind_GetLanguageSpecificData(context));
  if (state->state <= 0) {
    // The state is not correct - give up on this routine.
    _LIBCXXABI_TRACE_STATETAB("state=%d and is <= 0), continue unwinding\n", state->state);
    results.reason = _URC_CONTINUE_UNWIND;
    return;
  }
  // Parse the state table.
  FSM* const fsm = state->table;
  FSMEntry* currFSMEntry;

  if (fsm->magic != FSMMagic::number && fsm->magic != FSMMagic::number2 && fsm->magic != FSMMagic::number3) {
    // Something is wrong with the state table we found.
    if (_UA_SEARCH_PHASE & actions) {
      _LIBCXXABI_TRACE_STATETAB0("Invalid FSM table, return _URC_FATAL_PHASE1_ERROR\n");
      results.reason = _URC_FATAL_PHASE1_ERROR;
    } else if (_UA_CLEANUP_PHASE & actions) {
      _LIBCXXABI_TRACE_STATETAB0("Invalid FSM table, return _URC_FATAL_PHASE2_ERROR\n");
      results.reason = _URC_FATAL_PHASE2_ERROR;
    } else {
      // We should never get here.
      _LIBCXXABI_TRACE_STATETAB0("Invalid FSM table + RT Internal error, return _URC_FATAL_PHASE2_ERROR\n");
      results.reason = _URC_FATAL_PHASE2_ERROR;
    }
    return;
  }

  if (_LIBCXXABI_TRACING_STATETAB) {
    // Print the state table for debugging purposes.
    _LIBCXXABI_TRACE_STATETAB("state->state=%d, state->ignoreVBasePtrs=%d\n", state->state, state->ignoreVBasePtrs);
    _LIBCXXABI_TRACE_STATETAB("fsm->magic=%#x, fsm->numberOfStates=%d\n", fsm->magic, fsm->numberOfStates);
    // Print out the FSM table.
    _LIBCXXABI_TRACE_STATETAB0("FSM table:\n");
    _LIBCXXABI_TRACE_STATETAB("%12s %10s %8s  %10s %7s %7s %7s %7s\n", "Entry Addr", "state", "Offset", "DTR/lpad",
                              "count", "el_size", "flags", "next");
    for (int i = 0; i < fsm->numberOfStates; i++) {
      currFSMEntry = &fsm->table[i];
      _LIBCXXABI_TRACE_STATETAB("%12p (%8d) %8ld  %10p %7ld "
                                "%7ld %#7x %7d\n",
                                reinterpret_cast<void*>(&currFSMEntry), i + 1, currFSMEntry->offset,
                                reinterpret_cast<void*>(currFSMEntry->destructor),
                                currFSMEntry->elementCount, currFSMEntry->elemSize, currFSMEntry->flags,
                                currFSMEntry->nextState);
    }
  }

  if (_UA_SEARCH_PHASE & actions) {
    // Start walking the state table. Use a local copy of state->state so when
    // we return from search phase we don't change the state number.
    int currState = state->state;

    while (currState > 0) {
      currFSMEntry = &fsm->table[currState - 1];
      _LIBCXXABI_TRACE_STATETAB("Processing state=%d, flags=0x%hx\n", currState, currFSMEntry->flags);

      if (currFSMEntry->actionFlag == FSMEntryCount::beginCatch) {
        // Found a catch handler.
        if (fsm->magic == FSMMagic::number) {
          _LIBCXXABI_TRACE_STATETAB0("Found a xlC catch handler, return _URC_FATAL_PHASE1_ERROR\n");
          // xlC catch handlers cannot be entered because they use a
          // proprietary EH runtime that is not interoperable.
          results.reason = _URC_FATAL_PHASE1_ERROR;
          return;
        }
        // xlclang++ compiled frames use CXA-abi EH calls and any catch
        // block will include a catch(...) block so it is safe to assume that
        // the handler is found without checking the catch match. The
        // catch(...) block will rethrow the exception if there isn't a
        // match.
        _LIBCXXABI_TRACE_STATETAB0("Found a catch handler, return _URC_HANDLER_FOUND\n");
        results.reason = _URC_HANDLER_FOUND;
        return;
      }
      if (currFSMEntry->actionFlag == FSMEntryCount::terminate) {
        _LIBCXXABI_TRACE_STATETAB0("Found the terminate state, return _URC_HANDLER_FOUND\n");
        results.reason = _URC_HANDLER_FOUND;
        return;
      }
      if (currFSMEntry->flags & FSMEntryFlag::oldConditionalStateChange) {
        // Deprecated conditional expression.
        currState = *reinterpret_cast<int*>(currFSMEntry->nextStatePtr);
        _LIBCXXABI_TRACE_STATETAB("Flag: FSMEntryFlag::oldConditionalStateChange, dereference "
                                  "currFSMEntry->nextStatePtr(%ld), set state=%d\n",
                                  currFSMEntry->nextStatePtr, currState);
        continue; // We are done this iteration of the loop, since
                  // we changed a state.
      }
      if (currFSMEntry->flags & FSMEntryFlag::conditionalStateChange) {
        void* addr = compute_addr_from_table(currFSMEntry, state, context);
        currState = *reinterpret_cast<int*>(addr);
        _LIBCXXABI_TRACE_STATETAB("Flag: FSMEntryFlag::conditionalStateChange, dereference "
                                  "addr(%p), set state=%d\n", addr, currState);
        continue; // We are done this iteration of the loop, since we
                  // changed the state.
      }
      // Go to the next state.
      currState = currFSMEntry->nextState;
    }
    _LIBCXXABI_TRACE_STATETAB0("No catch handler found, return _URC_CONTINUE_UNWIND\n");
    results.reason = _URC_CONTINUE_UNWIND;
    return;
  }
  if (_UA_CLEANUP_PHASE & actions) {
    // Start walking the state table.
    while (state->state > 0) {
      currFSMEntry = &fsm->table[state->state - 1];

      if (currFSMEntry->actionFlag == FSMEntryCount::terminate) {
        _LIBCXXABI_TRACE_STATETAB0("Reached terminate state. Call terminate.\n");
        std::terminate();
      }
      // Perform action according to the currFSMEntry->actionFlag,
      // except when flag is FSMEntryFlag::conditionalStateChange or
      // FSMEntryFlag::oldConditionalStateChange.
      _LIBCXXABI_TRACE_STATETAB("Processing state=%d, flags=0x%hx\n", state->state, currFSMEntry->flags);
      if (currFSMEntry->flags & FSMEntryFlag::oldConditionalStateChange) {
        state->state = *reinterpret_cast<int*>(currFSMEntry->nextStatePtr);
        _LIBCXXABI_TRACE_STATETAB("Flag: FSMEntryFlag::oldConditionalStateChange, dereference "
                                  "currFSMEntry->nextStatePtr(%ld), set state=%d\n",
                                  currFSMEntry->nextStatePtr, state->state);
        continue; // We are done with this iteration of the loop, since we changed a state.
      }
      if (currFSMEntry->flags & FSMEntryFlag::conditionalStateChange) {
        // A conditional state table entry holds the address of a local
        // that holds the next state.
        void* addr = compute_addr_from_table(currFSMEntry, state, context);
        state->state = *reinterpret_cast<int*>(addr);
        _LIBCXXABI_TRACE_STATETAB("Flag: FSMEntryFlag::conditionalStateChange, dereference "
                                  "addr(%p), set state=%d\n", addr, state->state);
        continue; // We are done with this iteration of the loop, since we changed a state.
      }
      if (currFSMEntry->actionFlag == FSMEntryCount::beginCatch || currFSMEntry->actionFlag == FSMEntryCount::endCatch ||
          currFSMEntry->actionFlag == FSMEntryCount::cleanupLabel) {

        _LIBCXXABI_TRACE_STATETAB(
            "FSMEntryCount::%s: handler %p/%p, return _URC_HANDLER_FOUND\n",
            (currFSMEntry->actionFlag == FSMEntryCount::beginCatch
                 ? "beginCatch"
                 : (currFSMEntry->actionFlag == FSMEntryCount::endCatch ? "endCatch" : "cleanupLabel")),
            currFSMEntry->landingPad, *reinterpret_cast<void**>(currFSMEntry->landingPad));

        state->state = currFSMEntry->nextState;
        results.landingPad = reinterpret_cast<uintptr_t>(*reinterpret_cast<void**>(currFSMEntry->landingPad));
        results.reason = _URC_HANDLER_FOUND;
        return;
      }
      if (currFSMEntry->elementCount > 0) {
        if (currFSMEntry->flags & FSMEntryFlag::vBaseFlag && state->ignoreVBasePtrs) {
          _LIBCXXABI_TRACE_STATETAB0("Ignoring virtual base dtor.\n");
        } else {
          // We need to invoke the virtual base destructor. This must be
          // a frame from the legacy xlC compiler as the xlclang++ compiler
          // generates inline cleanup code rather than specifying
          // the destructor via the state table.
          void* addr = compute_addr_from_table(currFSMEntry, state, context);

          // An extra indirect to get to the object according to the object
          // model used by the xlC compiler.
          addr = reinterpret_cast<void*>(*reinterpret_cast<char**>(addr));
          _LIBCXXABI_TRACE_STATETAB("Invoke dtor for object=%p\n", addr);
          invoke_destructor(currFSMEntry, addr);
        }
      } else if (currFSMEntry->actionFlag == FSMEntryCount::deleteObject) {
        void* addr = compute_addr_from_table(currFSMEntry, state, context);
        if (currFSMEntry->flags & FSMEntryFlag::vBaseFlag) {
          // We need to invoke the virtual base delete function. This must be
          // a frame from the legacy xlC compiler as the xlclang++ compiler
          // generates inline cleanup code rather than specifying
          // the delete function via the state table.

          // An extra indirect to get to the object according to the object
          // model used by the xlC compiler.
          addr = reinterpret_cast<void*>(*reinterpret_cast<char**>(addr));
        }
        _LIBCXXABI_TRACE_STATETAB("Delete object at %p\n", addr);
        invoke_delete(currFSMEntry, addr);
      } else {
        _LIBCXXABI_TRACE_STATETAB("Unknown entry in FSM (count=%ld), ignored\n",
                                  currFSMEntry->elementCount);
      } // End of action switching.

      // Go to next state.
      state->state = currFSMEntry->nextState;
    }
    _LIBCXXABI_TRACE_STATETAB0("No catch handler, return _URC_CONTINUE_UNWIND\n");
    results.reason = _URC_CONTINUE_UNWIND;
    return;
  }
  _LIBCXXABI_TRACE_STATETAB0("No state table entry for this exception, call_terminate()\n");
  // It is possible that no state table entry specify how to handle
  // this exception. By spec, terminate it immediately.
  call_terminate(native_exception, unwind_exception);
}

// Personality routine for EH using the state table.
_LIBCXXABI_FUNC_VIS _Unwind_Reason_Code
__xlcxx_personality_v0(int version, _Unwind_Action actions, uint64_t exceptionClass,
                       _Unwind_Exception* unwind_exception, _Unwind_Context* context) {
  if (version != 1 || unwind_exception == 0 || context == 0)
    return _URC_FATAL_PHASE1_ERROR;

  bool native_exception = (exceptionClass & get_vendor_and_language) == (kOurExceptionClass & get_vendor_and_language);
  scan_results results;
  scan_state_tab(results, actions, native_exception, unwind_exception, context);
  if (actions & _UA_SEARCH_PHASE) {
    // Phase 1 search:  All we're looking for in phase 1 is a handler that
    //   halts unwinding
    return results.reason;
  }
  if (actions & _UA_CLEANUP_PHASE) {
    // Phase 2 cleanup:
    if (results.reason == _URC_HANDLER_FOUND) {
      // Jump to the handler.
      _Unwind_SetGR(context, REG_EXCP_OBJ, reinterpret_cast<uintptr_t>(unwind_exception));
      _Unwind_SetIP(context, results.landingPad);
      return _URC_INSTALL_CONTEXT;
    }
    // Did not find a handler. Return the results of the scan. Normally
    // _URC_CONTINUE_UNWIND, but could have been _URC_FATAL_PHASE2_ERROR.
    return results.reason;
  }
  // We were called improperly: neither a phase 1 or phase 2 search.
  return _URC_FATAL_PHASE1_ERROR;
}
} // namespace __state_table_eh

// The following are EH helper functions for xlclang++ compiled code.

// __xlc_catch_matchv2
// Check whether the thrown object matches the catch handler's exception
// declaration. If there is a match, the function returns true with adjusted
// address of the thrown object. Otherwise, returns false.
_LIBCXXABI_FUNC_VIS bool
__xlc_catch_matchv2(_Unwind_Exception* exceptionObject, std::type_info* catchTypeInfo, void*& obj) {
  _LIBCXXABI_TRACE_STATETAB("Entering %s, exceptionObject=%p\n", __func__, reinterpret_cast<void*>(exceptionObject));

  if (!__isOurExceptionClass(exceptionObject)) {
    _LIBCXXABI_TRACE_STATETAB0("No match, not a C++ exception\n");
    return false;
  }

  __cxa_exception* exceptionHeader = 0;

  if (__getExceptionClass(exceptionObject) == kOurDependentExceptionClass) {
    // Walk to the __cxa_dependent_exception primary exception for the
    // exception object and its type_info.
    __cxa_dependent_exception* dependentExceptionHeader =
        reinterpret_cast<__cxa_dependent_exception*>(exceptionObject + 1) - 1;
    exceptionHeader = reinterpret_cast<__cxa_exception*>(dependentExceptionHeader->primaryException) - 1;
    _LIBCXXABI_TRACE_STATETAB("exceptionObject 0x%p is a dependent, primary 0x%p\n",
                              reinterpret_cast<void*>(exceptionObject),
                              reinterpret_cast<void*>(&exceptionHeader->unwindHeader));
    exceptionObject = &exceptionHeader->unwindHeader;
  } else {
    _LIBCXXABI_TRACE_STATETAB("exceptionObject %p is NOT a dependent\n", reinterpret_cast<void*>(exceptionObject));
    exceptionHeader = reinterpret_cast<__cxa_exception*>(exceptionObject + 1) - 1;
  }

  void* thrownObject = reinterpret_cast<void*>(exceptionObject + 1);
  std::type_info* throwTypeInfo = exceptionHeader->exceptionType;

  // Get the type info for the thrown type and this catch clause and
  // see if the catch caluse can catch that type.

  __cxxabiv1::__shim_type_info* catchType = reinterpret_cast<__cxxabiv1::__shim_type_info*>(catchTypeInfo);
  __cxxabiv1::__shim_type_info* throwType = reinterpret_cast<__cxxabiv1::__shim_type_info*>(throwTypeInfo);
  _LIBCXXABI_TRACE_STATETAB("UnwindException=%p, thrownObject=%p, throwTypeInfo=%p(%s), catchTypeInfo=%p(%s)\n",
                            reinterpret_cast<void*>(exceptionObject), thrownObject, reinterpret_cast<void*>(throwType),
                            throwType->name(), reinterpret_cast<void*>(catchType), catchType->name());
  if (catchType->can_catch(throwType, thrownObject)) {
    exceptionHeader->adjustedPtr = thrownObject;
    obj = thrownObject;
    _LIBCXXABI_TRACE_STATETAB("Match found for thrownObject=%p\n", thrownObject);
    return true;
  }
  _LIBCXXABI_TRACE_STATETAB0("No match\n");
  return false;
}

// __xlc_throw_badexception
// This function is for xlclang++. It allocates and throws a bad_exception.
// During unwinding for this bad_exception, the previous exception which is
// not matching the throw spec will be cleaned up. Thus having the same
// effect as replace the top most exception (which is bad) with a bad_exception.
_LIBCXXABI_FUNC_VIS void __xlc_throw_badexception() {
  _LIBCXXABI_TRACE_STATETAB("Entering function: %s\n\n", __func__);
  void* newexception = new (__cxa_allocate_exception(sizeof(std::bad_exception))) std::bad_exception;
  __cxa_throw(newexception, const_cast<std::type_info*>(&typeid(std::bad_exception)), 0);
}

// __xlc_exception_handle
// This function is for xlclang++. It returns the address of the exception
// object set in gpr14 by the personality routine for xlclang++ compiled code.
_LIBCXXABI_FUNC_VIS uintptr_t __xlc_exception_handle() {
  uintptr_t exceptionObject;
  asm("mr %0, 14" : "=r"(exceptionObject));
  return exceptionObject;
}

// xlclang++ may generate calls to __Deleted_Virtual.
_LIBCXXABI_FUNC_VIS void __Deleted_Virtual() { abort(); }

// __catchThrownException is called during AIX library initialization and
// termination to handle exceptions.  An implementation is also provided in
// libC.a(shrcore.o).  This implementation is provided for applications that
// link with -lc++ (the xlclang++ or ibm-clang++ link default.)
_LIBCXXABI_FUNC_VIS int
__catchThrownException(void (*cdfunc)(void),   // function which may fail
                       void (*cleanup)(void*), // cleanup function
                       void* cleanuparg,       // parameter to cleanup function
                       int action) {           // control exception throwing and termination
  enum Action : int { None = 0, Rethrow = 1, Terminate = 2 };
  if (!cdfunc)
    return 0;
  if (action == Action::Rethrow && !cleanup) {
    // No cleanup and rethrow is effectively no-op.
    // Avoid the catch handler when possible to allow exceptions generated
    // from xlC binaries to flow through.
    (*cdfunc)();
    return 0;
  }
  try {
    (*cdfunc)();
  } catch (...) {
    if (action == Action::Terminate)
      std::terminate();
    if (cleanup)
      (*cleanup)(cleanuparg);
    if (action == Action::Rethrow)
      throw;
    assert(action == Action::None);
    return -1; // FAILED
  }
  return 0;
}

}  // extern "C"

}  // __cxxabiv1
