* Exim - an Internet mail transport agent *
*************************************************/
-/* Copyright (c) The Exim Maintainers 2020 - 2022 */
+/* Copyright (c) The Exim Maintainers 2020 - 2023 */
/* Copyright (c) University of Cambridge 1995 - 2018 */
/* See the file NOTICE for conditions of use and distribution. */
/* SPDX-License-Identifier: GPL-2.0-or-later */
*/
BOOL
-receive_check_set_sender(uschar *newsender)
+receive_check_set_sender(const uschar * newsender)
{
-uschar *qnewsender;
+const uschar * qnewsender;
if (f.trusted_caller) return TRUE;
if (!newsender || !untrusted_set_sender) return FALSE;
qnewsender = Ustrchr(newsender, '@')
*/
void
-receive_add_recipient(uschar * recipient, int pno)
+receive_add_recipient(const uschar * recipient, int pno)
{
if (recipients_count >= recipients_list_max)
{
*/
BOOL
-receive_remove_recipient(uschar *recipient)
+receive_remove_recipient(const uschar * recipient)
{
DEBUG(D_receive) debug_printf("receive_remove_recipient(\"%s\") called\n",
recipient);
if (ch == '\n')
{
- if (first_line_ended_crlf == TRUE_UNSET) first_line_ended_crlf = FALSE;
- else if (first_line_ended_crlf) receive_ungetc(' ');
+ if (first_line_ended_crlf == TRUE_UNSET)
+ first_line_ended_crlf = FALSE;
+ else if (first_line_ended_crlf)
+ receive_ungetc(' ');
goto EOL;
}
This implements the dot-doubling rule, though header lines starting with
dots aren't exactly common. They are legal in RFC 822, though. If the
following is CRLF or LF, this is the line that that terminates the
+
entire message. We set message_ended to indicate this has happened (to
prevent further reading), and break out of the loop, having freed the
empty header, and set next = NULL to indicate no data line. */
if (f.dot_ends && ptr == 0 && ch == '.')
{
ch = (receive_getc)(GETC_BUFFER_UNLIMITED);
- if (ch == '\r')
+ if (ch == '\n' && first_line_ended_crlf == TRUE /* and not TRUE_UNSET */ )
+ /* dot, LF but we are in CRLF mode. Attack? */
+ ch = ' '; /* replace the LF with a space */
+
+ else if (ch == '\r')
{
ch = (receive_getc)(GETC_BUFFER_UNLIMITED);
if (ch != '\n')
ch = (receive_getc)(GETC_BUFFER_UNLIMITED);
if (ch == '\n')
{
- if (first_line_ended_crlf == TRUE_UNSET) first_line_ended_crlf = TRUE;
+ if (first_line_ended_crlf == TRUE_UNSET)
+ first_line_ended_crlf = TRUE;
goto EOL;
}
}
}
- log_write(0, LOG_MAIN|LOG_PANIC, "%s %s found in headers",
- message_id, bad_addresses ? "bad addresses" : "no recipients");
+ log_write(0, LOG_MAIN|LOG_PANIC, "%s found in headers",
+ bad_addresses ? "bad addresses" : "no recipients");
fseek(spool_data_file, (long int)spool_data_start_offset(message_id), SEEK_SET);
/* Loop through recipients, responses must be in same order received */
for (unsigned int c = 0; recipients_count > c; c++)
{
- uschar * addr= recipients_list[c].address;
+ const uschar * addr = recipients_list[c].address;
uschar * msg= US"PRDR R=<%s> %s";
uschar * code;
DEBUG(D_receive)
possible for fclose() to fail - and this has been seen on obscure filesystems
(probably one that delayed the actual media write as long as possible)
but what to do? What has happened to the lock if this happens?
-It's a mes because we already logged the acceptance.
+It's a mess because we already logged the acceptance.
We can at least log the issue, try to remove spoolfiles and respond with
a temp-reject. We do not want to close before logging acceptance because
we want to hold the lock until we know that logging worked.
Uunlink(spool_fname(US"input", message_subdir, message_id, US"-H"));
Uunlink(spool_fname(US"msglog", message_subdir, message_id, US""));
- /* Claim a data ACL temp-reject, just to get reject logging and resposponse */
- smtp_handle_acl_fail(ACL_WHERE_DATA, rc, NULL, log_msg);
+ /* Claim a data ACL temp-reject, just to get reject logging and response */
+ if (smtp_input) smtp_handle_acl_fail(ACL_WHERE_DATA, rc, NULL, log_msg);
smtp_reply = US""; /* Indicate reply already sent */
message_id[0] = 0; /* no message accepted */