Gitweb:
https://git.exim.org/exim.git/commitdiff/17427537cf5a55f952bad37067f0801b66bf7c08
Commit: 17427537cf5a55f952bad37067f0801b66bf7c08
Parent: 3eb0bcd7a112a70bbdd61bedde4878ceae4e1297
Author: Jeremy Harris <jgh146exb@???>
AuthorDate: Fri Jan 1 14:31:14 2021 +0000
Committer: Jeremy Harris <jgh146exb@???>
CommitDate: Fri Jan 1 14:31:14 2021 +0000
malware: avoid partial packets, sending to ClamAV
---
src/src/malware.c | 31 ++++++++++++++++++++++---------
1 file changed, 22 insertions(+), 9 deletions(-)
diff --git a/src/src/malware.c b/src/src/malware.c
index dfa8e2b..a42e39a 100644
--- a/src/src/malware.c
+++ b/src/src/malware.c
@@ -132,6 +132,11 @@ static const uschar * malware_regex_default = US ".+";
static const pcre * malware_default_re = NULL;
+#ifdef TCP_CORK
+# define EXIM_TCP_CORK TCP_CORK
+#elif defined(TCP_NOPUSH)
+# define EXIM_TCP_CORK TCP_NOPUSH
+#endif
#ifndef DISABLE_MAL_CLAM
/* The maximum number of clamd servers that are supported in the configuration */
@@ -1570,8 +1575,8 @@ badseek: err = errno;
if (num_servers)
{
/* Confirmed in ClamAV source (0.95.3) that the TCPAddr option of clamd
- * only supports AF_INET, but we should probably be looking to the
- * future and rewriting this to be protocol-independent anyway. */
+ only supports AF_INET, but we should probably be looking to the
+ future and rewriting this to be protocol-independent anyway. */
while (num_servers > 0)
{
@@ -1582,7 +1587,7 @@ badseek: err = errno;
cd->hostspec, cd->tcp_port);
/* Lookup the host. This is to ensure that we connect to the same IP
- * on both connections (as one host could resolve to multiple ips) */
+ on both connections (as one host could resolve to multiple ips) */
for (;;)
{
/*XXX we trust that the cmd_str is ideempotent */
@@ -1625,9 +1630,9 @@ badseek: err = errno;
}
/* have socket in variable "sock"; command to use is semi-independent of
- * the socket protocol. We use SCAN if is local (either Unix/local
- * domain socket, or explicitly told local) else we stream the data.
- * How we stream the data depends upon how we were built. */
+ the socket protocol. We use SCAN if is local (either Unix/local
+ domain socket, or explicitly told local) else we stream the data.
+ How we stream the data depends upon how we were built. */
if (!use_scan_command)
{
@@ -1674,13 +1679,17 @@ badseek: err = errno;
malware_daemon_ctx.sock);
}
- /* send file body to socket */
+ /* send file size */
+#ifdef EXIM_TCP_CORK
+ (void) setsockopt(clam_fd, IPPROTO_TCP, EXIM_TCP_CORK, US &on, sizeof(on));
+#endif
send_size = htonl(fsize_uint);
if (send(malware_daemon_ctx.sock, &send_size, sizeof(send_size), 0) < 0)
return m_panic_defer_3(scanent, NULL,
string_sprintf("unable to send file size to socket (%s)", hostname),
malware_daemon_ctx.sock);
+ /* send file body */
while (fsize_uint)
{
unsigned n = MIN(fsize_uint, big_buffer_size);
@@ -1701,6 +1710,9 @@ badseek: err = errno;
return m_panic_defer_3(scanent, NULL,
string_sprintf("unable to send file terminator to socket (%s)", hostname),
malware_daemon_ctx.sock);
+#ifdef EXIM_TCP_CORK
+ (void) setsockopt(clam_fd, IPPROTO_TCP, EXIM_TCP_CORK, US &off, sizeof(off));
+#endif
}
else
{ /* use scan command */
@@ -1730,10 +1742,10 @@ badseek: err = errno;
malware_daemon_ctx.sock);
/* Do not shut down the socket for writing; a user report noted that
- * clamd 0.70 does not react well to this. */
+ clamd 0.70 does not react well to this. */
}
/* Commands have been sent, no matter which scan method or connection
- * type we're using; now just read the result, independent of method. */
+ type we're using; now just read the result, independent of method. */
/* Read the result */
memset(av_buffer, 0, sizeof(av_buffer));
@@ -1779,6 +1791,7 @@ badseek: err = errno;
/* strip newline at the end (won't be present for zINSTREAM)
(also any trailing whitespace, which shouldn't exist, but we depend upon
this below, so double-check) */
+
p = av_buffer + Ustrlen(av_buffer) - 1;
if (*p == '\n') *p = '\0';