Preparation for iLBC support.

git-svn-id: http://voip.null.ro/svn/yate@532 acf43c95-373e-0410-b603-e72c3f656dc1
This commit is contained in:
paulc 2005-09-30 22:46:16 +00:00
parent 57ec4cbe9b
commit e0e593b0f7
5 changed files with 78 additions and 15 deletions

View File

@ -216,19 +216,20 @@ AC_SUBST(HAVE_GSM)
AC_SUBST(GSM_INC)
HAVE_ILBC=no
ILBC_INC=""
AC_ARG_ENABLE(ilbc,AC_HELP_STRING([--enable-ilbc],[Enable iLBC codec]),want_ilbc=$enableval,want_ilbc=yes)
if [[ "x$want_ilbc" = "xyes" ]]; then
HAVE_ILBC=yes
fi
AC_MSG_CHECKING([for iLBC in contrib])
inci10="contrib/ilbc"
if [[ -f "$basedir/$inci10/iLBC_encode.h" ]]; then
HAVE_ILBC=yes
ILBC_INC="-I$basedir/$inci2"
ILBC_DEP="../$inci2/libiax.a"
ILBC_DEP="../$inci2/libilbc.a"
fi
AC_MSG_RESULT([$HAVE_ILBC])
fi
AC_SUBST(HAVE_ILBC)
AC_SUBST(ILBC_INC)
HAVE_PWLIB=no
PWLIB_RTTI=none

View File

