1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
1.2 +++ b/os/ossrv/genericopenlibs/liboil/src/liboilfault.c Fri Jun 15 03:10:57 2012 +0200
1.3 @@ -0,0 +1,199 @@
1.4 +/*
1.5 + * LIBOIL - Library of Optimized Inner Loops
1.6 + * Copyright (c) 2003,2004 David A. Schleef <ds@schleef.org>
1.7 + * All rights reserved.
1.8 + *
1.9 + * Redistribution and use in source and binary forms, with or without
1.10 + * modification, are permitted provided that the following conditions
1.11 + * are met:
1.12 + * 1. Redistributions of source code must retain the above copyright
1.13 + * notice, this list of conditions and the following disclaimer.
1.14 + * 2. Redistributions in binary form must reproduce the above copyright
1.15 + * notice, this list of conditions and the following disclaimer in the
1.16 + * documentation and/or other materials provided with the distribution.
1.17 + *
1.18 + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
1.19 + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
1.20 + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
1.21 + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
1.22 + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
1.23 + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
1.24 + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
1.25 + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
1.26 + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
1.27 + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
1.28 + * POSSIBILITY OF SUCH DAMAGE.
1.29 + */
1.30 +
1.31 +//Portions Copyright (c) 2006-2008 Nokia Corporation and/or its subsidiary(-ies). All rights reserved.
1.32 +
1.33 +
1.34 +#ifdef HAVE_CONFIG_H
1.35 +#include "config.h"
1.36 +#endif
1.37 +
1.38 +#include <liboil/liboilfunction.h>
1.39 +#include <liboil/liboildebug.h>
1.40 +#include <liboil/liboilfault.h>
1.41 +
1.42 +#include <stdlib.h>
1.43 +#include <string.h>
1.44 +#include <setjmp.h>
1.45 +#include <signal.h>
1.46 +
1.47 +#ifndef __SYMBIAN32__
1.48 +#ifndef _WIN32
1.49 +#include <windows.h>
1.50 +#endif
1.51 +#endif
1.52 +
1.53 +static jmp_buf jump_env;
1.54 +#ifdef HAVE_SIGACTION
1.55 +static struct sigaction action;
1.56 +static struct sigaction oldaction;
1.57 +#else
1.58 +static void * oldhandler;
1.59 +#endif
1.60 +static int in_try_block;
1.61 +static int enable_level;
1.62 +
1.63 +#ifdef __SYMBIAN32__
1.64 +#ifdef __WINSCW__
1.65 +#pragma warn_unusedarg off
1.66 +#endif//__WINSCW__
1.67 +#endif//__SYMBIAN32__
1.68 +
1.69 +#if 0
1.70 +#ifndef _WIN32
1.71 +static LONG __stdcall
1.72 +illegal_instruction_handler (EXCEPTION_POINTERS *e)
1.73 +{
1.74 + if (in_try_block) {
1.75 + /* according to the laws of win32, this isn't allowed.
1.76 + * It does, however, work. */
1.77 + longjmp (jump_env, 1);
1.78 + }
1.79 + /* kill the process */
1.80 + return EXCEPTION_EXECUTE_HANDLER;
1.81 +}
1.82 +#endif
1.83 +#endif
1.84 +//#else
1.85 +static void
1.86 +illegal_instruction_handler (int num)
1.87 +{
1.88 + if (in_try_block) {
1.89 +#ifdef HAVE_SIGPROCMASK
1.90 + sigset_t set;
1.91 + sigemptyset (&set);
1.92 + sigaddset (&set, SIGILL);
1.93 + sigprocmask (SIG_UNBLOCK, &set, NULL);
1.94 + longjmp (jump_env, 1);
1.95 + } else {
1.96 + abort ();
1.97 +#endif
1.98 + }
1.99 +}
1.100 +
1.101 +/**
1.102 + * oil_fault_check_enable:
1.103 + *
1.104 + * Enables fault checking mode. This function may be called multiple times.
1.105 + * Each call to this function must be paired with a corresponding call
1.106 + * to oil_fault_check_disable().
1.107 + *
1.108 + * This function sets a signal handler for SIGILL.
1.109 + */
1.110 +#ifdef __SYMBIAN32__
1.111 +EXPORT_C
1.112 +#endif
1.113 +void
1.114 +oil_fault_check_enable (void)
1.115 +{
1.116 +#ifndef __SYMBIAN32__
1.117 +if (enable_level == 0) {
1.118 +
1.119 +
1.120 +#ifndef _WIN32
1.121 +#ifdef HAVE_SIGACTION
1.122 + memset (&action, 0, sizeof(action));
1.123 + action.sa_handler = &illegal_instruction_handler;
1.124 + sigaction (SIGILL, &action, &oldaction);
1.125 +#else
1.126 + oldhandler = signal (SIGILL, illegal_instruction_handler);
1.127 +#endif
1.128 +#else
1.129 + oldhandler = SetUnhandledExceptionFilter(illegal_instruction_handler);
1.130 +#endif
1.131 +
1.132 + in_try_block = 0;
1.133 + OIL_INFO("enabling SIGILL handler. Make sure to continue past "
1.134 + "any SIGILL signals caught by gdb.");
1.135 + }
1.136 + enable_level++;
1.137 +#endif
1.138 +}
1.139 +
1.140 +/**
1.141 + * oil_fault_check_try:
1.142 + * @func: the function to attempt
1.143 + * @priv: a value to pass to the function
1.144 + *
1.145 + * Calls to this
1.146 + * function must be preceded by a call to oil_fault_check_enable()
1.147 + * to enable fault checking mode. This function sets up recovery
1.148 + * information and then calls the function @func with the parameter
1.149 + * @priv. If @func or any other functions it calls attempt to execute
1.150 + * an illegal instruction, the exception will be caught and recovered from.
1.151 + *
1.152 + * Returns: 1 if the function was executed sucessfully, 0 if the
1.153 + * function attempted to execute an illegal instruction.
1.154 + */
1.155 +#ifdef __SYMBIAN32__
1.156 +EXPORT_C
1.157 +#endif
1.158 +int
1.159 +oil_fault_check_try (void (*func) (void *), void *priv)
1.160 +{
1.161 + int ret;
1.162 +
1.163 + in_try_block = 1;
1.164 + ret = setjmp (jump_env);
1.165 + if (!ret) {
1.166 + func (priv);
1.167 + }
1.168 + in_try_block = 0;
1.169 +
1.170 + return (ret == 0);
1.171 +}
1.172 +
1.173 +/**
1.174 + * oil_fault_check_disable:
1.175 + *
1.176 + * Disables fault checking mode. See oil_fault_check_enable()
1.177 + * for details.
1.178 + */
1.179 +#ifdef __SYMBIAN32__
1.180 +EXPORT_C
1.181 +#endif
1.182 +void
1.183 +oil_fault_check_disable (void)
1.184 +{
1.185 +#ifndef __SYMBIAN32__
1.186 +enable_level--;
1.187 +
1.188 + if (enable_level == 0) {
1.189 +#ifndef _WIN32
1.190 +#ifdef HAVE_SIGACTION
1.191 + sigaction (SIGILL, &oldaction, NULL);
1.192 +#else
1.193 + signal (SIGILL, oldhandler);
1.194 +#endif
1.195 +#else
1.196 + SetUnhandledExceptionFilter(oldhandler);
1.197 +#endif
1.198 + OIL_INFO("disabling SIGILL handler");
1.199 + }
1.200 +#endif
1.201 +}
1.202 +