diff options
author | Werner Koch <[email protected]> | 2024-04-22 12:47:53 +0000 |
---|---|---|
committer | Werner Koch <[email protected]> | 2024-04-22 12:47:53 +0000 |
commit | 319a505623c197d06ca3e76f30691fe65a982d6f (patch) | |
tree | ca4dfdb7f76a0a389487dcdcd6e70913c72afe47 | |
parent | logging: Indent continuation lines of log_printhex. (diff) | |
download | libgpg-error-319a505623c197d06ca3e76f30691fe65a982d6f.tar.gz libgpg-error-319a505623c197d06ca3e76f30691fe65a982d6f.zip |
core: New function gpgrt_add_post_log_func.
* src/gpg-error.h.in (gpgrt_add_post_log_func): New.
* src/gpg-error.vers: Add new function
* src/gpg-error.def.in: Ditto.
* src/visibility.c (gpgrt_add_post_log_func): New.
* src/logging.c (struct post_log_func_item_s): New.
(post_log_func_list): New.
(_gpgrt_add_post_log_func): new.
(run_post_log_funcs): New.
(_gpgrt_logv_internal): Call for fatal and bug log levels.
--
This is required in case an application or library needs to do do some
quick cleanups after a log_fatal.
-rw-r--r-- | NEWS | 5 | ||||
-rw-r--r-- | src/gpg-error.def.in | 2 | ||||
-rw-r--r-- | src/gpg-error.h.in | 3 | ||||
-rw-r--r-- | src/gpg-error.vers | 2 | ||||
-rw-r--r-- | src/gpgrt-int.h | 1 | ||||
-rw-r--r-- | src/logging.c | 67 | ||||
-rw-r--r-- | src/visibility.c | 8 | ||||
-rw-r--r-- | src/visibility.h | 2 |
8 files changed, 88 insertions, 2 deletions
@@ -2,6 +2,11 @@ Noteworthy changes in version 1.49 (unreleased) [C35/A35/R_] ----------------------------------------------- + * Interface changes relative to the 1.48 release: + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + gpgrt_add_post_log_func NEW. + + Release-info: https://dev.gnupg.org/T7012 diff --git a/src/gpg-error.def.in b/src/gpg-error.def.in index 3bd18f7..eab681d 100644 --- a/src/gpg-error.def.in +++ b/src/gpg-error.def.in @@ -247,6 +247,6 @@ EXPORTS ;; gpgrt_close_all_fds @188 gpgrt_wipememory @189 - + gpgrt_add_post_log_func @190 ;; end of file with public symbols for Windows. diff --git a/src/gpg-error.h.in b/src/gpg-error.h.in index fcf4eb6..d00bf1b 100644 --- a/src/gpg-error.h.in +++ b/src/gpg-error.h.in @@ -995,11 +995,12 @@ enum gpgrt_log_levels }; -/* The next 4 functions are not thread-safe - call them early. */ +/* The next 5 functions are not thread-safe - call them early. */ void gpgrt_log_set_sink (const char *name, gpgrt_stream_t stream, int fd); void gpgrt_log_set_socket_dir_cb (const char *(*fnc)(void)); void gpgrt_log_set_pid_suffix_cb (int (*cb)(unsigned long *r_value)); void gpgrt_log_set_prefix (const char *text, unsigned int flags); +void gpgrt_add_post_log_func (void (*f)(int)); int gpgrt_get_errorcount (int clear); void gpgrt_inc_errorcount (void); diff --git a/src/gpg-error.vers b/src/gpg-error.vers index 78a0ae8..b095edf 100644 --- a/src/gpg-error.vers +++ b/src/gpg-error.vers @@ -211,6 +211,8 @@ GPG_ERROR_1.0 { gpgrt_wipememory; + gpgrt_add_post_log_func; + local: *; }; diff --git a/src/gpgrt-int.h b/src/gpgrt-int.h index 4ed64be..adddb26 100644 --- a/src/gpgrt-int.h +++ b/src/gpgrt-int.h @@ -537,6 +537,7 @@ void _gpgrt_log_set_sink (const char *name, estream_t stream, int fd); void _gpgrt_log_set_socket_dir_cb (const char *(*fnc)(void)); void _gpgrt_log_set_pid_suffix_cb (int (*cb)(unsigned long *r_value)); void _gpgrt_log_set_prefix (const char *text, unsigned int flags); +void _gpgrt_add_post_log_func (void (*f)(int)); const char *_gpgrt_log_get_prefix (unsigned int *flags); int _gpgrt_log_test_fd (int fd); int _gpgrt_log_get_fd (void); diff --git a/src/logging.c b/src/logging.c index 4dc0eba..4f52d80 100644 --- a/src/logging.c +++ b/src/logging.c @@ -101,6 +101,18 @@ static int force_prefixes; static int missing_lf; static int errorcount; +/* The list of registered functions to be called after logging. */ +struct post_log_func_item_s; +typedef struct post_log_func_item_s *post_log_func_item_t; +struct post_log_func_item_s +{ + post_log_func_item_t next; + void (*func) (int); +}; +static post_log_func_item_t post_log_func_list; + + + /* An object to convey data to the fmt_string_filter. */ struct fmt_string_filter_s @@ -655,6 +667,59 @@ _gpgrt_log_get_stream (void) } +/* Add a function F to the list of functions called after a log_fatal + * or log_bug right before terminating the process. If a function + * with that address has already been registered, it is not added a + * second time. */ +void +_gpgrt_add_post_log_func (void (*f)(int)) +{ + post_log_func_item_t item; + + for (item = post_log_func_list; item; item = item->next) + if (item->func == f) + return; /* Function has already been registered. */ + + /* We use a standard malloc here. */ + item = malloc (sizeof *item); + if (item) + { + item->func = f; + item->next = post_log_func_list; + post_log_func_list = item; + } + else + _gpgrt_log_fatal ("out of core in gpgrt_add_post_log_func\n"); +} + + +/* Run the post log function handlers. These are only called for + * fatal and bug errors and should be aware that the process will + * terminate. */ +static void +run_post_log_funcs (int level) +{ + static int running; /* Just to avoid recursive calls. */ + post_log_func_item_t next; + void (*f)(int); + + if (running) + return; + running = 1; + + while (post_log_func_list) + { + next = post_log_func_list->next; + f = post_log_func_list->func; + post_log_func_list->func = NULL; + post_log_func_list = next; + if (f) + f (level); + } +} + + + /* A filter used with the fprintf_sf function to sanitize the args for * "%s" format specifiers. */ static char * @@ -983,6 +1048,7 @@ _gpgrt_logv_internal (int level, int ignore_arg_ptr, const char *extrastring, { if (missing_lf) _gpgrt_putc_unlocked ('\n', logstream); + run_post_log_funcs (level); _gpgrt_funlockfile (logstream); exit (2); } @@ -990,6 +1056,7 @@ _gpgrt_logv_internal (int level, int ignore_arg_ptr, const char *extrastring, { if (missing_lf) _gpgrt_putc_unlocked ('\n', logstream ); + run_post_log_funcs (level); _gpgrt_funlockfile (logstream); /* Using backtrace requires a configure test and to pass * -rdynamic to gcc. Thus we do not enable it now. */ diff --git a/src/visibility.c b/src/visibility.c index 5ecef45..8c00168 100644 --- a/src/visibility.c +++ b/src/visibility.c @@ -961,6 +961,14 @@ gpgrt_log_get_stream (void) return _gpgrt_log_get_stream (); } + +void +gpgrt_add_post_log_func (void (*f)(int)) +{ + _gpgrt_add_post_log_func (f); +} + + void gpgrt_log (int level, const char *fmt, ...) { diff --git a/src/visibility.h b/src/visibility.h index 75aec0d..8f3bd8c 100644 --- a/src/visibility.h +++ b/src/visibility.h @@ -184,6 +184,7 @@ MARK_VISIBLE (gpgrt_log_get_prefix) MARK_VISIBLE (gpgrt_log_test_fd) MARK_VISIBLE (gpgrt_log_get_fd) MARK_VISIBLE (gpgrt_log_get_stream) +MARK_VISIBLE (gpgrt_add_post_log_func) MARK_VISIBLE (gpgrt_log) MARK_VISIBLE (gpgrt_logv) MARK_VISIBLE (gpgrt_logv_prefix) @@ -375,6 +376,7 @@ MARK_VISIBLE (gpgrt_absfnameconcat) #define gpgrt_log_test_fd _gpgrt_USE_UNDERSCORED_FUNCTION #define gpgrt_log_get_fd _gpgrt_USE_UNDERSCORED_FUNCTION #define gpgrt_log_get_stream _gpgrt_USE_UNDERSCORED_FUNCTION +#define gpgrt_add_post_log_func _gpgrt_USE_UNDERSCORED_FUNCTION #define gpgrt_log _gpgrt_USE_UNDERSCORED_FUNCTION #define gpgrt_logv _gpgrt_USE_UNDERSCORED_FUNCTION #define gpgrt_logv_prefix _gpgrt_USE_UNDERSCORED_FUNCTION |