RtlUnwindEx
VOID __fastcall RtlUnwindEx(
VOID *TargetFrame,
VOID *TargetPc,
_EXCEPTION_RECORD *ExceptionRecord,
VOID *ReturnValue,
_CONTEXT *OriginalContext,
_UNWIND_HISTORY_TABLE *HistoryTable){
_CONTEXT *v6;
_UNWIND_HISTORY_TABLE *v8;
char v10;
unsigned __int64 v11;
signed __int64 v12;
void *v13;
void *v14;
_KERNEL_STACK_LIMITS *v15;
INT64 v16;
INT64 v17;
INT64 v18;
UINT64 v19;
_IMAGE_ARM64_RUNTIME_FUNCTION_ENTRY *v20;
unsigned __int64 v21;
UINT64 v22;
unsigned int v23;
_KERNEL_STACK_LIMITS v24;
_EXCEPTION_RECORD *v25;
char v26;
NTSTATUS v27;
int v28;
_CONTEXT *v29;
int v30;
char v31;
_KERNEL_STACK_LIMITS *v32;
_EXCEPTION_RECORD *v33;
_CONTEXT *v34;
INT64 v35;
UINT64 v36;
unsigned __int64 Rip;
unsigned __int64 *Rsp;
_KERNEL_STACK_LIMITS Type;
unsigned int v40;
UINT64 StackFrame;
_CONTEXT *v42;
UINT64 LowLimit;
UINT64 HighLimit;
UINT64 v45;
UINT64 ImageBase;
INT64 v47;
_EXCEPTION_RECORD *ExceptionRecorda;
_UNWIND_HISTORY_TABLE *v49;
_CONTEXT *Destination;
VOID *v51;
VOID *v52;
UINT64 v53[10];
_CONTEXT *p_Type;
__int64 v55;
__int128 v56;
__int64 v57[20];
v6 = OriginalContext;
v8 = HistoryTable;
v52 = TargetPc;
ExceptionRecorda = ExceptionRecord;
v51 = ReturnValue;
Destination = OriginalContext;
v49 = HistoryTable;
memset(v53, 0i64, sizeof(v53));
memset(v57, 0i64, 0x98u);
v47 = 0i64;
HighLimit = 0i64;
ImageBase = 0i64;
v40 = 0;
LowLimit = 0i64;
Type = BugcheckStackLimits;
KeQueryCurrentStackInformation(&Type, &LowLimit, &HighLimit);
v10 = Type == ExceptionStackLimits;
if( !RtlpGetStackLimits(&LowLimit, &HighLimit) )
LABEL_65:
RtlRaiseStatus(-1073741784);
RtlGetExtendedContextLength2(0x10000Bui64, &v40, 0i64);
v11 = v40 + 15i64;
if( v11 <= v40 )
v11 = 0xFFFFFFFFFFFFFF0i64;
v12 = v11 & 0xFFFFFFFFFFFFFFF0ui64;
v13 = alloca(v12);
v14 = alloca(v12);
p_Type = (_CONTEXT *)&Type;
RtlInitializeExtendedContext2((__int64)&Type, 1048587, &v42, 0i64);
v42 = (_CONTEXT *)&Type;
v15 = &Type;
RtlCaptureContext2((INT64)OriginalContext, v16, v17, v18);
if( HistoryTable )
HistoryTable->Search = 1;
if( !ExceptionRecord )
{
Rip = OriginalContext->_Rip;
ExceptionRecorda = (_EXCEPTION_RECORD *)v57;
v57[2] = Rip;
LODWORD(v57[0]) = -1073741785;
v57[1] = 0i64;
LODWORD(v57[3]) = 0;
}
Type = ExpandedStackLimits;
if( !TargetFrame )
Type = IsrStackLimits;
StackFrame = 0i64;
while( 1 )
{
v19 = v6->_Rip;
v20 = RtlLookupFunctionEntry(v19, &ImageBase, v8);
if( v20 )
{
RtlpCopyContext((_CONTEXT *)v15, v6);
v45 = 0i64;
v55 = 0i64;
v56 = 0i64;
RtlpxVirtualUnwind(2, ImageBase, v19, v20, v15, 0i64, &v47, &StackFrame, &v45, &v55);
v21 = StackFrame;
v22 = v45;
if( (StackFrame & 7) != 0 || StackFrame < LowLimit || StackFrame >= HighLimit )
{
if( v10 != 1 )
goto LABEL_65;
v10 = 2;
if( !RtlpGetStackLimitsEx(StackFrame, (CHAR **)&LowLimit, &HighLimit) )
goto LABEL_65;
v21 = StackFrame;
}
if( TargetFrame && !v10 && (unsigned __int64)TargetFrame < v21 )
goto LABEL_65;
if( v22 )
{
v23 = 0;
v53[4] = (UINT64)v52;
v24 = Type;
v40 = 0;
while( 1 )
{
if( TargetFrame == (VOID *)v21 )
{
v24 |= 0x20u;
Type = v24;
}
v25 = ExceptionRecorda;
v26 = 0;
ExceptionRecorda->ExceptionFlags = v24;
v6->_Rax = (unsigned __int64)v51;
v53[1] = ImageBase;
v53[7] = v47;
v53[8] = (UINT64)v49;
v53[0] = v19;
v53[2] = (UINT64)v20;
v53[3] = StackFrame;
v53[5] = (UINT64)v6;
v53[6] = v22;
LODWORD(v53[9]) = v23;
if( (v6->ContextFlags & 0x100040) == 1048640 )
v26 = 1;
v27 = RtlpExecuteHandlerForUnwind((INT64)v25, StackFrame, (INT64)v6, (INT64)v53);
if( !v26 && (v6->ContextFlags & 0x100040) == 1048640 )
v6->ContextFlags &= ~0x40u;
Type &= 0xFFFFFF9F;
v28 = v27 - 1;
if( v28 )
{
if( v28 != 2 )
RtlRaiseStatus(-1073741786);
v19 = v53[0];
v20 = (_IMAGE_ARM64_RUNTIME_FUNCTION_ENTRY *)v53[2];
ImageBase = v53[1];
RtlpCopyContext(Destination, (_CONTEXT *)v53[5]);
v42 = p_Type;
v6 = v34;
RtlpCopyContext(p_Type, v34);
LODWORD(v36) = RtlVirtualUnwind(2i64, v35, v19);
v22 = v36;
if( v36 != v53[6] || (v21 = StackFrame, StackFrame != v53[3]) || v47 != v53[7] )
__fastfail(0x27u);
Type |= 0x40u;
v49 = (_UNWIND_HISTORY_TABLE *)v53[8];
v40 = v53[9];
if( (unsigned __int8)RtlpIsFrameInBounds(&LowLimit, StackFrame, &HighLimit) || v10 != 1 )
goto LABEL_32;
v10 = 2;
RtlpGetStackLimitsEx(v21, (CHAR **)&LowLimit, &HighLimit);
}
else
{
if( (VOID *)StackFrame != TargetFrame )
{
v29 = v6;
v6 = v42;
v42 = v29;
}
v30 = _mm_getcsr();
LODWORD(v45) = v30;
v6->_MxCsr = v30;
v6->FltSave._MxCsr = v30;
}
v21 = StackFrame;
LABEL_32:
v24 = Type;
v23 = v40;
if( (Type & 0x40) == 0 )
goto LABEL_33;
}
}
if( (VOID *)v21 == TargetFrame )
{
LABEL_33:
v15 = (_KERNEL_STACK_LIMITS *)v42;
}
else
{
v32 = (_KERNEL_STACK_LIMITS *)v6;
v6 = v42;
v15 = v32;
v42 = (_CONTEXT *)v32;
}
}
else
{
Rsp = (unsigned __int64 *)v6->_Rsp;
v6->_Rip = *Rsp;
v6->_Rsp = (unsigned __int64)(Rsp + 1);
RtlpPopUserShadowStack((INT64)v6);
v21 = StackFrame;
}
v31 = 0;
if( v10 != 2 )
v31 = v10;
if( (v21 & 7) != 0 || v21 < LowLimit || v21 >= HighLimit )
break;
if( (VOID *)v21 == TargetFrame )
goto LABEL_43;
v8 = v49;
v10 = v31;
}
if( (VOID *)v21 == TargetFrame )
{
LABEL_43:
v33 = ExceptionRecorda;
v6->_Rax = (unsigned __int64)v51;
if( v33->ExceptionCode != -2147483607 )
{
v6->_Rip = (unsigned __int64)v52;
if( v33->ExceptionCode != -2147483610 )
v33->ExceptionCode = -1073741785;
}
RtlGuardRestoreContext(v6, v33);
}
else
{
if( v19 == v6->_Rip )
RtlRaiseStatus(-1073741569);
ZwRaiseException(ExceptionRecorda, v6, 0);
}
}Referenced by:
KiSystemServiceHandler
RtlUnwind
_C_specific_handler
_longjmp_internal