falconia has uploaded this change for review. ( https://gerrit.osmocom.org/c/libosmo-abis/+/41159?usp=email )
Change subject: trau: factor out V.110 frame conversion functions ......................................................................
trau: factor out V.110 frame conversion functions
Implementation of CSD conversion between TRAU frames and CLEARMODE inside osmo_trau2rtp() and osmo_rtp2trau() contains lower-level functions for conversion of individual V.110 frames and for alignment checking. Factor these functions out into API, as they are useful for other applications besides TRAU<->RTP conversion:
* Compression and decompression functions that convert between standard (but inefficient) CLEARMODE and compressed-CSD RTP format of TW-TS-007;
* Implementations of IWFs that terminate CSD RTP streams at the CN and support both CLEARMODE and TW-TS-007.
Change-Id: I3f51254b4b985a0f8499c375b61069ca24f77ae8 --- M include/Makefile.am A include/osmocom/trau/csd_v110.h M src/Makefile.am A src/trau/csd_v110.c 4 files changed, 160 insertions(+), 0 deletions(-)
git pull ssh://gerrit.osmocom.org:29418/libosmo-abis refs/changes/59/41159/1
diff --git a/include/Makefile.am b/include/Makefile.am index 565e3cb..862292e 100644 --- a/include/Makefile.am +++ b/include/Makefile.am @@ -27,6 +27,7 @@ osmocom/trau/clearmode.h \ osmocom/trau/csd_ra2.h \ osmocom/trau/csd_raa_prime.h \ + osmocom/trau/csd_v110.h \ osmocom/trau/tfo_frame.h \ osmocom/trau/trau_frame.h \ osmocom/trau/trau_pcu_ericsson.h \ diff --git a/include/osmocom/trau/csd_v110.h b/include/osmocom/trau/csd_v110.h new file mode 100644 index 0000000..05d4ed5 --- /dev/null +++ b/include/osmocom/trau/csd_v110.h @@ -0,0 +1,40 @@ +/* + * This header file defines the public API for some helper functions that + * work with CSD V.110 frames represented in the standard 64 kbit/s CLEARMODE + * format of 3GPP TS 48.103, _without_ compression per TW-TS-007, but _with_ + * Osmocom-introduced constraint that the pair or quadruple of V.110 frames + * in RA2 encoding has to be naturally aligned within each 20 ms RTP packet. + * + * Author: Mychaela N. Falconia falcon@freecalypso.org, 2025 - however, + * Mother Mychaela's contributions are NOT subject to copyright. + * No rights reserved, all rights relinquished. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#pragma once + +#include <stdint.h> +#include <stdbool.h> +#include <osmocom/core/bits.h> + +/* conversion from distilled 63-bit format (as used in TRAU frames) to full + * 80-bit V.110 format, with or without RA2. */ + +void osmo_csd_63bits_to_v110_bits(ubit_t *out, const ubit_t *in); +void osmo_csd_63bits_to_v110_ir8(uint8_t *out, const ubit_t *in); +void osmo_csd_63bits_to_v110_ir16(uint8_t *out, const ubit_t *in); + +/* functions to verify V.110 frame alignment after RA2 decoding, and to convert + * to our distilled 63-bit format. */ + +bool osmo_csd_check_v110_align(const ubit_t *ra_bits); +void osmo_csd_v110_to_63bits(ubit_t *out, const ubit_t *ra_bits); diff --git a/src/Makefile.am b/src/Makefile.am index fc5b59b..6683d44 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -53,6 +53,7 @@ $(NULL) libosmotrau_la_LIBADD = $(COMMONLIBS) $(LIBOSMOCODEC_LIBS) $(ORTP_LIBS) libosmotrau_la_SOURCES = trau/csd_ra2.c \ + trau/csd_v110.c \ trau/raa_prime_decode.c \ trau/raa_prime_encode.c \ trau/tfo_frame.c \ diff --git a/src/trau/csd_v110.c b/src/trau/csd_v110.c new file mode 100644 index 0000000..431073c --- /dev/null +++ b/src/trau/csd_v110.c @@ -0,0 +1,118 @@ +/* + * This C module contains the implementation of CSD V.110 helper functions + * for CLEARMODE defined in <osmocom/trau/csd_v110.h>. + * + * Author: Mychaela N. Falconia falcon@freecalypso.org, 2025 - however, + * Mother Mychaela's contributions are NOT subject to copyright. + * No rights reserved, all rights relinquished. + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + */ + +#include <stdint.h> +#include <stdbool.h> +#include <string.h> + +#include <osmocom/core/bits.h> +#include <osmocom/trau/csd_ra2.h> +#include <osmocom/trau/csd_v110.h> + +/*! Convert V.110 frame from distilled 63-bit form (as it appears in TRAU + * frames) to full 80-bit form by adding sync pattern bits. + * \param[out] out buffer of size 80 ubit_t + * \param[in] in 63-bit distilled V.110 frame + */ +void osmo_csd_63bits_to_v110_bits(ubit_t *out, const ubit_t *in) +{ + int i; + + /* the first 8 bits are sync zeros */ + memset(out, 0, 8); + out += 8; + /* for the rest, we have to expand 63 bits into 72 */ + for (i = 0; i < 9; i++) { + *out++ = 1; + memcpy(out, in, 7); + in += 7; + out += 7; + } +} + +/*! Convert V.110 frame from distilled 63-bit form (as it appears in TRAU + * frames) to external octet form (RA2 with 8 kbit/s IR) form by adding + * sync pattern bits and applying RA2. + * \param[out] out buffer of size 80 octets + * \param[in] in 63-bit distilled V.110 frame + */ +void osmo_csd_63bits_to_v110_ir8(uint8_t *out, const ubit_t *in) +{ + ubit_t ra_bits[80]; + + osmo_csd_63bits_to_v110_bits(ra_bits, in); + /* RA2: 1 bit per output byte */ + osmo_csd_ra2_8k_pack(out, ra_bits, 80); +} + +/*! Convert V.110 frame from distilled 63-bit form (as it appears in TRAU + * frames) to external octet form (RA2 with 16 kbit/s IR) form by adding + * sync pattern bits and applying RA2. + * \param[out] out buffer of size 40 octets + * \param[in] in 63-bit distilled V.110 frame + */ +void osmo_csd_63bits_to_v110_ir16(uint8_t *out, const ubit_t *in) +{ + ubit_t ra_bits[80]; + + osmo_csd_63bits_to_v110_bits(ra_bits, in); + /* RA2: 2 bits per output byte */ + osmo_csd_ra2_16k_pack(out, ra_bits, 40); +} + +/*! Check alignment of unpacked 80-bit V.110 frame. + * \param[in] ra_bits candidate V.110 frame in standard 80-bit form + * \returns true if V.110 alignment pattern is correct, false otherwise + */ +bool osmo_csd_check_v110_align(const ubit_t *ra_bits) +{ + int i; + + for (i = 0; i < 8; i++) { + if (ra_bits[i]) + return false; + } + for (i = 1; i < 10; i++) { + if (!ra_bits[i * 8]) + return false; + } + return true; +} + +/*! Convert V.110 frame from standard 80-bit form (unpacked) to + * our distilled 63-bit form (as it appears in TRAU frames). + * \param[out] out buffer of size 63 ubit_t + * \param[in] in 80-bit standard V.110 frame + * + * This function ignores all 17 sync pattern bits and assumes that the + * V.110 frame is correctly aligned. Therefore, this function should + * be called after osmo_csd_check_v110_align(). + */ +void osmo_csd_v110_to_63bits(ubit_t *out, const ubit_t *ra_bits) +{ + memcpy(out, ra_bits + 9, 7); + memcpy(out + 7, ra_bits + 17, 7); + memcpy(out + 14, ra_bits + 25, 7); + memcpy(out + 21, ra_bits + 33, 7); + memcpy(out + 28, ra_bits + 41, 7); + memcpy(out + 35, ra_bits + 49, 7); + memcpy(out + 42, ra_bits + 57, 7); + memcpy(out + 49, ra_bits + 65, 7); + memcpy(out + 56, ra_bits + 73, 7); +}