/*
 * Copyright (c) 2005 Sendmail, Inc. and its suppliers.
 *      All rights reserved.
 *
 * By using this file, you agree to the terms and conditions set
 * forth in the LICENSE file which can be found at the top level of
 * the sendmail distribution.
 *
 *	$Id: qm_throttle.h,v 1.2 2005/06/16 00:39:08 ca Exp $
 */

#ifndef QM_THROTTLE_H
#define QM_THROTTLE_H 1

#include "sm/generic.h"
#include "sm/error.h"
#include "sm/evthr.h"
#include "sm/qmgr.h"

/* prototypes */
sm_ret_T q2s_throttle(qss_ctx_P _qss_ctx, sm_evthr_task_P _tsk, uint _nthreads);

sm_ret_T qm_unthrottle(qmgr_ctx_P _qmgr_ctx, thr_lock_T _locktype);
sm_ret_T qm_control(qmgr_ctx_P _qmgr_ctx, int _direction, uint _use, uint _resource, thr_lock_T _locktype);

/* calculate qss status based on total usage: 0...100% */
#define QSS_ST_CALC(usage)	\
		(((usage) == 0)  ? QSS_ST_OK :		\
		 ((usage) <= 25) ? QSS_ST_SLOW_0 :	\
		 ((usage) <= 50) ? QSS_ST_SLOW_1 :	\
		 ((usage) <= 75) ? QSS_ST_SLOW_2 :	\
				   QSS_ST_SLOW_3)


/* set qss_max_cur_thrs based on total usage: 0...100% */
#define QS_UNTHROTTLE(fct)				\
	do						\
	{						\
		uint h;					\
							\
		qss_ctx->qss_max_cur_thrs <<= 1;	\
		h = (qss_ctx->qss_max_thrs *		\
			(100 - qmgr_ctx->qmgr_total_usage)) / 100;	\
		if (qss_ctx->qss_max_cur_thrs < h)	\
			qss_ctx->qss_max_cur_thrs = h;	\
		if (qss_ctx->qss_max_cur_thrs > qss_ctx->qss_max_thrs)	\
			qss_ctx->qss_max_cur_thrs = qss_ctx->qss_max_thrs; \
		QM_LEV_DPRINTFC(QDC_RSRC, 2, (QM_DEBFP, "func=%s, unthrottle, total_usage=%u, h=%u, max_thrs=%u, ret=%r\n", fct, qmgr_ctx->qmgr_total_usage, h, qss_ctx->qss_max_thrs, ret));	\
							\
		ret = q2s_throttle(qss_ctx, tsk, qss_ctx->qss_max_cur_thrs); \
		if (sm_is_err(ret))			\
		{					\
			QM_LEV_DPRINTFC(QDC_RSRC, 2, (QM_DEBFP, "func=%s, q2s_throttle=%r\n", fct, ret));	\
		}					\
		qss_ctx->qss_status = QSS_ST_CALC(qmgr_ctx->qmgr_total_usage);\
	} while (0)
/* XXX qss_status should be set according to qmgr_total_usage */


#endif /* QM_THROTTLE_H */


syntax highlighted by Code2HTML, v. 0.9.1