_matherr -- Handle Math Function Error

SYNOPSIS

 #include <lcmath.h>

 int _matherr(struct exception *x);
 

DESCRIPTION

_matherr is called whenever one of the other math functions detects an error. Upon entry, it receives an exception block that describes the error in detail. This structure is defined in <lcmath.h>:
 struct exception {
    int type;       /* error type                    */
    char *name;     /* name of function having error */
    double arg1;    /* first argument                */
    double arg2;    /* second argument               */
    double retval;  /* proposed return value         */
 };
 

The error type names defined in <lcmath.h> are


   Error Type              Definition

    DOMAIN                  domain error

    SING                    singularity

    OVERFLOW                overflow

    UNDERFLOW               underflow

    TLOSS                   total loss of significance

    PLOSS                   partial loss of significance
 

RETURN VALUE

If _matherr returns 0, a diagnostic message is written to the standard error file (stderr). If _matherr returns a nonzero value, the diagnostic message is suppressed, and the calling function is forced to accept a new value from retval.

PORTABILITY

Traditional UNIX C compilers support the functionality of _matherr using the name matherr. Unfortunately, using the name matherr conflicts with the ANSI Standard. However, the header file lcmath.h contains the following macro:

 #define matherr _matherr
 
If you include this header file, use the name that is compatible with traditional UNIX C compilers.

IMPLEMENTATION

The standard version of _matherr supplied in the library places the appropriate error number into the external integer errno and returns 0. When _matherr is called, the function that detected the error places its proposed return value into the exception structure. The 0 return code indicates that the return value should be used.

Supply your own version of _matherr if desired. On particular errors, it may be desirable to cause the function detecting the error to return a value other than its usual default. You can accomplish this by storing a new return value in retval of the exception structure and then returning a nonzero value from _matherr, which forces the function to pick up the new value from the exception structure. If a nonzero value is returned, a diagnostic message is not printed for the error.

EXAMPLE

  #include <lcmath.h>
  #include <lcio.h>
  #include <lclib.h>

     /* user status flags */
  #define ERROR_OK            9000
  #define ERROR_WARNING       9001
  #define ERROR_SEVERE        9002

     /* global status flag */
  int status;

     /* user-defined math status handler */
  int _matherr(struct exception *err)
  {
     err->retval = -1;

        /* Check to see if an error occurred */
        /* in the call to sqrt.              */
     if (strcmp(err->name, "sqrt") == 0)
        status = ERROR_SEVERE;

        /* Check to see if an error occurred */
        /* in the call to log or log10.      */
     else if (strncmp(err->name, "log", 3) == 0)
        status = ERROR_WARNING;
     else status = ERROR_OK;

     return(1);
  }

  main()
  {
     double x, y;

     while (feof(stdin) == 0) {

           /* Read data and echo it. */
        scanf("%f", &x);
        printf("necho: x = %fn", x);
        y = cosh(x);

           /* If no unexpected error occurred, print result. */
        if (warning() == 0)
           printf("result = %fn", y);
        y = log10(x);

           /* If no unexpected error occurred, print result. */
        if (warning() == 0)
           printf("result = %fn", y);
        y = sqrt(x);

           /* If no unexpected error occurred, print result. */
        if (warning() == 0)
           printf("result = %fn", y);
     }  /* End while loop. */

     return(0);
  }

  int warning(void)
  {
     if (status == ERROR_SEVERE) {
        printf("A severe error occurred. status condition = %d"
               " ***All processing is terminated***n", status);
        exit(EXIT_FAILURE);
     }
     else if (status == ERROR_WARNING) {
        puts("An error occurred; processing will continue.");
        status = ERROR_OK;
        return(1);
     }

     status = ERROR_OK;
     return(0);
  }

 

RELATED FUNCTIONS

quiet

SEE ALSO

Mathematical Functions

Copyright (c) 1998 SAS Institute Inc. Cary, NC, USA. All rights reserved.