Time interval arithmetic can overflow especially when user
defined intervals are involved. E.g., see Trac #922.
Avoid this by reordering the arithmetic operation in
event_timeout_trigger(). Also avoid unnecessary casting of time
variable to int.
Time until wakeup is now calculated like:
time_t wakeup = (last - now) + delay
Here delay is of type int, but is +ve by construction. Time backtrack
protection in OpenVPN ensures (last - now) <= 0. Then the above
expression cannot overflow (provided time_t is at least as large
as int).
A similar expression in interval.h is also changed.
(This patch grew out of patch 168 by Steffan Karger.)
Trac: #922
Signed-off-by: Selva Nair <selva.nair@gmail.com>
Acked-by: Steffan Karger <steffan.karger@fox-it.com>
Message-Id: <
1520316568-8983-1-git-send-email-selva.nair@gmail.com>
URL: https://www.mail-archive.com/openvpn-devel@lists.sourceforge.net/msg16634.html
Signed-off-by: Gert Doering <gert@greenie.muc.de>
(cherry picked from commit
f158c0e1df13ae1b697cdc7f189ddd1575a0c1aa)
if (et->defined)
{
- int wakeup = (int) et->last + et->n - local_now;
+ time_t wakeup = et->last - local_now + et->n;
if (wakeup <= 0)
{
#if INTERVAL_DEBUG
- dmsg(D_INTERVAL, "EVENT event_timeout_trigger (%d) etcr=%d", et->n, et_const_retry);
+ dmsg(D_INTERVAL, "EVENT event_timeout_trigger (%d) etcr=%d", et->n,
+ et_const_retry);
#endif
if (et_const_retry < 0)
{
if (tv && wakeup < tv->tv_sec)
{
#if INTERVAL_DEBUG
- dmsg(D_INTERVAL, "EVENT event_timeout_wakeup (%d/%d) etcr=%d", wakeup, et->n, et_const_retry);
+ dmsg(D_INTERVAL, "EVENT event_timeout_wakeup (%d/%d) etcr=%d",
+ (int) wakeup, et->n, et_const_retry);
#endif
tv->tv_sec = wakeup;
tv->tv_usec = 0;
static inline interval_t
event_timeout_remaining(struct event_timeout *et)
{
- return (int) et->last + et->n - now;
+ return (interval_t) (et->last - now + et->n);
}
/*