X-Git-Url: https://git.exim.org/exim.git/blobdiff_plain/ee3c2fea18d0c940c2256c6bf041f546c703c375..bc3e80bcacbe4be437fe43a8babe2e4896837d95:/src/src/exim_dbutil.c diff --git a/src/src/exim_dbutil.c b/src/src/exim_dbutil.c index 2ae7ef44d..5f2e66417 100644 --- a/src/src/exim_dbutil.c +++ b/src/src/exim_dbutil.c @@ -3,7 +3,7 @@ *************************************************/ /* Copyright (c) University of Cambridge 1995 - 2018 */ -/* Copyright (c) The Exim Maintainers 2020 */ +/* Copyright (c) The Exim Maintainers 2020 - 2021 */ /* See the file NOTICE for conditions of use and distribution. */ @@ -17,11 +17,13 @@ maintaining Exim hints databases. In all cases, the first argument is the name of the spool directory. The second argument is the name of the database file. The available names are: - retry: retry delivery information - misc: miscellaneous hints data - wait-: message waiting information; is a transport name - callout: callout verification cache - tls: TLS session resumption cache + callout: callout verification cache + misc: miscellaneous hints data + ratelimit: record for ACL "ratelimit" condition + retry: etry delivery information + seen: imestamp records for ACL "seen" condition + tls: TLS session resumption cache + wait-: message waiting information; is a transport name There are a number of common subroutines, followed by three main programs, whose inclusion is controlled by -D on the compilation command. */ @@ -38,12 +40,15 @@ whose inclusion is controlled by -D on the compilation command. */ #define type_callout 4 #define type_ratelimit 5 #define type_tls 6 +#define type_seen 7 /* This is used by our cut-down dbfn_open(). */ uschar *spool_directory; +BOOL utc = FALSE; + /******************************************************************************/ /* dummies needed by Solaris build */ @@ -69,6 +74,13 @@ struct global_flags f; unsigned int log_selector[1]; uschar * queue_name; BOOL split_spool_directory; + + +/* These introduced by the taintwarn handling */ +#ifdef ALLOW_INSECURE_TAINTED_DATA +BOOL allow_insecure_tainted_data; +#endif + /******************************************************************************/ @@ -119,8 +131,8 @@ static void usage(uschar *name, uschar *options) { printf("Usage: exim_%s%s \n", name, options); -printf(" = retry | misc | wait- | callout | ratelimit | tls\n"); -exit(1); +printf(" = retry | misc | wait- | callout | ratelimit | tls | seen\n"); +exit(EXIT_FAILURE); } @@ -135,20 +147,38 @@ second of them to be sure it is a known database name. */ static int check_args(int argc, uschar **argv, uschar *name, uschar *options) { -if (argc == 3) +uschar * aname = argv[optind + 1]; +if (argc - optind == 2) { - if (Ustrcmp(argv[2], "retry") == 0) return type_retry; - if (Ustrcmp(argv[2], "misc") == 0) return type_misc; - if (Ustrncmp(argv[2], "wait-", 5) == 0) return type_wait; - if (Ustrcmp(argv[2], "callout") == 0) return type_callout; - if (Ustrcmp(argv[2], "ratelimit") == 0) return type_ratelimit; - if (Ustrcmp(argv[2], "tls") == 0) return type_tls; + if (Ustrcmp(aname, "retry") == 0) return type_retry; + if (Ustrcmp(aname, "misc") == 0) return type_misc; + if (Ustrncmp(aname, "wait-", 5) == 0) return type_wait; + if (Ustrcmp(aname, "callout") == 0) return type_callout; + if (Ustrcmp(aname, "ratelimit") == 0) return type_ratelimit; + if (Ustrcmp(aname, "tls") == 0) return type_tls; + if (Ustrcmp(aname, "seen") == 0) return type_seen; } usage(name, options); return -1; /* Never obeyed */ } +static void +options(int argc, uschar * argv[], uschar * name) +{ +int opt; + +opterr = 0; +while ((opt = getopt(argc, (char * const *)argv, "z")) != -1) + switch (opt) + { + case 'z': utc = TRUE; break; + default: usage(name, US" [-z]"); + } +} + + + /************************************************* * Handle attempts to write the log * @@ -189,7 +219,7 @@ static uschar time_buffer[sizeof("09-xxx-1999 hh:mm:ss ")]; uschar * print_time(time_t t) { -struct tm *tmstr = localtime(&t); +struct tm *tmstr = utc ? gmtime(&t) : localtime(&t); Ustrftime(time_buffer, sizeof(time_buffer), "%d-%b-%Y %H:%M:%S", tmstr); return time_buffer; } @@ -203,8 +233,8 @@ return time_buffer; uschar * print_cache(int value) { -return (value == ccache_accept)? US"accept" : - (value == ccache_reject)? US"reject" : +return value == ccache_accept ? US"accept" : + value == ccache_reject ? US"reject" : US"unknown"; } @@ -552,12 +582,15 @@ uschar **argv = USS cargv; uschar keybuffer[1024]; store_init(); +options(argc, argv, US"dumpdb"); /* Check the arguments, and open the database */ -dbdata_type = check_args(argc, argv, US"dumpdb", US""); -spool_directory = argv[1]; -if (!(dbm = dbfn_open(argv[2], O_RDONLY, &dbblock, FALSE, TRUE))) +dbdata_type = check_args(argc, argv, US"dumpdb", US" [-z]"); +argc -= optind; argv += optind; +spool_directory = argv[0]; + +if (!(dbm = dbfn_open(argv[1], O_RDONLY, &dbblock, FALSE, TRUE))) exit(1); /* Scan the file, formatting the information for each entry. Note @@ -574,6 +607,7 @@ for (uschar * key = dbfn_scan(dbm, TRUE, &cursor); dbdata_ratelimit *ratelimit; dbdata_ratelimit_unique *rate_unique; dbdata_tls_session *session; + dbdata_seen *seen; int count_bad = 0; int length; uschar *t; @@ -713,6 +747,11 @@ for (uschar * key = dbfn_scan(dbm, TRUE, &cursor); session = (dbdata_tls_session *)value; printf(" %s %.*s\n", keybuffer, length, session->session); break; + + case type_seen: + seen = (dbdata_seen *)value; + printf("%s\t%s\n", keybuffer, print_time(seen->time_stamp)); + break; } } store_reset(reset_point); @@ -759,22 +798,29 @@ If the record name is omitted from (2) or (3), the previously used record name is re-used. */ -int main(int argc, char **cargv) +int +main(int argc, char **cargv) { int dbdata_type; uschar **argv = USS cargv; uschar buffer[256]; uschar name[256]; rmark reset_point; +uschar * aname; store_init(); +options(argc, argv, US"fixdb"); name[0] = 0; /* No name set */ /* Sort out the database type, verify what we are working on and then process user requests */ -dbdata_type = check_args(argc, argv, US"fixdb", US""); -printf("Modifying Exim hints database %s/db/%s\n", argv[1], argv[2]); +dbdata_type = check_args(argc, argv, US"fixdb", US" [-z]"); +argc -= optind; argv += optind; +spool_directory = argv[0]; +aname = argv[1]; + +printf("Modifying Exim hints database %s/db/%s\n", spool_directory, aname); for(; (reset_point = store_mark()); store_reset(reset_point)) { @@ -821,9 +867,8 @@ for(; (reset_point = store_mark()); store_reset(reset_point)) if (field[0] != 0) { int verify = 1; - spool_directory = argv[1]; - if (!(dbm = dbfn_open(argv[2], O_RDWR, &dbblock, FALSE, TRUE))) + if (!(dbm = dbfn_open(aname, O_RDWR, &dbblock, FALSE, TRUE))) continue; if (Ustrcmp(field, "d") == 0) @@ -992,8 +1037,7 @@ for(; (reset_point = store_mark()); store_reset(reset_point)) /* Handle a read request, or verify after an update. */ - spool_directory = argv[1]; - if (!(dbm = dbfn_open(argv[2], O_RDONLY, &dbblock, FALSE, TRUE))) + if (!(dbm = dbfn_open(aname, O_RDONLY, &dbblock, FALSE, TRUE))) continue; if (!(record = dbfn_read_with_length(dbm, name, &oldlength))) @@ -1123,7 +1167,8 @@ typedef struct key_item { } key_item; -int main(int argc, char **cargv) +int +main(int argc, char **cargv) { struct stat statbuf; int maxkeep = 30 * 24 * 60 * 60;