提交 63900a6d authored 作者: Dragos Oancea's avatar Dragos Oancea

FS-9664: mod_amr: add AMR NB transcoding capability in bandwidth-efficient mode.…

FS-9664: mod_amr: add AMR NB transcoding capability in bandwidth-efficient mode. Tested with VOLTE devices.
上级 7d6ed4a4
LEGAL.
Please bear in mind that the software, as modified by Athonet, implements
functions for the AMR standard, which are covered by third parties' essential patents.
To the best of Athonet's knowledge, such essential patent rights holders are:
Nokia, Orange, Acacia (now VoiceAge) and Ericsson.
ATHONET HEREBY DISCLAIMS ANY AND ALL LIABILITY IN CASE YOUR USE,
MODIFICATION, COPY OR FURTHER DISTRIBUTION OF THE SOFTWARE, AS
MODIFIED BY ATHONET, INFRINGES IN ANY WAY THIRD PARTY'S INTELLECTUAL PROPERTY RIGHTS.
THIS DISCLAIMER SHALL NOT PREJUDICE ANY OTHER LIMITATION OF LIABILITY
INCLUDED IN THE APPLICABLE LICENSE.
include $(top_srcdir)/build/modmake.rulesam
MODNAME=mod_amr
AMR_DIR=$(switch_srcdir)/libs/amr
AMR_BUILDDIR=$(switch_builddir)/libs/amr
AMR_A=$(AMR_BUILDDIR)/libamr.a
mod_LTLIBRARIES = mod_amr.la
mod_amr_la_SOURCES = mod_amr.c
if HAVE_AMR
mod_amr_la_SOURCES = mod_amr.c bitshift.c amr_be.c
else
mod_amr_la_SOURCES = mod_amr.c
endif
mod_amr_la_CFLAGS = $(AM_CFLAGS)
mod_amr_la_LIBADD = $(switch_builddir)/libfreeswitch.la
mod_amr_la_LDFLAGS = -avoid-version -module -no-undefined -shared
if HAVE_AMR
BUILT_SOURCES= $(AMR_A)
mod_amr_la_CFLAGS += -I$(AMR_DIR)
mod_amr_la_LIBADD += $(AMR_A)
# install AMR library opencore-amrnb (check README)
mod_amr_la_CFLAGS += -I/usr/include/opencore-amrnb
mod_amr_la_LIBADD += -lopencore-amrnb
mod_amr_la_CFLAGS +=
else
mod_amr_la_CFLAGS += -DAMR_PASSTHROUGH
endif
......
Tested with mobile devices (VOLTE) :
Samsung S6 Edge, iPhone, Samsung Note4, Samsung S6
INSTALL
1. install the AMR library debs
libopencore-amrnb-dev - Adaptive Multi Rate speech codec - development files
libopencore-amrnb0 - Adaptive Multi Rate speech codec - shared library
libopencore-amrnb0-dbg - Adaptive Multi Rate speech codec - debugging symbols
apt-get install libopencore-amrnb-dev libopencore-amrnb0 libopencore-amrnb0-dbg
This was tested on Debian 8
2. copy these two files in the current directory (mod_amr)
cp ./usr/include/opencore-amrnb/interf_enc.h .
cp ./usr/include/opencore-amrnb/interf_dec.h .
3. run make, make install
/*
* Copyright (c) 2016, Athonet (www.athonet.com)
* Dragos Oancea <dragos.oancea@athonet.com>
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* * Neither the name of the original author; nor the names of any contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
* OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef __AMR_BE_H__
#include "bitshift.h"
#include "amr_be.h"
extern const int switch_amr_frame_sizes[];
/* Bandwidth Efficient AMR-NB */
/* https://tools.ietf.org/html/rfc4867#page-17 */
extern switch_bool_t switch_amr_pack_be(unsigned char *shift_buf, int n)
{
uint8_t save_toc, ft;
save_toc = shift_buf[1];
/* we must convert OA TOC -> BE TOC */
/* OA TOC
0 1 2 3 4 5 6 7
+-+-+-+-+-+-+-+-+
|F| FT |Q|P1|P2|
+-+-+-+-+-+-+-+-+
F (1 bit): see definition in Section 4.3.2.
FT (4 bits, unsigned integer): see definition in Section 4.3.2.
Q (1 bit): see definition in Section 4.3.2.
P bits: padding bits, MUST be set to zero, and MUST be ignored on reception.
*/
/* BE TOC:
0 1 2 3 4 5
+-+-+-+-+-+-+
|F| FT |Q|
+-+-+-+-+-+-+
F = 0 , FT = XXXX , Q = 1
eg: Frame Types (FT): ftp://www.3gpp.org/tsg_sa/TSG_SA/TSGS_04/Docs/PDF/SP-99253.pdf - table 1a
*/
ft = save_toc >> 3 ; /* drop Q, P1, P2 */
ft &= ~(1 << 5); /* clear - will mark just 1 frame - bit F */
/* we only encode one frame, so bit 0 of TOC will be 0 */
shift_buf[0] |= (ft >> 1); /* first 3 bits of FT */
switch_amr_array_lshift(6, shift_buf+1, n);
/*make sure we clear the bit - it will be used as padding of the trailing byte */
shift_buf[1] |= 1 << 6; /* set bit Q instead of P1 */
if (( ft >> 0 ) & 1) {
/* set last bit of TOC instead of P2 */
shift_buf[1] |= 1 << 7;
} else {
/* reset last bit of TOC instead of P2 */
shift_buf[1] &= ~(1 << 7);
}
return SWITCH_TRUE;
}
extern switch_bool_t switch_amr_unpack_be(unsigned char *encoded_buf, uint8_t *tmp, int encoded_len)
{
int framesz, index, ft;
uint8_t shift_tocs[2] = {0x00, 0x00};
uint8_t *shift_buf;
memcpy(shift_tocs, encoded_buf, 2);
/* shift for BE */
switch_amr_array_lshift(4, shift_tocs, 2);
ft = shift_tocs[0] >> 3;
ft &= ~(1 << 5); /* Frame Type*/
shift_buf = encoded_buf + 1; /* skip CMR */
/* shift for BE */
switch_amr_array_lshift(2, shift_buf, encoded_len - 1);
/* get frame size */
index = ((shift_tocs[0] >> 3) & 0x0f);
if (index > 9) {
return SWITCH_FALSE;
}
framesz = switch_amr_frame_sizes[index];
tmp[0] = shift_tocs[0]; /* save TOC */
memcpy(&tmp[1], shift_buf, framesz);
return SWITCH_TRUE;
}
#endif
/* For Emacs:
* Local Variables:
* mode:c
* indent-tabs-mode:t
* tab-width:4
* c-basic-offset:4
* End:
* For VIM:
* vim:set softtabstop=4 shiftwidth=4 tabstop=4 noet:
*/
/*
* Copyright (c) 2016, Athonet (www.athonet.com)
* Dragos Oancea <dragos.oancea@athonet.com>
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* * Neither the name of the original author; nor the names of any contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
* OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef __AMR_BE_H__
#define __AMR_BE_H__
/* Bandwidth Efficient AMR */
extern switch_bool_t switch_amr_pack_be(unsigned char *shift_buf, int n);
extern switch_bool_t switch_amr_unpack_be(unsigned char *encoded_buf, uint8_t *tmp, int encoded_len);
#endif
/* For Emacs:
* Local Variables:
* mode:c
* indent-tabs-mode:t
* tab-width:4
* c-basic-offset:4
* End:
* For VIM:
* vim:set softtabstop=4 shiftwidth=4 tabstop=4 noet:
*/
/*
* Copyright (c) 2016, Athonet (www.athonet.com)
* Paolo Missiaggia <paolo.missiaggia@athonet.com>
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* * Neither the name of the original author; nor the names of any contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
* OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef __BITSHIFT_H__
#include "bitshift.h"
/*
* LEFT shift of an entire array of N bits, with N included between 0 and 8
*/
extern int switch_amr_array_lshift(uint8_t lshift, uint8_t *buf, int a_len)
{
int i = 0;
uint8_t first_byte;
uint8_t second_byte;
if (!buf || !a_len)
return (-1);
if ((lshift < 0) || (lshift > 8))
return (-1);
first_byte = 0xFF >> lshift;
second_byte = ~first_byte;
for (i = 1; i < a_len; i++) {
buf[i - 1] = ((buf[i - 1] & first_byte) << lshift) |
((buf[i] & second_byte) >> (8 - lshift));
}
i--;
buf[i] = ((buf[i] & first_byte) << lshift);
return (0);
}
#endif
/* For Emacs:
* Local Variables:
* mode:c
* indent-tabs-mode:t
* tab-width:4
* c-basic-offset:4
* End:
* For VIM:
* vim:set softtabstop=4 shiftwidth=4 tabstop=4 noet:
*/
/*
* Copyright (c) 2016, Athonet (www.athonet.com)
* Paolo Missiaggia <paolo.missiaggia@athonet.com>
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* * Neither the name of the original author; nor the names of any contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
* OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#ifndef __BITSHIFT_H__
#define __BITSHIFT_H__
#include "switch.h"
/*
* LEFT shift of an entire array of N bits, with N included between 0 and 8
*/
extern int switch_amr_array_lshift(uint8_t lshift, uint8_t *buf, int a_len);
#endif
/* For Emacs:
* Local Variables:
* mode:c
* indent-tabs-mode:t
* tab-width:4
* c-basic-offset:4
* End:
* For VIM:
* vim:set softtabstop=4 shiftwidth=4 tabstop=4 noet:
*/
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论