You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
357 lines
15 KiB
357 lines
15 KiB
//Copyright 2020 Siemens Digital Industries Software
|
|
//==================================================
|
|
//Copyright $2010.
|
|
//Siemens Product Lifecycle Management Software Inc.
|
|
//All Rights Reserved.
|
|
//==================================================
|
|
//Copyright 2020 Siemens Digital Industries Software
|
|
|
|
/**
|
|
@file ErrorStoreBase.hxx
|
|
|
|
This file contains the declarations of the ErrorStoreBase class in module libbase_utils.
|
|
ErrorStoreBase is the keeper of error codes raised by ERROR_raise() in libsyss.
|
|
ErrorStoreBase is a singleton, which can be accessed through the static function Teamcenter::ErrorStoreBase::getInstance().
|
|
The system (Teamcenter) needs to do the following in order to fully initialise ErrorStore functionality:
|
|
<ol>
|
|
<li>implement a decoder function that translates an error code into an internationalized error message (something like EMH_get_err_string())
|
|
<li>this decoder function must set its return value and success/failure flag via @c libbase_utils Teamcenter::ErrorStoreBase::set_error_string()
|
|
<li>register this decoder function once per session via @c libbase_utils Teamcenter::ErrorStoreBase::set_decoder_function(...) (e.g. in ERROR_store_init_table())
|
|
<li>register this decoder function for various error code ranges via @c libsyss ERROR_register_decoder_fn() (e.g. in ERROR_store_init_table())
|
|
</ol>
|
|
*/
|
|
|
|
#ifndef BASE_UTILS_ERROR_STORE_HXX
|
|
#define BASE_UTILS_ERROR_STORE_HXX
|
|
|
|
#include <set>
|
|
#include <stdio.h>
|
|
#include <stdlib.h>
|
|
#include <string>
|
|
#include <unidefs.h>
|
|
#include <vector>
|
|
|
|
#include <base_utils/libbase_utils_exports.h>
|
|
|
|
namespace Teamcenter
|
|
{
|
|
|
|
class BASE_UTILS_API ErrorStoreBase
|
|
{
|
|
public:
|
|
typedef int ERROR_severity_t;
|
|
typedef char * (*ERROR_decode_function_t) (int ifail, void * data);
|
|
typedef void (*ERROR_decode_free_function_t) (void * decoded_text);
|
|
typedef void (*ERROR_journal_comment_function_t)( const char * );
|
|
typedef void (*ERROR_journal_flush_function_t)( void );
|
|
|
|
static const ERROR_severity_t ERRORSTORE_SEVERITY_INFORMATION = 1; // EMH_severity_information
|
|
static const ERROR_severity_t ERRORSTORE_SEVERITY_WARNING = 2; // EMH_severity_warning
|
|
static const ERROR_severity_t ERRORSTORE_SEVERITY_ERROR = 3; // EMH_severity_error
|
|
static const ERROR_severity_t ERRORSTORE_SEVERITY_USER_ERROR = 4; // EMH_severity_user_error
|
|
static const ERROR_severity_t ERRORSTORE_SEVERITY_PROTECT_MARK = 100;
|
|
|
|
static ErrorStoreBase & getInstance();
|
|
|
|
/**
|
|
Returns the top-most error message from the error stack.
|
|
<br/>If the error stack is empty, return "".
|
|
*/
|
|
static std::string getTopErrorMessage( int presumed_top_ifail );
|
|
|
|
/**
|
|
Adds the given error to the store.
|
|
|
|
@note The parameters @p s1 to @p s7 will be substituted into the parameterized error message
|
|
to form the localized error message.
|
|
<br/>Parameters show as @c "%n$" in the parameterized error message, where @c n is the n-th argument to substitute.
|
|
|
|
@note If @p ifail is zero, the first string is taken as the total error message.
|
|
|
|
@returns The provided @p ifail.
|
|
*/
|
|
int store( ERROR_severity_t severity, int ifail,
|
|
const char *s1=0, const char *s2=0, const char *s3=0, const char *s4=0, const char *s5=0, const char *s6=0, const char *s7=0);
|
|
|
|
/**
|
|
Clears the error stack and adds the given error.
|
|
|
|
@note It might complain indignantly if the error store was not empty anyway (i.e. you ignored an error).
|
|
|
|
@returns The provided @p ifail.
|
|
*/
|
|
int store_initial_error( ERROR_severity_t severity, int ifail,
|
|
const char *s1=0, const char *s2=0, const char *s3=0, const char *s4=0, const char *s5=0, const char *s6=0, const char *s7=0);
|
|
|
|
/**
|
|
Stores the given error as the last-but-one error.
|
|
|
|
@returns The provided @p ifail.
|
|
*/
|
|
int store_before_latest( ERROR_severity_t severity, int ifail,
|
|
const char *s1=0, const char *s2=0, const char *s3=0, const char *s4=0, const char *s5=0, const char *s6=0, const char *s7=0);
|
|
|
|
/**
|
|
Stores the given error, but replaces its normal error message with a provided message.
|
|
|
|
@note It might complain indignantly if the error store was not empty anyway (i.e. you ignored an error).
|
|
|
|
@returns The provided @p ifail.
|
|
*/
|
|
int store_substituted( ERROR_severity_t severity, int ifail, const char *s);
|
|
|
|
/**
|
|
Forgets the last-stored error.
|
|
*/
|
|
void forget_last_error (int ifail_to_forget);
|
|
|
|
/**
|
|
Forgets all errors on the error stack.
|
|
*/
|
|
void clear();
|
|
|
|
/**
|
|
Forgets all errors with a given severity.
|
|
*/
|
|
void clear(
|
|
ERROR_severity_t level /**<(I) The severity level. */
|
|
);
|
|
|
|
/**
|
|
Forgets the first error with the given number found starting from the top of the error stack.
|
|
*/
|
|
void clear_topmost_ifail( int ifail_to_be_cleared );
|
|
|
|
/**
|
|
Protects the current errors from any call to call to ErrorStoreBase::clear (either method).
|
|
*/
|
|
void set_protect_mark( int * mark, const char * fileName, int lineNumber );
|
|
|
|
/**
|
|
Removes the protection mark set through ErrorStoreBase::set_protect_mark.
|
|
*/
|
|
void clear_protect_mark( int mark );
|
|
|
|
/**
|
|
Watches for an error of the given value to be added to the error stack.
|
|
<br/>If such an error is added, the call stack is printed in the syslog file.
|
|
*/
|
|
void catch_this_ifail(
|
|
int ifail /**< (I) The ifail to watch for.
|
|
<br/>If the value is a multiple of @c 1000 (i.e. an error base),
|
|
all errors from this error base and @c 999 are watched.
|
|
<br/>If the value is @c -42, all the errors are being watched. */
|
|
);
|
|
|
|
/**
|
|
Returns the error currently being watched.
|
|
*/
|
|
int ask_catching_ifail( void ) const;
|
|
|
|
/**
|
|
A potential ERROR_internal call
|
|
*/
|
|
void assert_empty( void ) const;
|
|
|
|
/**
|
|
Returns the last error added to the error stack.
|
|
*/
|
|
int ask_last_ifail( void ) const;
|
|
|
|
/**
|
|
Retrieves the translated error message corresponding to the last error.
|
|
|
|
@returns A static pointer valid until the next ERROR store operation.
|
|
<br/>A pointer to an empty string will be returned if
|
|
the error stack is empty or the last entry is a protect mark.
|
|
*/
|
|
const char * ask_last_message( int presumed_top_ifail ) const;
|
|
|
|
/**
|
|
Retrieves all stored errors.
|
|
|
|
@returns Static pointers that are valid until the next ERROR store operation
|
|
<br/>Messages are in historical order (message zero is the oldest).
|
|
<br/>Tracebacks will only be set if a) it is non-null and b) CHECKING is on
|
|
*/
|
|
void ask( int * count, const ERROR_severity_t ** severities, const int ** ifails, const char *const ** messages, const char *const ** tracebacks = 0) const;
|
|
|
|
/**
|
|
Checks through the error stack down to the top protect mark, if a given error is in the error stack.
|
|
|
|
@returns @c true if this particular error is in the error stack.
|
|
*/
|
|
logical ask_had_error( int ifail ) const;
|
|
|
|
/**
|
|
Checks through the error stack down to the top protect mark, if a given error (of severity warning) is in the error stack.
|
|
|
|
@return true if found.
|
|
*/
|
|
logical ask_had_warning() const;
|
|
|
|
/**
|
|
Prints the error store.
|
|
*/
|
|
void print( FILE *fp = 0 ) const;
|
|
|
|
/**
|
|
Returns a mini-traceback that is SM allocated (@c UGII_CHECKING_LEVEL must be set to 2).
|
|
*/
|
|
char* traceback_as_string() const;
|
|
|
|
/**
|
|
Function to provide a string giving the interesting bits of a traceback.
|
|
Used by the TC_USAGE tool.
|
|
@param ignore_first_n The number of entries in the stack trace to ignore.
|
|
|
|
@returns The SM_allocated string for writing to the TC_USAGE table.
|
|
*/
|
|
char * traceback_as_string_for_usage (
|
|
int ignore_first_n /**< (I) The number of rows in the traceback to skip before gathering the stack trace information. */
|
|
);
|
|
|
|
/**
|
|
The inital error is stored the first time ERROR_raise is called since the
|
|
last call to clear_initial_traceback
|
|
the returned integer was the failure code, if non-zero then it may be interesting to ask_initial_traceback()
|
|
*/
|
|
static int ask_initial_error();
|
|
|
|
/**
|
|
The initial trace back is stored the first time ERROR_raise is called until the last call to ErrorStoreBase::clear_initial_traceback.
|
|
|
|
@returns The first error raised since the last call ot ErrorStoreBase::clear_initial_traceback
|
|
<br/>If it is non-zero, the traceback string may be of interest.
|
|
*/
|
|
static int ask_initial_traceback( const char *separator, /**< (I) The separator used in @p traceback in between different errors. */
|
|
char ** traceback /**< (OF) The traceback information. */
|
|
);
|
|
|
|
/**
|
|
The inital trace back is stored the first time ERROR_raise is called since the
|
|
last call to clear_initial_traceback
|
|
*/
|
|
static void clear_initial_traceback();
|
|
|
|
/**
|
|
A check to allow us to be confident that ERROR_decode did or did not use
|
|
the decode function registered with ERROR_register_decoder_fn.
|
|
<br/>Functions registered with ERROR_register_decoder_fn should call ErrorStoreBase::set_last_decoded_error_string so to:
|
|
<ol>
|
|
<li>Enable ErrorStorebase to use the right function to free memory
|
|
<li>Enable ErrorStorebase to determine whether ERROR_decode did or did not use the registered function
|
|
</ol>
|
|
|
|
@note Refer to ErrorStoreBase::ask_last_decoded_error_string
|
|
*/
|
|
void set_last_decoded_error_string( const char * decoded_error_string, /**< (I) The decoded I18n error message, e.g. "CXPOM_wrong_class: given %1$ when expecting %2$"
|
|
or "CXPOM_wrong_class: %1$ vorhanden, wenn %2$ erwartet". */
|
|
logical translation_found, /**< (I) Whether or not the message represents a successfully internationalized error message,
|
|
e.g. use "false" for the fallback error message "error_7023". */
|
|
ERROR_decode_free_function_t remover /**< (I) The function to use in order to free the memory pointed to by 'decoded_error_string'. */
|
|
);
|
|
|
|
/**
|
|
Allows to find out whether ERROR_decode did or did not use
|
|
the decode function registered with ERROR_register_decoder_fn.
|
|
<br/>The function registered with ERROR_register_decoder_fn should call ErrorStoreBase::set_last_decoded_error_string so to enable ErrorStorebase to:
|
|
<ol>
|
|
<li>Use the right function to free memory
|
|
<li>Determine whether ERROR_decode did or did not use the registered function
|
|
</ol>
|
|
The function returns NULL if the decoded error message (e.g. "CXPOM_wrong_class: given %1$ when expecting %2$")
|
|
has already been substituted (e.g. "CXPOM_wrong_class: given WorkspaceObject when expecting Item").
|
|
|
|
@note Refer to ErrorStoreBase::set_last_decoded_error_string
|
|
*/
|
|
void ask_last_decoded_error_string( const char ** error_string, /**< (O) The last known decoded error message whose placeholder have not yet been substituted,
|
|
something like "CXPOM_wrong_class: given %1$ when expecting %2$" or "CXPOM_wrong_class: %1$ vorhanden, wenn %2$ erwartet". */
|
|
logical * translation_found, /**< (O) Whether or not the message represents a successfully internationalized error message,
|
|
e.g. "false" for the fallback error message "error_7023". */
|
|
ERROR_decode_free_function_t * remover /**< (O) The function to use in order to free the memory pointed to by 'decoded_error_string'. */
|
|
) const;
|
|
|
|
/**
|
|
Returns the error decoding function, which is the function used to decode an error number into its associated error string (with placeholders for I18n).
|
|
*/
|
|
ERROR_decode_function_t ask_decoder_function() const;
|
|
|
|
/**
|
|
Sets the error decoding function, which is the function used to decode an error number into its associated error string (with placeholders for I18n).
|
|
*/
|
|
void set_decoder_function( ERROR_decode_function_t decode_function );
|
|
|
|
/**
|
|
Registers specific error codes that should trigger the following call:
|
|
@code
|
|
ERROR_note( ERROR_line, "internal programming error %d", ifail );
|
|
@endcode
|
|
*/
|
|
void register_internal_error( int ifail );
|
|
|
|
/**
|
|
Unregisters the error codes (i.e. stop triggering a call to ERROR_note).
|
|
*/
|
|
void unregister_internal_error( int ifail );
|
|
|
|
/**
|
|
Returns the registered error codes (i.e. the ones that trigger a call to ERROR_note).
|
|
*/
|
|
const std::set< int > & ask_registered_internal_errors() const;
|
|
|
|
/**
|
|
Sets the journal comment function, which is the function that records a comment into the journal file.
|
|
*/
|
|
void set_journal_comment_function( ERROR_journal_comment_function_t journal_comment_function );
|
|
|
|
/**
|
|
Sets the journal flush function, which is the function that flushes the journal.
|
|
*/
|
|
void set_journal_flush_function( ERROR_journal_flush_function_t journal_flush_function );
|
|
|
|
/**
|
|
Frees the memory associated with an error message returned from ERROR_decode.
|
|
*/
|
|
void free_error_decode_message( const char *error_decode_message );
|
|
|
|
private:
|
|
ErrorStoreBase();
|
|
virtual ~ErrorStoreBase();
|
|
|
|
int * ifail_store;
|
|
const char ** message_store;
|
|
ERROR_severity_t * severity_store;
|
|
const char ** substitutions_store;
|
|
const char ** tracebacks_store;
|
|
|
|
std::set< int > registered_internal_errors; // specific internal error codes that should trigger a ERROR_note( ERROR_line, "internal programming error %d", ifail );
|
|
|
|
int store_size;
|
|
int store_allocated;
|
|
int ifail_to_catch;
|
|
|
|
logical record_error_protect_calls;
|
|
|
|
ERROR_decode_function_t decode_function;
|
|
const char * decoded_error_string;
|
|
logical decoded_error_translated;
|
|
ERROR_decode_free_function_t decoded_error_remover;
|
|
ERROR_journal_comment_function_t journal_comment_function;
|
|
ERROR_journal_flush_function_t journal_flush_function;
|
|
|
|
void increment_store_size();
|
|
void delete_top_error();
|
|
void delete_given_error( int where_ );
|
|
void internal_store_error( ERROR_severity_t severity, int ifail, const char *s1, const char *s2, const char *s3, const char *s4, const char *s5, const char *s6, const char *s7);
|
|
void record_error_protect_call( int mark, const char * fileName, int lineNumber );
|
|
void ensure_errors_translated();
|
|
void print_error_n( FILE * fp, int entry, int max_message_length ) const;
|
|
};
|
|
|
|
} // namespace Teamcenter
|
|
|
|
|
|
#include <base_utils/libbase_utils_undef.h>
|
|
#endif // BASE_UTILS_ERROR_STORE_HXX
|