diff options
author | Todd Lyons <tlyons@exim.org> | 2013-12-30 15:02:21 -0800 |
---|---|---|
committer | Todd Lyons <tlyons@exim.org> | 2013-12-30 15:56:37 -0800 |
commit | a3bddaa8058346a11835f0d9947f3f60bb029fef (patch) | |
tree | b64598c2a3bd568a3b20ffa5b900b4462e3179fa /src | |
parent | aa26e1378803587c24924ad0055318959d597802 (diff) |
Proxy negotiation saves socket timeout values.
Rename proxy expansions conforming to Exim standards.
Update documentation to reflect rename.
Seperate restore socket function
Diffstat (limited to 'src')
-rw-r--r-- | src/src/expand.c | 4 | ||||
-rw-r--r-- | src/src/globals.c | 4 | ||||
-rw-r--r-- | src/src/globals.h | 4 | ||||
-rw-r--r-- | src/src/receive.c | 2 | ||||
-rw-r--r-- | src/src/smtp_in.c | 40 |
5 files changed, 43 insertions, 11 deletions
diff --git a/src/src/expand.c b/src/src/expand.c index 325b05178..de52e6000 100644 --- a/src/src/expand.c +++ b/src/src/expand.c @@ -559,8 +559,8 @@ static var_entry var_table[] = { { "pid", vtype_pid, NULL }, { "primary_hostname", vtype_stringptr, &primary_hostname }, #ifdef EXPERIMENTAL_PROXY - { "proxy_host", vtype_stringptr, &proxy_host }, - { "proxy_port", vtype_int, &proxy_port }, + { "proxy_host_address", vtype_stringptr, &proxy_host_address }, + { "proxy_host_port", vtype_int, &proxy_host_port }, { "proxy_session", vtype_bool, &proxy_session }, #endif { "prvscheck_address", vtype_stringptr, &prvscheck_address }, diff --git a/src/src/globals.c b/src/src/globals.c index ec6700df5..1572461ec 100644 --- a/src/src/globals.c +++ b/src/src/globals.c @@ -919,8 +919,8 @@ uschar *process_log_path = NULL; BOOL prod_requires_admin = TRUE; #ifdef EXPERIMENTAL_PROXY -uschar *proxy_host = US""; -int proxy_port = 0; +uschar *proxy_host_address = US""; +int proxy_host_port = 0; uschar *proxy_required_hosts = US""; BOOL proxy_session = FALSE; BOOL proxy_session_failed = FALSE; diff --git a/src/src/globals.h b/src/src/globals.h index 5661489a7..bf54fb41f 100644 --- a/src/src/globals.h +++ b/src/src/globals.h @@ -594,8 +594,8 @@ extern uschar *process_log_path; /* Alternate path */ extern BOOL prod_requires_admin; /* TRUE if prodding requires admin */ #ifdef EXPERIMENTAL_PROXY -extern uschar *proxy_host; /* IP of proxy server */ -extern int proxy_port; /* Port of proxy server */ +extern uschar *proxy_host_address; /* IP of proxy server */ +extern int proxy_host_port; /* Port of proxy server */ extern uschar *proxy_required_hosts; /* Hostlist which (require) use proxy protocol */ extern BOOL proxy_session; /* TRUE if receiving mail from valid proxy */ extern BOOL proxy_session_failed; /* TRUE if required proxy negotiation failed */ diff --git a/src/src/receive.c b/src/src/receive.c index 02db23f94..0295b7e54 100644 --- a/src/src/receive.c +++ b/src/src/receive.c @@ -3759,7 +3759,7 @@ if (prdr_requested) if (proxy_session && (log_extra_selector & LX_proxy) != 0) { - s = string_append(s, &size, &sptr, 2, US" PRX=", proxy_host); + s = string_append(s, &size, &sptr, 2, US" PRX=", proxy_host_address); } #endif diff --git a/src/src/smtp_in.c b/src/src/smtp_in.c index 144ad28a2..95c615e37 100644 --- a/src/src/smtp_in.c +++ b/src/src/smtp_in.c @@ -555,6 +555,25 @@ exim_exit(EXIT_FAILURE); #ifdef EXPERIMENTAL_PROXY /************************************************* +* Restore socket timeout to previous value * +*************************************************/ +/* If the previous value was successfully retrieved, restore +it before returning control to the non-proxy routines + +Arguments: fd - File descriptor for input + get_ok - Successfully retrieved previous values + tvtmp - Time struct with previous values + vslen - Length of time struct +Returns: none +*/ +static void +restore_socket_timeout(int fd, int get_ok, struct timeval tvtmp, socklen_t vslen) +{ +if (get_ok == 0) + setsockopt(fd, SOL_SOCKET, SO_RCVTIMEO, (char *)&tvtmp, vslen); +} + +/************************************************* * Check if host is required proxy host * *************************************************/ /* The function determines if inbound host will be a regular smtp host @@ -650,15 +669,25 @@ uschar *tmpip; const char v2sig[13] = "\x0D\x0A\x0D\x0A\x00\x0D\x0A\x51\x55\x49\x54\x0A\x02"; uschar *iptype; /* To display debug info */ struct timeval tv; +int get_ok = 0; +socklen_t vslen = 0; +struct timeval tvtmp; + +vslen = sizeof(struct timeval); fd = fileno(smtp_in); +/* Save current socket timeout values */ +get_ok = getsockopt(fd, SOL_SOCKET, SO_RCVTIMEO, (char *)&tvtmp, + &vslen); + /* Proxy Protocol host must send header within a short time (default 3 seconds) or it's considered invalid */ tv.tv_sec = PROXY_NEGOTIATION_TIMEOUT_SEC; tv.tv_usec = PROXY_NEGOTIATION_TIMEOUT_USEC; setsockopt(fd, SOL_SOCKET, SO_RCVTIMEO, (char *)&tv, sizeof(struct timeval)); + do { ret = recv(fd, &hdr, sizeof(hdr), MSG_PEEK); @@ -666,7 +695,10 @@ do while (ret == -1 && errno == EINTR); if (ret == -1) + { + restore_socket_timeout(fd, get_ok, tvtmp, vslen); return (errno == EAGAIN) ? 0 : ERRNO_PROXYFAIL; + } if (ret >= 16 && memcmp(&hdr.v2, v2sig, 13) == 0) @@ -768,7 +800,7 @@ else if (ret >= 8 && debug_printf("Proxied src arg is not an %s address\n", iptype); goto proxyfail; } - proxy_host = sender_host_address; + proxy_host_address = sender_host_address; sender_host_address = p; p = sp + 1; if ((sp = Ustrchr(p, ' ')) == NULL) @@ -799,7 +831,7 @@ else if (ret >= 8 && debug_printf("Proxied src port '%s' not an integer\n", p); goto proxyfail; } - proxy_port = sender_host_port; + proxy_host_port = sender_host_port; sender_host_port = tmp_port; p = sp + 1; if ((sp = Ustrchr(p, '\0')) == NULL) @@ -826,11 +858,13 @@ else } proxyfail: +restore_socket_timeout(fd, get_ok, tvtmp, vslen); /* Don't flush any potential buffer contents. Any input should cause a synchronization failure or we just don't want to speak SMTP to them */ return FALSE; done: +restore_socket_timeout(fd, get_ok, tvtmp, vslen); flush_input(); DEBUG(D_receive) debug_printf("Valid %s sender from Proxy Protocol header\n", @@ -839,8 +873,6 @@ return proxy_session; } #endif - - /************************************************* * Read one command line * *************************************************/ |