mirror of
https://github.com/reactos/reactos.git
synced 2025-08-05 15:52:57 +00:00
modified include/reactos/libs/pseh/pseh2.h
modified lib/pseh/framebased-gcchack.c modified lib/pseh/i386/framebased-gcchack.S (Re)added arguments to _SEH2_EXCEPT nested routines, so that using _SEH2_GetExceptionCode and _SEH2_GetExceptionInformation in exception filters doesn't force the creation of function trampolines (and related horrid inline code) Reimplemented some internal library routines in C svn path=/trunk/; revision=38295
This commit is contained in:
parent
4750c0b942
commit
f72b85bdf7
3 changed files with 87 additions and 102 deletions
|
@ -46,7 +46,6 @@ typedef struct __SEH2Frame
|
||||||
{
|
{
|
||||||
_SEH2Registration_t SF_Registration;
|
_SEH2Registration_t SF_Registration;
|
||||||
volatile struct __SEH2TryLevel * volatile SF_TopTryLevel;
|
volatile struct __SEH2TryLevel * volatile SF_TopTryLevel;
|
||||||
struct _EXCEPTION_POINTERS * volatile SF_ExceptionInformation;
|
|
||||||
volatile unsigned long SF_Code;
|
volatile unsigned long SF_Code;
|
||||||
}
|
}
|
||||||
_SEH2Frame_t;
|
_SEH2Frame_t;
|
||||||
|
@ -140,15 +139,23 @@ void * _SEHClosureFromTrampoline(_SEHTrampoline_t * trampoline_)
|
||||||
#define __SEH_FORCE_NEST \
|
#define __SEH_FORCE_NEST \
|
||||||
__asm__ __volatile__("#%0" : : "r" (&_SEHFrame))
|
__asm__ __volatile__("#%0" : : "r" (&_SEHFrame))
|
||||||
|
|
||||||
#define __SEH_DECLARE_EXCEPT_PFN(NAME_) int (__cdecl * NAME_)(void)
|
#define __SEH_EXCEPT_RET long
|
||||||
#define __SEH_DECLARE_EXCEPT(NAME_) int __cdecl NAME_(void)
|
#define __SEH_EXCEPT_ARGS __attribute__((unused)) _SEH2Frame_t * _SEH2FrameP, __attribute__((unused)) struct _EXCEPTION_POINTERS * _SEHExceptionInformation
|
||||||
#define __SEH_DEFINE_EXCEPT(NAME_) int __cdecl NAME_(void)
|
#define __SEH_EXCEPT_ARGS_ , __SEH_EXCEPT_ARGS
|
||||||
|
#define __SEH_EXCEPT_PFN __SEH_DECLARE_EXCEPT_PFN
|
||||||
|
#define __SEH_DECLARE_EXCEPT_PFN(NAME_) __SEH_EXCEPT_RET (__cdecl * NAME_)(__SEH_EXCEPT_ARGS)
|
||||||
|
#define __SEH_DECLARE_EXCEPT(NAME_) __SEH_EXCEPT_RET __cdecl NAME_(__SEH_EXCEPT_ARGS)
|
||||||
|
#define __SEH_DEFINE_EXCEPT(NAME_) __SEH_EXCEPT_RET __cdecl NAME_(__SEH_EXCEPT_ARGS)
|
||||||
|
|
||||||
#define __SEH_DECLARE_FINALLY_PFN(NAME_) void (__cdecl * NAME_)(void)
|
#define __SEH_FINALLY_RET void
|
||||||
#define __SEH_DECLARE_FINALLY(NAME_) void __cdecl NAME_(void)
|
#define __SEH_FINALLY_ARGS void
|
||||||
#define __SEH_DEFINE_FINALLY(NAME_) void __cdecl NAME_(void)
|
#define __SEH_FINALLY_ARGS_
|
||||||
|
#define __SEH_FINALLY_PFN __SEH_DECLARE_FINALLY_PFN
|
||||||
|
#define __SEH_DECLARE_FINALLY_PFN(NAME_) __SEH_FINALLY_RET (__cdecl * NAME_)(__SEH_FINALLY_ARGS)
|
||||||
|
#define __SEH_DECLARE_FINALLY(NAME_) __SEH_FINALLY_RET __cdecl NAME_(__SEH_FINALLY_ARGS)
|
||||||
|
#define __SEH_DEFINE_FINALLY(NAME_) __SEH_FINALLY_RET __cdecl NAME_(__SEH_FINALLY_ARGS)
|
||||||
|
|
||||||
#define __SEH_RETURN_EXCEPT(R_) return (int)(R_)
|
#define __SEH_RETURN_EXCEPT(R_) return (long)(R_)
|
||||||
#define __SEH_RETURN_FINALLY() return
|
#define __SEH_RETURN_FINALLY() return
|
||||||
|
|
||||||
#define __SEH_BEGIN_TRY \
|
#define __SEH_BEGIN_TRY \
|
||||||
|
@ -175,9 +182,9 @@ void * _SEHClosureFromTrampoline(_SEHTrampoline_t * trampoline_)
|
||||||
#define __SEH_LEAVE_TRYLEVEL() __SEH_SET_TRYLEVEL(_SEHPrevTryLevelP)
|
#define __SEH_LEAVE_TRYLEVEL() __SEH_SET_TRYLEVEL(_SEHPrevTryLevelP)
|
||||||
|
|
||||||
#define __SEH_END_SCOPE_CHAIN \
|
#define __SEH_END_SCOPE_CHAIN \
|
||||||
static const int _SEH2ScopeKind = 1; \
|
static __attribute__((unused)) const int _SEH2ScopeKind = 1; \
|
||||||
static _SEH2Frame_t * const _SEH2FrameP = 0; \
|
static __attribute__((unused)) _SEH2Frame_t * const _SEH2FrameP = 0; \
|
||||||
static _SEH2TryLevel_t * const _SEH2TryLevelP = 0;
|
static __attribute__((unused)) _SEH2TryLevel_t * const _SEH2TryLevelP = 0;
|
||||||
|
|
||||||
#define __SEH_BEGIN_SCOPE \
|
#define __SEH_BEGIN_SCOPE \
|
||||||
for(;;) \
|
for(;;) \
|
||||||
|
@ -286,6 +293,9 @@ void * _SEHClosureFromTrampoline(_SEHTrampoline_t * trampoline_)
|
||||||
goto _SEHAfterTry; \
|
goto _SEHAfterTry; \
|
||||||
\
|
\
|
||||||
_SEHBeforeTry:; \
|
_SEHBeforeTry:; \
|
||||||
|
\
|
||||||
|
{ \
|
||||||
|
__attribute__((unused)) struct _EXCEPTION_POINTERS * volatile _SEHExceptionInformation; \
|
||||||
\
|
\
|
||||||
if(__builtin_constant_p((__VA_ARGS__))) \
|
if(__builtin_constant_p((__VA_ARGS__))) \
|
||||||
{ \
|
{ \
|
||||||
|
@ -317,6 +327,7 @@ void * _SEHClosureFromTrampoline(_SEHTrampoline_t * trampoline_)
|
||||||
_SEHTryLevel.ST_Body = &&_SEHBeginExcept; \
|
_SEHTryLevel.ST_Body = &&_SEHBeginExcept; \
|
||||||
__SEH_USE_LABEL(_SEHBeginExcept); \
|
__SEH_USE_LABEL(_SEHBeginExcept); \
|
||||||
} \
|
} \
|
||||||
|
} \
|
||||||
\
|
\
|
||||||
__SEH_BARRIER; \
|
__SEH_BARRIER; \
|
||||||
\
|
\
|
||||||
|
@ -347,8 +358,6 @@ void * _SEHClosureFromTrampoline(_SEHTrampoline_t * trampoline_)
|
||||||
_SEHBeginExcept:; \
|
_SEHBeginExcept:; \
|
||||||
{ \
|
{ \
|
||||||
{ \
|
{ \
|
||||||
_SEH2Frame_t * const _SEH2FrameP = _SEHTopTryLevel ? &_SEHFrame : _SEHCurFrameP; \
|
|
||||||
(void)_SEH2FrameP; \
|
|
||||||
__SEH_BARRIER;
|
__SEH_BARRIER;
|
||||||
|
|
||||||
#define _SEH2_END \
|
#define _SEH2_END \
|
||||||
|
@ -360,7 +369,7 @@ void * _SEHClosureFromTrampoline(_SEHTrampoline_t * trampoline_)
|
||||||
} \
|
} \
|
||||||
__SEH_END_SCOPE;
|
__SEH_END_SCOPE;
|
||||||
|
|
||||||
#define _SEH2_GetExceptionInformation() ((_SEH2FrameP)->SF_ExceptionInformation)
|
#define _SEH2_GetExceptionInformation() (_SEHExceptionInformation)
|
||||||
#define _SEH2_GetExceptionCode() ((_SEH2FrameP)->SF_Code)
|
#define _SEH2_GetExceptionCode() ((_SEH2FrameP)->SF_Code)
|
||||||
#define _SEH2_AbnormalTermination() (_SEHAbnormalTermination)
|
#define _SEH2_AbnormalTermination() (_SEHAbnormalTermination)
|
||||||
|
|
||||||
|
|
|
@ -20,14 +20,15 @@
|
||||||
DEALINGS IN THE SOFTWARE.
|
DEALINGS IN THE SOFTWARE.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#define _NTSYSTEM_
|
#define _NTSYSTEM_ /* removes dllimport attribute from RtlUnwind */
|
||||||
|
|
||||||
#define STRICT
|
#define STRICT
|
||||||
#define WIN32_LEAN_AND_MEAN
|
#define WIN32_LEAN_AND_MEAN
|
||||||
#include <windows.h>
|
#include <windows.h>
|
||||||
|
|
||||||
#include <pseh/pseh2.h>
|
#include <pseh/pseh2.h>
|
||||||
|
|
||||||
#include <excpt.h>
|
#include <excpt.h>
|
||||||
|
#include <intrin.h>
|
||||||
|
|
||||||
#ifndef EXCEPTION_EXIT_UNWIND
|
#ifndef EXCEPTION_EXIT_UNWIND
|
||||||
#define EXCEPTION_EXIT_UNWIND 4
|
#define EXCEPTION_EXIT_UNWIND 4
|
||||||
|
@ -37,18 +38,29 @@
|
||||||
#define EXCEPTION_UNWINDING 2
|
#define EXCEPTION_UNWINDING 2
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
extern _SEH2Registration_t * __cdecl _SEH2CurrentRegistration(void);
|
|
||||||
|
|
||||||
extern int __SEH2Except(void *, void *);
|
|
||||||
extern void __SEH2Finally(void *, void *);
|
|
||||||
extern DECLSPEC_NORETURN int __SEH2Handle(void *, void *, void *);
|
extern DECLSPEC_NORETURN int __SEH2Handle(void *, void *, void *);
|
||||||
|
|
||||||
extern void __cdecl __SEH2EnterFrame(_SEH2Registration_t *);
|
|
||||||
extern void __cdecl __SEH2LeaveFrame(void);
|
|
||||||
|
|
||||||
extern int __cdecl __SEH2FrameHandler(struct _EXCEPTION_RECORD *, void *, struct _CONTEXT *, void *);
|
extern int __cdecl __SEH2FrameHandler(struct _EXCEPTION_RECORD *, void *, struct _CONTEXT *, void *);
|
||||||
extern int __cdecl __SEH2NestedHandler(struct _EXCEPTION_RECORD *, void *, struct _CONTEXT *, void *);
|
extern int __cdecl __SEH2NestedHandler(struct _EXCEPTION_RECORD *, void *, struct _CONTEXT *, void *);
|
||||||
|
|
||||||
|
FORCEINLINE
|
||||||
|
_SEH2Registration_t * __cdecl _SEH2CurrentRegistration(void)
|
||||||
|
{
|
||||||
|
return (_SEH2Registration_t *)__readfsdword(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
FORCEINLINE
|
||||||
|
void __cdecl __SEH2EnterFrame(_SEH2Registration_t * frame)
|
||||||
|
{
|
||||||
|
frame->SER_Prev = _SEH2CurrentRegistration();
|
||||||
|
__writefsdword(0, (unsigned long)frame);
|
||||||
|
}
|
||||||
|
|
||||||
|
FORCEINLINE
|
||||||
|
void __cdecl __SEH2LeaveFrame(void)
|
||||||
|
{
|
||||||
|
__writefsdword(0, (unsigned long)_SEH2CurrentRegistration()->SER_Prev);
|
||||||
|
}
|
||||||
|
|
||||||
FORCEINLINE
|
FORCEINLINE
|
||||||
void _SEH2GlobalUnwind(void * target)
|
void _SEH2GlobalUnwind(void * target)
|
||||||
{
|
{
|
||||||
|
@ -67,11 +79,12 @@ void _SEH2GlobalUnwind(void * target)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
FORCEINLINE
|
static
|
||||||
int _SEH2Except(_SEH2Frame_t * frame, volatile _SEH2TryLevel_t * trylevel)
|
__SEH_EXCEPT_RET _SEH2Except(_SEH2Frame_t * frame, volatile _SEH2TryLevel_t * trylevel, struct _EXCEPTION_POINTERS * ep)
|
||||||
{
|
{
|
||||||
void * filter = trylevel->ST_Filter;
|
void * filter = trylevel->ST_Filter;
|
||||||
void * context = NULL;
|
void * context = NULL;
|
||||||
|
__SEH_EXCEPT_RET ret;
|
||||||
|
|
||||||
if(filter == (void *)0)
|
if(filter == (void *)0)
|
||||||
return 0;
|
return 0;
|
||||||
|
@ -88,10 +101,22 @@ int _SEH2Except(_SEH2Frame_t * frame, volatile _SEH2TryLevel_t * trylevel)
|
||||||
filter = _SEHFunctionFromTrampoline((_SEHTrampoline_t *)filter);
|
filter = _SEHFunctionFromTrampoline((_SEHTrampoline_t *)filter);
|
||||||
}
|
}
|
||||||
|
|
||||||
return __SEH2Except(filter, context);
|
__asm__ __volatile__
|
||||||
|
(
|
||||||
|
"push %[ep]\n"
|
||||||
|
"push %[frame]\n"
|
||||||
|
"call *%[filter]\n"
|
||||||
|
"pop %%edx\n"
|
||||||
|
"pop %%edx\n" :
|
||||||
|
[ret] "=a" (ret) :
|
||||||
|
"c" (context), [filter] "r" (filter), [frame] "g" (frame), [ep] "g" (ep) :
|
||||||
|
"edx", "flags", "memory"
|
||||||
|
);
|
||||||
|
|
||||||
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
FORCEINLINE
|
static
|
||||||
void _SEH2Finally(_SEH2Frame_t * frame, volatile _SEH2TryLevel_t * trylevel)
|
void _SEH2Finally(_SEH2Frame_t * frame, volatile _SEH2TryLevel_t * trylevel)
|
||||||
{
|
{
|
||||||
if(trylevel->ST_Filter == NULL && trylevel->ST_Body != NULL)
|
if(trylevel->ST_Filter == NULL && trylevel->ST_Body != NULL)
|
||||||
|
@ -105,7 +130,7 @@ void _SEH2Finally(_SEH2Frame_t * frame, volatile _SEH2TryLevel_t * trylevel)
|
||||||
body = _SEHFunctionFromTrampoline((_SEHTrampoline_t *)body);
|
body = _SEHFunctionFromTrampoline((_SEHTrampoline_t *)body);
|
||||||
}
|
}
|
||||||
|
|
||||||
__SEH2Finally(body, context);
|
__asm__ __volatile__("call *%1\n" : : "c" (context), "r" (body) : "eax", "edx", "flags", "memory");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -179,11 +204,10 @@ int __cdecl _SEH2FrameHandler
|
||||||
ep.ContextRecord = ContextRecord;
|
ep.ContextRecord = ContextRecord;
|
||||||
|
|
||||||
frame->SF_Code = ExceptionRecord->ExceptionCode;
|
frame->SF_Code = ExceptionRecord->ExceptionCode;
|
||||||
frame->SF_ExceptionInformation = &ep;
|
|
||||||
|
|
||||||
for(trylevel = frame->SF_TopTryLevel; trylevel != NULL; trylevel = trylevel->ST_Next)
|
for(trylevel = frame->SF_TopTryLevel; trylevel != NULL; trylevel = trylevel->ST_Next)
|
||||||
{
|
{
|
||||||
ret = _SEH2Except(frame, trylevel);
|
ret = _SEH2Except(frame, trylevel, &ep);
|
||||||
|
|
||||||
if(ret < 0)
|
if(ret < 0)
|
||||||
return ExceptionContinueExecution;
|
return ExceptionContinueExecution;
|
||||||
|
|
|
@ -21,32 +21,6 @@
|
||||||
.text
|
.text
|
||||||
.intel_syntax noprefix
|
.intel_syntax noprefix
|
||||||
|
|
||||||
.func _SEH2CurrentRegistration
|
|
||||||
.globl __SEH2CurrentRegistration
|
|
||||||
__SEH2CurrentRegistration:
|
|
||||||
mov eax, [fs:0]
|
|
||||||
ret
|
|
||||||
.endfunc
|
|
||||||
|
|
||||||
.func __SEH2EnterFrame
|
|
||||||
.globl ___SEH2EnterFrame
|
|
||||||
___SEH2EnterFrame:
|
|
||||||
mov eax, [esp+4]
|
|
||||||
mov ecx, [fs:0]
|
|
||||||
mov [eax], ecx
|
|
||||||
mov [fs:0], eax
|
|
||||||
ret
|
|
||||||
.endfunc
|
|
||||||
|
|
||||||
.func __SEH2LeaveFrame
|
|
||||||
.globl ___SEH2LeaveFrame
|
|
||||||
___SEH2LeaveFrame:
|
|
||||||
mov eax, [fs:0]
|
|
||||||
mov eax, [eax]
|
|
||||||
mov [fs:0], eax
|
|
||||||
ret
|
|
||||||
.endfunc
|
|
||||||
|
|
||||||
.func __SEH2Handle
|
.func __SEH2Handle
|
||||||
.globl ___SEH2Handle
|
.globl ___SEH2Handle
|
||||||
___SEH2Handle:
|
___SEH2Handle:
|
||||||
|
@ -56,28 +30,6 @@ ___SEH2Handle:
|
||||||
jmp eax
|
jmp eax
|
||||||
.endfunc
|
.endfunc
|
||||||
|
|
||||||
.func __SEH2Except
|
|
||||||
.globl ___SEH2Except
|
|
||||||
___SEH2Except:
|
|
||||||
mov eax, [esp+4]
|
|
||||||
mov ecx, [esp+8]
|
|
||||||
|
|
||||||
call eax
|
|
||||||
|
|
||||||
ret
|
|
||||||
.endfunc
|
|
||||||
|
|
||||||
.func __SEH2Finally
|
|
||||||
.globl ___SEH2Finally
|
|
||||||
___SEH2Finally:
|
|
||||||
mov eax, [esp+4]
|
|
||||||
mov ecx, [esp+8]
|
|
||||||
|
|
||||||
call eax
|
|
||||||
|
|
||||||
ret
|
|
||||||
.endfunc
|
|
||||||
|
|
||||||
.func __SEH2FrameHandler
|
.func __SEH2FrameHandler
|
||||||
.globl ___SEH2FrameHandler
|
.globl ___SEH2FrameHandler
|
||||||
___SEH2FrameHandler:
|
___SEH2FrameHandler:
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue