From 58c3aa204906def9a157ea9a9db091f69af76e4b Mon Sep 17 00:00:00 2001 From: Rafael Espindola Date: Wed, 1 May 2013 21:05:05 +0000 Subject: [PATCH] Add support for other typeinfo encodings in the ExceptionDemo. The old jit always uses DW_EH_PE_absptr, but MCJIT can use other encodings. This is in preparation for adding EH support to MCJIT, but not directly related, so I am committing it first. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@180883 91177308-0d34-0410-b5e6-96231b3b80d8 --- examples/ExceptionDemo/ExceptionDemo.cpp | 50 +++++++++++++++++++----- 1 file changed, 41 insertions(+), 9 deletions(-) diff --git a/examples/ExceptionDemo/ExceptionDemo.cpp b/examples/ExceptionDemo/ExceptionDemo.cpp index 264ef5481f57..0bd49a373213 100644 --- a/examples/ExceptionDemo/ExceptionDemo.cpp +++ b/examples/ExceptionDemo/ExceptionDemo.cpp @@ -418,6 +418,30 @@ static uintptr_t readSLEB128(const uint8_t **data) { return result; } +unsigned getEncodingSize(uint8_t Encoding) { + if (Encoding == llvm::dwarf::DW_EH_PE_omit) + return 0; + + switch (Encoding & 0x0F) { + case llvm::dwarf::DW_EH_PE_absptr: + return sizeof(uintptr_t); + case llvm::dwarf::DW_EH_PE_udata2: + return sizeof(uint16_t); + case llvm::dwarf::DW_EH_PE_udata4: + return sizeof(uint32_t); + case llvm::dwarf::DW_EH_PE_udata8: + return sizeof(uint64_t); + case llvm::dwarf::DW_EH_PE_sdata2: + return sizeof(int16_t); + case llvm::dwarf::DW_EH_PE_sdata4: + return sizeof(int32_t); + case llvm::dwarf::DW_EH_PE_sdata8: + return sizeof(int64_t); + default: + // not supported + abort(); + } +} /// Read a pointer encoded value and advance pointer /// See Variable Length Data in: @@ -523,7 +547,8 @@ static uintptr_t readEncodedPointer(const uint8_t **data, uint8_t encoding) { /// @returns whether or not a type info was found. False is returned if only /// a cleanup was found static bool handleActionValue(int64_t *resultAction, - struct OurExceptionType_t **classInfo, + uint8_t TTypeEncoding, + const uint8_t *ClassInfo, uintptr_t actionEntry, uint64_t exceptionClass, struct _Unwind_Exception *exceptionObject) { @@ -572,16 +597,22 @@ static bool handleActionValue(int64_t *resultAction, // Note: A typeOffset == 0 implies that a cleanup llvm.eh.selector // argument has been matched. - if ((typeOffset > 0) && - (type == (classInfo[-typeOffset])->type)) { + if (typeOffset > 0) { #ifdef DEBUG fprintf(stderr, "handleActionValue(...):actionValue <%d> found.\n", i); #endif - *resultAction = i + 1; - ret = true; - break; + unsigned EncSize = getEncodingSize(TTypeEncoding); + const uint8_t *EntryP = ClassInfo - typeOffset * EncSize; + uintptr_t P = readEncodedPointer(&EntryP, TTypeEncoding); + struct OurExceptionType_t *ThisClassInfo = + reinterpret_cast(P); + if (ThisClassInfo->type == type) { + *resultAction = i + 1; + ret = true; + break; + } } #ifdef DEBUG @@ -633,7 +664,7 @@ static _Unwind_Reason_Code handleLsda(int version, // emitted dwarf code) uintptr_t funcStart = _Unwind_GetRegionStart(context); uintptr_t pcOffset = pc - funcStart; - struct OurExceptionType_t **classInfo = NULL; + const uint8_t *ClassInfo = NULL; // Note: See JITDwarfEmitter::EmitExceptionTable(...) for corresponding // dwarf emission @@ -653,7 +684,7 @@ static _Unwind_Reason_Code handleLsda(int version, // were flagged by type info arguments to llvm.eh.selector // intrinsic classInfoOffset = readULEB128(&lsda); - classInfo = (struct OurExceptionType_t**) (lsda + classInfoOffset); + ClassInfo = lsda + classInfoOffset; } // Walk call-site table looking for range that @@ -714,7 +745,8 @@ static _Unwind_Reason_Code handleLsda(int version, if (actionEntry) { exceptionMatched = handleActionValue(&actionValue, - classInfo, + ttypeEncoding, + ClassInfo, actionEntry, exceptionClass, exceptionObject);