You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
110 lines
2.5 KiB
110 lines
2.5 KiB
/*
|
|
* Copyright 2002-2019 Intel Corporation.
|
|
*
|
|
* This software is provided to you as Sample Source Code as defined in the accompanying
|
|
* End User License Agreement for the Intel(R) Software Development Products ("Agreement")
|
|
* section 1.L.
|
|
*
|
|
* This software and the related documents are provided as is, with no express or implied
|
|
* warranties, other than those that are expressly stated in the License.
|
|
*/
|
|
|
|
/*
|
|
* This test verifies the flags are correctly delivered at exceptions
|
|
*/
|
|
#define _GNU_SOURCE
|
|
#include <signal.h>
|
|
#include <sys/ucontext.h>
|
|
#include <stdio.h>
|
|
#include <setjmp.h>
|
|
#include <assert.h>
|
|
#include <sys/mman.h>
|
|
|
|
|
|
static sigjmp_buf JumpBuffer;
|
|
static unsigned int TestNumber = 0;
|
|
|
|
|
|
|
|
extern int GetFlags_asm();
|
|
// from faultcheck_flags_ia32_asm.s
|
|
extern int SetAppFlagsAndSegv_asm();
|
|
extern int ClearAppFlagsAndSegv_asm();
|
|
int DoTest(unsigned int tnum)
|
|
{
|
|
|
|
switch (tnum)
|
|
{
|
|
case 0:
|
|
printf ("AllFlagsSet\n");
|
|
SetAppFlagsAndSegv_asm();
|
|
return (1);
|
|
|
|
case 1:
|
|
printf ("AllFlagsClear\n");
|
|
ClearAppFlagsAndSegv_asm();
|
|
return (1);
|
|
|
|
default:
|
|
return (0);
|
|
}
|
|
}
|
|
|
|
void PrintEflagsAtSignal(int sig, const siginfo_t *info, void *vctxt)
|
|
{
|
|
ucontext_t *ctxt = vctxt;
|
|
// note that the resume flag is turned on when exception occurs,
|
|
// but if pin needs to retrieve the flags from memory then the
|
|
// resume flag will not be there - so we test only the lower 16 bits
|
|
#if defined(TARGET_MAC)
|
|
unsigned long flags = (unsigned long)ctxt->uc_mcontext->__ss.__eflags&0xffff;
|
|
#else
|
|
unsigned long flags = (unsigned long)ctxt->uc_mcontext.gregs[REG_EFL]&0xffff;
|
|
#endif
|
|
printf(" Signal %d, eflags=0x%lx\n", sig, flags);
|
|
}
|
|
|
|
static void Handle(int sig, siginfo_t* info, void* ctxt)
|
|
{
|
|
PrintEflagsAtSignal(sig, info, ctxt);
|
|
TestNumber++;
|
|
siglongjmp(JumpBuffer, 1);
|
|
}
|
|
|
|
int main()
|
|
{
|
|
struct sigaction sigact;
|
|
|
|
sigact.sa_sigaction = Handle;
|
|
sigemptyset(&sigact.sa_mask);
|
|
sigact.sa_flags = SA_SIGINFO;
|
|
if (sigaction(SIGSEGV, &sigact, 0) == -1)
|
|
{
|
|
fprintf(stderr, "Unable handle SIGSEGV\n");
|
|
return 1;
|
|
}
|
|
|
|
if (sigaction(SIGBUS, &sigact, 0) == -1)
|
|
{
|
|
fprintf(stderr, "Unable handle SIGBUS\n");
|
|
return 1;
|
|
}
|
|
|
|
sigsetjmp(JumpBuffer, 1);
|
|
|
|
for (;;)
|
|
{
|
|
if (!DoTest(TestNumber))
|
|
{
|
|
printf("Last test\n");
|
|
break;
|
|
}
|
|
printf("Failed to raise signal\n");
|
|
TestNumber++;
|
|
}
|
|
|
|
|
|
return 0;
|
|
}
|
|
|