lsquic_spi.c revision 03fb9352
1229fce07SDmitri Tikhonov/* Copyright (c) 2017 - 2019 LiteSpeed Technologies Inc.  See LICENSE. */
250aadb33SDmitri Tikhonov/*
350aadb33SDmitri Tikhonov * lsquic_spi.c - implementation of Stream Priority Iterator.
450aadb33SDmitri Tikhonov */
550aadb33SDmitri Tikhonov
650aadb33SDmitri Tikhonov#include <assert.h>
750aadb33SDmitri Tikhonov#include <inttypes.h>
850aadb33SDmitri Tikhonov#include <stdint.h>
950aadb33SDmitri Tikhonov#include <stdlib.h>
10c51ce338SDmitri Tikhonov#include <string.h>
1150aadb33SDmitri Tikhonov#include <sys/queue.h>
1250aadb33SDmitri Tikhonov#include <sys/types.h>
13461e84d8SAmol Deshpande#ifdef WIN32
14461e84d8SAmol Deshpande#include <vc_compat.h>
15461e84d8SAmol Deshpande#endif
1650aadb33SDmitri Tikhonov
1750aadb33SDmitri Tikhonov#include "lsquic_types.h"
1850aadb33SDmitri Tikhonov#include "lsquic_int_types.h"
1950aadb33SDmitri Tikhonov#include "lsquic_sfcw.h"
2050aadb33SDmitri Tikhonov#include "lsquic_stream.h"
2150aadb33SDmitri Tikhonov#include "lsquic_spi.h"
2250aadb33SDmitri Tikhonov
2350aadb33SDmitri Tikhonov#define LSQUIC_LOGGER_MODULE LSQLM_SPI
2450aadb33SDmitri Tikhonov#define LSQUIC_LOG_CONN_ID iter->spi_cid
2550aadb33SDmitri Tikhonov#include "lsquic_logger.h"
2650aadb33SDmitri Tikhonov
27461e84d8SAmol Deshpande#define SPI_DEBUG(fmt, ...) LSQ_DEBUG("%s: " fmt, iter->spi_name, __VA_ARGS__)
2850aadb33SDmitri Tikhonov
2950aadb33SDmitri Tikhonov#define NEXT_STREAM(stream, off) \
3050aadb33SDmitri Tikhonov    (* (struct lsquic_stream **) ((unsigned char *) (stream) + (off)))
3150aadb33SDmitri Tikhonov
3250aadb33SDmitri Tikhonov
3350aadb33SDmitri Tikhonovstatic void
3450aadb33SDmitri Tikhonovadd_stream_to_spi (struct stream_prio_iter *iter, lsquic_stream_t *stream)
3550aadb33SDmitri Tikhonov{
3650aadb33SDmitri Tikhonov    unsigned set, bit;
3750aadb33SDmitri Tikhonov    set = stream->sm_priority >> 6;
3850aadb33SDmitri Tikhonov    bit = stream->sm_priority & 0x3F;
3950aadb33SDmitri Tikhonov    if (!(iter->spi_set[set] & (1ULL << bit)))
4050aadb33SDmitri Tikhonov    {
4150aadb33SDmitri Tikhonov        iter->spi_set[set] |= 1ULL << bit;
4250aadb33SDmitri Tikhonov        TAILQ_INIT(&iter->spi_streams[ stream->sm_priority ]);
4350aadb33SDmitri Tikhonov    }
4450aadb33SDmitri Tikhonov    TAILQ_INSERT_TAIL(&iter->spi_streams[ stream->sm_priority ],
4550aadb33SDmitri Tikhonov                                                stream, next_prio_stream);
4650aadb33SDmitri Tikhonov}
4750aadb33SDmitri Tikhonov
4850aadb33SDmitri Tikhonov
4950aadb33SDmitri Tikhonovvoid
50c51ce338SDmitri Tikhonovlsquic_spi_init (struct stream_prio_iter *iter, struct lsquic_stream *first,
51c51ce338SDmitri Tikhonov        struct lsquic_stream *last, uintptr_t next_ptr_offset,
5219f667fbSDmitri Tikhonov        enum stream_flags onlist_mask, lsquic_cid_t cid, const char *name,
5319f667fbSDmitri Tikhonov        int (*filter)(void *filter_ctx, struct lsquic_stream *),
5419f667fbSDmitri Tikhonov        void *filter_ctx)
5550aadb33SDmitri Tikhonov{
5650aadb33SDmitri Tikhonov    struct lsquic_stream *stream;
5750aadb33SDmitri Tikhonov    unsigned count;
5850aadb33SDmitri Tikhonov
5950aadb33SDmitri Tikhonov    iter->spi_cid           = cid;
6050aadb33SDmitri Tikhonov    iter->spi_name          = name ? name : "UNSET";
6150aadb33SDmitri Tikhonov    iter->spi_set[0]        = 0;
6250aadb33SDmitri Tikhonov    iter->spi_set[1]        = 0;
6350aadb33SDmitri Tikhonov    iter->spi_set[2]        = 0;
6450aadb33SDmitri Tikhonov    iter->spi_set[3]        = 0;
6550aadb33SDmitri Tikhonov    iter->spi_onlist_mask   = onlist_mask;
6650aadb33SDmitri Tikhonov    iter->spi_cur_prio      = 0;
6750aadb33SDmitri Tikhonov    iter->spi_prev_stream   = NULL;
6850aadb33SDmitri Tikhonov    iter->spi_next_stream   = NULL;
6950aadb33SDmitri Tikhonov
7050aadb33SDmitri Tikhonov    stream = first;
7150aadb33SDmitri Tikhonov    count = 0;
7250aadb33SDmitri Tikhonov
7319f667fbSDmitri Tikhonov    if (filter)
7419f667fbSDmitri Tikhonov        while (1)
7519f667fbSDmitri Tikhonov        {
7619f667fbSDmitri Tikhonov            if (filter(filter_ctx, stream))
7719f667fbSDmitri Tikhonov            {
7819f667fbSDmitri Tikhonov                add_stream_to_spi(iter, stream);
7919f667fbSDmitri Tikhonov                ++count;
8019f667fbSDmitri Tikhonov            }
8119f667fbSDmitri Tikhonov            if (stream == last)
8219f667fbSDmitri Tikhonov                break;
8319f667fbSDmitri Tikhonov            stream = NEXT_STREAM(stream, next_ptr_offset);
8419f667fbSDmitri Tikhonov        }
8519f667fbSDmitri Tikhonov    else
8619f667fbSDmitri Tikhonov        while (1)
8719f667fbSDmitri Tikhonov        {
8819f667fbSDmitri Tikhonov            add_stream_to_spi(iter, stream);
8919f667fbSDmitri Tikhonov            ++count;
9019f667fbSDmitri Tikhonov            if (stream == last)
9119f667fbSDmitri Tikhonov                break;
9219f667fbSDmitri Tikhonov            stream = NEXT_STREAM(stream, next_ptr_offset);
9319f667fbSDmitri Tikhonov        }
94c51ce338SDmitri Tikhonov
9550aadb33SDmitri Tikhonov    if (count > 2)
9650aadb33SDmitri Tikhonov        SPI_DEBUG("initialized; # elems: %u; sets: [ %016"PRIX64", %016"PRIX64
9750aadb33SDmitri Tikhonov            ", %016"PRIX64", %016"PRIX64" ]", count, iter->spi_set[0],
9850aadb33SDmitri Tikhonov            iter->spi_set[1], iter->spi_set[2], iter->spi_set[3]);
9950aadb33SDmitri Tikhonov}
10050aadb33SDmitri Tikhonov
10150aadb33SDmitri Tikhonov
10250aadb33SDmitri Tikhonovstatic int
10350aadb33SDmitri Tikhonovfind_and_set_lowest_priority (struct stream_prio_iter *iter)
10450aadb33SDmitri Tikhonov{
10550aadb33SDmitri Tikhonov    unsigned set, prio;
10650aadb33SDmitri Tikhonov    uint64_t mask;
10750aadb33SDmitri Tikhonov
10850aadb33SDmitri Tikhonov    for (set = 0, prio = 0; set < 4; ++set, prio += 64)
10950aadb33SDmitri Tikhonov        if (iter->spi_set[ set ])
11050aadb33SDmitri Tikhonov            break;
11150aadb33SDmitri Tikhonov
11250aadb33SDmitri Tikhonov    if (set == 4)
11350aadb33SDmitri Tikhonov    {
11450aadb33SDmitri Tikhonov        //SPI_DEBUG("%s: cannot find any", __func__);
11550aadb33SDmitri Tikhonov        return -1;
11650aadb33SDmitri Tikhonov    }
11750aadb33SDmitri Tikhonov
11850aadb33SDmitri Tikhonov    mask = iter->spi_set[set];
11950aadb33SDmitri Tikhonov    if (!(mask & ((1ULL << 32) - 1))) { prio += 32; mask >>= 32; }
12050aadb33SDmitri Tikhonov    if (!(mask & ((1ULL << 16) - 1))) { prio += 16; mask >>= 16; }
12150aadb33SDmitri Tikhonov    if (!(mask & ((1ULL <<  8) - 1))) { prio +=  8; mask >>=  8; }
12250aadb33SDmitri Tikhonov    if (!(mask & ((1ULL <<  4) - 1))) { prio +=  4; mask >>=  4; }
12350aadb33SDmitri Tikhonov    if (!(mask & ((1ULL <<  2) - 1))) { prio +=  2; mask >>=  2; }
12450aadb33SDmitri Tikhonov    if (!(mask & ((1ULL <<  1) - 1))) { prio +=  1;              }
12550aadb33SDmitri Tikhonov
12650aadb33SDmitri Tikhonov#ifndef NDEBUG
12750aadb33SDmitri Tikhonov    unsigned bit;
12850aadb33SDmitri Tikhonov    set = prio >> 6;
12950aadb33SDmitri Tikhonov    bit = prio & 0x3F;
13050aadb33SDmitri Tikhonov    assert(iter->spi_set[ set ] & (1ULL << bit));
13150aadb33SDmitri Tikhonov#endif
13250aadb33SDmitri Tikhonov
13350aadb33SDmitri Tikhonov    SPI_DEBUG("%s: prio %u -> %u", __func__, iter->spi_cur_prio, prio);
1342d296031SDmitri Tikhonov    iter->spi_cur_prio = (unsigned char) prio;
13550aadb33SDmitri Tikhonov    return 0;
13650aadb33SDmitri Tikhonov}
13750aadb33SDmitri Tikhonov
13850aadb33SDmitri Tikhonov
13950aadb33SDmitri Tikhonovstatic int
14050aadb33SDmitri Tikhonovfind_and_set_next_priority (struct stream_prio_iter *iter)
14150aadb33SDmitri Tikhonov{
14250aadb33SDmitri Tikhonov    unsigned set, bit, prio;
14350aadb33SDmitri Tikhonov    uint64_t mask;
14450aadb33SDmitri Tikhonov
14550aadb33SDmitri Tikhonov    /* Examine values in the same set first */
14650aadb33SDmitri Tikhonov    set = iter->spi_cur_prio >> 6;
14750aadb33SDmitri Tikhonov    bit = iter->spi_cur_prio & 0x3F;
14850aadb33SDmitri Tikhonov    prio = 64 * set;
14950aadb33SDmitri Tikhonov
15050aadb33SDmitri Tikhonov    if (bit < 63)
15150aadb33SDmitri Tikhonov    {
15250aadb33SDmitri Tikhonov        mask = iter->spi_set[set];
15350aadb33SDmitri Tikhonov        mask &= ~((1ULL << (bit + 1)) - 1);
15450aadb33SDmitri Tikhonov        if (mask)
15550aadb33SDmitri Tikhonov            goto calc_priority;
15650aadb33SDmitri Tikhonov    }
15750aadb33SDmitri Tikhonov
15850aadb33SDmitri Tikhonov    ++set;
15950aadb33SDmitri Tikhonov    prio += 64;
16050aadb33SDmitri Tikhonov    for (; set < 4; ++set, prio += 64)
16150aadb33SDmitri Tikhonov        if (iter->spi_set[ set ])
16250aadb33SDmitri Tikhonov            break;
16350aadb33SDmitri Tikhonov
16403fb9352SDmitri Tikhonov    if (set >= 4)
16550aadb33SDmitri Tikhonov    {
16650aadb33SDmitri Tikhonov        //SPI_DEBUG("%s: cannot find any", __func__);
16750aadb33SDmitri Tikhonov        return -1;
16850aadb33SDmitri Tikhonov    }
16950aadb33SDmitri Tikhonov
17050aadb33SDmitri Tikhonov    mask = iter->spi_set[set];
17150aadb33SDmitri Tikhonov
17250aadb33SDmitri Tikhonov  calc_priority:
17350aadb33SDmitri Tikhonov    if (!(mask & ((1ULL << 32) - 1))) { prio += 32; mask >>= 32; }
17450aadb33SDmitri Tikhonov    if (!(mask & ((1ULL << 16) - 1))) { prio += 16; mask >>= 16; }
17550aadb33SDmitri Tikhonov    if (!(mask & ((1ULL <<  8) - 1))) { prio +=  8; mask >>=  8; }
17650aadb33SDmitri Tikhonov    if (!(mask & ((1ULL <<  4) - 1))) { prio +=  4; mask >>=  4; }
17750aadb33SDmitri Tikhonov    if (!(mask & ((1ULL <<  2) - 1))) { prio +=  2; mask >>=  2; }
17850aadb33SDmitri Tikhonov    if (!(mask & ((1ULL <<  1) - 1))) { prio +=  1;              }
17950aadb33SDmitri Tikhonov
18050aadb33SDmitri Tikhonov#ifndef NDEBUG
18150aadb33SDmitri Tikhonov    set = prio >> 6;
18250aadb33SDmitri Tikhonov    bit = prio & 0x3F;
18350aadb33SDmitri Tikhonov    assert(iter->spi_set[ set ] & (1ULL << bit));
18450aadb33SDmitri Tikhonov#endif
18550aadb33SDmitri Tikhonov
18650aadb33SDmitri Tikhonov    SPI_DEBUG("%s: prio %u -> %u", __func__, iter->spi_cur_prio, prio);
1872d296031SDmitri Tikhonov    iter->spi_cur_prio = (unsigned char) prio;
18850aadb33SDmitri Tikhonov    return 0;
18950aadb33SDmitri Tikhonov}
19050aadb33SDmitri Tikhonov
19150aadb33SDmitri Tikhonov
19250aadb33SDmitri Tikhonov/* Each stream returned by the iterator is processed in some fashion.  If,
19350aadb33SDmitri Tikhonov * as a result of this, the stream gets taken off the original list, we
19450aadb33SDmitri Tikhonov * have to follow suit and remove it from the iterator's set of streams.
19550aadb33SDmitri Tikhonov */
19650aadb33SDmitri Tikhonovstatic void
19750aadb33SDmitri Tikhonovmaybe_evict_prev (struct stream_prio_iter *iter)
19850aadb33SDmitri Tikhonov{
19950aadb33SDmitri Tikhonov    unsigned set, bit;
20050aadb33SDmitri Tikhonov
20150aadb33SDmitri Tikhonov    if (0 == (iter->spi_prev_stream->stream_flags & iter->spi_onlist_mask))
20250aadb33SDmitri Tikhonov    {
20350aadb33SDmitri Tikhonov        SPI_DEBUG("evict stream %u", iter->spi_prev_stream->id);
20450aadb33SDmitri Tikhonov        TAILQ_REMOVE(&iter->spi_streams[ iter->spi_prev_prio ],
20550aadb33SDmitri Tikhonov                                    iter->spi_prev_stream, next_prio_stream);
20650aadb33SDmitri Tikhonov        if (TAILQ_EMPTY(&iter->spi_streams[ iter->spi_prev_prio ]))
20750aadb33SDmitri Tikhonov        {
20850aadb33SDmitri Tikhonov            set = iter->spi_prev_prio >> 6;
20950aadb33SDmitri Tikhonov            bit = iter->spi_prev_prio & 0x3F;
21050aadb33SDmitri Tikhonov            iter->spi_set[ set ] &= ~(1ULL << bit);
21150aadb33SDmitri Tikhonov            SPI_DEBUG("priority %u now has no elements", iter->spi_prev_prio);
21250aadb33SDmitri Tikhonov        }
21350aadb33SDmitri Tikhonov        iter->spi_prev_stream = NULL;
21450aadb33SDmitri Tikhonov    }
21550aadb33SDmitri Tikhonov}
21650aadb33SDmitri Tikhonov
21750aadb33SDmitri Tikhonov
21850aadb33SDmitri Tikhonovlsquic_stream_t *
21950aadb33SDmitri Tikhonovlsquic_spi_first (struct stream_prio_iter *iter)
22050aadb33SDmitri Tikhonov{
22150aadb33SDmitri Tikhonov    lsquic_stream_t *stream;
22250aadb33SDmitri Tikhonov    unsigned set, bit;
22350aadb33SDmitri Tikhonov
22450aadb33SDmitri Tikhonov    if (iter->spi_prev_stream)
22550aadb33SDmitri Tikhonov        maybe_evict_prev(iter);
22650aadb33SDmitri Tikhonov
22750aadb33SDmitri Tikhonov    iter->spi_cur_prio = 0;
22850aadb33SDmitri Tikhonov    set = iter->spi_cur_prio >> 6;
22950aadb33SDmitri Tikhonov    bit = iter->spi_cur_prio & 0x3F;
23050aadb33SDmitri Tikhonov
23150aadb33SDmitri Tikhonov    if (!(iter->spi_set[set] & (1ULL << bit)))
23250aadb33SDmitri Tikhonov    {
23350aadb33SDmitri Tikhonov        if (0 != find_and_set_lowest_priority(iter))
23450aadb33SDmitri Tikhonov        {
23550aadb33SDmitri Tikhonov            SPI_DEBUG("%s: return NULL", __func__);
23650aadb33SDmitri Tikhonov            return NULL;
23750aadb33SDmitri Tikhonov        }
23850aadb33SDmitri Tikhonov    }
23950aadb33SDmitri Tikhonov
24050aadb33SDmitri Tikhonov    stream = TAILQ_FIRST(&iter->spi_streams[ iter->spi_cur_prio ]);
24150aadb33SDmitri Tikhonov    iter->spi_prev_prio   = iter->spi_cur_prio;
24250aadb33SDmitri Tikhonov    iter->spi_prev_stream = stream;
24350aadb33SDmitri Tikhonov    iter->spi_next_stream = TAILQ_NEXT(stream, next_prio_stream);
24450aadb33SDmitri Tikhonov    if (stream->id != 1 && stream->id != 3)
24550aadb33SDmitri Tikhonov        SPI_DEBUG("%s: return stream %u, priority %u", __func__, stream->id,
24650aadb33SDmitri Tikhonov                                                            iter->spi_cur_prio);
24750aadb33SDmitri Tikhonov    return stream;
24850aadb33SDmitri Tikhonov}
24950aadb33SDmitri Tikhonov
25050aadb33SDmitri Tikhonov
25150aadb33SDmitri Tikhonovlsquic_stream_t *
25250aadb33SDmitri Tikhonovlsquic_spi_next (struct stream_prio_iter *iter)
25350aadb33SDmitri Tikhonov{
25450aadb33SDmitri Tikhonov    lsquic_stream_t *stream;
25550aadb33SDmitri Tikhonov
25650aadb33SDmitri Tikhonov    if (iter->spi_prev_stream)
25750aadb33SDmitri Tikhonov        maybe_evict_prev(iter);
25850aadb33SDmitri Tikhonov
25950aadb33SDmitri Tikhonov    stream = iter->spi_next_stream;
26050aadb33SDmitri Tikhonov    if (stream)
26150aadb33SDmitri Tikhonov    {
26250aadb33SDmitri Tikhonov        assert(iter->spi_prev_prio == iter->spi_cur_prio);
26350aadb33SDmitri Tikhonov        iter->spi_prev_stream = stream;
26450aadb33SDmitri Tikhonov        iter->spi_next_stream = TAILQ_NEXT(stream, next_prio_stream);
26550aadb33SDmitri Tikhonov        if (stream->id != 1 && stream->id != 3)
26650aadb33SDmitri Tikhonov            SPI_DEBUG("%s: return stream %u, priority %u", __func__, stream->id,
26750aadb33SDmitri Tikhonov                                                            iter->spi_cur_prio);
26850aadb33SDmitri Tikhonov        return stream;
26950aadb33SDmitri Tikhonov    }
27050aadb33SDmitri Tikhonov
27150aadb33SDmitri Tikhonov    if (0 != find_and_set_next_priority(iter))
27250aadb33SDmitri Tikhonov    {
27350aadb33SDmitri Tikhonov        //SPI_DEBUG("%s: return NULL", __func__);
27450aadb33SDmitri Tikhonov        return NULL;
27550aadb33SDmitri Tikhonov    }
27650aadb33SDmitri Tikhonov
27750aadb33SDmitri Tikhonov    stream = TAILQ_FIRST(&iter->spi_streams[ iter->spi_cur_prio ]);
27850aadb33SDmitri Tikhonov    iter->spi_prev_prio   = iter->spi_cur_prio;
27950aadb33SDmitri Tikhonov    iter->spi_prev_stream = stream;
28050aadb33SDmitri Tikhonov    iter->spi_next_stream = TAILQ_NEXT(stream, next_prio_stream);
28150aadb33SDmitri Tikhonov
282c51ce338SDmitri Tikhonov    if (!lsquic_stream_is_critical(stream))
28350aadb33SDmitri Tikhonov        SPI_DEBUG("%s: return stream %u, priority %u", __func__, stream->id,
28450aadb33SDmitri Tikhonov                                                        iter->spi_cur_prio);
28550aadb33SDmitri Tikhonov    return stream;
28650aadb33SDmitri Tikhonov}
28750aadb33SDmitri Tikhonov
28850aadb33SDmitri Tikhonov
289c51ce338SDmitri Tikhonovstatic int
290c51ce338SDmitri Tikhonovhave_non_critical_streams (const struct stream_prio_iter *iter)
291c51ce338SDmitri Tikhonov{
292c51ce338SDmitri Tikhonov    const struct lsquic_stream *stream;
293c51ce338SDmitri Tikhonov    TAILQ_FOREACH(stream, &iter->spi_streams[ iter->spi_cur_prio ],
294c51ce338SDmitri Tikhonov                                                        next_prio_stream)
295c51ce338SDmitri Tikhonov        if (!lsquic_stream_is_critical(stream))
296c51ce338SDmitri Tikhonov            return 1;
297c51ce338SDmitri Tikhonov    return 0;
298c51ce338SDmitri Tikhonov}
299c51ce338SDmitri Tikhonov
300c51ce338SDmitri Tikhonov
301c51ce338SDmitri Tikhonovstatic void
302c51ce338SDmitri Tikhonovspi_drop_high_or_non_high (struct stream_prio_iter *iter, int drop_high)
303c51ce338SDmitri Tikhonov{
304c51ce338SDmitri Tikhonov    uint64_t new_set[ sizeof(iter->spi_set) / sizeof(iter->spi_set[0]) ];
305c51ce338SDmitri Tikhonov    unsigned bit, set, n;
306c51ce338SDmitri Tikhonov
307c51ce338SDmitri Tikhonov    memset(new_set, 0, sizeof(new_set));
308c51ce338SDmitri Tikhonov
309c51ce338SDmitri Tikhonov    find_and_set_lowest_priority(iter);
310c51ce338SDmitri Tikhonov    set = iter->spi_cur_prio >> 6;
311c51ce338SDmitri Tikhonov    bit = iter->spi_cur_prio & 0x3F;
312c51ce338SDmitri Tikhonov    new_set[set] |= 1ULL << bit;
313c51ce338SDmitri Tikhonov
314c51ce338SDmitri Tikhonov    if (!have_non_critical_streams(iter))
315c51ce338SDmitri Tikhonov    {
316c51ce338SDmitri Tikhonov        ++iter->spi_cur_prio;
317c51ce338SDmitri Tikhonov        find_and_set_lowest_priority(iter);
318c51ce338SDmitri Tikhonov        set = iter->spi_cur_prio >> 6;
319c51ce338SDmitri Tikhonov        bit = iter->spi_cur_prio & 0x3F;
320c51ce338SDmitri Tikhonov        new_set[set] |= 1ULL << bit;
321c51ce338SDmitri Tikhonov    }
322c51ce338SDmitri Tikhonov
323c51ce338SDmitri Tikhonov    for (n = 0; n < sizeof(new_set) / sizeof(new_set[0]); ++n)
324c51ce338SDmitri Tikhonov        if (drop_high)
325c51ce338SDmitri Tikhonov            iter->spi_set[n] &= ~new_set[n];
326c51ce338SDmitri Tikhonov        else
327c51ce338SDmitri Tikhonov            iter->spi_set[n] = new_set[n];
328c51ce338SDmitri Tikhonov}
329c51ce338SDmitri Tikhonov
330c51ce338SDmitri Tikhonov
331c51ce338SDmitri Tikhonovvoid
332c51ce338SDmitri Tikhonovlsquic_spi_drop_high (struct stream_prio_iter *iter)
333c51ce338SDmitri Tikhonov{
334c51ce338SDmitri Tikhonov    spi_drop_high_or_non_high(iter, 1);
335c51ce338SDmitri Tikhonov}
336c51ce338SDmitri Tikhonov
337c51ce338SDmitri Tikhonov
33850aadb33SDmitri Tikhonovvoid
339c51ce338SDmitri Tikhonovlsquic_spi_drop_non_high (struct stream_prio_iter *iter)
34050aadb33SDmitri Tikhonov{
341c51ce338SDmitri Tikhonov    spi_drop_high_or_non_high(iter, 0);
34250aadb33SDmitri Tikhonov}
343