/*
  include/common/ticks.h
  Functions and macros for manipulation of expiration timers

  Copyright (C) 2000-2009 Willy Tarreau - w@1wt.eu
  
  This library is free software; you can redistribute it and/or
  modify it under the terms of the GNU Lesser General Public
  License as published by the Free Software Foundation, version 2.1
  exclusively.

  This library is distributed in the hope that it will be useful,
  but WITHOUT ANY WARRANTY; without even the implied warranty of
  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  Lesser General Public License for more details.

  You should have received a copy of the GNU Lesser General Public
  License along with this library; if not, write to the Free Software
  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
*/

/*
 * Using a mix of milliseconds and timeval for internal timers is expensive and
 * overkill, because we don't need such a precision to compute timeouts.
 * So we're converting them to "ticks".
 *
 * A tick is a representation of a date relative to another one, and is
 * measured in milliseconds. The natural usage is to represent an absolute date
 * relative to the current date. Since it is not practical to update all values
 * each time the current date changes, instead we use the absolute date rounded
 * down to fit in a tick. We then have to compare a tick to the current date to
 * know whether it is in the future or in the past. If a tick is below the
 * current date, it is in the past. If it is above, it is in the future. The
 * values will wrap so we can't compare that easily, instead we check the sign
 * of the difference between a tick and the current date.
 *
 * Proceeding like this allows us to manipulate dates that are stored in
 * scalars with enough precision and range. For this reason, we store ticks in
 * 32-bit integers. This is enough to handle dates that are between 24.85 days
 * in the past and as much in the future.
 * 
 * We must both support absolute dates (well in fact, dates relative to now+/-
 * 24 days), and intervals (for timeouts). Both types need an "eternity" magic
 * value. For optimal code generation, we'll use zero as the magic value
 * indicating that an expiration timer or a timeout is not set. We have to
 * check that we don't return this value when adding timeouts to <now>. If a
 * computation returns 0, we must increase it to 1 (which will push the timeout
 * 1 ms further). For this reason, timeouts must not be added by hand but via
 * the dedicated tick_add() function.
 */

#ifndef _COMMON_TICKS_H
#define _COMMON_TICKS_H

#include <haproxy/api.h>
#include <common/standard.h>

#define TICK_ETERNITY   0

/* right now, ticks are milliseconds. Both negative ms and negative ticks
 * indicate eternity.
 */
#define MS_TO_TICKS(ms) (ms)
#define TICKS_TO_MS(tk) (tk)

/* return 1 if tick is set, otherwise 0 */
static inline int tick_isset(int expire)
{
	return expire != 0;
}

/* Add <timeout> to <now>, and return the resulting expiration date.
 * <timeout> will not be checked for null values.
 */
static inline int tick_add(int now, int timeout)
{
	now += timeout;
	if (unlikely(!now))
		now++;    /* unfortunate value */
	return now;
}

/* add <timeout> to <now> if it is set, otherwise set it to eternity.
 * Return the resulting expiration date.
 */
static inline int tick_add_ifset(int now, int timeout)
{
	if (!timeout)
		return TICK_ETERNITY;
	return tick_add(now, timeout);
}

/* return 1 if timer <t1> is before <t2>, none of which can be infinite. */
static inline int tick_is_lt(int t1, int t2)
{
	return (t1 - t2) < 0;
}

/* return 1 if timer <t1> is before or equal to <t2>, none of which can be infinite. */
static inline int tick_is_le(int t1, int t2)
{
	return (t1 - t2) <= 0;
}

/* return 1 if timer <timer> is expired at date <now>, otherwise zero */
static inline int tick_is_expired(int timer, int now)
{
	if (unlikely(!tick_isset(timer)))
		return 0;
	if (unlikely((timer - now) <= 0))
		return 1;
	return 0;
}

/* return the first one of the two timers, both of which may be infinite */
static inline int tick_first(int t1, int t2)
{
	if (!tick_isset(t1))
		return t2;
	if (!tick_isset(t2))
		return t1;
	if ((t1 - t2) <= 0)
		return t1;
	else
		return t2;
}

/* return the first one of the two timers, where only the first one may be infinite */
static inline int tick_first_2nz(int t1, int t2)
{
	if (!tick_isset(t1))
		return t2;
	if ((t1 - t2) <= 0)
		return t1;
	else
		return t2;
}

/* return the number of ticks remaining from <now> to <exp>, or zero if expired */
static inline int tick_remain(int now, int exp)
{
	if (tick_is_expired(exp, now))
		return 0;
	return exp - now;
}

#endif /* _COMMON_TICKS_H */

/*
 * Local variables:
 *  c-indent-level: 8
 *  c-basic-offset: 8
 * End:
 */
