blob: 3ad7efce8a909800f495dd201385d759e28eb9ad [file] [log] [blame]
Jacob Erlbeck4f666bc2015-07-20 12:40:42 +02001/* gprs_codel.h
2 *
3 * This is an implementation of the CoDel algorithm based on the reference
4 * pseudocode (see http://queue.acm.org/appendices/codel.html).
5 * Instead of abstracting the queue itself, the following implementation
6 * provides a time stamp based automaton. The main work is done by a single
7 * decision function which updates the state and tells whether to pass or to
8 * drop a packet after it has been taken from the queue.
9 *
10 * Copyright (C) 2015 by Sysmocom s.f.m.c. GmbH
11 * Author: Jacob Erlbeck <jerlbeck@sysmocom.de>
12 *
13 * This program is free software; you can redistribute it and/or
14 * modify it under the terms of the GNU General Public License
15 * as published by the Free Software Foundation; either version 2
16 * of the License, or (at your option) any later version.
17 *
18 * This program is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU General Public License for more details.
22 *
23 * You should have received a copy of the GNU General Public License
24 * along with this program; if not, write to the Free Software
25 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
26 */
27
28#pragma once
29
Pau Espin Pedrol1de68732020-03-11 14:04:52 +010030#include <time.h>
Jacob Erlbeck4f666bc2015-07-20 12:40:42 +020031
32/* Spec default values */
33#define GPRS_CODEL_DEFAULT_INTERVAL_MS 100
34#define GPRS_CODEL_DEFAULT_MAXPACKET 512
35
36#ifdef __cplusplus
37extern "C" {
38#endif
39
40struct gprs_codel {
41 int dropping;
42 unsigned count;
Pau Espin Pedrol1de68732020-03-11 14:04:52 +010043 struct timespec first_above_time;
44 struct timespec drop_next;
45 struct timespec target;
46 struct timespec interval;
Jacob Erlbeck4f666bc2015-07-20 12:40:42 +020047 unsigned maxpacket;
48};
49
50/*!
51 * \brief Decide about packet drop and update CoDel state
52 *
53 * This function takes timing information and decides whether the packet in
54 * question should be dropped in order to keep related queue in a 'good' state.
55 * The function is meant to be called when the packet is dequeued.
56 *
57 * The CoDel state is updated by this function.
58 *
59 * \param state A pointer to the CoDel state of this queue
60 * \param recv The time when the packet has entered the queue,
61 * use NULL if dequeueing was not possible because the queue is
62 * empty
63 * \param now The current (dequeueing) time
64 * \param bytes The number of bytes currently stored in the queue (-1 if
65 * unknown)
66 *
67 * \return != 0 if the packet should be dropped, 0 otherwise
68 */
Pau Espin Pedrol1de68732020-03-11 14:04:52 +010069int gprs_codel_control(struct gprs_codel *state, const struct timespec *recv,
70 const struct timespec *now, int bytes);
Jacob Erlbeck4f666bc2015-07-20 12:40:42 +020071
72/*!
73 * \brief Initialise CoDel state
74 *
75 * This function initialises the CoDel state object. It sets the interval time
76 * to the default value (GPRS_CODEL_DEFAULT_INTERVAL_MS).
77 *
78 * \param state A pointer to the CoDel state of this queue
79 */
80void gprs_codel_init(struct gprs_codel *state);
81
82/*!
83 * \brief Set interval time
84 *
85 * This function changes the interval time.
86 * The target time is derived from the interval time as proposed in the spec
87 * (5% of interval time).
88 *
89 * \param state A pointer to the CoDel state of this queue
90 * \param interval_ms The initial interval in ms to be used (<= 0 selects the
91 * default value)
92 */
93void gprs_codel_set_interval(struct gprs_codel *state, int interval_ms);
94
95/*!
96 * \brief Set max packet size
97 *
98 * This function changes the maxpacket value. If no more than this number of
99 * bytes are still stored in the queue, no dropping will be done.
100 *
101 * \param state A pointer to the CoDel state of this queue
102 * \param maxpacket The value in bytes
103 */
104void gprs_codel_set_maxpacket(struct gprs_codel *state, int maxpacket);
105
106#ifdef __cplusplus
107}
108#endif