annotate src/twjit.c @ 3:d10ea5dc61b3

twjit: initial import from previous work repository The initial development of twjit was done in a private branch of osmo-bts git repository; the intent was to prototype twjit in osmo-bts. However, as I am getting a better feel for the full scope of the problem (producing a replacement for libortp), I changed course to the present themwi-rtp-lib (libtwrtp) approach.
author Mychaela Falconia <falcon@freecalypso.org>
date Fri, 05 Jul 2024 18:50:48 +0000
parents
children 1bb26347e253
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
3
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
1 /*
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
2 * Themyscira Wireless jitter buffer implementation: code body.
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
3 */
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
4
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
5 #include <stdint.h>
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
6 #include <stdbool.h>
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
7 #include <string.h>
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
8 #include <arpa/inet.h> /* for network byte order functions */
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
9
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
10 #include <osmocom/core/linuxlist.h>
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
11 #include <osmocom/core/msgb.h>
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
12 #include <osmocom/core/talloc.h>
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
13 #include <osmocom/core/timer.h>
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
14 #include <osmocom/core/utils.h>
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
15
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
16 /* FIXME: this libosmo-netif dependency needs to be removed */
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
17 #include <osmocom/netif/rtp.h>
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
18
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
19 #include <themwi/rtp/twjit.h>
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
20
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
21 void twrtp_jibuf_init_defaults(struct twrtp_jibuf_config *config)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
22 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
23 memset(config, 0, sizeof(struct twrtp_jibuf_config));
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
24 config->bd_start = 2; /* smallest allowed */
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
25 config->bd_hiwat = 3; /* Nstart+1 is practically-useful minimum */
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
26 config->thinning_int = 17; /* prime number, usually 340 ms */
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
27 config->max_future_sec = 10; /* 10 s is a long time for voice */
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
28 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
29
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
30 /* create and destroy functions */
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
31
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
32 struct twrtp_jibuf_inst *
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
33 twrtp_jibuf_create(void *ctx, uint16_t quantum_ms, uint32_t quantum_ts_inc,
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
34 struct twrtp_jibuf_config *config)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
35 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
36 struct twrtp_jibuf_inst *twjit;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
37
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
38 twjit = talloc_zero(ctx, struct twrtp_jibuf_inst);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
39 if (!twjit)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
40 return NULL;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
41
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
42 twjit->ext_config = config;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
43 twjit->ts_quantum = quantum_ts_inc;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
44 twjit->quanta_per_sec = 1000 / quantum_ms;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
45 twjit->state = TWJIT_STATE_EMPTY;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
46 INIT_LLIST_HEAD(&twjit->sb[0].queue);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
47 INIT_LLIST_HEAD(&twjit->sb[1].queue);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
48
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
49 return twjit;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
50 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
51
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
52 void twrtp_jibuf_destroy(struct twrtp_jibuf_inst *twjit)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
53 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
54 msgb_queue_free(&twjit->sb[0].queue);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
55 msgb_queue_free(&twjit->sb[1].queue);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
56 talloc_free(twjit);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
57 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
58
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
59 /* RTP input to twjit */
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
60
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
61 static void get_current_time(struct timeval *tp)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
62 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
63 struct timespec now;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
64
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
65 osmo_clock_gettime(CLOCK_MONOTONIC, &now);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
66 tp->tv_sec = now.tv_sec;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
67 tp->tv_usec = now.tv_nsec / 1000;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
68 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
69
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
70 static void
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
71 init_subbuf_first_packet(struct twrtp_jibuf_inst *twjit, struct msgb *msg,
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
72 uint32_t rx_ssrc, uint32_t rx_ts,
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
73 const struct timeval *new_time)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
74 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
75 struct twrtp_jibuf_sub *sb = &twjit->sb[twjit->write_sb];
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
76
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
77 OSMO_ASSERT(llist_empty(&sb->queue));
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
78 OSMO_ASSERT(sb->depth == 0);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
79 /* all good, proceed */
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
80 sb->ssrc = rx_ssrc;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
81 sb->head_ts = rx_ts;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
82 msgb_enqueue(&sb->queue, msg);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
83 sb->depth = 1;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
84 memcpy(&sb->last_arrival, &new_time, sizeof(struct timeval));
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
85 memcpy(&sb->conf, twjit->ext_config, sizeof(struct twrtp_jibuf_config));
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
86 sb->drop_int_count = 0;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
87 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
88
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
89 enum input_decision {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
90 INPUT_CONTINUE,
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
91 INPUT_TOO_OLD,
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
92 INPUT_RESET,
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
93 };
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
94
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
95 static enum input_decision
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
96 check_input_for_subbuf(struct twrtp_jibuf_inst *twjit, bool starting,
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
97 uint32_t rx_ssrc, uint32_t rx_ts,
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
98 const struct timeval *new_time)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
99 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
100 struct twrtp_jibuf_sub *sb = &twjit->sb[twjit->write_sb];
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
101 struct timeval time_delta;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
102 int32_t ts_delta;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
103
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
104 if (rx_ssrc != sb->ssrc)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
105 return INPUT_RESET;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
106 if (starting) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
107 timersub(new_time, &sb->last_arrival, &time_delta);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
108 sb->delta_ms = time_delta.tv_sec * 1000 +
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
109 time_delta.tv_usec / 1000;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
110 memcpy(&sb->last_arrival, new_time, sizeof(struct timeval));
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
111 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
112 ts_delta = (int32_t)(rx_ts - sb->head_ts);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
113 if (ts_delta < 0)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
114 return INPUT_TOO_OLD;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
115 if (ts_delta % twjit->ts_quantum)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
116 return INPUT_RESET;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
117 if (starting) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
118 if (sb->conf.start_max_delta &&
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
119 sb->delta_ms > sb->conf.start_max_delta)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
120 return INPUT_RESET;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
121 } else {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
122 uint32_t fwd = ts_delta / twjit->ts_quantum;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
123
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
124 if (fwd >= sb->conf.max_future_sec * twjit->quanta_per_sec)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
125 return INPUT_RESET;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
126 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
127 return INPUT_CONTINUE;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
128 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
129
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
130 static void toss_write_queue(struct twrtp_jibuf_inst *twjit)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
131 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
132 struct twrtp_jibuf_sub *sb = &twjit->sb[twjit->write_sb];
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
133
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
134 msgb_queue_free(&sb->queue);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
135 sb->depth = 0;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
136 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
137
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
138 static void insert_pkt_write_sb(struct twrtp_jibuf_inst *twjit,
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
139 struct msgb *new_msg, uint32_t rx_ts)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
140 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
141 struct twrtp_jibuf_sub *sb = &twjit->sb[twjit->write_sb];
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
142 uint32_t ts_delta = rx_ts - sb->head_ts;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
143 uint32_t ins_depth = ts_delta / twjit->ts_quantum;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
144 struct msgb *old_msg;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
145 uint32_t old_ts_delta;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
146
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
147 /* are we increasing total depth, and can we do simple tail append? */
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
148 if (ins_depth >= sb->depth) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
149 msgb_enqueue(&sb->queue, new_msg);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
150 sb->depth = ins_depth + 1;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
151 return;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
152 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
153 /* nope - do it the hard way */
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
154 llist_for_each_entry(old_msg, &sb->queue, list) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
155 old_ts_delta = old_msg->cb[0] - sb->head_ts;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
156 if (old_ts_delta == ts_delta) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
157 /* two packets with the same timestamp! */
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
158 twjit->stats.duplicate_ts++;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
159 msgb_free(new_msg);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
160 return;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
161 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
162 if (old_ts_delta > ts_delta)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
163 break;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
164 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
165 llist_add_tail(&new_msg->list, &old_msg->list);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
166 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
167
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
168 static void trim_starting_sb(struct twrtp_jibuf_inst *twjit)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
169 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
170 struct twrtp_jibuf_sub *sb = &twjit->sb[twjit->write_sb];
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
171 struct msgb *msg;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
172 uint32_t msg_ts, ts_adv, quantum_adv;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
173
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
174 while (sb->depth > sb->conf.bd_start) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
175 msg = msgb_dequeue(&sb->queue);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
176 OSMO_ASSERT(msg);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
177 msgb_free(msg);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
178 OSMO_ASSERT(!llist_empty(&sb->queue));
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
179 msg = llist_entry(sb->queue.next, struct msgb, list);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
180 msg_ts = msg->cb[0];
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
181 ts_adv = msg_ts - sb->head_ts;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
182 quantum_adv = ts_adv / twjit->ts_quantum;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
183 OSMO_ASSERT(sb->depth > quantum_adv);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
184 sb->head_ts = msg_ts;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
185 sb->depth -= quantum_adv;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
186 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
187 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
188
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
189 static void rx_raw_analytics(struct twrtp_jibuf_inst *twjit, uint32_t rx_ssrc,
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
190 uint16_t rx_seq, uint32_t rx_ts)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
191 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
192 int16_t seq_delta;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
193 int32_t ts_delta;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
194
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
195 if (twjit->last_ssrc != rx_ssrc) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
196 twjit->stats.ssrc_changes++;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
197 return;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
198 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
199 seq_delta = (int16_t)(rx_seq - twjit->last_seq);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
200 if (seq_delta < 0)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
201 twjit->stats.seq_backwards++;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
202 else if (seq_delta == 0)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
203 twjit->stats.seq_repeats++;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
204 else if (seq_delta == 1) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
205 ts_delta = (int32_t)(rx_ts - twjit->last_ts);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
206 if (ts_delta != twjit->ts_quantum) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
207 if (ts_delta > 0 && (ts_delta % twjit->ts_quantum) == 0)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
208 twjit->stats.intentional_gaps++;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
209 else
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
210 twjit->stats.ts_resets++;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
211 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
212 } else
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
213 twjit->stats.seq_skips++;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
214 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
215
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
216 void twrtp_jibuf_input(struct twrtp_jibuf_inst *twjit, struct msgb *msg)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
217 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
218 struct rtp_hdr *rtph;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
219 uint32_t rx_ssrc, rx_ts;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
220 uint16_t rx_seq;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
221 struct timeval new_time;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
222 enum input_decision id;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
223
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
224 rtph = osmo_rtp_get_hdr(msg);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
225 if (!rtph) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
226 /* invalid packet, couldn't even get header from it */
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
227 twjit->stats.bad_packets++;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
228 msgb_free(msg);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
229 return;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
230 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
231 rx_ssrc = ntohl(rtph->ssrc);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
232 rx_ts = ntohl(rtph->timestamp);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
233 rx_seq = ntohs(rtph->sequence);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
234 get_current_time(&new_time);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
235 if (twjit->got_first_packet)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
236 rx_raw_analytics(twjit, rx_ssrc, rx_seq, rx_ts);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
237 twjit->last_ssrc = rx_ssrc;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
238 twjit->last_seq = rx_seq;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
239 twjit->last_ts = rx_ts;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
240 twjit->got_first_packet = true;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
241 msg->cb[0] = rx_ts;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
242
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
243 switch (twjit->state) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
244 case TWJIT_STATE_EMPTY:
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
245 /* first packet into totally empty buffer */
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
246 twjit->state = TWJIT_STATE_HUNT;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
247 twjit->write_sb = 0;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
248 init_subbuf_first_packet(twjit, msg, rx_ssrc, rx_ts, &new_time);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
249 return;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
250 case TWJIT_STATE_HUNT:
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
251 case TWJIT_STATE_HANDOVER:
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
252 id = check_input_for_subbuf(twjit, true, rx_ssrc, rx_ts,
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
253 &new_time);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
254 if (id == INPUT_TOO_OLD) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
255 msgb_free(msg);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
256 return;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
257 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
258 if (id == INPUT_RESET) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
259 toss_write_queue(twjit);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
260 init_subbuf_first_packet(twjit, msg, rx_ssrc, rx_ts,
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
261 &new_time);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
262 return;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
263 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
264 insert_pkt_write_sb(twjit, msg, rx_ts);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
265 trim_starting_sb(twjit);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
266 return;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
267 case TWJIT_STATE_FLOWING:
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
268 id = check_input_for_subbuf(twjit, false, rx_ssrc, rx_ts,
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
269 &new_time);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
270 if (id == INPUT_TOO_OLD) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
271 twjit->stats.too_old++;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
272 msgb_free(msg);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
273 return;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
274 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
275 if (id == INPUT_RESET) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
276 twjit->state = TWJIT_STATE_HANDOVER;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
277 twjit->write_sb = !twjit->write_sb;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
278 init_subbuf_first_packet(twjit, msg, rx_ssrc, rx_ts,
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
279 &new_time);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
280 twjit->stats.handovers++;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
281 return;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
282 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
283 insert_pkt_write_sb(twjit, msg, rx_ts);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
284 return;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
285 default:
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
286 OSMO_ASSERT(0);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
287 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
288 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
289
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
290 /* Output from twjit to the fixed timing system */
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
291
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
292 static bool starting_sb_is_ready(struct twrtp_jibuf_inst *twjit)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
293 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
294 struct twrtp_jibuf_sub *sb = &twjit->sb[twjit->write_sb];
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
295
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
296 if (sb->depth < sb->conf.bd_start)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
297 return false;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
298 if (sb->delta_ms < sb->conf.start_min_delta)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
299 return false;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
300 return true;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
301 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
302
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
303 static bool read_sb_is_empty(struct twrtp_jibuf_inst *twjit)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
304 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
305 struct twrtp_jibuf_sub *sb = &twjit->sb[twjit->read_sb];
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
306
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
307 return sb->depth == 0;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
308 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
309
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
310 static struct msgb *pull_from_read_sb(struct twrtp_jibuf_inst *twjit)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
311 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
312 struct twrtp_jibuf_sub *sb = &twjit->sb[twjit->read_sb];
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
313 struct msgb *msg;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
314
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
315 OSMO_ASSERT(!llist_empty(&sb->queue));
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
316 OSMO_ASSERT(sb->depth > 0);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
317 msg = llist_entry(sb->queue.next, struct msgb, list);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
318 if (msg->cb[0] == sb->head_ts) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
319 llist_del(&msg->list);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
320 twjit->stats.delivered_pkt++;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
321 twjit->stats.delivered_bytes += msg->len;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
322 } else {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
323 msg = NULL;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
324 twjit->stats.output_gaps++;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
325 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
326 sb->head_ts += twjit->ts_quantum;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
327 sb->depth--;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
328 return msg;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
329 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
330
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
331 static void read_sb_thinning(struct twrtp_jibuf_inst *twjit)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
332 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
333 struct twrtp_jibuf_sub *sb = &twjit->sb[twjit->read_sb];
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
334 struct msgb *msg;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
335
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
336 if (sb->drop_int_count) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
337 sb->drop_int_count--;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
338 return;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
339 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
340 if (sb->depth <= sb->conf.bd_hiwat)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
341 return;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
342 twjit->stats.thinning_drops++;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
343 msg = pull_from_read_sb(twjit);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
344 if (msg)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
345 msgb_free(msg);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
346 sb->drop_int_count = sb->conf.thinning_int - 2;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
347 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
348
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
349 static void toss_read_queue(struct twrtp_jibuf_inst *twjit)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
350 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
351 struct twrtp_jibuf_sub *sb = &twjit->sb[twjit->read_sb];
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
352
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
353 msgb_queue_free(&sb->queue);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
354 sb->depth = 0;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
355 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
356
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
357 struct msgb *twrtp_jibuf_output(struct twrtp_jibuf_inst *twjit)
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
358 {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
359 switch (twjit->state) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
360 case TWJIT_STATE_EMPTY:
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
361 return NULL;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
362 case TWJIT_STATE_HUNT:
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
363 if (!starting_sb_is_ready(twjit))
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
364 return NULL;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
365 twjit->state = TWJIT_STATE_FLOWING;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
366 twjit->read_sb = twjit->write_sb;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
367 return pull_from_read_sb(twjit);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
368 case TWJIT_STATE_FLOWING:
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
369 if (read_sb_is_empty(twjit)) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
370 twjit->state = TWJIT_STATE_EMPTY;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
371 twjit->stats.underruns++;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
372 return NULL;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
373 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
374 read_sb_thinning(twjit);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
375 return pull_from_read_sb(twjit);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
376 case TWJIT_STATE_HANDOVER:
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
377 if (starting_sb_is_ready(twjit)) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
378 toss_read_queue(twjit);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
379 twjit->state = TWJIT_STATE_FLOWING;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
380 twjit->read_sb = twjit->write_sb;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
381 return pull_from_read_sb(twjit);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
382 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
383 if (read_sb_is_empty(twjit)) {
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
384 twjit->state = TWJIT_STATE_HUNT;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
385 twjit->stats.underruns++;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
386 return NULL;
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
387 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
388 read_sb_thinning(twjit);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
389 return pull_from_read_sb(twjit);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
390 default:
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
391 OSMO_ASSERT(0);
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
392 }
d10ea5dc61b3 twjit: initial import from previous work repository
Mychaela Falconia <falcon@freecalypso.org>
parents:
diff changeset
393 }