@ -44,7 +44,7 @@ using namespace TelEngine;
static TokenDict dict_iaxformats[] = {
// audio formats
{ "gsm", AST_FORMAT_GSM },
{ "ilbc", AST_FORMAT_ILBC },
{ "ilbc30", AST_FORMAT_ILBC },
{ "speex", AST_FORMAT_SPEEX },
{ "lpc10", AST_FORMAT_LPC10 },
{ "mulaw", AST_FORMAT_ULAW },

View File

@ -44,6 +44,8 @@ public:
private:
void detectAuFormat();
void detectWavFormat();
void detectIlbcFormat();
bool computeDataRate();
CallEndpoint* m_chan;
DataBlock m_data;
int m_fd;
@ -117,7 +119,7 @@ private:
INIT_PLUGIN(WaveFileDriver);
WaveSource::WaveSource(const String& file, CallEndpoint* chan, bool autoclose)
: m_chan(chan), m_fd(-1), m_swap(false), m_brate(16000),
: m_chan(chan), m_fd(-1), m_swap(false), m_brate(0),
m_total(0), m_time(0), m_autoclose(autoclose)
{
Debug(&__plugin,DebugAll,"WaveSource::WaveSource(\"%s\",%p) [%p]",file.c_str(),chan,this);
@ -132,25 +134,28 @@ WaveSource::WaveSource(const String& file, CallEndpoint* chan, bool autoclose)
m_format.clear();
return;
}
if (file.endsWith(".gsm")) {
if (file.endsWith(".gsm"))
m_format = "gsm";
m_brate = 1650;
}
else if (file.endsWith(".alaw") || file.endsWith(".A")) {
else if (file.endsWith(".alaw") || file.endsWith(".A"))
m_format = "alaw";
m_brate = 8000;
}
else if (file.endsWith(".mulaw") || file.endsWith(".u")) {
else if (file.endsWith(".mulaw") || file.endsWith(".u"))
m_format = "mulaw";
m_brate = 8000;
}
else if (file.endsWith(".ilbc20"))
m_format = "ilbc20";
else if (file.endsWith(".ilbc30"))
m_format = "ilbc30";
else if (file.endsWith(".au"))
detectAuFormat();
else if (file.endsWith(".wav"))
detectWavFormat();
else if (file.endsWith(".lbc"))
detectIlbcFormat();
else if (!file.endsWith(".slin"))
Debug(DebugMild,"Unknown format for file '%s', assuming signed linear",file.c_str());
start("WaveSource");
if (computeDataRate())
start("WaveSource");
else
Debug(DebugWarn,"Unable to compute data rate for file '%s'",file.c_str());
}
WaveSource::~WaveSource()
@ -217,6 +222,35 @@ void WaveSource::detectWavFormat()
Debug(DebugMild,".wav not supported yet, assuming raw signed linear");
}
#define ILBC_HEADER_LEN 9
void WaveSource::detectIlbcFormat()
{
char header[ILBC_HEADER_LEN+1];
if (::read(m_fd,&header,ILBC_HEADER_LEN) == ILBC_HEADER_LEN) {
header[ILBC_HEADER_LEN] = '\0';
if (::strcmp(header,"#!iLBC20\n") == 0) {
m_format = "ilbc20";
return;
}
else if (::strcmp(header,"#!iLBC30\n") == 0) {
m_format = "ilbc30";
return;
}
}
Debug(DebugMild,"Invalid iLBC file, assuming raw signed linear");
}
bool WaveSource::computeDataRate()
{
if (m_brate)
return true;
const FormatInfo* info = m_format.getInfo();
if (!info)
return false;
m_brate = info->dataRate();
return (m_brate != 0);
}
void WaveSource::run()
{
unsigned long ts = 0;
@ -293,6 +327,10 @@ WaveConsumer::WaveConsumer(const String& file, CallEndpoint* chan, unsigned maxl
m_format = "alaw";
else if (file.endsWith(".mulaw") || file.endsWith(".u"))
m_format = "mulaw";
else if (file.endsWith(".ilbc20"))
m_format = "ilbc20";
else if (file.endsWith(".ilbc30"))
m_format = "ilbc30";
m_fd = ::creat(file.safe(),S_IRUSR|S_IWUSR);
if (m_fd < 0)
Debug(DebugGoOn,"Creating '%s': error %d: %s",

View File

@ -44,6 +44,9 @@ static TokenDict dict_payloads[] = {
{ "g723", 4 },
{ "g728", 15 },
{ "g729", 18 },
{ "ilbc", 98 },
{ "ilbc20", 98 },
{ "ilbc30", 98 },
{ "h261", 31 },
{ "h263", 34 },
{ "mpv", 32 },

View File

@ -42,6 +42,9 @@ static TokenDict dict_payloads[] = {
{ "g723", 4 },
{ "g728", 15 },
{ "g729", 18 },
{ "ilbc", 98 },
{ "ilbc20", 98 },
{ "ilbc30", 98 },
{ "h261", 31 },
{ "h263", 34 },
{ "mpv", 32 },
@ -60,6 +63,7 @@ static TokenDict dict_rtpmap[] = {
{ "G723/8000", 4 },
{ "G728/8000", 15 },
{ "G729/8000", 18 },
{ "iLBC/8000", 98 },
{ "H261/90000", 31 },
{ "H263/90000", 34 },
{ "MPV/90000", 32 },
@ -1663,10 +1667,16 @@ SDPBody* YateSIPConnection::createSDP(const char* addr, ObjList* mediaList)
frm = *m;
frm << " " << m->localPort() << " RTP/AVP";
ObjList rtpmap;
int ptime = 0;
ObjList* f = l;
for (; f; f = f->next()) {
String* s = static_cast<String*>(f->get());
if (s) {
int mode = 0;
if (*s == "ilbc20")
ptime = mode = 20;
else if (*s == "ilbc30")
ptime = mode = 30;
int payload = s->toInteger(dict_payloads,-1);
if (payload >= 0) {
const char* map = lookup(payload,dict_rtpmap);
@ -1675,6 +1685,11 @@ SDPBody* YateSIPConnection::createSDP(const char* addr, ObjList* mediaList)
String* temp = new String("rtpmap:");
*temp << payload << " " << map;
rtpmap.append(temp);
if (mode) {
temp = new String("fmtp:");
*temp << payload << " mode=" << mode;
rtpmap.append(temp);
}
}
}
}
@ -1687,6 +1702,12 @@ SDPBody* YateSIPConnection::createSDP(const char* addr, ObjList* mediaList)
rtpmap.append(new String("rtpmap:101 telephone-event/8000"));
}
if (ptime) {
String* temp = new String("ptime:");
*temp << ptime;
rtpmap.append(temp);
}
sdp->addLine("m",frm);
for (f = rtpmap.skipNull(); f; f = f->skipNext()) {
String* s = static_cast<String*>(f->get());