X-Git-Url: https://git.exim.org/exim.git/blobdiff_plain/d4c9963ace2b653f657c74abecfecb7546c722b1..a1108b5118d32e969c5fe91b2110944f7483a7cb:/src/src/exim.c diff --git a/src/src/exim.c b/src/src/exim.c index dcfc06623..8526cbbf3 100644 --- a/src/src/exim.c +++ b/src/src/exim.c @@ -53,7 +53,7 @@ return store_get((int)size, TRUE); } static void -function_dummy_free(void *block) { block = block; } +function_dummy_free(void * block) {} static void * function_store_malloc(size_t size) @@ -62,7 +62,7 @@ return store_malloc((int)size); } static void -function_store_free(void *block) +function_store_free(void * block) { store_free(block); } @@ -383,14 +383,20 @@ return 0; *************************************************/ #ifdef _POSIX_MONOTONIC_CLOCK -/* Amount CLOCK_MONOTONIC is behind realtime, at startup. */ +# ifdef CLOCK_BOOTTIME +# define EXIM_CLOCKTYPE CLOCK_BOOTTIME +# else +# define EXIM_CLOCKTYPE CLOCK_MONOTONIC +# endif + +/* Amount EXIM_CLOCK is behind realtime, at startup. */ static struct timespec offset_ts; static void exim_clock_init(void) { struct timeval tv; -if (clock_gettime(CLOCK_MONOTONIC, &offset_ts) != 0) return; +if (clock_gettime(EXIM_CLOCKTYPE, &offset_ts) != 0) return; (void)gettimeofday(&tv, NULL); offset_ts.tv_sec = tv.tv_sec - offset_ts.tv_sec; offset_ts.tv_nsec = tv.tv_usec * 1000 - offset_ts.tv_nsec; @@ -401,6 +407,29 @@ offset_ts.tv_nsec += 1000*1000*1000; #endif +void +exim_gettime(struct timeval * tv) +{ +#ifdef _POSIX_MONOTONIC_CLOCK +struct timespec now_ts; + +if (clock_gettime(EXIM_CLOCKTYPE, &now_ts) == 0) + { + now_ts.tv_sec += offset_ts.tv_sec; + if ((now_ts.tv_nsec += offset_ts.tv_nsec) >= 1000*1000*1000) + { + now_ts.tv_sec++; + now_ts.tv_nsec -= 1000*1000*1000; + } + tv->tv_sec = now_ts.tv_sec; + tv->tv_usec = now_ts.tv_nsec / 1000; + } +else +#endif + (void)gettimeofday(tv, NULL); +} + + /* Exim uses a time + a pid to generate a unique identifier in two places: its message IDs, and in file names for maildir deliveries. Because some OS now re-use pids within the same second, sub-second times are now being used. @@ -427,28 +456,9 @@ exim_wait_tick(struct timeval * tgt_tv, int resolution) struct timeval now_tv; long int now_true_usec; -#ifdef _POSIX_MONOTONIC_CLOCK -struct timespec now_ts; - -if (clock_gettime(CLOCK_MONOTONIC, &now_ts) == 0) - { - now_ts.tv_sec += offset_ts.tv_sec; - if ((now_ts.tv_nsec += offset_ts.tv_nsec) >= 1000*1000*1000) - { - now_ts.tv_sec++; - now_ts.tv_nsec -= 1000*1000*1000; - } - now_tv.tv_sec = now_ts.tv_sec; - now_true_usec = (now_ts.tv_nsec / (resolution * 1000)) * resolution; - now_tv.tv_usec = now_true_usec; - } -else -#endif - { - (void)gettimeofday(&now_tv, NULL); - now_true_usec = now_tv.tv_usec; - now_tv.tv_usec = (now_true_usec/resolution) * resolution; - } +exim_gettime(&now_tv); +now_true_usec = now_tv.tv_usec; +now_tv.tv_usec = (now_true_usec/resolution) * resolution; while (exim_tvcmp(&now_tv, tgt_tv) <= 0) { @@ -554,7 +564,7 @@ for (int i = 0; i <= 2; i++) { if (devnull < 0) devnull = open("/dev/null", O_RDWR); if (devnull < 0) log_write(0, LOG_MAIN|LOG_PANIC_DIE, "%s", - string_open_failed(errno, "/dev/null", NULL)); + string_open_failed("/dev/null", NULL)); if (devnull != i) (void)dup2(devnull, i); } } @@ -1000,6 +1010,9 @@ g = string_cat(NULL, US"Support for:"); #ifdef EXPERIMENTAL_DSN_INFO g = string_cat(g, US" Experimental_DSN_info"); #endif +#ifdef EXPERIMENTAL_ESMTP_LIMITS + g = string_cat(g, US" Experimental_ESMTP_Limits"); +#endif #ifdef EXPERIMENTAL_QUEUEFILE g = string_cat(g, US" Experimental_QUEUEFILE"); #endif @@ -1659,6 +1672,8 @@ extern char **environ; (void)gettimeofday(×tamp_startup, NULL); #endif +store_init(); /* Initialise the memory allocation susbsystem */ + /* If the Exim user and/or group and/or the configuration file owner/group were defined by ref:name at build time, we must now find the actual uid/gid values. This is a feature to make the lives of binary distributors easier. */ @@ -1728,7 +1743,7 @@ make quite sure. */ setlocale(LC_ALL, "C"); -/* Get the offset between CLOCK_MONOTONIC and wallclock */ +/* Get the offset between CLOCK_MONOTONIC/CLOCK_BOOTTIME and wallclock */ #ifdef _POSIX_MONOTONIC_CLOCK exim_clock_init(); @@ -2245,7 +2260,7 @@ on the second character (the one after '-'), to save some effort. */ case 'P': /* -bP config: we need to setup here, because later, - * when list_options is checked, the config is read already */ + when list_options is checked, the config is read already */ if (*argrest) badarg = TRUE; else if (argv[i+1] && Ustrcmp(argv[i+1], "config") == 0) @@ -2363,6 +2378,7 @@ on the second character (the one after '-'), to save some effort. */ int len = Ustrlen(ALT_CONFIG_PREFIX); const uschar *list = argrest; uschar *filename; + /* The argv is untainted, so big_buffer (also untainted) is ok to use */ while((filename = string_nextinlist(&list, &sep, big_buffer, big_buffer_size))) if ( ( Ustrlen(filename) < len @@ -2775,11 +2791,42 @@ on the second character (the one after '-'), to save some effort. */ case 'K': smtp_peer_options |= OPTION_CHUNKING; break; +#ifdef EXPERIMENTAL_ESMTP_LIMITS + /* -MCL: peer used LIMITS RCPTMAX and/or RCPTDOMAINMAX */ + case 'L': if (++i < argc) continue_limit_mail = Uatoi(argv[i]); + else badarg = TRUE; + if (++i < argc) continue_limit_rcpt = Uatoi(argv[i]); + else badarg = TRUE; + if (++i < argc) continue_limit_rcptdom = Uatoi(argv[i]); + else badarg = TRUE; + break; +#endif + /* -MCP: set the smtp_use_pipelining flag; this is useful only when it preceded -MC (see above) */ case 'P': smtp_peer_options |= OPTION_PIPE; break; +#ifdef SUPPORT_SOCKS + /* -MCp: Socks proxy in use; nearside IP, port, external IP, port */ + case 'p': proxy_session = TRUE; + if (++i < argc) + { + proxy_local_address = string_copy_taint(argv[i], TRUE); + if (++i < argc) + { + proxy_local_port = Uatoi(argv[i]); + if (++i < argc) + { + proxy_external_address = string_copy_taint(argv[i], TRUE); + if (++i < argc) + { + proxy_external_port = Uatoi(argv[i]); + break; + } } } } + badarg = TRUE; + break; +#endif /* -MCQ: pass on the pid of the queue-running process that started this chain of deliveries and the fd of its synchronizing pipe; this is useful only when it precedes -MC (see above) */ @@ -2803,10 +2850,22 @@ on the second character (the one after '-'), to save some effort. */ case 'S': smtp_peer_options |= OPTION_SIZE; break; #ifndef DISABLE_TLS + /* -MCs: used with -MCt; SNI was sent */ + /* -MCr: ditto, DANE */ + + case 'r': + case 's': if (++i < argc) + { + continue_proxy_sni = string_copy_taint(argv[i], TRUE); + if (argrest[1] == 'r') continue_proxy_dane = TRUE; + } + else badarg = TRUE; + break; + /* -MCt: similar to -MCT below but the connection is still open via a proxy process which handles the TLS context and coding. Require three arguments for the proxied local address and port, - and the TLS cipher. */ + and the TLS cipher. */ case 't': if (++i < argc) sending_ip_address = string_copy_taint(argv[i], TRUE); @@ -3198,6 +3257,13 @@ on the second character (the one after '-'), to save some effort. */ else override_local_interfaces = string_copy_taint(argv[++i], TRUE); break; + /* -oY: Override creation of daemon notifier socket */ + + case 'Y': + if (*argrest) badarg = TRUE; + else notifier_socket = NULL; + break; + /* Unknown -o argument */ default: @@ -4101,10 +4167,8 @@ privilege by now. Before the chdir, we try to ensure that the directory exists. if (Uchdir(spool_directory) != 0) { - int dummy; - (void)directory_make(spool_directory, US"", SPOOL_DIRECTORY_MODE, FALSE); - dummy = /* quieten compiler */ Uchdir(spool_directory); - dummy = dummy; /* yet more compiler quietening, sigh */ + (void) directory_make(spool_directory, US"", SPOOL_DIRECTORY_MODE, FALSE); + (void) Uchdir(spool_directory); } /* Handle calls with the -bi option. This is a sendmail option to rebuild *the* @@ -4115,7 +4179,7 @@ script. */ if (bi_option) { - (void)fclose(config_file); + (void) fclose(config_file); if (bi_command && *bi_command) { int i = 0; @@ -4750,16 +4814,16 @@ for (i = 0;;) configuration specifies something to use. When running in the test harness, any setting of unknown_login overrides the actual name. */ -if (originator_login == NULL || f.running_in_test_harness) +if (!originator_login || f.running_in_test_harness) { - if (unknown_login != NULL) + if (unknown_login) { originator_login = expand_string(unknown_login); - if (originator_name == NULL && unknown_username != NULL) + if (!originator_name && unknown_username) originator_name = expand_string(unknown_username); - if (originator_name == NULL) originator_name = US""; + if (!originator_name) originator_name = US""; } - if (originator_login == NULL) + if (!originator_login) log_write(0, LOG_MAIN|LOG_PANIC_DIE, "Failed to get user name for uid %d", (int)real_uid); } @@ -4767,8 +4831,7 @@ if (originator_login == NULL || f.running_in_test_harness) /* Ensure that the user name is in a suitable form for use as a "phrase" in an RFC822 address.*/ -originator_name = string_copy(parse_fix_phrase(originator_name, - Ustrlen(originator_name), big_buffer, big_buffer_size)); +originator_name = US parse_fix_phrase(originator_name, Ustrlen(originator_name)); /* If a message is created by this call of Exim, the uid/gid of its originator are those of the caller. These values are overridden if an existing message is