Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/libcfa/interpose.c

    r169d944 r2b8bc41  
    1010// Created On       : Wed Mar 29 16:10:31 2017
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Thu Feb  8 16:18:09 2018
    13 // Update Count     : 75
     12// Last Modified On : Tue Feb  6 17:57:56 2018
     13// Update Count     : 49
    1414//
    1515
     
    3232#include "bits/signal.h"
    3333#include "startup.h"
    34 
    35 //=============================================================================================
    36 // Interposing helpers
    37 //=============================================================================================
    3834
    3935typedef void (*generic_fptr_t)(void);
     
    5046                        error = dlerror();
    5147                        if ( error ) {
    52                                 abort( "interpose_symbol : failed to open libc, %s\n", error );
     48                                abortf( "interpose_symbol : failed to open libc, %s\n", error );
    5349                        }
    5450                #endif
     
    6864
    6965        error = dlerror();
    70         if ( error ) abort( "interpose_symbol : internal error, %s\n", error );
     66        if ( error ) abortf( "interpose_symbol : internal error, %s\n", error );
    7167
    7268        return originalFunc.fptr;
    7369}
    7470
     71
     72__typeof__( exit ) libc_exit __attribute__(( noreturn ));
     73__typeof__( abort ) libc_abort __attribute__(( noreturn ));
     74
    7575forall(dtype T)
    76 static inline void ptr_from_symbol( T** symbol_ptr, const char * symbol_name, const char * version) {
     76static inline void assign_ptr( T** symbol_ptr, const char * symbol_name, const char * version) {
    7777        union {
    7878                generic_fptr_t gp;
     
    8585}
    8686
    87 #define INTERPOSE_LIBC( x, ver ) ptr_from_symbol( (void**)&__cabi_libc.x, #x, ver)
    88 
    89 //=============================================================================================
    90 // Terminating Signals logic
    91 //=============================================================================================
     87#define INIT_REALRTN( x, ver ) assign_ptr( (void**)&libc_##x, #x, ver)
    9288
    9389void sigHandler_segv ( __CFA_SIGPARMS__ );
     
    9692void sigHandler_abort( __CFA_SIGPARMS__ );
    9793
    98 struct {
    99         void (* exit)( int ) __attribute__ (( __noreturn__ ));
    100         void (* abort)( void ) __attribute__ (( __noreturn__ ));
    101 } __cabi_libc;
    102 
    10394extern "C" {
    10495        void __cfaabi_interpose_startup(void)  __attribute__(( constructor( STARTUP_PRIORITY_CORE ) ));
     
    10697                const char *version = NULL;
    10798
    108                 INTERPOSE_LIBC( abort, version );
    109                 INTERPOSE_LIBC( exit , version );
     99                INIT_REALRTN( abort, version );
     100                INIT_REALRTN( exit, version );
    110101
    111102                __cfaabi_sigaction( SIGSEGV, sigHandler_segv , SA_SIGINFO ); // Failure handler
     
    121112//=============================================================================================
    122113
    123 // Forward declare abort after the __typeof__ call to avoid ambiguities
    124 void exit( int status, const char fmt[], ... ) __attribute__ (( format(printf, 2, 3), __nothrow__, __leaf__, __noreturn__ ));
    125 void abort( const char fmt[], ... ) __attribute__ (( format(printf, 1, 2), __nothrow__, __leaf__, __noreturn__ ));
    126 
    127 extern "C" {
    128         void abort( void ) __attribute__ (( __nothrow__, __leaf__, __noreturn__ )) {
    129                 abort( NULL );
    130         }
    131 
    132         void __cabi_abort( const char fmt[], ... ) __attribute__ (( format(printf, 1, 2), __nothrow__, __leaf__, __noreturn__ )) {
    133                 va_list argp;
    134                 va_start( argp, fmt );
    135                 abort( fmt, argp );
    136                 va_end( argp );
    137         }
    138 
    139         void exit( int status ) __attribute__ (( __nothrow__, __leaf__, __noreturn__ )) {
    140                 __cabi_libc.exit( status );
    141         }
    142 }
    143 
    144 void * kernel_abort    ( void ) __attribute__ (( __nothrow__, __leaf__, __weak__ )) { return NULL; }
    145 void   kernel_abort_msg( void * data, char * buffer, int size ) __attribute__ (( __nothrow__, __leaf__, __weak__ )) {}
    146 int kernel_abort_lastframe( void ) __attribute__ (( __nothrow__, __leaf__, __weak__ )) { return 4; }
     114extern "C" {
     115        void abort( void ) __attribute__ ((__nothrow__, __leaf__, __noreturn__)) {
     116                abortf( NULL );
     117        }
     118
     119        void exit( int __status ) __attribute__ ((__nothrow__, __leaf__, __noreturn__)) {
     120                libc_exit(__status);
     121        }
     122}
     123
     124void abort( const char fmt[], ... ) __attribute__ ((__nothrow__, __leaf__, __noreturn__)) {
     125        va_list argp;
     126        va_start( argp, fmt );
     127        abortf( fmt, argp );
     128        va_end( argp );
     129}
     130
     131void * kernel_abort    ( void ) __attribute__ ((__nothrow__, __leaf__, __weak__)) { return NULL; }
     132void   kernel_abort_msg( void * data, char * buffer, int size ) __attribute__ ((__nothrow__, __leaf__, __weak__)) {}
     133int kernel_abort_lastframe( void ) __attribute__ ((__nothrow__, __leaf__, __weak__)) { return 4; }
    147134
    148135enum { abort_text_size = 1024 };
     
    150137static int abort_lastframe;
    151138
    152 void exit( int status, const char fmt[], ... ) __attribute__ (( format(printf, 2, 3), __nothrow__, __leaf__, __noreturn__ )) {
    153     va_list args;
    154     va_start( args, fmt );
    155     vfprintf( stderr, fmt, args );
    156     va_end( args );
    157         __cabi_libc.exit( status );
    158 }
    159 
    160 void abort( const char fmt[], ... ) __attribute__ (( format(printf, 1, 2), __nothrow__, __leaf__, __noreturn__ )) {
    161         void * kernel_data = kernel_abort();                    // must be done here to lock down kernel
    162         int len;
    163 
    164         abort_lastframe = kernel_abort_lastframe();
    165         len = snprintf( abort_text, abort_text_size, "Cforall Runtime error (UNIX pid:%ld) ", (long int)getpid() ); // use UNIX pid (versus getPid)
    166         __cfaabi_dbg_bits_write( abort_text, len );
    167 
    168         if ( fmt ) {
    169                 va_list args;
    170                 va_start( args, fmt );
    171 
    172                 len = vsnprintf( abort_text, abort_text_size, fmt, args );
    173                 va_end( args );
     139extern "C" {
     140        void abortf( const char fmt[], ... ) __attribute__ ((__nothrow__, __leaf__, __noreturn__)) {
     141                void * kernel_data = kernel_abort();                    // must be done here to lock down kernel
     142                int len;
     143
     144                abort_lastframe = kernel_abort_lastframe();
     145                len = snprintf( abort_text, abort_text_size, "Cforall Runtime error (UNIX pid:%ld) ", (long int)getpid() ); // use UNIX pid (versus getPid)
    174146                __cfaabi_dbg_bits_write( abort_text, len );
    175147
    176                 if ( fmt[strlen( fmt ) - 1] != '\n' ) {         // add optional newline if missing at the end of the format text
    177                         __cfaabi_dbg_bits_write( "\n", 1 );
    178                 }
    179         }
    180 
    181         kernel_abort_msg( kernel_data, abort_text, abort_text_size );
    182         __cabi_libc.abort();
     148                if ( fmt ) {
     149                        va_list args;
     150                        va_start( args, fmt );
     151
     152                        len = vsnprintf( abort_text, abort_text_size, fmt, args );
     153                        va_end( args );
     154                        __cfaabi_dbg_bits_write( abort_text, len );
     155
     156                        if ( fmt[strlen( fmt ) - 1] != '\n' ) {         // add optional newline if missing at the end of the format text
     157                                __cfaabi_dbg_bits_write( "\n", 1 );
     158                        }
     159                }
     160
     161                kernel_abort_msg( kernel_data, abort_text, abort_text_size );
     162                libc_abort();
     163        }
    183164}
    184165
     
    234215
    235216void sigHandler_segv( __CFA_SIGPARMS__ ) {
    236         abort( "Addressing invalid memory at location %p\n"
     217        abortf( "Attempt to address location %p\n"
    237218                        "Possible cause is reading outside the address space or writing to a protected area within the address space with an invalid pointer or subscript.\n",
    238219                        sfp->si_addr );
     
    240221
    241222void sigHandler_ill( __CFA_SIGPARMS__ ) {
    242         abort( "Executing illegal instruction at location %p.\n"
     223        abortf( "Attempt to execute code at location %p.\n"
    243224                        "Possible cause is stack corruption.\n",
    244225                        sfp->si_addr );
     
    248229        const char * msg;
    249230
    250         choose( sfp->si_code ) {
    251           case FPE_INTDIV, FPE_FLTDIV: msg = "divide by zero";
    252           case FPE_FLTOVF: msg = "overflow";
    253           case FPE_FLTUND: msg = "underflow";
    254           case FPE_FLTRES: msg = "inexact result";
    255           case FPE_FLTINV: msg = "invalid operation";
     231        switch ( sfp->si_code ) {
     232          case FPE_INTDIV:
     233          case FPE_FLTDIV: msg = "divide by zero"; break;
     234          case FPE_FLTOVF: msg = "overflow"; break;
     235          case FPE_FLTUND: msg = "underflow"; break;
     236          case FPE_FLTRES: msg = "inexact result"; break;
     237          case FPE_FLTINV: msg = "invalid operation"; break;
    256238          default: msg = "unknown";
    257         } // choose
    258         abort( "Computation error %s at location %p.\n", msg, sfp->si_addr );
     239        } // switch
     240        abortf( "Floating point error.\n"
     241                        "Cause is %s.\n", msg );
    259242}
    260243
Note: See TracChangeset for help on using the changeset viewer.