blob: b15bdf37dd7e971751ea2dfcdd81cc6bf77a5f7b [file] [log] [blame]
Neels Hofmeyr17518fe2017-06-20 04:35:06 +02001/*! \file gsm660.c
2 * GSM 06.60 - GSM EFR Codec. */
Sylvain Munaut1a4ea5b2010-10-08 15:09:16 +02003/*
4 * (C) 2010 Sylvain Munaut <tnt@246tNt.com>
5 *
6 * All Rights Reserved
7 *
Harald Weltee08da972017-11-13 01:00:26 +09008 * SPDX-License-Identifier: GPL-2.0+
9 *
Sylvain Munaut1a4ea5b2010-10-08 15:09:16 +020010 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation; either version 2 of the License, or
13 * (at your option) any later version.
14 *
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
19 *
Sylvain Munaut1a4ea5b2010-10-08 15:09:16 +020020 */
21
22#include <stdint.h>
Mychaela N. Falconia7f918802023-03-24 00:46:12 +000023#include <stdbool.h>
24
25#include <osmocom/core/bitvec.h>
26#include <osmocom/core/utils.h>
Harald Weltedee71722017-05-31 02:48:48 +020027#include <osmocom/codec/codec.h>
Sylvain Munaut1a4ea5b2010-10-08 15:09:16 +020028
29/* GSM EFR - subjective importance bit ordering */
30 /* This array encodes GSM 05.03 Table 6.
31 *
32 * It converts between serial parameter output (as described in
33 * GSM 06.60 Table 6 and GSM 05.03 Table 5) and the order needed
34 * before channel encoding. CRC poly and bit repetition must be
35 * applied prior to this table, as in GSM 05.03 3.1.1, to get 260
36 * bits from a 244 bits raw EFR frame.
37 */
Diego Elio Pettenò23431c72012-06-29 13:01:27 -070038const uint16_t gsm660_bitorder[260] = {
Sylvain Munaut1a4ea5b2010-10-08 15:09:16 +020039 38, 39, 40, 41, 42, 43, /* 0 -> LTP-LAG 1: b8..b3 */
40 145, 146, 147, 148, 149, 150, /* 6 -> LTP-LAG 3: b8..b3 */
41 93, 94, /* 12 -> LTP-LAG 2: b5..b4 */
42 200, 201, /* 14 -> LTP-LAG 4: b5..b4 */
43 47, /* 16 -> LTP-GAIN 1: b3 */
44 88, /* 17 -> FCB-GAIN 1: b4 */
45 99, /* 18 -> LTP-GAIN 2: b3 */
46 140, /* 19 -> FCB-GAIN 2: b4 */
47 44, /* 20 -> LTP-LAG 1: b2 */
48 151, /* 21 -> LTP-LAG 3: b2 */
49 95, /* 22 -> LTP-LAG 2: b3 */
50 202, /* 23 -> LTP-LAG 4: b3 */
51 1, 2, /* 24 -> LPC 1: b5..b4 */
52 7, /* 26 -> LPC 2: b7 */
53 9, /* 27 -> LPC 2: b5 */
54 17, 18, /* 28 -> LPC 3: b6..b5 */
55 23, /* 30 -> LPC 3: b0 */
56 45, 46, /* 31 -> LTP-LAG 1: b1..b0 */
57 152, 153, /* 33 -> LTP-LAG 3: b1..b0 */
58 96, /* 35 -> LTP-LAG 2: b2 */
59 203, /* 36 -> LTP-LAG 4: b2 */
60 3, 4, /* 37 -> LPC 1: b3..b2 */
61 10, 11, /* 39 -> LPC 2: b4..b3 */
62 15, /* 41 -> LPC 3: b8 */
63 8, /* 42 -> LPC 2: b6 */
64 5, 6, /* 43 -> LPC 1: b1..b0 */
65 12, /* 45 -> LPC 2: b2 */
66 16, /* 46 -> LPC 3: b7 */
67 19, /* 47 -> LPC 3: b4 */
68 97, /* 48 -> LTP-LAG 2: b1 */
69 204, /* 49 -> LTP-LAG 4: b1 */
70 0, /* 50 -> LPC 1: b6 */
71 13, 14, /* 51 -> LPC 2: b1..b0 */
72 20, /* 53 -> LPC 3: b3 */
73 24, 25, /* 54 -> LPC 4: b7..b6 */
74 27, /* 56 -> LPC 4: b4 */
75 154, /* 57 -> LTP-GAIN 3: b3 */
76 206, /* 58 -> LTP-GAIN 4: b3 */
77 195, /* 59 -> FCB-GAIN 3: b4 */
78 247, /* 60 -> FCB-GAIN 4: b4 */
79 89, /* 61 -> FCB-GAIN 1: b3 */
80 141, /* 62 -> FCB-GAIN 2: b3 */
81 196, /* 63 -> FCB-GAIN 3: b3 */
82 248, /* 64 -> FCB-GAIN 4: b3 */
83 252, 253, 254, 255, 256, 257, 258, 259, /* 65 -> CRC-POLY: b7..b0 */
84 48, /* 73 -> LTP-GAIN 1: b2 */
85 100, /* 74 -> LTP-GAIN 2: b2 */
86 155, /* 75 -> LTP-GAIN 3: b2 */
87 207, /* 76 -> LTP-GAIN 4: b2 */
88 21, 22, /* 77 -> LPC 3: b2..b1 */
89 26, /* 79 -> LPC 4: b5 */
90 28, /* 80 -> LPC 4: b3 */
91 51, /* 81 -> PULSE 1_1: b3 */
92 55, /* 82 -> PULSE 1_2: b3 */
93 59, /* 83 -> PULSE 1_3: b3 */
94 63, /* 84 -> PULSE 1_4: b3 */
95 67, /* 85 -> PULSE 1_5: b3 */
96 103, /* 86 -> PULSE 2_1: b3 */
97 107, /* 87 -> PULSE 2_2: b3 */
98 111, /* 88 -> PULSE 2_3: b3 */
99 115, /* 89 -> PULSE 2_4: b3 */
100 119, /* 90 -> PULSE 2_5: b3 */
101 158, /* 91 -> PULSE 3_1: b3 */
102 162, /* 92 -> PULSE 3_2: b3 */
103 166, /* 93 -> PULSE 3_3: b3 */
104 170, /* 94 -> PULSE 3_4: b3 */
105 174, /* 95 -> PULSE 3_5: b3 */
106 210, /* 96 -> PULSE 4_1: b3 */
107 214, /* 97 -> PULSE 4_2: b3 */
108 218, /* 98 -> PULSE 4_3: b3 */
109 222, /* 99 -> PULSE 4_4: b3 */
110 226, /* 100 -> PULSE 4_5: b3 */
111 90, /* 101 -> FCB-GAIN 1: b2 */
112 142, /* 102 -> FCB-GAIN 2: b2 */
113 197, /* 103 -> FCB-GAIN 3: b2 */
114 249, /* 104 -> FCB-GAIN 4: b2 */
115 49, /* 105 -> LTP-GAIN 1: b1 */
116 101, /* 106 -> LTP-GAIN 2: b1 */
117 156, /* 107 -> LTP-GAIN 3: b1 */
118 208, /* 108 -> LTP-GAIN 4: b1 */
119 29, 30, 31, /* 109 -> LPC 4: b2..b0 */
120 32, 33, 34, 35, /* 112 -> LPC 5: b5..b2 */
121 98, /* 116 -> LTP-LAG 2: b0 */
122 205, /* 117 -> LTP-LAG 4: b0 */
123 52, /* 118 -> PULSE 1_1: b2 */
124 56, /* 119 -> PULSE 1_2: b2 */
125 60, /* 120 -> PULSE 1_3: b2 */
126 64, /* 121 -> PULSE 1_4: b2 */
127 68, /* 122 -> PULSE 1_5: b2 */
128 104, /* 123 -> PULSE 2_1: b2 */
129 108, /* 124 -> PULSE 2_2: b2 */
130 112, /* 125 -> PULSE 2_3: b2 */
131 116, /* 126 -> PULSE 2_4: b2 */
132 120, /* 127 -> PULSE 2_5: b2 */
133 159, /* 128 -> PULSE 3_1: b2 */
134 163, /* 129 -> PULSE 3_2: b2 */
135 167, /* 130 -> PULSE 3_3: b2 */
136 171, /* 131 -> PULSE 3_4: b2 */
137 175, /* 132 -> PULSE 3_5: b2 */
138 211, /* 133 -> PULSE 4_1: b2 */
139 215, /* 134 -> PULSE 4_2: b2 */
140 219, /* 135 -> PULSE 4_3: b2 */
141 223, /* 136 -> PULSE 4_4: b2 */
142 227, /* 137 -> PULSE 4_5: b2 */
143 53, /* 138 -> PULSE 1_1: b1 */
144 57, /* 139 -> PULSE 1_2: b1 */
145 61, /* 140 -> PULSE 1_3: b1 */
146 65, /* 141 -> PULSE 1_4: b1 */
147 105, /* 142 -> PULSE 2_1: b1 */
148 109, /* 143 -> PULSE 2_2: b1 */
149 113, /* 144 -> PULSE 2_3: b1 */
150 117, /* 145 -> PULSE 2_4: b1 */
151 160, /* 146 -> PULSE 3_1: b1 */
152 164, /* 147 -> PULSE 3_2: b1 */
153 168, /* 148 -> PULSE 3_3: b1 */
154 172, /* 149 -> PULSE 3_4: b1 */
155 212, /* 150 -> PULSE 4_1: b1 */
156 220, /* 151 -> PULSE 4_3: b1 */
157 224, /* 152 -> PULSE 4_4: b1 */
158 91, /* 153 -> FCB-GAIN 1: b1 */
159 143, /* 154 -> FCB-GAIN 2: b1 */
160 198, /* 155 -> FCB-GAIN 3: b1 */
161 250, /* 156 -> FCB-GAIN 4: b1 */
162 50, /* 157 -> LTP-GAIN 1: b0 */
163 102, /* 158 -> LTP-GAIN 2: b0 */
164 157, /* 159 -> LTP-GAIN 3: b0 */
165 209, /* 160 -> LTP-GAIN 4: b0 */
166 92, /* 161 -> FCB-GAIN 1: b0 */
167 144, /* 162 -> FCB-GAIN 2: b0 */
168 199, /* 163 -> FCB-GAIN 3: b0 */
169 251, /* 164 -> FCB-GAIN 4: b0 */
170 54, /* 165 -> PULSE 1_1: b0 */
171 58, /* 166 -> PULSE 1_2: b0 */
172 62, /* 167 -> PULSE 1_3: b0 */
173 66, /* 168 -> PULSE 1_4: b0 */
174 106, /* 169 -> PULSE 2_1: b0 */
175 110, /* 170 -> PULSE 2_2: b0 */
176 114, /* 171 -> PULSE 2_3: b0 */
177 118, /* 172 -> PULSE 2_4: b0 */
178 161, /* 173 -> PULSE 3_1: b0 */
179 165, /* 174 -> PULSE 3_2: b0 */
180 169, /* 175 -> PULSE 3_3: b0 */
181 173, /* 176 -> PULSE 3_4: b0 */
182 213, /* 177 -> PULSE 4_1: b0 */
183 221, /* 178 -> PULSE 4_3: b0 */
184 225, /* 179 -> PULSE 4_4: b0 */
185 36, 37, /* 180 -> LPC 5: b1..b0 */
186 69, /* 182 -> PULSE 1_5: b1 */
187 71, 72, /* 183 -> PULSE 1_5: b1..b1 */
188 121, /* 185 -> PULSE 2_5: b1 */
189 123, 124, /* 186 -> PULSE 2_5: b1..b1 */
190 176, /* 188 -> PULSE 3_5: b1 */
191 178, 179, /* 189 -> PULSE 3_5: b1..b1 */
192 228, /* 191 -> PULSE 4_5: b1 */
193 230, 231, /* 192 -> PULSE 4_5: b1..b1 */
194 216, 217, /* 194 -> PULSE 4_2: b1..b0 */
195 70, /* 196 -> PULSE 1_5: b0 */
196 122, /* 197 -> PULSE 2_5: b0 */
197 177, /* 198 -> PULSE 3_5: b0 */
198 229, /* 199 -> PULSE 4_5: b0 */
199 73, /* 200 -> PULSE 1_6: b2 */
200 76, /* 201 -> PULSE 1_7: b2 */
201 79, /* 202 -> PULSE 1_8: b2 */
202 82, /* 203 -> PULSE 1_9: b2 */
203 85, /* 204 -> PULSE 1_10: b2 */
204 125, /* 205 -> PULSE 2_6: b2 */
205 128, /* 206 -> PULSE 2_7: b2 */
206 131, /* 207 -> PULSE 2_8: b2 */
207 134, /* 208 -> PULSE 2_9: b2 */
208 137, /* 209 -> PULSE 2_10: b2 */
209 180, /* 210 -> PULSE 3_6: b2 */
210 183, /* 211 -> PULSE 3_7: b2 */
211 186, /* 212 -> PULSE 3_8: b2 */
212 189, /* 213 -> PULSE 3_9: b2 */
213 192, /* 214 -> PULSE 3_10: b2 */
214 232, /* 215 -> PULSE 4_6: b2 */
215 235, /* 216 -> PULSE 4_7: b2 */
216 238, /* 217 -> PULSE 4_8: b2 */
217 241, /* 218 -> PULSE 4_9: b2 */
218 244, /* 219 -> PULSE 4_10: b2 */
219 74, /* 220 -> PULSE 1_6: b1 */
220 77, /* 221 -> PULSE 1_7: b1 */
221 80, /* 222 -> PULSE 1_8: b1 */
222 83, /* 223 -> PULSE 1_9: b1 */
223 86, /* 224 -> PULSE 1_10: b1 */
224 126, /* 225 -> PULSE 2_6: b1 */
225 129, /* 226 -> PULSE 2_7: b1 */
226 132, /* 227 -> PULSE 2_8: b1 */
227 135, /* 228 -> PULSE 2_9: b1 */
228 138, /* 229 -> PULSE 2_10: b1 */
229 181, /* 230 -> PULSE 3_6: b1 */
230 184, /* 231 -> PULSE 3_7: b1 */
231 187, /* 232 -> PULSE 3_8: b1 */
232 190, /* 233 -> PULSE 3_9: b1 */
233 193, /* 234 -> PULSE 3_10: b1 */
234 233, /* 235 -> PULSE 4_6: b1 */
235 236, /* 236 -> PULSE 4_7: b1 */
236 239, /* 237 -> PULSE 4_8: b1 */
237 242, /* 238 -> PULSE 4_9: b1 */
238 245, /* 239 -> PULSE 4_10: b1 */
239 75, /* 240 -> PULSE 1_6: b0 */
240 78, /* 241 -> PULSE 1_7: b0 */
241 81, /* 242 -> PULSE 1_8: b0 */
242 84, /* 243 -> PULSE 1_9: b0 */
243 87, /* 244 -> PULSE 1_10: b0 */
244 127, /* 245 -> PULSE 2_6: b0 */
245 130, /* 246 -> PULSE 2_7: b0 */
246 133, /* 247 -> PULSE 2_8: b0 */
247 136, /* 248 -> PULSE 2_9: b0 */
248 139, /* 249 -> PULSE 2_10: b0 */
249 182, /* 250 -> PULSE 3_6: b0 */
250 185, /* 251 -> PULSE 3_7: b0 */
251 188, /* 252 -> PULSE 3_8: b0 */
252 191, /* 253 -> PULSE 3_9: b0 */
253 194, /* 254 -> PULSE 3_10: b0 */
254 234, /* 255 -> PULSE 4_6: b0 */
255 237, /* 256 -> PULSE 4_7: b0 */
256 240, /* 257 -> PULSE 4_8: b0 */
257 243, /* 258 -> PULSE 4_9: b0 */
258 246, /* 259 -> PULSE 4_10: b0 */
259};
Mychaela N. Falconia7f918802023-03-24 00:46:12 +0000260
Mychaela N. Falconiaec650852023-04-16 01:34:35 +0000261static const uint8_t sid_code_word_bits[95] = {
262 /* bit numbers are relative to "pure" EFR frame beginning,
263 * not counting the signature bits. */
264 45, 46, 48, 49, 50, 51, 52, 53, 54, 55,
265 56, 57, 58, 59, 60, 61, 62, 63, 64, 65,
266 66, 67, 68, 94, 95, 96, 98, 99, 100, 101,
267 102, 103, 104, 105, 106, 107, 108, 109, 110, 111,
268 112, 113, 114, 115, 116, 117, 118, 148, 149, 150,
269 151, 152, 153, 154, 155, 156, 157, 158, 159, 160,
270 161, 162, 163, 164, 165, 166, 167, 168, 169, 170,
271 171, 196, 197, 198, 199, 200, 201, 202, 203, 204,
272 205, 206, 207, 208, 209, 212, 213, 214, 215, 216,
273 217, 218, 219, 220, 221
274};
275
Mychaela N. Falconia7f918802023-03-24 00:46:12 +0000276/*! Check whether RTP frame contains EFR SID code word according to
277 * TS 101 318 §5.3.2
278 * \param[in] rtp_payload Buffer with RTP payload
279 * \param[in] payload_len Length of payload
280 * \returns true if code word is found, false otherwise
281 */
282bool osmo_efr_check_sid(const uint8_t *rtp_payload, size_t payload_len)
283{
284 struct bitvec bv;
285 uint16_t i;
Mychaela N. Falconia7f918802023-03-24 00:46:12 +0000286
287 /* signature does not match Enhanced Full Rate SID */
288 if ((rtp_payload[0] >> 4) != 0xC)
289 return false;
290
291 bv.data = (uint8_t *) rtp_payload;
292 bv.data_len = payload_len;
293
294 /* code word is all 1 at given bits */
295 for (i = 0; i < ARRAY_SIZE(sid_code_word_bits); i++) {
296 if (bitvec_get_bit_pos(&bv, sid_code_word_bits[i]+4) != ONE)
297 return false;
298 }
299
300 return true;
301}
Mychaela N. Falconiaec650852023-04-16 01:34:35 +0000302
303/*! Classify potentially-SID EFR codec frame in RTP format according
304 * to the rules of GSM 06.81 §6.1.1
305 * \param[in] rtp_payload Buffer with RTP payload
306 * \returns enum osmo_gsm631_sid_class, with symbolic values
307 * OSMO_GSM631_SID_CLASS_SPEECH, OSMO_GSM631_SID_CLASS_INVALID or
308 * OSMO_GSM631_SID_CLASS_VALID corresponding to the 3 possible bit-counting
309 * classifications prescribed by the spec.
310 *
311 * Differences between the more familiar osmo_efr_check_sid() and the present
312 * function are:
313 *
314 * 1. osmo_efr_check_sid() returns true only if the SID frame is absolutely
315 * perfect, with all 95 bits of the SID code word set. However, the
316 * rules of GSM 06.81 §6.1.1 allow up to one bit to be in error,
317 * and the frame is still accepted as valid SID.
318 *
319 * 2. The third possible state of invalid SID is not handled at all by the
320 * simpler osmo_efr_check_sid() function.
321 *
322 * 3. osmo_efr_check_sid() includes a check for 0xC RTP signature, and returns
323 * false if that signature nibble is wrong. That check is not included
324 * in the present version because there is no place for it in the
325 * ETSI-prescribed classification, it is neither speech nor SID. The
326 * assumption is that this function is used to classify the bit content
327 * of received codec frames, not their RTP encoding - the latter needs
328 * to be validated beforehand.
329 *
330 * Which function should one use? The answer depends on the specific
331 * circumstances, and needs to be addressed on a case-by-case basis.
332 */
333enum osmo_gsm631_sid_class osmo_efr_sid_classify(const uint8_t *rtp_payload)
334{
335 struct bitvec bv;
336 uint16_t i, n;
337
338 bv.data = (uint8_t *) rtp_payload;
339 bv.data_len = GSM_EFR_BYTES;
340
341 /* count not-SID-matching bits per the spec */
342 n = 0;
343 for (i = 0; i < ARRAY_SIZE(sid_code_word_bits); i++) {
344 if (bitvec_get_bit_pos(&bv, sid_code_word_bits[i]+4) != ONE)
345 n++;
346 if (n >= 16)
347 return OSMO_GSM631_SID_CLASS_SPEECH;
348 }
349 if (n >= 2)
350 return OSMO_GSM631_SID_CLASS_INVALID;
351 else
352 return OSMO_GSM631_SID_CLASS_VALID;
353}
Mychaela N. Falconia295636b2023-04-16 17:19:50 +0000354
Mychaela N. Falconia2974a232023-05-26 20:38:02 +0000355/*! Reset the SID field of a potentially corrupted, but still valid GSM-EFR
356 * SID frame in RTP encoding to its pristine state (full SID code word).
357 * \param[in] rtp_payload Buffer with RTP payload - must be writable!
358 *
359 * Per GSM 06.62 section 5.3, a freshly minted SID frame consists of 58 bits
360 * of comfort noise parameters (LSF and 4 times fixed codebook gain), 95 bits
361 * of SID code word (all 1s) and 91 unused bits (all 0s). Network elements
362 * that receive SID frames from call leg A uplink and need to retransmit them
363 * on leg B downlink should "rejuvenate" received SID frames prior to
364 * retransmission by resetting the SID field to its pristine state of all 1s;
365 * this function does the job.
366 *
367 * Potential TODO: it would be nice to also zero out the remaining 91 bits
368 * which the spec leaves as reserved, clearing out leg A radio bit errors -
369 * but do we really need to?
370 */
371void osmo_efr_sid_reset(uint8_t *rtp_payload)
372{
373 /* set all 95 SID code word bits to 1 */
374 rtp_payload[6] |= 0x6F;
375 rtp_payload[7] = 0xFF;
376 rtp_payload[8] = 0xFF;
377 rtp_payload[9] |= 0x80;
378 rtp_payload[12] |= 0x3B;
379 rtp_payload[13] = 0xFF;
380 rtp_payload[14] = 0xFF;
381 rtp_payload[15] |= 0xE0;
382 rtp_payload[19] = 0xFF;
383 rtp_payload[20] = 0xFF;
384 rtp_payload[21] = 0xFF;
385 rtp_payload[25] = 0xFF;
386 rtp_payload[26] |= 0xFC;
387 rtp_payload[27] = 0xFF;
388 rtp_payload[28] |= 0xC0;
389}
390
Mychaela N. Falconia295636b2023-04-16 17:19:50 +0000391/*! Preen potentially-SID EFR codec frame in RTP format, ensuring that it is
392 * either a speech frame or a valid SID, and if the latter, making it a
393 * perfect, error-free SID frame.
394 * \param[in] rtp_payload Buffer with RTP payload - must be writable!
395 * \returns true if the frame is good, false otherwise
396 */
397bool osmo_efr_sid_preen(uint8_t *rtp_payload)
398{
399 enum osmo_gsm631_sid_class sidc;
400
401 sidc = osmo_efr_sid_classify(rtp_payload);
402 switch (sidc) {
403 case OSMO_GSM631_SID_CLASS_SPEECH:
404 return true;
405 case OSMO_GSM631_SID_CLASS_INVALID:
406 return false;
407 case OSMO_GSM631_SID_CLASS_VALID:
Mychaela N. Falconia2974a232023-05-26 20:38:02 +0000408 /* "Rejuvenate" this SID frame, correcting any errors */
409 osmo_efr_sid_reset(rtp_payload);
Mychaela N. Falconia295636b2023-04-16 17:19:50 +0000410 return true;
411 default:
412 /* There are only 3 possible SID classifications per GSM 06.81
413 * section 6.1.1, thus any other return value is a grave error
414 * in the code. */
415 OSMO_ASSERT(0);
416 }
417}