Next Previous Contents

3. Error Handling

Many of the S-Lang functions return 0 upon success or -1 to signify failure. Other functions may return NULL to indicate failure. In addition, upon failure, many will set the error state of the library to a value that indicates the nature of the error. The value of this state may be queried via the SLang_get_error function. This function will return 0 to indicate that there is no error, or a non-zero value such as one of the following constants:

     SL_Any_Error                      SL_Index_Error
     SL_OS_Error                       SL_Parse_Error
     SL_Malloc_Error                   SL_Syntax_Error
     SL_IO_Error                       SL_DuplicateDefinition_Error
     SL_Write_Error                    SL_UndefinedName_Error
     SL_Read_Error                     SL_Usage_Error
     SL_Open_Error                     SL_Application_Error
     SL_RunTime_Error                  SL_Internal_Error
     SL_InvalidParm_Error              SL_NotImplemented_Error
     SL_TypeMismatch_Error             SL_LimitExceeded_Error
     SL_UserBreak_Error                SL_Forbidden_Error
     SL_Stack_Error                    SL_Math_Error
     SL_StackOverflow_Error            SL_DivideByZero_Error
     SL_StackUnderflow_Error           SL_ArithOverflow_Error
     SL_ReadOnly_Error                 SL_ArithUnderflow_Error
     SL_VariableUninitialized_Error    SL_Domain_Error
     SL_NumArgs_Error                  SL_Data_Error
     SL_Unknown_Error                  SL_Unicode_Error
     SL_Import_Error                   SL_InvalidUTF8_Error
For example, if a function tries to allocate memory but fails, then SLang_get_error will return SL_Malloc_Error.

If the application makes use of the interpreter, then it is important that application-specific functions called from the interpreter set the error state of the library in order for exception handling to work. This may be accomplished using the SLang_set_error function, e.g.,

     if (NULL == (fp = fopen (file, "r")))
       SLang_set_error (SL_Open_Error);

Often it is desirable to give error message that contains more information about the error. The SLang_verror function may be used for this purpose:

     if (NULL == (fp = fopen (file, "r")))
       SLang_verror (SL_Open_Error, "Failed to open %s: errno=%d",
                     file, errno);
By default, SLang_verror will write the error message to stderr. For applications that make use of the SLsmg routines it is probably better for the error message to be printed to a specific area of the display. The SLang_Error_Hook variable may be used to redirect error messages to an application defined function, e.g.,
     static void write_error (char *err)
     {
        SLsmg_gotorc (0, 0);
        SLsmg_set_color (ERROR_COLOR);
        SLsmg_write_string (err);
     }
     int main (int argc, char **argv)
     {
        /* Redirect error messages to write_error */
        SLang_Error_Hook = write_error;
              .
              .
     }

Under extremely rare circumstances the library will call the C exit function causing the application to exit. This will happen if the SLtt_get_terminfo is called but the terminal is not sufficiently powerful. If this behavior is undesirable, then another function exists (SLtt_initialize) that returns an error code. The other times the library will exit are when the interpreter is called upon to do something but has not been properly initialized by the application. Such a condition is regarded as misuse of the libary and should be caught by routine testing of the application during development. In any case, when the library does call the exit function, it will call an application-defined exit hook specified by the SLang_Exit_Error_Hook variable:

     static int exit_error_hook (char *fmt, va_list ap)
     {
        fprintf (stderr, "Fatal Error.  Reason:");
        vfprintf (stderr, fmt, va_list);
     }
     int main (int argc, char **argv)
     {
        SLang_Exit_Error_Hook = exit_error_hook;
          .
          .
     }
The idea is that the hook can be used to perform some cleanup, free resources, and other tasks that the application needs to do for a clean exit.


Next Previous Contents