home *** CD-ROM | disk | FTP | other *** search
/ Photo CD Demo 1 / Demo.bin / hdf / unix / hdf3_2r2 / src / herr.c < prev    next >
Encoding:
C/C++ Source or Header  |  1992-10-29  |  7.9 KB  |  298 lines

  1. /***************************************************************************
  2. *
  3. *
  4. *                         NCSA HDF version 3.2r2
  5. *                            October 30, 1992
  6. *
  7. * NCSA HDF Version 3.2 source code and documentation are in the public
  8. * domain.  Specifically, we give to the public domain all rights for future
  9. * licensing of the source code, all resale rights, and all publishing rights.
  10. *
  11. * We ask, but do not require, that the following message be included in all
  12. * derived works:
  13. *
  14. * Portions developed at the National Center for Supercomputing Applications at
  15. * the University of Illinois at Urbana-Champaign, in collaboration with the
  16. * Information Technology Institute of Singapore.
  17. *
  18. * THE UNIVERSITY OF ILLINOIS GIVES NO WARRANTY, EXPRESSED OR IMPLIED, FOR THE
  19. * SOFTWARE AND/OR DOCUMENTATION PROVIDED, INCLUDING, WITHOUT LIMITATION,
  20. * WARRANTY OF MERCHANTABILITY AND WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE
  21. *
  22. ****************************************************************************
  23. */
  24.  
  25. #ifdef RCSID
  26. static char RcsId[] = "@(#)$Revision: 1.1 $";
  27. #endif
  28. /*
  29. $Header: /hdf/hdf/v3.2r2/src/RCS/herr.c,v 1.1 1992/08/25 21:40:44 koziol beta koziol $
  30.  
  31. $Log: herr.c,v $
  32.  * Revision 1.1  1992/08/25  21:40:44  koziol
  33.  * Initial revision
  34.  *
  35. */
  36. /*LINTLIBRARY*/
  37. /*+ herr.c
  38. *** error routines
  39. +*/
  40.  
  41. #define _H_ERR_MASTER_
  42.  
  43. #include "hdf.h"
  44. #include "herr.h"
  45.  
  46. /*
  47. ** Include files for variable argument processing for HEreport
  48. */
  49. #if defined PROTOTYPE
  50. #include <stdarg.h>
  51. #else
  52. #include <varargs.h>
  53. #endif
  54.  
  55. /* We use a stack to hold the errors plus we keep track of the function,
  56.    file and line where the error occurs.*/
  57.  
  58. /* the strcuture of the error stack element */
  59.  
  60. typedef struct error_t {
  61.     int16 error_code;          /* Error number */
  62.     char *function_name;       /* function where error occur */
  63.     char *file_name;           /* file where error occur */
  64.     intn line;                 /* line in file where error occurs */
  65.     intn system;               /* bool for system or HDF error */
  66.     char *desc;                /* optional supplied description */
  67. } error_t;
  68.  
  69. /* error_stack is the error stack.  error_top is the stack top pointer, and points to
  70.    the next available slot on the stack */
  71.  
  72. #ifndef ERR_STACK_SZ
  73. #   define ERR_STACK_SZ 10
  74. #endif
  75.  
  76. /* max size of a stored error description */
  77. #ifndef ERR_STRING_SIZE
  78. #   define ERR_STRING_SIZE 512
  79. #endif
  80.  
  81. /* pointer to the structure to hold error messages */
  82. PRIVATE error_t *error_stack = NULL;
  83.  
  84.  
  85. /* always points to the next available slot; the last error record is in slot (top-1) */
  86. int32 error_top = 0;
  87.  
  88. #ifndef DEFAULT_MESG
  89. #   define DEFAULT_MESG "Unknown error"
  90. #endif
  91.  
  92. /* size of error message table */
  93.  
  94. #define ERRMESG_SZ (sizeof(error_messages) / sizeof(error_messages[0]))
  95.  
  96. /*- HEstring
  97. *** returns the error message associated with error_code, uses a
  98. *** linear search but efficiency should not be a problem here
  99. -*/
  100. #ifdef PROTOTYPE
  101. char *HEstring(int16 error_code)
  102. #else
  103. char *HEstring(error_code)
  104.     int16 error_code;
  105. #endif
  106. {
  107.     int i;                     /* temp int index */
  108.  
  109.     /* look for the error_code in error message table */
  110.  
  111.     for (i = 0; i < ERRMESG_SZ; i++)
  112.        if (error_messages[i].error_code == error_code)
  113.            return error_messages[i].str;
  114.  
  115.     /* otherwise, return default message */
  116.  
  117.     return DEFAULT_MESG;
  118. }
  119.  
  120. #if 0 /* macro-izing to save time cjh 8-may-92 */
  121. /*- HEclear
  122. *** clears the error stack
  123. -*/
  124. #ifdef PROTOTYPE
  125. VOID HEclear(void)
  126. #else
  127. VOID HEclear()
  128. #endif
  129. {
  130.     /* error_top == 0 means no error in stack */
  131.  
  132.     error_top = 0;
  133. }
  134. #endif
  135.  
  136. /*- HEpush
  137. *** push a new error onto stack.  If stack is full, error is ignored.
  138. *** assumes that the character strings (function_name and file_name) referred
  139. ***  are in some semi-permanent storage, so it just saves the pointer to
  140. ***  the strings.
  141. *** blank out the description field so that a description is reported
  142. ***  only if REreport is called
  143. ***
  144. -*/
  145. #ifdef PROTOTYPE
  146. VOID HEpush(int16 error_code, char *function_name, char *file_name, int line)
  147. #else
  148. VOID HEpush(error_code, function_name, file_name, line)
  149.     int16  error_code;           /* internal number of the error */
  150.     char   *function_name;       /* name of function that error occurred */
  151.     char   *file_name;           /* name of file that error occurred */
  152.     int    line;                 /* line number in file that error occurred */
  153. #endif
  154. {
  155.     int i;
  156.  
  157.     /* if the stack is not allocated, then do it */
  158.  
  159.     if (!error_stack) {
  160.        error_stack =(error_t *)HDgetspace((uint32)sizeof(error_t)*ERR_STACK_SZ);
  161.        if (!error_stack) {
  162.            puts("HEpush cannot allocate space.  Unable to continue!!");
  163.            exit(8);
  164.        }
  165.        for(i = 0; i < ERR_STACK_SZ; i++)
  166.         error_stack[i].desc = NULL;
  167.     }
  168.  
  169.     /* if stack is full, discard error */
  170.     /* otherwise, push error details onto stack */
  171.  
  172.     if (error_top < ERR_STACK_SZ)  {
  173.        error_stack[error_top].function_name = function_name;
  174.        error_stack[error_top].file_name = file_name;
  175.        error_stack[error_top].line = line;
  176.        error_stack[error_top].error_code = error_code;
  177.        if(error_stack[error_top].desc) {
  178.         HDfreespace(error_stack[error_top].desc);
  179.         error_stack[error_top].desc = NULL;
  180.        }
  181.        error_top++;
  182.     }
  183. }
  184.  
  185.  
  186. /* ====================================================================== */
  187. /* Write a nicely formatted string to a log file */
  188. #if defined PROTOTYPE
  189. VOID HEreport(char *format, ...) {
  190.   va_list arg_ptr;
  191.   char *tmp;
  192.   char *FUNC="HEreport";   /* name of function if HIalloc fails */
  193.  
  194.   va_start(arg_ptr, format);
  195.  
  196.   if((error_top < ERR_STACK_SZ+1) && (error_top > 0)){
  197.     tmp = (char *) HDgetspace(ERR_STRING_SIZE);
  198.     if (!tmp) {
  199.       HERROR(DFE_NOSPACE);
  200.       return;
  201.     }
  202.     vsprintf(tmp, format, arg_ptr);
  203.     error_stack[error_top - 1].desc = tmp;
  204.   }
  205.   
  206.   va_end(arg_ptr);
  207.   return;
  208. }
  209. #else
  210. VOID HEreport(va_alist)
  211. va_dcl
  212. {
  213.   char *FUNC="HEreport";   /* name of function if HIalloc fails */
  214.   char *tmp;
  215.   char * format;
  216.   va_list arg_ptr;
  217.   
  218.   va_start(arg_ptr);
  219.  
  220.   format = va_arg(arg_ptr, char *);
  221.  
  222.   if((error_top < ERR_STACK_SZ+1) && (error_top > 0)){
  223.     tmp = (char *) HDgetspace(ERR_STRING_SIZE);
  224.     if (!tmp) {
  225.       HERROR(DFE_NOSPACE);
  226.       return;
  227.     }
  228.  
  229.  
  230.     vsprintf(tmp, format, arg_ptr);
  231.  
  232. /* can't do this w/o stdC <stdio.h>
  233. *
  234. * For example, on xongmao a sun4, stdio.h declares:
  235. *
  236. * extern char *sprintf();
  237. *
  238. *    count = vsprintf(tmp, format, arg_ptr);
  239. *
  240. *    if(count > ERR_STRING_SIZE) {
  241. *           printf("HEreport overwrote array. %d Unsafe to continue!!", count);
  242. *           exit(8);     
  243. *    }
  244. */
  245.     error_stack[error_top - 1].desc = tmp;
  246.  
  247.   }
  248.   
  249.   va_end(arg_ptr);
  250.   return;
  251. }
  252. #endif /* PROTOTYPE */
  253.  
  254.  
  255. /*- HEprint
  256. *** print a number of error, starting from the error_top of the stack
  257. -*/
  258. #ifdef PROTOTYPE
  259. VOID HEprint(FILE *stream, int32 print_levels)
  260. #else
  261. VOID HEprint(stream, print_levels)
  262.      FILE *stream;             /* stream to print to */
  263.      int32 print_levels;         /* levels to print */
  264. #endif
  265. {
  266.     if (print_levels == 0 || print_levels > error_top)
  267.        /* print all errors */
  268.        print_levels = error_top;
  269.  
  270.     /* print the errors starting from most recent */
  271.  
  272.     for (print_levels--; print_levels >= 0; print_levels--) {
  273.        fprintf(stream, "HDF error: <%s>\n\tDetected in %s() [%s line %d]\n",
  274.                HEstring(error_stack[print_levels].error_code),
  275.                error_stack[print_levels].function_name,
  276.                error_stack[print_levels].file_name,
  277.                error_stack[print_levels].line);
  278.        if(error_stack[print_levels].desc)
  279.         fprintf(stream, "\t%s\n", error_stack[print_levels].desc);
  280.      }
  281. }
  282.  
  283. /*- HEvalue
  284. *** return the nth most recent error
  285. -*/
  286. #ifdef PROTOTYPE
  287. int16 HEvalue(int32 level)
  288. #else
  289. int16 HEvalue(level)
  290.     int32 level;                 /* level of error code to return */
  291. #endif
  292. {
  293.     if (level > 0 && level <= error_top)
  294.        return error_stack[error_top - level].error_code;
  295.  
  296.     else return DFE_NONE;
  297. }
  298.