mirror of
https://github.com/signalwire/freeswitch.git
synced 2026-10-31 07:34:19 +00:00
Merge branch 'master' into smgmaster
This commit is contained in:
commit
f1dc7b1ddb
398 files changed
+38753
-4037
No files matched your search
@@ -643,7 +643,9 @@
|
||||
/spandsp/src/at_interpreter_dictionary.h
|
||||
/spandsp/src/config.h
|
||||
/spandsp/src/make_at_dictionary
|
||||
/spandsp/src/make_math_fixed_tables
|
||||
/spandsp/src/make_modem_filter
|
||||
/spandsp/src/math_fixed_tables.h
|
||||
/spandsp/src/spandsp.h
|
||||
/spandsp/src/stamp-h1
|
||||
/spandsp/src/v17_v32bis_rx_fixed_rrc.h
|
||||
@@ -917,6 +919,8 @@
|
||||
/unimrcp/build/pkgconfig/unimrcpclient.pc
|
||||
/unimrcp/build/pkgconfig/unimrcpplugin.pc
|
||||
/unimrcp/build/pkgconfig/unimrcpserver.pc
|
||||
/unimrcp/build/svnrev/Makefile
|
||||
/unimrcp/build/svnrev/Makefile.in
|
||||
/unimrcp/conf/Makefile
|
||||
/unimrcp/conf/Makefile.in
|
||||
/unimrcp/config.log
|
||||
@@ -924,6 +928,7 @@
|
||||
/unimrcp/configure
|
||||
/unimrcp/data/Makefile
|
||||
/unimrcp/data/Makefile.in
|
||||
/unimrcp/docs/doxygen.conf
|
||||
/unimrcp/libs/Makefile
|
||||
/unimrcp/libs/Makefile.in
|
||||
/unimrcp/libs/apr-toolkit/Makefile
|
||||
@@ -981,6 +986,8 @@
|
||||
/unimrcp/plugins/mrcp-pocketsphinx/Makefile.in
|
||||
/unimrcp/plugins/mrcp-recorder/Makefile
|
||||
/unimrcp/plugins/mrcp-recorder/Makefile.in
|
||||
/unimrcp/plugins/demo-verifier/Makefile
|
||||
/unimrcp/plugins/demo-verifier/Makefile.in
|
||||
/unimrcp/tests/Makefile
|
||||
/unimrcp/tests/Makefile.in
|
||||
/unimrcp/tests/apttest/Makefile
|
||||
|
||||
@@ -1284,7 +1284,7 @@ if test "$ac_cv_sizeof_size_t" = "$ac_cv_sizeof_int"; then
|
||||
elif test "$ac_cv_sizeof_size_t" = "$ac_cv_sizeof_long"; then
|
||||
size_t_fmt='#define APR_SIZE_T_FMT "ld"'
|
||||
else
|
||||
size_t_fmt='#error Can not determine the proper size for size_t'
|
||||
size_t_fmt='#define APR_SIZE_T_FMT "zu"'
|
||||
fi
|
||||
|
||||
APR_CHECK_SIZEOF_EXTENDED([#include <sys/types.h>], off_t, 8)
|
||||
|
||||
@@ -409,7 +409,7 @@ APR_DECLARE(int) apr_pool_is_ancestor(apr_pool_t *a, apr_pool_t *b);
|
||||
* @param pool The pool to tag
|
||||
* @param tag The tag
|
||||
*/
|
||||
APR_DECLARE(void) apr_pool_tag(apr_pool_t *pool, const char *tag);
|
||||
APR_DECLARE(char *) apr_pool_tag(apr_pool_t *pool, const char *tag);
|
||||
|
||||
#if APR_HAS_THREADS
|
||||
/**
|
||||
|
||||
@@ -1895,9 +1895,13 @@ APR_DECLARE(int) apr_pool_is_ancestor(apr_pool_t *a, apr_pool_t *b)
|
||||
return 0;
|
||||
}
|
||||
|
||||
APR_DECLARE(void) apr_pool_tag(apr_pool_t *pool, const char *tag)
|
||||
APR_DECLARE(char *) apr_pool_tag(apr_pool_t *pool, const char *tag)
|
||||
{
|
||||
pool->tag = tag;
|
||||
if (tag) {
|
||||
pool->tag = tag;
|
||||
}
|
||||
|
||||
return pool->tag;
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -311,7 +311,6 @@ ESL_DECLARE(esl_status_t) esl_event_del_header_val(esl_event_t *event, const cha
|
||||
|
||||
if (hp->idx) {
|
||||
int i = 0;
|
||||
hp->value = NULL;
|
||||
|
||||
for (i = 0; i < hp->idx; i++) {
|
||||
FREE(hp->array[i]);
|
||||
@@ -642,7 +641,7 @@ ESL_DECLARE(void) esl_event_destroy(esl_event_t **event)
|
||||
|
||||
if (this->idx) {
|
||||
int i = 0;
|
||||
this->value = NULL;
|
||||
|
||||
for (i = 0; i < this->idx; i++) {
|
||||
FREE(this->array[i]);
|
||||
}
|
||||
|
||||
@@ -275,5 +275,37 @@ with the signaling protocols that you can run on top of your I/O interfaces.
|
||||
-->
|
||||
</span>
|
||||
</r2_spans>
|
||||
|
||||
<!--
|
||||
PRI passive tapping spans. Requires patched version from libpri at http://svn.digium.com/svn/libpri/team/moy/tap-1.4
|
||||
You must also configure FreeTDM with "-with-pritap" (see ./configure help for details)
|
||||
-->
|
||||
<pritap_spans>
|
||||
<span name="tapped1">
|
||||
<!-- The peer span name used to tap the link -->
|
||||
<param name="peerspan" value="tapped2"/>
|
||||
|
||||
<!--
|
||||
Whether to mix the audio from the peerspan with the audio from this span
|
||||
This is most likely what you want (and therefore the default) so you can hear
|
||||
the full conversation being tapped instead of just one side
|
||||
-->
|
||||
<!-- <param name="mixaudio" value="yes"/> -->
|
||||
|
||||
<!-- switch parameters (required), where to send calls to -->
|
||||
<param name="dialplan" value="XML"/>
|
||||
<param name="context" value="default"/>
|
||||
</span>
|
||||
|
||||
<span name="tapped2">
|
||||
<!-- This span is linked to "tapped1" through its peerspan parameter -->
|
||||
<param name="peerspan" value="tapped1"/>
|
||||
<!-- <param name="mixaudio" value="yes"/> -->
|
||||
|
||||
<!-- switch parameters (required), where to send calls to -->
|
||||
<param name="dialplan" value="XML"/>
|
||||
<param name="context" value="default"/>
|
||||
</span>
|
||||
</pritap_spans>
|
||||
</configuration>
|
||||
|
||||
@@ -2806,7 +2806,7 @@ static ftdm_status_t ftdmchan_activate_dtmf_buffer(ftdm_channel_t *ftdmchan)
|
||||
static ftdm_status_t ftdm_insert_dtmf_pause(ftdm_channel_t *ftdmchan, ftdm_size_t pausems)
|
||||
{
|
||||
void *data = NULL;
|
||||
unsigned int datalen = pausems * sizeof(uint16_t);
|
||||
ftdm_size_t datalen = pausems * sizeof(uint16_t);
|
||||
|
||||
data = ftdm_malloc(datalen);
|
||||
ftdm_assert(data, "Failed to allocate memory\n");
|
||||
@@ -3800,7 +3800,6 @@ FT_DECLARE(void) ftdm_generate_sln_silence(int16_t *data, uint32_t samples, uint
|
||||
|
||||
FT_DECLARE(ftdm_status_t) ftdm_channel_process_media(ftdm_channel_t *ftdmchan, void *data, ftdm_size_t *datalen)
|
||||
{
|
||||
ftdm_status_t status = FTDM_FAIL;
|
||||
fio_codec_t codec_func = NULL;
|
||||
ftdm_size_t max = *datalen;
|
||||
|
||||
@@ -3822,11 +3821,10 @@ FT_DECLARE(ftdm_status_t) ftdm_channel_process_media(ftdm_channel_t *ftdmchan, v
|
||||
}
|
||||
|
||||
if (codec_func) {
|
||||
status = codec_func(data, max, datalen);
|
||||
codec_func(data, max, datalen);
|
||||
} else {
|
||||
snprintf(ftdmchan->last_error, sizeof(ftdmchan->last_error), "codec error!");
|
||||
ftdm_log_chan(ftdmchan, FTDM_LOG_ERROR, "no codec function to perform transcoding from %d to %d\n", ftdmchan->native_codec, ftdmchan->effective_codec);
|
||||
status = FTDM_FAIL;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3861,7 +3859,6 @@ FT_DECLARE(ftdm_status_t) ftdm_channel_process_media(ftdm_channel_t *ftdmchan, v
|
||||
} else {
|
||||
snprintf(ftdmchan->last_error, sizeof(ftdmchan->last_error), "codec error!");
|
||||
ftdm_log_chan(ftdmchan, FTDM_LOG_ERROR, "invalid effective codec %d\n", ftdmchan->effective_codec);
|
||||
status = FTDM_FAIL;
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
@@ -4591,6 +4588,7 @@ static ftdm_status_t load_config(void)
|
||||
ftdm_analog_start_type_t tmp;
|
||||
ftdm_size_t len = 0;
|
||||
ftdm_channel_config_t chan_config;
|
||||
ftdm_status_t ret = FTDM_SUCCESS;
|
||||
|
||||
memset(&chan_config, 0, sizeof(chan_config));
|
||||
sprintf(chan_config.group_name, "__default");
|
||||
@@ -4627,6 +4625,13 @@ static ftdm_status_t load_config(void)
|
||||
*name++ = '\0';
|
||||
}
|
||||
|
||||
/* Verify is trunk_type was specified for previous span */
|
||||
if (span && span->trunk_type == FTDM_TRUNK_NONE) {
|
||||
ftdm_log(FTDM_LOG_ERROR, "trunk_type not specified for span %d (%s)\n", span->span_id, span->name);
|
||||
ret = FTDM_FAIL;
|
||||
goto done;
|
||||
}
|
||||
|
||||
if (ftdm_span_create(type, name, &span) == FTDM_SUCCESS) {
|
||||
ftdm_log(FTDM_LOG_DEBUG, "created span %d (%s) of type %s\n", span->span_id, span->name, type);
|
||||
d = 0;
|
||||
@@ -4824,11 +4829,22 @@ static ftdm_status_t load_config(void)
|
||||
ftdm_log(FTDM_LOG_ERROR, "unknown param [%s] '%s' / '%s'\n", cfg.category, var, val);
|
||||
}
|
||||
}
|
||||
|
||||
/* Verify is trunk_type was specified for the last span */
|
||||
if (span && span->trunk_type == FTDM_TRUNK_NONE) {
|
||||
ftdm_log(FTDM_LOG_ERROR, "trunk_type not specified for span %d (%s)\n", span->span_id, span->name);
|
||||
ret = FTDM_FAIL;
|
||||
}
|
||||
|
||||
done:
|
||||
ftdm_config_close_file(&cfg);
|
||||
|
||||
ftdm_log(FTDM_LOG_INFO, "Configured %u channel(s)\n", configured);
|
||||
if (!configured) {
|
||||
ret = FTDM_FAIL;
|
||||
}
|
||||
|
||||
return configured ? FTDM_SUCCESS : FTDM_FAIL;
|
||||
return ret;
|
||||
}
|
||||
|
||||
static ftdm_status_t process_module_config(ftdm_io_interface_t *fio)
|
||||
|
||||
@@ -401,7 +401,7 @@ static void analog_dial(ftdm_channel_t *ftdmchan, uint32_t *state_counter, uint3
|
||||
ftdmchan->needed_tones[FTDM_TONEMAP_FAIL1] = 1;
|
||||
ftdmchan->needed_tones[FTDM_TONEMAP_FAIL2] = 1;
|
||||
ftdmchan->needed_tones[FTDM_TONEMAP_FAIL3] = 1;
|
||||
*dial_timeout = ((ftdmchan->dtmf_on + ftdmchan->dtmf_off) * strlen(ftdmchan->caller_data.dnis.digits)) + 2000;
|
||||
*dial_timeout = (uint32_t)((ftdmchan->dtmf_on + ftdmchan->dtmf_off) * strlen(ftdmchan->caller_data.dnis.digits)) + 2000;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -932,6 +932,7 @@ static void *ftdm_analog_channel_run(ftdm_thread_t *me, void *obj)
|
||||
ftdm_channel_lock(closed_chan);
|
||||
|
||||
if (ftdmchan->type == FTDM_CHAN_TYPE_FXO && ftdm_test_flag(ftdmchan, FTDM_CHANNEL_OFFHOOK)) {
|
||||
ftdm_log_chan_msg(ftdmchan, FTDM_LOG_DEBUG, "Going onhook");
|
||||
ftdm_channel_command(ftdmchan, FTDM_COMMAND_ONHOOK, NULL);
|
||||
}
|
||||
|
||||
|
||||
@@ -34,6 +34,10 @@
|
||||
#include "private/ftdm_core.h"
|
||||
#include "ftmod_libpri.h"
|
||||
|
||||
#ifndef MIN
|
||||
#define MIN(x,y) (((x) < (y)) ? (x) : (y))
|
||||
#endif
|
||||
|
||||
static void _ftdm_channel_set_state_force(ftdm_channel_t *chan, const ftdm_channel_state_t state)
|
||||
{
|
||||
assert(chan);
|
||||
@@ -476,7 +480,7 @@ static ftdm_state_map_t isdn_state_map = {
|
||||
ZSD_INBOUND,
|
||||
ZSM_UNACCEPTABLE,
|
||||
{FTDM_CHANNEL_STATE_DOWN, FTDM_END},
|
||||
{FTDM_CHANNEL_STATE_DIALTONE, FTDM_CHANNEL_STATE_RING, FTDM_END}
|
||||
{FTDM_CHANNEL_STATE_DIALTONE, FTDM_CHANNEL_STATE_COLLECT, FTDM_CHANNEL_STATE_RING, FTDM_END}
|
||||
},
|
||||
{
|
||||
ZSD_INBOUND,
|
||||
@@ -484,6 +488,12 @@ static ftdm_state_map_t isdn_state_map = {
|
||||
{FTDM_CHANNEL_STATE_DIALTONE, FTDM_END},
|
||||
{FTDM_CHANNEL_STATE_RING, FTDM_CHANNEL_STATE_HANGUP, FTDM_CHANNEL_STATE_TERMINATING, FTDM_END}
|
||||
},
|
||||
{
|
||||
ZSD_INBOUND,
|
||||
ZSM_UNACCEPTABLE,
|
||||
{FTDM_CHANNEL_STATE_COLLECT, FTDM_END},
|
||||
{FTDM_CHANNEL_STATE_RING, FTDM_CHANNEL_STATE_HANGUP, FTDM_CHANNEL_STATE_TERMINATING, FTDM_END}
|
||||
},
|
||||
{
|
||||
ZSD_INBOUND,
|
||||
ZSM_UNACCEPTABLE,
|
||||
@@ -656,6 +666,29 @@ static ftdm_status_t state_advance(ftdm_channel_t *chan)
|
||||
}
|
||||
break;
|
||||
|
||||
case FTDM_CHANNEL_STATE_COLLECT: /* Overlap receive */
|
||||
{
|
||||
if (!ftdm_test_flag(chan, FTDM_CHANNEL_OUTBOUND)) {
|
||||
if (!call) {
|
||||
ftdm_log_chan_msg(chan, FTDM_LOG_ERROR, "No call handle\n");
|
||||
ftdm_set_state_locked(chan, FTDM_CHANNEL_STATE_RESTART);
|
||||
}
|
||||
else if (pri_need_more_info(isdn_data->spri.pri, call, ftdm_channel_get_id(chan), 0)) {
|
||||
ftdm_caller_data_t *caller_data = ftdm_channel_get_caller_data(chan);
|
||||
|
||||
ftdm_log_chan_msg(chan, FTDM_LOG_ERROR, "Failed to send INFORMATION request\n");
|
||||
|
||||
/* hangup call */
|
||||
caller_data->hangup_cause = FTDM_CAUSE_DESTINATION_OUT_OF_ORDER;
|
||||
ftdm_set_state_locked(chan, FTDM_CHANNEL_STATE_HANGUP);
|
||||
}
|
||||
} else {
|
||||
ftdm_log_chan_msg(chan, FTDM_LOG_ERROR, "Overlap receiving on outbound call?\n");
|
||||
ftdm_set_state_locked(chan, FTDM_CHANNEL_STATE_RESTART);
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case FTDM_CHANNEL_STATE_RING:
|
||||
{
|
||||
/*
|
||||
@@ -837,11 +870,57 @@ static __inline__ void check_state(ftdm_span_t *span)
|
||||
*/
|
||||
static int on_info(lpwrap_pri_t *spri, lpwrap_pri_event_t event_type, pri_event *pevent)
|
||||
{
|
||||
ftdm_log(FTDM_LOG_DEBUG, "number is: %s\n", pevent->ring.callednum);
|
||||
ftdm_span_t *span = spri->span;
|
||||
ftdm_channel_t *chan = ftdm_span_get_channel(span, pevent->ring.channel);
|
||||
ftdm_caller_data_t *caller_data = NULL;
|
||||
|
||||
if (strlen(pevent->ring.callednum) > 3) {
|
||||
ftdm_log(FTDM_LOG_DEBUG, "final number is: %s\n", pevent->ring.callednum);
|
||||
pri_answer(spri->pri, pevent->ring.call, 0, 1);
|
||||
if (!chan) {
|
||||
ftdm_log(FTDM_LOG_CRIT, "-- Info on channel %d:%d %s but it's not in use?\n", ftdm_span_get_id(span), pevent->ring.channel);
|
||||
return 0;
|
||||
}
|
||||
|
||||
caller_data = ftdm_channel_get_caller_data(chan);
|
||||
|
||||
switch (ftdm_channel_get_state(chan)) {
|
||||
case FTDM_CHANNEL_STATE_COLLECT: /* TE-mode overlap receiving */
|
||||
ftdm_log_chan(chan, FTDM_LOG_DEBUG, "-- Incoming INFORMATION indication, current called number: '%s', number complete: %s\n",
|
||||
pevent->ring.callednum, pevent->ring.complete ? "yes" : "no");
|
||||
|
||||
/* append digits to dnis */
|
||||
if (!ftdm_strlen_zero(pevent->ring.callednum)) {
|
||||
int digits = strlen(pevent->ring.callednum);
|
||||
int offset = strlen(caller_data->dnis.digits);
|
||||
int len = MIN(sizeof(caller_data->dnis.digits) - 1 - offset, digits); /* max. length without terminator */
|
||||
|
||||
if (len < digits) {
|
||||
ftdm_log_chan(chan, FTDM_LOG_WARNING, "Length %d of digit string exceeds available space %d of DNIS, truncating!\n",
|
||||
digits, len);
|
||||
}
|
||||
|
||||
ftdm_copy_string(&caller_data->dnis.digits[offset], (char *)pevent->ring.callednum, len + 1); /* max. length with terminator */
|
||||
caller_data->dnis.digits[offset + len] = '\0';
|
||||
}
|
||||
if (pevent->ring.complete) {
|
||||
ftdm_log_chan_msg(chan, FTDM_LOG_DEBUG, "Number complete indicated, moving channel to RING state\n");
|
||||
/* notify switch */
|
||||
ftdm_set_state(chan, FTDM_CHANNEL_STATE_RING);
|
||||
}
|
||||
break;
|
||||
case FTDM_CHANNEL_STATE_DIALTONE: /* NT-mode overlap receiving */
|
||||
ftdm_log_chan(chan, FTDM_LOG_DEBUG, "-- Incoming INFORMATION indication, current called number: '%s'\n",
|
||||
pevent->ring.callednum);
|
||||
|
||||
/* Need to add proper support for overlap receiving in NT-mode (requires FreeSWITCH + FreeTDM core support) */
|
||||
if (strlen(pevent->ring.callednum) > 3) {
|
||||
ftdm_log(FTDM_LOG_DEBUG, "final number is: %s\n", pevent->ring.callednum);
|
||||
pri_answer(spri->pri, pevent->ring.call, 0, 1);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
ftdm_log_chan(chan, FTDM_LOG_ERROR, "-- INFORMATION indication on channel %d:%d in invalid state '%s'\n",
|
||||
ftdm_channel_get_span_id(chan),
|
||||
ftdm_channel_get_id(chan),
|
||||
ftdm_channel_get_state_str(chan));
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
@@ -878,7 +957,15 @@ static int on_hangup(lpwrap_pri_t *spri, lpwrap_pri_event_t event_type, pri_even
|
||||
pri_hangup(spri->pri, pevent->hangup.call, pevent->hangup.cause);
|
||||
|
||||
chan->caller_data.hangup_cause = pevent->hangup.cause;
|
||||
ftdm_set_state(chan, FTDM_CHANNEL_STATE_TERMINATING);
|
||||
|
||||
switch (ftdm_channel_get_state(chan)) {
|
||||
case FTDM_CHANNEL_STATE_DIALTONE:
|
||||
case FTDM_CHANNEL_STATE_COLLECT:
|
||||
ftdm_set_state(chan, FTDM_CHANNEL_STATE_HANGUP);
|
||||
break;
|
||||
default:
|
||||
ftdm_set_state(chan, FTDM_CHANNEL_STATE_TERMINATING);
|
||||
}
|
||||
break;
|
||||
|
||||
case LPWRAP_PRI_EVENT_HANGUP_ACK: /* */
|
||||
@@ -1112,6 +1199,7 @@ out:
|
||||
static int on_ring(lpwrap_pri_t *spri, lpwrap_pri_event_t event_type, pri_event *pevent)
|
||||
{
|
||||
ftdm_span_t *span = spri->span;
|
||||
ftdm_libpri_data_t *isdn_data = span->signal_data;
|
||||
ftdm_channel_t *chan = ftdm_span_get_channel(span, pevent->ring.channel);
|
||||
ftdm_caller_data_t *caller_data = NULL;
|
||||
int ret = 0;
|
||||
@@ -1187,8 +1275,14 @@ static int on_ring(lpwrap_pri_t *spri, lpwrap_pri_event_t event_type, pri_event
|
||||
/* hurr, this is valid as along as nobody releases the call */
|
||||
chan->call_data = pevent->ring.call;
|
||||
|
||||
ftdm_set_state(chan, FTDM_CHANNEL_STATE_RING);
|
||||
|
||||
/* only go to RING state if we have the complete called number (indicated via pevent->complete flag) */
|
||||
if (!pevent->ring.complete && (isdn_data->overlap & FTMOD_LIBPRI_OVERLAP_RECEIVE)) {
|
||||
ftdm_log(FTDM_LOG_DEBUG, "RING event without complete indicator, waiting for more digits\n");
|
||||
ftdm_set_state(chan, FTDM_CHANNEL_STATE_COLLECT);
|
||||
} else {
|
||||
ftdm_log(FTDM_LOG_DEBUG, "RING event with complete indicator (or overlap receive disabled)\n");
|
||||
ftdm_set_state(chan, FTDM_CHANNEL_STATE_RING);
|
||||
}
|
||||
done:
|
||||
ftdm_channel_unlock(chan);
|
||||
return ret;
|
||||
@@ -1878,6 +1972,25 @@ static int parse_ton(const char *ton)
|
||||
return PRI_UNKNOWN;
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief Parse overlap string to value
|
||||
* \param val String to parse
|
||||
* \return Overlap flags
|
||||
*/
|
||||
static int parse_overlap_dial(const char *val)
|
||||
{
|
||||
if (!strcasecmp(val, "yes") || !strcasecmp(val, "both"))
|
||||
return FTMOD_LIBPRI_OVERLAP_BOTH;
|
||||
if (!strcasecmp(val, "incoming") || !strcasecmp(val, "receive"))
|
||||
return FTMOD_LIBPRI_OVERLAP_RECEIVE;
|
||||
if (!strcasecmp(val, "outgoing") || !strcasecmp(val, "send"))
|
||||
return FTMOD_LIBPRI_OVERLAP_SEND;
|
||||
if (!strcasecmp(val, "no"))
|
||||
return FTMOD_LIBPRI_OVERLAP_NONE;
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
/**
|
||||
* \brief Parses an option string to flags
|
||||
* \param in String to parse for configuration options
|
||||
@@ -2034,6 +2147,12 @@ static FIO_CONFIGURE_SPAN_SIGNALING_FUNCTION(ftdm_libpri_configure_span)
|
||||
else if (!strcasecmp(var, "l1") || !strcasecmp(var, "layer1")) {
|
||||
isdn_data->layer1 = parse_layer1(val);
|
||||
}
|
||||
else if (!strcasecmp(var, "overlapdial")) {
|
||||
if ((isdn_data->overlap = parse_overlap_dial(val)) == -1) {
|
||||
ftdm_log(FTDM_LOG_ERROR, "Invalid overlap flag, ignoring parameter\n");
|
||||
isdn_data->overlap = FTMOD_LIBPRI_OVERLAP_NONE;
|
||||
}
|
||||
}
|
||||
else if (!strcasecmp(var, "debug")) {
|
||||
if (parse_debug(val, &isdn_data->debug_mask) == -1) {
|
||||
ftdm_log(FTDM_LOG_ERROR, "Invalid debug flag, ignoring parameter\n");
|
||||
|
||||
@@ -51,6 +51,12 @@ typedef enum {
|
||||
FTMOD_LIBPRI_RUNNING = (1 << 0)
|
||||
} ftdm_isdn_flag_t;
|
||||
|
||||
typedef enum {
|
||||
FTMOD_LIBPRI_OVERLAP_NONE = 0,
|
||||
FTMOD_LIBPRI_OVERLAP_RECEIVE = (1 << 0),
|
||||
FTMOD_LIBPRI_OVERLAP_SEND = (1 << 1)
|
||||
#define FTMOD_LIBPRI_OVERLAP_BOTH (FTMOD_LIBPRI_OVERLAP_RECEIVE | FTMOD_LIBPRI_OVERLAP_SEND)
|
||||
} ftdm_isdn_overlap_t;
|
||||
|
||||
struct ftdm_libpri_data {
|
||||
ftdm_channel_t *dchan;
|
||||
@@ -60,6 +66,7 @@ struct ftdm_libpri_data {
|
||||
|
||||
int mode;
|
||||
int dialect;
|
||||
int overlap; /*!< Overlap dial flags */
|
||||
unsigned int layer1;
|
||||
unsigned int ton;
|
||||
|
||||
|
||||
@@ -57,6 +57,7 @@ typedef struct pritap {
|
||||
int32_t flags;
|
||||
struct pri *pri;
|
||||
int debug;
|
||||
uint8_t mixaudio;
|
||||
ftdm_channel_t *dchan;
|
||||
ftdm_span_t *span;
|
||||
ftdm_span_t *peerspan;
|
||||
@@ -752,6 +753,7 @@ static ftdm_status_t ftdm_pritap_sig_read(ftdm_channel_t *ftdmchan, void *data,
|
||||
ftdm_status_t status;
|
||||
fio_codec_t codec_func;
|
||||
ftdm_channel_t *peerchan = ftdmchan->call_data;
|
||||
pritap_t *pritap = ftdmchan->span->signal_data;
|
||||
int16_t chanbuf[size];
|
||||
int16_t peerbuf[size];
|
||||
int16_t mixedbuf[size];
|
||||
@@ -762,6 +764,11 @@ static ftdm_status_t ftdm_pritap_sig_read(ftdm_channel_t *ftdmchan, void *data,
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
if (!pritap->mixaudio) {
|
||||
/* No mixing requested */
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
if (ftdmchan->native_codec != peerchan->native_codec) {
|
||||
ftdm_log_chan(ftdmchan, FTDM_LOG_CRIT, "Invalid peer channel with format %d, ours = %d\n",
|
||||
peerchan->native_codec, ftdmchan->native_codec);
|
||||
@@ -829,6 +836,7 @@ static FIO_CONFIGURE_SPAN_SIGNALING_FUNCTION(ftdm_pritap_configure_span)
|
||||
uint32_t i;
|
||||
const char *var, *val;
|
||||
const char *debug = NULL;
|
||||
uint8_t mixaudio = 1;
|
||||
ftdm_channel_t *dchan = NULL;
|
||||
pritap_t *pritap = NULL;
|
||||
ftdm_span_t *peerspan = NULL;
|
||||
@@ -857,6 +865,8 @@ static FIO_CONFIGURE_SPAN_SIGNALING_FUNCTION(ftdm_pritap_configure_span)
|
||||
|
||||
if (!strcasecmp(var, "debug")) {
|
||||
debug = val;
|
||||
} else if (!strcasecmp(var, "mixaudio")) {
|
||||
mixaudio = ftdm_true(val);
|
||||
} else if (!strcasecmp(var, "peerspan")) {
|
||||
if (ftdm_span_find_by_name(val, &peerspan) != FTDM_SUCCESS) {
|
||||
ftdm_log(FTDM_LOG_ERROR, "Invalid tapping peer span %s\n", val);
|
||||
@@ -880,6 +890,7 @@ static FIO_CONFIGURE_SPAN_SIGNALING_FUNCTION(ftdm_pritap_configure_span)
|
||||
pritap->debug = parse_debug(debug);
|
||||
pritap->dchan = dchan;
|
||||
pritap->peerspan = peerspan;
|
||||
pritap->mixaudio = mixaudio;
|
||||
|
||||
span->start = ftdm_pritap_start;
|
||||
span->stop = ftdm_pritap_stop;
|
||||
|
||||
@@ -344,7 +344,6 @@ static void *ftdm_sangoma_isdn_io_run(ftdm_thread_t *me, void *obj)
|
||||
uint8_t data[1000];
|
||||
unsigned i = 0;
|
||||
ftdm_status_t status = FTDM_SUCCESS;
|
||||
ftdm_wait_flag_t wflags = FTDM_READ;
|
||||
ftdm_span_t *span = (ftdm_span_t*) obj;
|
||||
ftdm_size_t len = 0;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
@@ -356,10 +355,6 @@ static void *ftdm_sangoma_isdn_io_run(ftdm_thread_t *me, void *obj)
|
||||
|
||||
/* Initialize the d-channel */
|
||||
ftdm_assert(((sngisdn_span_data_t*)span->signal_data)->dchan, "Span does not have a dchannel");
|
||||
ftdm_channel_set_feature(((sngisdn_span_data_t*)span->signal_data)->dchan, FTDM_CHANNEL_FEATURE_IO_STATS);
|
||||
ftdm_sangoma_isdn_dchan_set_queue_size(((sngisdn_span_data_t*)span->signal_data)->dchan);
|
||||
ftdm_channel_open_chan(((sngisdn_span_data_t*)span->signal_data)->dchan);
|
||||
|
||||
chaniter = ftdm_span_get_chan_iterator(span, NULL);
|
||||
if (!chaniter) {
|
||||
ftdm_log(FTDM_LOG_CRIT, "Failed to allocate channel iterator for span %s!\n", span->name);
|
||||
@@ -369,7 +364,6 @@ static void *ftdm_sangoma_isdn_io_run(ftdm_thread_t *me, void *obj)
|
||||
while (ftdm_running() && !(ftdm_test_flag(span, FTDM_SPAN_STOP_THREAD))) {
|
||||
len = 1000;
|
||||
waitms = 1000;
|
||||
wflags = FTDM_READ;
|
||||
memset(poll_events, 0, sizeof(short)*span->chan_count);
|
||||
|
||||
poll_events[i] |= FTDM_EVENTS;
|
||||
@@ -1039,7 +1033,13 @@ static ftdm_status_t ftdm_sangoma_isdn_dtmf(ftdm_channel_t *ftdmchan, const char
|
||||
static ftdm_status_t ftdm_sangoma_isdn_start(ftdm_span_t *span)
|
||||
{
|
||||
sngisdn_span_data_t *signal_data = span->signal_data;
|
||||
|
||||
ftdm_log(FTDM_LOG_INFO,"Starting span %s:%u.\n",span->name,span->span_id);
|
||||
|
||||
ftdm_channel_set_feature(((sngisdn_span_data_t*)span->signal_data)->dchan, FTDM_CHANNEL_FEATURE_IO_STATS);
|
||||
ftdm_channel_open_chan(((sngisdn_span_data_t*)span->signal_data)->dchan);
|
||||
ftdm_sangoma_isdn_dchan_set_queue_size(((sngisdn_span_data_t*)span->signal_data)->dchan);
|
||||
|
||||
if (sngisdn_stack_start(span) != FTDM_SUCCESS) {
|
||||
ftdm_log(FTDM_LOG_CRIT, "Failed to start span %s\n", span->name);
|
||||
return FTDM_FAIL;
|
||||
@@ -1073,6 +1073,11 @@ static ftdm_status_t ftdm_sangoma_isdn_start(ftdm_span_t *span)
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
if (signal_data->restart_timeout) {
|
||||
ftdm_log(FTDM_LOG_DEBUG, "%s:Scheduling Restart timeout\n", signal_data->ftdm_span->name);
|
||||
ftdm_sched_timer(signal_data->sched, "restart_timeout", signal_data->restart_timeout,
|
||||
sngisdn_restart_timeout, (void*) signal_data, &signal_data->timers[SNGISDN_SPAN_TIMER_RESTART]);
|
||||
}
|
||||
ftdm_log(FTDM_LOG_DEBUG,"Finished starting span %s\n", span->name);
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
@@ -154,12 +154,18 @@ typedef struct ftdm_sngisdn_prog_ind {
|
||||
} ftdm_sngisdn_progind_t;
|
||||
|
||||
/* Only timers that can be cancelled are listed here */
|
||||
#define SNGISDN_NUM_TIMERS 2
|
||||
/* Increase NUM_TIMERS as number of ftdm_sngisdn_timer_t increases */
|
||||
typedef enum {
|
||||
SNGISDN_TIMER_FACILITY = 0,
|
||||
SNGISDN_TIMER_ATT_TRANSFER,
|
||||
} ftdm_sngisdn_timer_t;
|
||||
#define SNGISDN_NUM_CHAN_TIMERS 2
|
||||
/* Increase SNGISDN_NUM_CHAN_TIMERS as number of ftdm_sngisdn_chan_timer_t increases */
|
||||
typedef enum {
|
||||
SNGISDN_CHAN_TIMER_FACILITY,
|
||||
SNGISDN_CHAN_TIMER_ATT_TRANSFER,
|
||||
} ftdm_sngisdn_chan_timer_t;
|
||||
|
||||
#define SNGISDN_NUM_SPAN_TIMERS 1
|
||||
/* Increase SNGISDN_NUM_SPAN_TIMERS as number of ftdm_sngisdn_spanan_timer_t increases */
|
||||
typedef enum {
|
||||
SNGISDN_SPAN_TIMER_RESTART,
|
||||
} ftdm_sngisdn_span_timer_t;
|
||||
|
||||
typedef struct sngisdn_glare_data {
|
||||
int16_t suId;
|
||||
@@ -210,7 +216,7 @@ typedef struct sngisdn_chan_data {
|
||||
|
||||
uint8_t globalFlg;
|
||||
sngisdn_glare_data_t glare;
|
||||
ftdm_timer_id_t timers[SNGISDN_NUM_TIMERS];
|
||||
ftdm_timer_id_t timers[SNGISDN_NUM_CHAN_TIMERS];
|
||||
sngisdn_transfer_data_t transfer_data;
|
||||
|
||||
/* variables saved here will be sent to the user application
|
||||
@@ -252,8 +258,10 @@ typedef struct sngisdn_span_data {
|
||||
uint8_t raw_trace_q921; /* TODO: combine with trace_flags */
|
||||
uint8_t timer_t3;
|
||||
uint8_t restart_opt;
|
||||
uint8_t restart_timeout;
|
||||
uint8_t force_sending_complete;
|
||||
char* local_numbers[SNGISDN_NUM_LOCAL_NUMBERS];
|
||||
ftdm_timer_id_t timers[SNGISDN_NUM_SPAN_TIMERS];
|
||||
ftdm_sched_t *sched;
|
||||
ftdm_queue_t *event_queue;
|
||||
} sngisdn_span_data_t;
|
||||
@@ -452,8 +460,7 @@ ftdm_status_t get_calling_num(ftdm_channel_t *ftdmchan, CgPtyNmb *cgPtyNmb);
|
||||
ftdm_status_t get_calling_num2(ftdm_channel_t *ftdmchan, CgPtyNmb *cgPtyNmb);
|
||||
ftdm_status_t get_called_num(ftdm_channel_t *ftdmchan, CdPtyNmb *cdPtyNmb);
|
||||
ftdm_status_t get_redir_num(ftdm_channel_t *ftdmchan, RedirNmb *redirNmb);
|
||||
ftdm_status_t get_calling_name_from_display(ftdm_channel_t *ftdmchan, Display *display);
|
||||
ftdm_status_t get_calling_name_from_usr_usr(ftdm_channel_t *ftdmchan, UsrUsr *usrUsr);
|
||||
ftdm_status_t get_calling_name(ftdm_channel_t *ftdmchan, ConEvnt *conEvnt);
|
||||
ftdm_status_t get_calling_subaddr(ftdm_channel_t *ftdmchan, CgPtySad *cgPtySad);
|
||||
ftdm_status_t get_prog_ind_ie(ftdm_channel_t *ftdmchan, ProgInd *progInd);
|
||||
ftdm_status_t get_facility_ie(ftdm_channel_t *ftdmchan, FacilityStr *facilityStr);
|
||||
@@ -514,6 +521,7 @@ void sngisdn_delayed_connect(void* p_sngisdn_info);
|
||||
void sngisdn_delayed_disconnect(void* p_sngisdn_info);
|
||||
void sngisdn_facility_timeout(void* p_sngisdn_info);
|
||||
void sngisdn_t3_timeout(void* p_sngisdn_info);
|
||||
void sngisdn_restart_timeout(void* p_signal_data);
|
||||
|
||||
/* Stack management functions */
|
||||
ftdm_status_t sngisdn_stack_cfg(ftdm_span_t *span);
|
||||
|
||||
@@ -359,6 +359,8 @@ ftdm_status_t ftmod_isdn_parse_cfg(ftdm_conf_parameter_t *ftdm_parameters, ftdm_
|
||||
ftdm_set_bearer_layer1(val, (uint8_t*)&span->default_caller_data.bearer_layer1);
|
||||
} else if (!strcasecmp(var, "channel-restart-on-link-up")) {
|
||||
parse_yesno(var, val, &signal_data->restart_opt);
|
||||
} else if (!strcasecmp(var, "channel-restart-timeout")) {
|
||||
signal_data->restart_timeout = atoi(val);
|
||||
} else if (!strcasecmp(var, "local-number")) {
|
||||
if (add_local_number(val, span) != FTDM_SUCCESS) {
|
||||
return FTDM_FAIL;
|
||||
|
||||
@@ -422,7 +422,7 @@ ftdm_status_t sngisdn_stack_cfg_q921_dlsap(ftdm_span_t *span, uint8_t management
|
||||
|
||||
cfg.t.cfg.s.bdDLSAP.n200 = 3; /* n200 */
|
||||
cfg.t.cfg.s.bdDLSAP.congTmr = 300; /* congestion timer */
|
||||
cfg.t.cfg.s.bdDLSAP.t200Tmr = 1; /* t1 changed from 25 */
|
||||
cfg.t.cfg.s.bdDLSAP.t200Tmr = 3; /* t1 changed from 25 */
|
||||
cfg.t.cfg.s.bdDLSAP.t203Tmr = 10; /* t3 changed from 50 */
|
||||
cfg.t.cfg.s.bdDLSAP.mod = 128; /* modulo */
|
||||
cfg.t.cfg.s.bdDLSAP.selector = 0; /* Selector 0 */
|
||||
@@ -681,12 +681,7 @@ ftdm_status_t sngisdn_stack_cfg_q931_dlsap(ftdm_span_t *span)
|
||||
cfg.t.cfg.s.inDLSAP.clrGlr = FALSE; /* in case of glare, do not clear local call */
|
||||
cfg.t.cfg.s.inDLSAP.statEnqOpt = TRUE;
|
||||
|
||||
if (signal_data->switchtype == SNGISDN_SWITCH_EUROISDN ||
|
||||
signal_data->switchtype == SNGISDN_SWITCH_INSNET) {
|
||||
cfg.t.cfg.s.inDLSAP.rstOpt = FALSE;
|
||||
} else {
|
||||
cfg.t.cfg.s.inDLSAP.rstOpt = TRUE;
|
||||
}
|
||||
cfg.t.cfg.s.inDLSAP.rstOpt = TRUE;
|
||||
} else {
|
||||
cfg.t.cfg.s.inDLSAP.ackOpt = FALSE;
|
||||
cfg.t.cfg.s.inDLSAP.intType = USER;
|
||||
@@ -803,8 +798,10 @@ ftdm_status_t sngisdn_stack_cfg_q931_dlsap(ftdm_span_t *span)
|
||||
cfg.t.cfg.s.inDLSAP.tmr.t322.val = 4;
|
||||
cfg.t.cfg.s.inDLSAP.tmr.t332.enb = FALSE;
|
||||
cfg.t.cfg.s.inDLSAP.tmr.t332.val = 35;
|
||||
|
||||
cfg.t.cfg.s.inDLSAP.tmr.tRst.enb = TRUE;
|
||||
cfg.t.cfg.s.inDLSAP.tmr.tRst.val = 8;
|
||||
|
||||
cfg.t.cfg.s.inDLSAP.tmr.tAns.enb = FALSE; /* non-standard timer */
|
||||
cfg.t.cfg.s.inDLSAP.tmr.t396.enb = FALSE; /* non-standard timer */
|
||||
cfg.t.cfg.s.inDLSAP.tmr.t397.enb = TRUE; /* non-standard timer */
|
||||
|
||||
@@ -34,8 +34,7 @@
|
||||
|
||||
#include "ftmod_sangoma_isdn.h"
|
||||
static ftdm_status_t sngisdn_cause_val_requires_disconnect(ftdm_channel_t *ftdmchan, CauseDgn *causeDgn);
|
||||
static void sngisdn_process_restart_confirm(ftdm_channel_t *ftdmchan);
|
||||
static ftdm_status_t sngisdn_force_down(ftdm_channel_t *ftdmchan);
|
||||
static ftdm_status_t sngisdn_bring_down(ftdm_channel_t *ftdmchan);
|
||||
|
||||
/* Remote side transmit a SETUP */
|
||||
void sngisdn_process_con_ind (sngisdn_event_data_t *sngisdn_event)
|
||||
@@ -135,11 +134,8 @@ void sngisdn_process_con_ind (sngisdn_event_data_t *sngisdn_event)
|
||||
get_calling_subaddr(ftdmchan, &conEvnt->cgPtySad);
|
||||
get_prog_ind_ie(ftdmchan, &conEvnt->progInd);
|
||||
get_facility_ie(ftdmchan, &conEvnt->facilityStr);
|
||||
get_calling_name(ftdmchan, conEvnt);
|
||||
|
||||
if (get_calling_name_from_display(ftdmchan, &conEvnt->display) != FTDM_SUCCESS) {
|
||||
get_calling_name_from_usr_usr(ftdmchan, &conEvnt->usrUsr);
|
||||
}
|
||||
|
||||
ftdm_log_chan(sngisdn_info->ftdmchan, FTDM_LOG_INFO, "Incoming call: Called No:[%s] Calling No:[%s]\n", ftdmchan->caller_data.dnis.digits, ftdmchan->caller_data.cid_num.digits);
|
||||
|
||||
if (conEvnt->bearCap[0].eh.pres) {
|
||||
@@ -185,7 +181,7 @@ void sngisdn_process_con_ind (sngisdn_event_data_t *sngisdn_event)
|
||||
/* Launch timer in case we never get a FACILITY msg */
|
||||
if (signal_data->facility_timeout) {
|
||||
ftdm_sched_timer(signal_data->sched, "facility_timeout", signal_data->facility_timeout,
|
||||
sngisdn_facility_timeout, (void*) sngisdn_info, &sngisdn_info->timers[SNGISDN_TIMER_FACILITY]);
|
||||
sngisdn_facility_timeout, (void*) sngisdn_info, &sngisdn_info->timers[SNGISDN_CHAN_TIMER_FACILITY]);
|
||||
}
|
||||
break;
|
||||
} else if (ret_val == 0) {
|
||||
@@ -836,7 +832,7 @@ void sngisdn_process_fac_ind (sngisdn_event_data_t *sngisdn_event)
|
||||
}
|
||||
if (signal_data->facility_timeout) {
|
||||
/* Cancel facility timeout */
|
||||
ftdm_sched_cancel_timer(signal_data->sched, sngisdn_info->timers[SNGISDN_TIMER_FACILITY]);
|
||||
ftdm_sched_cancel_timer(signal_data->sched, sngisdn_info->timers[SNGISDN_CHAN_TIMER_FACILITY]);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -927,7 +923,7 @@ void sngisdn_process_sta_cfm (sngisdn_event_data_t *sngisdn_event)
|
||||
switch(call_state) {
|
||||
/* Sere ITU-T Q931 for definition of call states */
|
||||
case 0: /* Remote switch thinks there are no calls on this channel */
|
||||
if (sngisdn_force_down(ftdmchan) != FTDM_SUCCESS) {
|
||||
if (sngisdn_bring_down(ftdmchan) != FTDM_SUCCESS) {
|
||||
ftdm_log_chan(ftdmchan, FTDM_LOG_CRIT, "Don't know how to handle incompatible state. remote call state:%d our state:%s\n", call_state, ftdm_channel_state2str(ftdmchan->state));
|
||||
}
|
||||
break;
|
||||
@@ -1121,29 +1117,12 @@ void sngisdn_process_srv_cfm (sngisdn_event_data_t *sngisdn_event)
|
||||
return;
|
||||
}
|
||||
|
||||
static void sngisdn_process_restart_confirm(ftdm_channel_t *ftdmchan)
|
||||
{
|
||||
switch (ftdmchan->state) {
|
||||
case FTDM_CHANNEL_STATE_RESET:
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_DOWN);
|
||||
break;
|
||||
case FTDM_CHANNEL_STATE_DOWN:
|
||||
/* Do nothing */
|
||||
break;
|
||||
default:
|
||||
ftdm_log_chan(ftdmchan, FTDM_LOG_CRIT, "Received RESTART CFM in an invalid state (%s)\n",
|
||||
ftdm_channel_state2str(ftdmchan->state));
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
static ftdm_status_t sngisdn_force_down(ftdm_channel_t *ftdmchan)
|
||||
static ftdm_status_t sngisdn_bring_down(ftdm_channel_t *ftdmchan)
|
||||
{
|
||||
sngisdn_chan_data_t *sngisdn_info = (sngisdn_chan_data_t*)ftdmchan->call_data;
|
||||
ftdm_status_t status = FTDM_SUCCESS;
|
||||
|
||||
ftdm_log_chan(ftdmchan, FTDM_LOG_DEBUG, "Forcing channel to DOWN state (%s)\n", ftdm_channel_state2str(ftdmchan->state));
|
||||
|
||||
ftdm_log_chan(ftdmchan, FTDM_LOG_DEBUG, "Bringing channel to DOWN state (%s)\n", ftdm_channel_state2str(ftdmchan->state));
|
||||
switch (ftdmchan->state) {
|
||||
case FTDM_CHANNEL_STATE_DOWN:
|
||||
/* Do nothing */
|
||||
@@ -1196,38 +1175,36 @@ void sngisdn_process_rst_cfm (sngisdn_event_data_t *sngisdn_event)
|
||||
return;
|
||||
}
|
||||
|
||||
if (rstEvnt->rstInd.eh.pres != PRSNT_NODEF && rstEvnt->rstInd.rstClass.pres != PRSNT_NODEF) {
|
||||
ftdm_log(FTDM_LOG_DEBUG, "Received RESTART, but Restart Indicator IE not present\n");
|
||||
return;
|
||||
}
|
||||
|
||||
switch(rstEvnt->rstInd.rstClass.val) {
|
||||
case IN_CL_INDCHAN: /* Indicated b-channel */
|
||||
if (rstEvnt->chanId.eh.pres) {
|
||||
if (rstEvnt->chanId.intType.val == IN_IT_BASIC) {
|
||||
if (rstEvnt->chanId.infoChanSel.pres == PRSNT_NODEF) {
|
||||
chan_no = rstEvnt->chanId.infoChanSel.val;
|
||||
}
|
||||
} else if (rstEvnt->chanId.intType.val == IN_IT_OTHER) {
|
||||
if (rstEvnt->chanId.chanNmbSlotMap.pres == PRSNT_NODEF) {
|
||||
chan_no = rstEvnt->chanId.chanNmbSlotMap.val[0];
|
||||
if (rstEvnt->rstInd.eh.pres == PRSNT_NODEF && rstEvnt->rstInd.rstClass.pres == PRSNT_NODEF) {
|
||||
switch(rstEvnt->rstInd.rstClass.val) {
|
||||
case IN_CL_INDCHAN: /* Indicated b-channel */
|
||||
if (rstEvnt->chanId.eh.pres) {
|
||||
if (rstEvnt->chanId.intType.val == IN_IT_BASIC) {
|
||||
if (rstEvnt->chanId.infoChanSel.pres == PRSNT_NODEF) {
|
||||
chan_no = rstEvnt->chanId.infoChanSel.val;
|
||||
}
|
||||
} else if (rstEvnt->chanId.intType.val == IN_IT_OTHER) {
|
||||
if (rstEvnt->chanId.chanNmbSlotMap.pres == PRSNT_NODEF) {
|
||||
chan_no = rstEvnt->chanId.chanNmbSlotMap.val[0];
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!chan_no) {
|
||||
ftdm_log(FTDM_LOG_CRIT, "Failed to determine channel from RESTART\n");
|
||||
if (!chan_no) {
|
||||
ftdm_log(FTDM_LOG_CRIT, "Failed to determine channel from RESTART\n");
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case IN_CL_SNGINT: /* Single interface */
|
||||
case IN_CL_ALLINT: /* All interfaces */
|
||||
/* In case restart class indicates all interfaces, we will duplicate
|
||||
this event on each span associated to this d-channel in sngisdn_rcv_rst_cfm,
|
||||
so treat it as a single interface anyway */
|
||||
chan_no = 0;
|
||||
break;
|
||||
default:
|
||||
ftdm_log(FTDM_LOG_CRIT, "Invalid restart indicator class:%d\n", rstEvnt->rstInd.rstClass.val);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case IN_CL_SNGINT: /* Single interface */
|
||||
case IN_CL_ALLINT: /* All interfaces */
|
||||
/* In case restart class indicates all interfaces, we will duplicate
|
||||
this event on each span associated to this d-channel in sngisdn_rcv_rst_cfm,
|
||||
so treat it as a single interface anyway */
|
||||
break;
|
||||
default:
|
||||
ftdm_log(FTDM_LOG_CRIT, "Invalid restart indicator class:%d\n", rstEvnt->rstInd.rstClass.val);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
if (chan_no) { /* For a single channel */
|
||||
@@ -1235,7 +1212,7 @@ void sngisdn_process_rst_cfm (sngisdn_event_data_t *sngisdn_event)
|
||||
ftdm_log(FTDM_LOG_CRIT, "Received RESTART on invalid channel:%d\n", chan_no);
|
||||
} else {
|
||||
ftdm_channel_t *ftdmchan = ftdm_span_get_channel(signal_data->ftdm_span, chan_no);
|
||||
sngisdn_process_restart_confirm(ftdmchan);
|
||||
sngisdn_bring_down(ftdmchan);
|
||||
}
|
||||
} else { /* for all channels */
|
||||
ftdm_iterator_t *chaniter = NULL;
|
||||
@@ -1243,7 +1220,7 @@ void sngisdn_process_rst_cfm (sngisdn_event_data_t *sngisdn_event)
|
||||
|
||||
chaniter = ftdm_span_get_chan_iterator(signal_data->ftdm_span, NULL);
|
||||
for (curr = chaniter; curr; curr = ftdm_iterator_next(curr)) {
|
||||
sngisdn_process_restart_confirm((ftdm_channel_t*)ftdm_iterator_current(curr));
|
||||
sngisdn_bring_down((ftdm_channel_t*)ftdm_iterator_current(curr));
|
||||
}
|
||||
ftdm_iterator_free(chaniter);
|
||||
}
|
||||
@@ -1272,10 +1249,6 @@ void sngisdn_process_rst_ind (sngisdn_event_data_t *sngisdn_event)
|
||||
|
||||
/* TODO: readjust this when NFAS is implemented as signal_data will not always be the first
|
||||
* span for that d-channel */
|
||||
if (!rstEvnt->rstInd.eh.pres || !rstEvnt->rstInd.rstClass.pres) {
|
||||
ftdm_log(FTDM_LOG_DEBUG, "Received RESTART IND, but Restart Indicator IE not present\n");
|
||||
return;
|
||||
}
|
||||
|
||||
signal_data = g_sngisdn_data.dchans[dChan].spans[1];
|
||||
|
||||
@@ -1283,46 +1256,48 @@ void sngisdn_process_rst_ind (sngisdn_event_data_t *sngisdn_event)
|
||||
ftdm_log(FTDM_LOG_CRIT, "Received RESTART IND on unconfigured span (suId:%d)\n", suId);
|
||||
return;
|
||||
}
|
||||
|
||||
if (signal_data->restart_timeout) {
|
||||
ftdm_sched_cancel_timer(signal_data->sched, signal_data->timers[SNGISDN_SPAN_TIMER_RESTART]);
|
||||
}
|
||||
|
||||
ftdm_log(FTDM_LOG_DEBUG, "Processing RESTART IND (suId:%u dChan:%d ces:%d %s)\n", suId, dChan, ces,
|
||||
ftdm_log(FTDM_LOG_DEBUG, "Processing RESTART IND (suId:%u dChan:%d ces:%d %s(%d))\n", suId, dChan, ces,
|
||||
(evntType == IN_LNK_DWN)?"LNK_DOWN":
|
||||
(evntType == IN_LNK_UP)?"LNK_UP":
|
||||
(evntType == IN_INDCHAN)?"b-channel":
|
||||
(evntType == IN_LNK_DWN_DM_RLS)?"NFAS service procedures":
|
||||
(evntType == IN_SWCHD_BU_DCHAN)?"NFAS switchover to backup":"Unknown");
|
||||
(evntType == IN_SWCHD_BU_DCHAN)?"NFAS switchover to backup":"Unknown", evntType);
|
||||
|
||||
if (!rstEvnt->rstInd.eh.pres || !rstEvnt->rstInd.rstClass.pres) {
|
||||
ftdm_log(FTDM_LOG_DEBUG, "Received RESTART IND, but Restart Indicator IE not present\n");
|
||||
return;
|
||||
}
|
||||
|
||||
switch(rstEvnt->rstInd.rstClass.val) {
|
||||
case IN_CL_INDCHAN: /* Indicated b-channel */
|
||||
if (rstEvnt->chanId.eh.pres) {
|
||||
if (rstEvnt->chanId.intType.val == IN_IT_BASIC) {
|
||||
if (rstEvnt->chanId.infoChanSel.pres == PRSNT_NODEF) {
|
||||
chan_no = rstEvnt->chanId.infoChanSel.val;
|
||||
}
|
||||
} else if (rstEvnt->chanId.intType.val == IN_IT_OTHER) {
|
||||
if (rstEvnt->chanId.chanNmbSlotMap.pres == PRSNT_NODEF) {
|
||||
chan_no = rstEvnt->chanId.chanNmbSlotMap.val[0];
|
||||
if (rstEvnt->rstInd.eh.pres == PRSNT_NODEF && rstEvnt->rstInd.rstClass.pres == PRSNT_NODEF) {
|
||||
switch(rstEvnt->rstInd.rstClass.val) {
|
||||
case IN_CL_INDCHAN: /* Indicated b-channel */
|
||||
if (rstEvnt->chanId.eh.pres) {
|
||||
if (rstEvnt->chanId.intType.val == IN_IT_BASIC) {
|
||||
if (rstEvnt->chanId.infoChanSel.pres == PRSNT_NODEF) {
|
||||
chan_no = rstEvnt->chanId.infoChanSel.val;
|
||||
}
|
||||
} else if (rstEvnt->chanId.intType.val == IN_IT_OTHER) {
|
||||
if (rstEvnt->chanId.chanNmbSlotMap.pres == PRSNT_NODEF) {
|
||||
chan_no = rstEvnt->chanId.chanNmbSlotMap.val[0];
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!chan_no) {
|
||||
ftdm_log(FTDM_LOG_CRIT, "Failed to determine channel from RESTART\n");
|
||||
if (!chan_no) {
|
||||
ftdm_log(FTDM_LOG_CRIT, "Failed to determine channel from RESTART\n");
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case IN_CL_SNGINT: /* Single interface */
|
||||
case IN_CL_ALLINT: /* All interfaces */
|
||||
/* In case restart class indicates all interfaces, we will duplicate
|
||||
this event on each span associated to this d-channel in sngisdn_rcv_rst_cfm,
|
||||
so treat it as a single interface anyway */
|
||||
chan_no = 0;
|
||||
break;
|
||||
default:
|
||||
ftdm_log(FTDM_LOG_CRIT, "Invalid restart indicator class:%d\n", rstEvnt->rstInd.rstClass.val);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case IN_CL_SNGINT: /* Single interface */
|
||||
case IN_CL_ALLINT: /* All interfaces */
|
||||
/* In case restart class indicates all interfaces, we will duplicate
|
||||
this event on each span associated to this d-channel in sngisdn_rcv_rst_cfm,
|
||||
so treat it as a single interface anyway */
|
||||
break;
|
||||
default:
|
||||
ftdm_log(FTDM_LOG_CRIT, "Invalid restart indicator class:%d\n", rstEvnt->rstInd.rstClass.val);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
if (chan_no) { /* For a single channel */
|
||||
@@ -1336,7 +1311,7 @@ void sngisdn_process_rst_ind (sngisdn_event_data_t *sngisdn_event)
|
||||
for (curr = chaniter; curr; curr = ftdm_iterator_next(curr)) {
|
||||
ftdm_channel_t *ftdmchan = (ftdm_channel_t*)ftdm_iterator_current(curr);
|
||||
if (ftdmchan->physical_chan_id == chan_no) {
|
||||
sngisdn_force_down(ftdmchan);
|
||||
sngisdn_bring_down(ftdmchan);
|
||||
}
|
||||
}
|
||||
ftdm_iterator_free(chaniter);
|
||||
@@ -1347,7 +1322,7 @@ void sngisdn_process_rst_ind (sngisdn_event_data_t *sngisdn_event)
|
||||
|
||||
chaniter = ftdm_span_get_chan_iterator(signal_data->ftdm_span, NULL);
|
||||
for (curr = chaniter; curr; curr = ftdm_iterator_next(curr)) {
|
||||
sngisdn_force_down((ftdm_channel_t*)ftdm_iterator_current(curr));
|
||||
sngisdn_bring_down((ftdm_channel_t*)ftdm_iterator_current(curr));
|
||||
}
|
||||
ftdm_iterator_free(chaniter);
|
||||
}
|
||||
|
||||
@@ -491,7 +491,18 @@ void sngisdn_snd_data(ftdm_channel_t *dchan, uint8_t *data, ftdm_size_t len)
|
||||
/* Should we trigger congestion here? */
|
||||
l1_frame.flags |= SNG_L1FRAME_QUEUE_FULL;
|
||||
}
|
||||
#if 0
|
||||
if (1) {
|
||||
int i;
|
||||
char string [2000];
|
||||
unsigned string_len = 0;
|
||||
for (i = 0; i < l1_frame.len; i++) {
|
||||
string_len += sprintf(&string[string_len], "0x%02x ", l1_frame.data[i]);
|
||||
}
|
||||
|
||||
ftdm_log_chan(dchan, FTDM_LOG_CRIT, "\nL1 RX [%s] flags:%x\n", string, l1_frame.flags);
|
||||
}
|
||||
#endif
|
||||
sng_isdn_data_ind(signal_data->dchan_id, &l1_frame);
|
||||
}
|
||||
|
||||
|
||||
@@ -903,6 +903,17 @@ int16_t sngisdn_rcv_l1_data_req(uint16_t spId, sng_l1_frame_t *l1_frame)
|
||||
|
||||
|
||||
if ((flags & FTDM_WRITE)) {
|
||||
#if 0
|
||||
int i;
|
||||
char string [2000];
|
||||
unsigned string_len = 0;
|
||||
for (i = 0; i < length; i++) {
|
||||
string_len += sprintf(&string[string_len], "0x%02x ", l1_frame->data[i]);
|
||||
}
|
||||
|
||||
ftdm_log_chan(signal_data->dchan, FTDM_LOG_CRIT, "\nL1 TX [%s]\n", string);
|
||||
#endif
|
||||
|
||||
status = signal_data->dchan->fio->write(signal_data->dchan, l1_frame->data, (ftdm_size_t*)&length);
|
||||
if (status != FTDM_SUCCESS) {
|
||||
ftdm_log_chan_msg(signal_data->dchan, FTDM_LOG_CRIT, "Failed to transmit frame\n");
|
||||
|
||||
@@ -45,6 +45,9 @@ SNGISDN_STR2ENUM(ftdm_str2ftdm_sngisdn_progind_loc, ftdm_sngisdn_progind_loc2str
|
||||
|
||||
static uint8_t get_trillium_val(ftdm2trillium_t *vals, uint8_t ftdm_val, uint8_t default_val);
|
||||
static uint8_t get_ftdm_val(ftdm2trillium_t *vals, uint8_t trillium_val, uint8_t default_val);
|
||||
ftdm_status_t get_calling_name_from_usr_usr(ftdm_channel_t *ftdmchan, UsrUsr *usrUsr);
|
||||
ftdm_status_t get_calling_name_from_display(ftdm_channel_t *ftdmchan, Display *display);
|
||||
ftdm_status_t get_calling_name_from_ntDisplay(ftdm_channel_t *ftdmchan, NtDisplay *display);
|
||||
|
||||
extern ftdm_sngisdn_data_t g_sngisdn_data;
|
||||
|
||||
@@ -355,6 +358,20 @@ ftdm_status_t get_calling_name_from_display(ftdm_channel_t *ftdmchan, Display *d
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
ftdm_status_t get_calling_name_from_ntDisplay(ftdm_channel_t *ftdmchan, NtDisplay *display)
|
||||
{
|
||||
ftdm_caller_data_t *caller_data = &ftdmchan->caller_data;
|
||||
if (display->eh.pres != PRSNT_NODEF) {
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
if (display->dispInfo.pres != PRSNT_NODEF) {
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
ftdm_copy_string(caller_data->cid_name, (const char*)display->dispInfo.val, display->dispInfo.len+1);
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
ftdm_status_t get_calling_name_from_usr_usr(ftdm_channel_t *ftdmchan, UsrUsr *usrUsr)
|
||||
{
|
||||
ftdm_caller_data_t *caller_data = &ftdmchan->caller_data;
|
||||
@@ -374,6 +391,24 @@ ftdm_status_t get_calling_name_from_usr_usr(ftdm_channel_t *ftdmchan, UsrUsr *us
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
ftdm_status_t get_calling_name(ftdm_channel_t *ftdmchan, ConEvnt *conEvnt)
|
||||
{
|
||||
ftdm_status_t status = FTDM_FAIL;
|
||||
sngisdn_span_data_t *signal_data = (sngisdn_span_data_t*) ftdmchan->span->signal_data;
|
||||
|
||||
if (signal_data->switchtype == SNGISDN_SWITCH_DMS100) {
|
||||
status = get_calling_name_from_ntDisplay(ftdmchan, &conEvnt->ntDisplay[0]);
|
||||
} else {
|
||||
status = get_calling_name_from_display(ftdmchan, &conEvnt->display);
|
||||
|
||||
}
|
||||
if (status != FTDM_SUCCESS) {
|
||||
status = get_calling_name_from_usr_usr(ftdmchan, &conEvnt->usrUsr);
|
||||
}
|
||||
return status;
|
||||
}
|
||||
|
||||
|
||||
ftdm_status_t get_calling_subaddr(ftdm_channel_t *ftdmchan, CgPtySad *cgPtySad)
|
||||
{
|
||||
char subaddress[100];
|
||||
@@ -694,12 +729,22 @@ ftdm_status_t set_calling_name(ftdm_channel_t *ftdmchan, ConEvnt *conEvnt)
|
||||
/* follow through */
|
||||
case SNGISDN_SWITCH_5ESS:
|
||||
case SNGISDN_SWITCH_4ESS:
|
||||
case SNGISDN_SWITCH_DMS100:
|
||||
conEvnt->display.eh.pres = PRSNT_NODEF;
|
||||
conEvnt->display.dispInfo.pres = PRSNT_NODEF;
|
||||
conEvnt->display.dispInfo.len = len;
|
||||
memcpy(conEvnt->display.dispInfo.val, caller_data->cid_name, len);
|
||||
break;
|
||||
case SNGISDN_SWITCH_DMS100:
|
||||
conEvnt->ntDisplay[0].eh.pres = PRSNT_NODEF;
|
||||
conEvnt->ntDisplay[0].dispTypeNt.pres = PRSNT_NODEF;
|
||||
conEvnt->ntDisplay[0].dispTypeNt.val = 0x01; /* Calling Party Name */
|
||||
conEvnt->ntDisplay[0].assocInfo.pres = PRSNT_NODEF;
|
||||
conEvnt->ntDisplay[0].assocInfo.val = 0x03; /* Included */
|
||||
conEvnt->ntDisplay[0].eh.pres = PRSNT_NODEF;
|
||||
conEvnt->ntDisplay[0].eh.pres = PRSNT_NODEF;
|
||||
conEvnt->ntDisplay[0].dispInfo.pres = PRSNT_NODEF;
|
||||
conEvnt->ntDisplay[0].dispInfo.len = len;
|
||||
memcpy(conEvnt->ntDisplay[0].dispInfo.val, caller_data->cid_name, len);
|
||||
break;
|
||||
case SNGISDN_SWITCH_QSIG:
|
||||
/* It seems like QSIG does not support Caller ID Name */
|
||||
break;
|
||||
@@ -976,7 +1021,7 @@ ftdm_status_t set_restart_ind_ie(ftdm_channel_t *ftdmchan, RstInd *rstInd)
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
void sngisdn_t3_timeout(void* p_sngisdn_info)
|
||||
void sngisdn_t3_timeout(void *p_sngisdn_info)
|
||||
{
|
||||
sngisdn_chan_data_t *sngisdn_info = (sngisdn_chan_data_t*)p_sngisdn_info;
|
||||
ftdm_channel_t *ftdmchan = sngisdn_info->ftdmchan;
|
||||
@@ -998,7 +1043,31 @@ void sngisdn_t3_timeout(void* p_sngisdn_info)
|
||||
ftdm_mutex_unlock(ftdmchan->mutex);
|
||||
}
|
||||
|
||||
void sngisdn_delayed_setup(void* p_sngisdn_info)
|
||||
void sngisdn_restart_timeout(void *p_signal_data)
|
||||
{
|
||||
sngisdn_span_data_t *signal_data = (sngisdn_span_data_t *)p_signal_data;
|
||||
ftdm_span_t *span = signal_data->ftdm_span;
|
||||
|
||||
ftdm_log(FTDM_LOG_DEBUG, "s%d:Did not receive a RESTART from remote switch in %d ms - restarting\n", span->name, signal_data->restart_timeout);
|
||||
|
||||
ftdm_iterator_t *chaniter = NULL;
|
||||
ftdm_iterator_t *curr = NULL;
|
||||
|
||||
chaniter = ftdm_span_get_chan_iterator(span, NULL);
|
||||
for (curr = chaniter; curr; curr = ftdm_iterator_next(curr)) {
|
||||
ftdm_channel_t *ftdmchan = (ftdm_channel_t*)ftdm_iterator_current(curr);
|
||||
if (FTDM_IS_VOICE_CHANNEL(ftdmchan)) {
|
||||
ftdm_mutex_lock(ftdmchan->mutex);
|
||||
if (ftdmchan->state == FTDM_CHANNEL_STATE_DOWN) {
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_RESET);
|
||||
}
|
||||
ftdm_mutex_unlock(ftdmchan->mutex);
|
||||
}
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
void sngisdn_delayed_setup(void *p_sngisdn_info)
|
||||
{
|
||||
sngisdn_chan_data_t *sngisdn_info = (sngisdn_chan_data_t*)p_sngisdn_info;
|
||||
ftdm_channel_t *ftdmchan = sngisdn_info->ftdmchan;
|
||||
@@ -1009,7 +1078,7 @@ void sngisdn_delayed_setup(void* p_sngisdn_info)
|
||||
return;
|
||||
}
|
||||
|
||||
void sngisdn_delayed_release(void* p_sngisdn_info)
|
||||
void sngisdn_delayed_release(void *p_sngisdn_info)
|
||||
{
|
||||
sngisdn_chan_data_t *sngisdn_info = (sngisdn_chan_data_t*)p_sngisdn_info;
|
||||
ftdm_channel_t *ftdmchan = sngisdn_info->ftdmchan;
|
||||
@@ -1032,7 +1101,7 @@ void sngisdn_delayed_release(void* p_sngisdn_info)
|
||||
return;
|
||||
}
|
||||
|
||||
void sngisdn_delayed_connect(void* p_sngisdn_info)
|
||||
void sngisdn_delayed_connect(void *p_sngisdn_info)
|
||||
{
|
||||
sngisdn_chan_data_t *sngisdn_info = (sngisdn_chan_data_t*)p_sngisdn_info;
|
||||
ftdm_channel_t *ftdmchan = sngisdn_info->ftdmchan;
|
||||
@@ -1047,7 +1116,7 @@ void sngisdn_delayed_connect(void* p_sngisdn_info)
|
||||
return;
|
||||
}
|
||||
|
||||
void sngisdn_delayed_disconnect(void* p_sngisdn_info)
|
||||
void sngisdn_delayed_disconnect(void *p_sngisdn_info)
|
||||
{
|
||||
sngisdn_chan_data_t *sngisdn_info = (sngisdn_chan_data_t*)p_sngisdn_info;
|
||||
ftdm_channel_t *ftdmchan = sngisdn_info->ftdmchan;
|
||||
@@ -1069,7 +1138,7 @@ void sngisdn_delayed_disconnect(void* p_sngisdn_info)
|
||||
return;
|
||||
}
|
||||
|
||||
void sngisdn_facility_timeout(void* p_sngisdn_info)
|
||||
void sngisdn_facility_timeout(void *p_sngisdn_info)
|
||||
{
|
||||
sngisdn_chan_data_t *sngisdn_info = (sngisdn_chan_data_t*)p_sngisdn_info;
|
||||
ftdm_channel_t *ftdmchan = sngisdn_info->ftdmchan;
|
||||
|
||||
@@ -114,7 +114,7 @@ void sngisdn_trace_interpreted_q921(sngisdn_span_data_t *signal_data, ftdm_trace
|
||||
{
|
||||
char *data_str = ftdm_calloc(1,200); /* TODO Find a proper size */
|
||||
sngisdn_decode_q921(data_str, data, data_len);
|
||||
ftdm_log(FTDM_LOG_INFO, "[SNGISDN Q921] %s FRAME %s:%s\n", signal_data->ftdm_span->name, ftdm_trace_dir2str(dir), data_str);
|
||||
ftdm_log(FTDM_LOG_DEBUG, "[SNGISDN Q921] %s FRAME %s:\n%s\n", signal_data->ftdm_span->name, ftdm_trace_dir2str(dir), data_str);
|
||||
ftdm_safe_free(data_str);
|
||||
}
|
||||
|
||||
@@ -144,7 +144,7 @@ void sngisdn_trace_raw_q921(sngisdn_span_data_t *signal_data, ftdm_trace_dir_t d
|
||||
|
||||
void sngisdn_decode_q921(char* str, uint8_t* data, uint32_t data_len)
|
||||
{
|
||||
int str_len;
|
||||
uint32_t str_len;
|
||||
uint32_t i;
|
||||
uint8_t sapi, cr, ea, tei, ns, nr, pf, p, cmd;
|
||||
uint8_t frame_format = 0;
|
||||
@@ -211,6 +211,8 @@ void sngisdn_decode_q921(char* str, uint8_t* data, uint32_t data_len)
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
print_hex_dump(str, &str_len, (uint8_t*) data, 0, data_len);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -219,7 +221,7 @@ void sngisdn_trace_interpreted_q931(sngisdn_span_data_t *signal_data, ftdm_trace
|
||||
{
|
||||
char *data_str = ftdm_calloc(1,MAX_DECODE_STR_LEN); /* TODO Find a proper size */
|
||||
sngisdn_decode_q931(data_str, data, data_len);
|
||||
ftdm_log(FTDM_LOG_INFO, "[SNGISDN Q931] %s FRAME %s:%s\n", signal_data->ftdm_span->name, ftdm_trace_dir2str(dir), data_str);
|
||||
ftdm_log(FTDM_LOG_DEBUG, "[SNGISDN Q931] %s FRAME %s:\n%s\n", signal_data->ftdm_span->name, ftdm_trace_dir2str(dir), data_str);
|
||||
ftdm_safe_free(data_str);
|
||||
}
|
||||
|
||||
@@ -584,11 +586,20 @@ uint32_t sngisdn_decode_ie(char *str, uint32_t *str_len, uint8_t current_codeset
|
||||
break;
|
||||
case PROT_Q931_IE_DISPLAY:
|
||||
{
|
||||
uint8_t displayStrOct=2, j;
|
||||
uint8_t j;
|
||||
char displayStr[82];
|
||||
uint8_t displayNtEnabled = 0;
|
||||
uint8_t displayStrOct = 2;
|
||||
uint8_t displayType = 0;
|
||||
uint8_t assocInfo = 0;
|
||||
|
||||
memset(displayStr, 0, sizeof(displayStr));
|
||||
|
||||
if(get_bits(OCTET(3),8,8)) {
|
||||
displayType = get_bits(OCTET(3),1,4);
|
||||
assocInfo = get_bits(OCTET(3),5,7);
|
||||
|
||||
displayNtEnabled = 1;
|
||||
displayStrOct++;
|
||||
}
|
||||
j = 0;
|
||||
@@ -599,8 +610,15 @@ uint32_t sngisdn_decode_ie(char *str, uint32_t *str_len, uint8_t current_codeset
|
||||
displayStr[j++]=ia5[get_bits(OCTET(displayStrOct),1,4)][get_bits(OCTET(displayStrOct),5,8)];
|
||||
}
|
||||
displayStr[j]='\0';
|
||||
*str_len+= sprintf(&str[*str_len], "%s(l:%d)\n",
|
||||
displayStr, len);
|
||||
if (displayNtEnabled) {
|
||||
*str_len+= sprintf(&str[*str_len], "%s(l:%d) type:%s(%d) info:%s(%d)\n",
|
||||
displayStr, len,
|
||||
get_code_2_str(displayType, dcodQ931DisplayTypeTable), displayType,
|
||||
get_code_2_str(assocInfo, dcodQ931AssocInfoTable), assocInfo);
|
||||
} else {
|
||||
*str_len+= sprintf(&str[*str_len], "%s(l:%d)\n",
|
||||
displayStr, len);
|
||||
}
|
||||
}
|
||||
break;
|
||||
case PROT_Q931_IE_RESTART_IND:
|
||||
|
||||
@@ -578,5 +578,17 @@ struct code2str dcodQ931TypeOfSubaddressTable[] = {
|
||||
{ -1, "Invalid"},
|
||||
};
|
||||
|
||||
#endif /* __FTMOD_SANGOMA_ISDN_TRACE_H__ */
|
||||
struct code2str dcodQ931DisplayTypeTable[] = {
|
||||
{ 0x00, "Calling Party Name"},
|
||||
{ 0x01, "Connected Party Name"},
|
||||
{ 0x05, "Original Called Party Name"},
|
||||
{ -1, "Invalid"},
|
||||
};
|
||||
|
||||
struct code2str dcodQ931AssocInfoTable[] = {
|
||||
{ 0x00, "Requested"},
|
||||
{ 0x03, "Included"},
|
||||
{ -1, "Invalid"},
|
||||
};
|
||||
|
||||
#endif /* __FTMOD_SANGOMA_ISDN_TRACE_H__ */
|
||||
@@ -164,7 +164,7 @@ static ftdm_status_t att_courtesy_vru(ftdm_channel_t *ftdmchan, sngisdn_transfer
|
||||
sngisdn_send_signal(sngisdn_info, FTDM_SIGEVENT_UP);
|
||||
}
|
||||
if (signal_data->transfer_timeout) {
|
||||
ftdm_sched_timer(((sngisdn_span_data_t*)ftdmchan->span->signal_data)->sched, "courtesy_transfer_timeout", signal_data->transfer_timeout, att_courtesy_transfer_timeout, (void*) sngisdn_info, &sngisdn_info->timers[SNGISDN_TIMER_ATT_TRANSFER]);
|
||||
ftdm_sched_timer(((sngisdn_span_data_t*)ftdmchan->span->signal_data)->sched, "courtesy_transfer_timeout", signal_data->transfer_timeout, att_courtesy_transfer_timeout, (void*) sngisdn_info, &sngisdn_info->timers[SNGISDN_CHAN_TIMER_ATT_TRANSFER]);
|
||||
}
|
||||
|
||||
status = FTDM_SUCCESS;
|
||||
@@ -260,7 +260,7 @@ ftdm_status_t sngisdn_att_transfer_process_dtmf(ftdm_channel_t *ftdmchan, const
|
||||
sngisdn_info->transfer_data.response = FTDM_TRANSFER_RESPONSE_INVALID;
|
||||
}
|
||||
if (signal_data->transfer_timeout) {
|
||||
ftdm_sched_cancel_timer(signal_data->sched, sngisdn_info->timers[SNGISDN_TIMER_ATT_TRANSFER]);
|
||||
ftdm_sched_cancel_timer(signal_data->sched, sngisdn_info->timers[SNGISDN_CHAN_TIMER_ATT_TRANSFER]);
|
||||
}
|
||||
|
||||
if (sngisdn_info->transfer_data.response == FTDM_TRANSFER_RESPONSE_OK &&
|
||||
|
||||
@@ -29,6 +29,11 @@
|
||||
* 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.
|
||||
*
|
||||
* Contributors:
|
||||
*
|
||||
* Ricardo Barroetaveña <rbarroetavena@anura.com.ar>
|
||||
*
|
||||
*/
|
||||
|
||||
/* INCLUDE ********************************************************************/
|
||||
|
||||
@@ -950,31 +950,31 @@ if (ftdmchan->state == new_state) { \
|
||||
#define SS7_FUNC_TRACE_EXIT(a) if (g_ftdm_sngss7_data.function_trace) { \
|
||||
switch (g_ftdm_sngss7_data.function_trace_level) { \
|
||||
case 0: \
|
||||
ftdm_log(FTDM_LOG_EMERG,"Exitting %s\n", a); \
|
||||
ftdm_log(FTDM_LOG_EMERG,"Exiting %s\n", a); \
|
||||
break; \
|
||||
case 1: \
|
||||
ftdm_log(FTDM_LOG_ALERT,"Exitting %s\n", a); \
|
||||
ftdm_log(FTDM_LOG_ALERT,"Exiting %s\n", a); \
|
||||
break; \
|
||||
case 2: \
|
||||
ftdm_log(FTDM_LOG_CRIT,"Exitting %s\n", a); \
|
||||
ftdm_log(FTDM_LOG_CRIT,"Exiting %s\n", a); \
|
||||
break; \
|
||||
case 3: \
|
||||
ftdm_log(FTDM_LOG_ERROR,"Exitting %s\n", a); \
|
||||
ftdm_log(FTDM_LOG_ERROR,"Exiting %s\n", a); \
|
||||
break; \
|
||||
case 4: \
|
||||
ftdm_log(FTDM_LOG_WARNING,"Exitting %s\n", a); \
|
||||
ftdm_log(FTDM_LOG_WARNING,"Exiting %s\n", a); \
|
||||
break; \
|
||||
case 5: \
|
||||
ftdm_log(FTDM_LOG_NOTICE,"Exitting %s\n", a); \
|
||||
ftdm_log(FTDM_LOG_NOTICE,"Exiting %s\n", a); \
|
||||
break; \
|
||||
case 6: \
|
||||
ftdm_log(FTDM_LOG_INFO,"Exitting %s\n", a); \
|
||||
ftdm_log(FTDM_LOG_INFO,"Exiting %s\n", a); \
|
||||
break; \
|
||||
case 7: \
|
||||
ftdm_log(FTDM_LOG_DEBUG,"Exitting %s\n", a); \
|
||||
ftdm_log(FTDM_LOG_DEBUG,"Exiting %s\n", a); \
|
||||
break; \
|
||||
default: \
|
||||
ftdm_log(FTDM_LOG_INFO,"Exitting %s\n", a); \
|
||||
ftdm_log(FTDM_LOG_INFO,"Exiting %s\n", a); \
|
||||
break; \
|
||||
} /* switch (g_ftdm_sngss7_data.function_trace_level) */ \
|
||||
} /* if(g_ftdm_sngss7_data.function_trace) */
|
||||
|
||||
@@ -725,7 +725,7 @@ static FIO_COMMAND_FUNCTION(zt_command)
|
||||
{
|
||||
int command = ZT_OFFHOOK;
|
||||
if (ioctl(ftdmchan->sockfd, codes.HOOK, &command)) {
|
||||
snprintf(ftdmchan->last_error, sizeof(ftdmchan->last_error), "OFFHOOK Failed");
|
||||
ftdm_log_chan_msg(ftdmchan, FTDM_LOG_ERROR, "OFFHOOK Failed");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
ftdm_set_flag_locked(ftdmchan, FTDM_CHANNEL_OFFHOOK);
|
||||
@@ -735,7 +735,7 @@ static FIO_COMMAND_FUNCTION(zt_command)
|
||||
{
|
||||
int command = ZT_ONHOOK;
|
||||
if (ioctl(ftdmchan->sockfd, codes.HOOK, &command)) {
|
||||
snprintf(ftdmchan->last_error, sizeof(ftdmchan->last_error), "ONHOOK Failed");
|
||||
ftdm_log_chan_msg(ftdmchan, FTDM_LOG_ERROR, "ONHOOK Failed");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
ftdm_clear_flag_locked(ftdmchan, FTDM_CHANNEL_OFFHOOK);
|
||||
@@ -745,7 +745,7 @@ static FIO_COMMAND_FUNCTION(zt_command)
|
||||
{
|
||||
int command = ZT_FLASH;
|
||||
if (ioctl(ftdmchan->sockfd, codes.HOOK, &command)) {
|
||||
snprintf(ftdmchan->last_error, sizeof(ftdmchan->last_error), "FLASH Failed");
|
||||
ftdm_log_chan_msg(ftdmchan, FTDM_LOG_ERROR, "FLASH Failed");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
}
|
||||
@@ -754,7 +754,7 @@ static FIO_COMMAND_FUNCTION(zt_command)
|
||||
{
|
||||
int command = ZT_WINK;
|
||||
if (ioctl(ftdmchan->sockfd, codes.HOOK, &command)) {
|
||||
snprintf(ftdmchan->last_error, sizeof(ftdmchan->last_error), "WINK Failed");
|
||||
ftdm_log_chan_msg(ftdmchan, FTDM_LOG_ERROR, "WINK Failed");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
}
|
||||
@@ -763,7 +763,7 @@ static FIO_COMMAND_FUNCTION(zt_command)
|
||||
{
|
||||
int command = ZT_RING;
|
||||
if (ioctl(ftdmchan->sockfd, codes.HOOK, &command)) {
|
||||
snprintf(ftdmchan->last_error, sizeof(ftdmchan->last_error), "Ring Failed");
|
||||
ftdm_log_chan_msg(ftdmchan, FTDM_LOG_ERROR, "RING Failed");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
ftdm_set_flag_locked(ftdmchan, FTDM_CHANNEL_RINGING);
|
||||
@@ -773,7 +773,7 @@ static FIO_COMMAND_FUNCTION(zt_command)
|
||||
{
|
||||
int command = ZT_RINGOFF;
|
||||
if (ioctl(ftdmchan->sockfd, codes.HOOK, &command)) {
|
||||
snprintf(ftdmchan->last_error, sizeof(ftdmchan->last_error), "Ring-off failed");
|
||||
ftdm_log_chan_msg(ftdmchan, FTDM_LOG_ERROR, "Ring-off Failed");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
ftdm_clear_flag_locked(ftdmchan, FTDM_CHANNEL_RINGING);
|
||||
|
||||
@@ -48,7 +48,7 @@
|
||||
#define FTDM_MAX_CHANNELS_PHYSICAL_SPAN 32
|
||||
|
||||
/*! \brief Max number of physical spans per logical span */
|
||||
#define FTDM_MAX_PHYSICAL_SPANS_PER_LOGICAL_SPAN 32
|
||||
#define FTDM_MAX_PHYSICAL_SPANS_PER_LOGICAL_SPAN 128
|
||||
|
||||
/*! \brief Max number of channels a logical span can contain */
|
||||
#define FTDM_MAX_CHANNELS_SPAN FTDM_MAX_CHANNELS_PHYSICAL_SPAN * FTDM_MAX_PHYSICAL_SPANS_PER_LOGICAL_SPAN
|
||||
@@ -57,7 +57,7 @@
|
||||
#define FTDM_MAX_SPANS_INTERFACE 128
|
||||
|
||||
/*! \brief Max number of channels per hunting group */
|
||||
#define FTDM_MAX_CHANNELS_GROUP 1024
|
||||
#define FTDM_MAX_CHANNELS_GROUP 2048
|
||||
|
||||
/*! \brief Max number of groups */
|
||||
#define FTDM_MAX_GROUPS_INTERFACE FTDM_MAX_SPANS_INTERFACE
|
||||
|
||||
@@ -607,7 +607,9 @@ static int on_disco_default(void *user_data, ikspak *pak)
|
||||
int all = 0;
|
||||
|
||||
iks_insert_attrib(iq, "from", handle->login);
|
||||
iks_insert_attrib(iq, "to", pak->from->full);
|
||||
if (pak->from) {
|
||||
iks_insert_attrib(iq, "to", pak->from->full);
|
||||
}
|
||||
iks_insert_attrib(iq, "id", pak->id);
|
||||
iks_insert_attrib(iq, "type", "result");
|
||||
|
||||
|
||||
@@ -1 +1 @@
|
||||
Wed Apr 27 11:49:37 CDT 2011
|
||||
Wed Jul 6 15:11:41 CDT 2011
|
||||
@@ -110,6 +110,7 @@ nua_handle_t *nh_create_handle(nua_t *nua,
|
||||
assert(nua->nua_home);
|
||||
|
||||
if ((nh = su_home_clone(nua->nua_home, sizeof(*nh)))) {
|
||||
//if ((nh = su_home_new(sizeof(*nh)))) {
|
||||
nh->nh_valid = nua_valid_handle_cookie;
|
||||
nh->nh_nua = nua;
|
||||
nh->nh_magic = hmagic;
|
||||
@@ -171,10 +172,16 @@ _nua_handle_ref_by(nua_handle_t *nh,
|
||||
char const *file, unsigned line,
|
||||
char const *function)
|
||||
{
|
||||
if (nh)
|
||||
SU_DEBUG_0(("%p - nua_handle_ref() => "MOD_ZU" by %s:%u: %s()\n",
|
||||
nh, su_home_refcount((su_home_t *)nh) + 1, file, line, by));
|
||||
return (nua_handle_t *)su_home_ref((su_home_t *)nh);
|
||||
|
||||
#if (HAVE_MEMLEAK_LOG == 1)
|
||||
if (nh)
|
||||
SU_DEBUG_0(("%p - nua_handle_ref() => "MOD_ZU" by %s:%u: %s()\n",
|
||||
nh, su_home_refcount((su_home_t *)nh) + 1, file, line, function));
|
||||
return (nua_handle_t *)su_home_ref((su_home_t *)nh);
|
||||
#else
|
||||
|
||||
return (nua_handle_t *)_su_home_ref_by((su_home_t *)nh, file, line, function);
|
||||
#endif
|
||||
}
|
||||
|
||||
int
|
||||
@@ -182,26 +189,23 @@ _nua_handle_unref_by(nua_handle_t *nh,
|
||||
char const *file, unsigned line,
|
||||
char const *function)
|
||||
{
|
||||
if (nh) {
|
||||
size_t refcount = su_home_refcount((su_home_t *)nh) - 1;
|
||||
int freed = su_home_unref((su_home_t *)nh);
|
||||
if (freed) refcount = 0;
|
||||
SU_DEBUG_0(("%p - nua_handle_unref() => "MOD_ZU" by %s:%u: %s()\n",
|
||||
nh, refcount, file, line, by));
|
||||
return freed;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
#if (HAVE_MEMLEAK_LOG == 1)
|
||||
|
||||
nua_handle_t *nua_handle_ref(nua_handle_t *nh)
|
||||
{
|
||||
return _nua_handle_ref_by(nh, "<app>", 0, "<app>")
|
||||
}
|
||||
if (nh) {
|
||||
size_t refcount = su_home_refcount((su_home_t *)nh) - 1;
|
||||
int freed = su_home_unref((su_home_t *)nh);
|
||||
|
||||
int nua_handle_unref(nua_handle_t *nh)
|
||||
{
|
||||
return _nua_handle_unref_by(nh, "<app>", 0, "<app>")
|
||||
if (freed) refcount = 0;
|
||||
SU_DEBUG_0(("%p - nua_handle_unref() => "MOD_ZU" by %s:%u: %s()\n",
|
||||
nh, refcount, file, line, function));
|
||||
return freed;
|
||||
}
|
||||
|
||||
return 0;
|
||||
#else
|
||||
return _su_home_unref_by((su_home_t *)nh, file, line, function);
|
||||
#endif
|
||||
}
|
||||
|
||||
#else
|
||||
|
||||
@@ -373,11 +373,14 @@ nua_dialog_usage_remove_at(nua_owner_t *own,
|
||||
nua_client_request_t *cr0,
|
||||
nua_server_request_t *sr0)
|
||||
{
|
||||
int unref = 0;
|
||||
nua_dialog_usage_t *du = NULL;
|
||||
|
||||
if (*at) {
|
||||
nua_dialog_usage_t *du = *at;
|
||||
sip_event_t const *o = NULL;
|
||||
nua_client_request_t *cr, *cr_next;
|
||||
nua_server_request_t *sr, *sr_next;
|
||||
du = *at;
|
||||
|
||||
*at = du->du_next;
|
||||
|
||||
@@ -409,8 +412,7 @@ nua_dialog_usage_remove_at(nua_owner_t *own,
|
||||
}
|
||||
}
|
||||
|
||||
su_home_unref(own);
|
||||
su_free(own, du);
|
||||
unref = 1;
|
||||
}
|
||||
|
||||
/* Zap dialog if there are no more usages */
|
||||
@@ -419,11 +421,20 @@ nua_dialog_usage_remove_at(nua_owner_t *own,
|
||||
else if (ds->ds_usage == NULL) {
|
||||
nua_dialog_remove(own, ds, NULL);
|
||||
ds->ds_has_events = 0;
|
||||
if (unref) {
|
||||
su_home_unref(own);
|
||||
su_free(own, du);
|
||||
}
|
||||
return;
|
||||
}
|
||||
else {
|
||||
nua_dialog_log_usage(own, ds);
|
||||
}
|
||||
|
||||
if (unref) {
|
||||
su_home_unref(own);
|
||||
su_free(own, du);
|
||||
}
|
||||
}
|
||||
|
||||
static
|
||||
|
||||
@@ -3721,6 +3721,9 @@ static int nua_bye_client_init(nua_client_request_t *cr,
|
||||
static int nua_bye_client_request(nua_client_request_t *cr,
|
||||
msg_t *msg, sip_t *sip,
|
||||
tagi_t const *tags);
|
||||
static int nua_bye_client_response(nua_client_request_t *cr,
|
||||
int status, char const *phrase,
|
||||
sip_t const *sip);
|
||||
static int nua_bye_client_report(nua_client_request_t *cr,
|
||||
int status, char const *phrase,
|
||||
sip_t const *sip,
|
||||
@@ -3739,7 +3742,7 @@ nua_client_methods_t const nua_bye_client_methods = {
|
||||
nua_bye_client_init, /* crm_init */
|
||||
nua_bye_client_request, /* crm_send */
|
||||
NULL, /* crm_check_restart */
|
||||
NULL, /* crm_recv */
|
||||
nua_bye_client_response, /* crm_recv */
|
||||
NULL, /* crm_preliminary */
|
||||
nua_bye_client_report, /* crm_report */
|
||||
NULL, /* crm_complete */
|
||||
@@ -3818,6 +3821,18 @@ static int nua_bye_client_request(nua_client_request_t *cr,
|
||||
|
||||
return error;
|
||||
}
|
||||
static int nua_bye_client_response(nua_client_request_t *cr,
|
||||
int status, char const *phrase,
|
||||
sip_t const *sip) {
|
||||
|
||||
nua_dialog_usage_t *du = cr->cr_usage;
|
||||
nua_session_usage_t *ss = nua_dialog_usage_private(du);
|
||||
|
||||
if (ss && ss->ss_reporting && status >= 900)
|
||||
return 1;
|
||||
|
||||
return nua_base_client_response(cr, status, phrase, sip, NULL);
|
||||
}
|
||||
|
||||
/** @NUA_EVENT nua_r_bye
|
||||
*
|
||||
|
||||
@@ -396,7 +396,9 @@ void nua_application_event(nua_t *dummy, su_msg_r sumsg, nua_ee_data_t *ee)
|
||||
e->e_msg ? sip_object(e->e_msg) : NULL,
|
||||
e->e_tags);
|
||||
|
||||
su_msg_destroy(frame->nf_saved);
|
||||
if (su_msg_is_non_null(frame->nf_saved)) {
|
||||
su_msg_destroy(frame->nf_saved);
|
||||
}
|
||||
nua->nua_current = frame->nf_next;
|
||||
}
|
||||
|
||||
@@ -417,6 +419,23 @@ msg_t *nua_current_request(nua_t const *nua)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
su_msg_t *nua_current_msg(nua_t const *nua, int clear)
|
||||
{
|
||||
if (nua && nua->nua_current && su_msg_is_non_null(nua->nua_current->nf_saved)) {
|
||||
su_msg_t *r = nua->nua_current->nf_saved[0];
|
||||
if (clear) {
|
||||
nua->nua_current->nf_saved[0] = NULL;
|
||||
}
|
||||
return r;
|
||||
//return su_msg_data(nua->nua_current->nf_saved)->ee_data->e_msg;
|
||||
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
/** Get request message from saved nua event. @NEW_1_12_4.
|
||||
*
|
||||
* @sa nua_save_event(), nua_respond(), NUTAG_WITH_SAVED(),
|
||||
@@ -638,8 +657,10 @@ void nua_stack_signal(nua_t *nua, su_msg_r msg, nua_ee_data_t *ee)
|
||||
nua_stack_respond(nua, nh, e->e_status, e->e_phrase, tags);
|
||||
break;
|
||||
case nua_r_destroy:
|
||||
nua_stack_destroy_handle(nua, nh, tags);
|
||||
su_msg_destroy(nua->nua_signal);
|
||||
if (!nh->nh_destroyed) {
|
||||
nua_stack_destroy_handle(nua, nh, tags);
|
||||
su_msg_destroy(nua->nua_signal);
|
||||
}
|
||||
return;
|
||||
default:
|
||||
break;
|
||||
@@ -912,6 +933,10 @@ nua_handle_t *nh_validate(nua_t *nua, nua_handle_t *maybe)
|
||||
|
||||
void nua_stack_destroy_handle(nua_t *nua, nua_handle_t *nh, tagi_t const *tags)
|
||||
{
|
||||
if (nh->nh_destroyed) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (nh->nh_notifier)
|
||||
nua_stack_terminate(nua, nh, (enum nua_event_e)0, NULL);
|
||||
|
||||
@@ -949,6 +974,12 @@ void nh_destroy(nua_t *nua, nua_handle_t *nh)
|
||||
{
|
||||
assert(nh); assert(nh != nua->nua_dhandle);
|
||||
|
||||
if (nh->nh_destroyed) {
|
||||
return;
|
||||
}
|
||||
|
||||
nh->nh_destroyed = 1;
|
||||
|
||||
if (nh->nh_notifier)
|
||||
nea_server_destroy(nh->nh_notifier), nh->nh_notifier = NULL;
|
||||
|
||||
|
||||
@@ -150,6 +150,7 @@ struct nua_handle_s
|
||||
unsigned nh_ref_by_user:1; /**< Has user used the handle? */
|
||||
unsigned nh_init:1; /**< Handle has been initialized */
|
||||
unsigned nh_used_ptags:1; /**< Ptags has been used */
|
||||
unsigned nh_destroyed:1; /**< nh_destroy already called */
|
||||
unsigned :0;
|
||||
|
||||
nua_dialog_state_t nh_ds[1];
|
||||
@@ -338,6 +339,8 @@ int nua_stack_event(nua_t *nua, nua_handle_t *nh, msg_t *msg,
|
||||
nua_event_t event, int status, char const *phrase,
|
||||
tagi_t const *tags);
|
||||
|
||||
su_msg_t *nua_current_msg(nua_t const *nua, int clear);
|
||||
|
||||
void nua_move_event(nua_saved_event_t a[1], nua_saved_event_t b[1]);
|
||||
|
||||
nua_handle_t *nh_create_handle(nua_t *nua, nua_hmagic_t *hmagic, tagi_t *tags);
|
||||
|
||||
@@ -64,8 +64,33 @@ struct su_home_s {
|
||||
|
||||
SU_DLL void *su_home_new(isize_t size)
|
||||
__attribute__((__malloc__));
|
||||
|
||||
#if (defined(HAVE_MEMLEAK_LOG) && (HAVE_MEMLEAK_LOG != 1))
|
||||
|
||||
int _su_home_mutex_lock(su_home_t *home, const char *file, unsigned int line, const char *function);
|
||||
int _su_home_mutex_lock(su_home_t *home, const char *file, unsigned int line, const char *function);
|
||||
|
||||
#define su_home_mutex_lock(home) \
|
||||
_su_home_mutex_lock((home), __FILE__, __LINE__, __func__)
|
||||
|
||||
#define su_home_mutex_unlock(home) \
|
||||
_su_home_mutex_unlock((home), __FILE__, __LINE__, __func__)
|
||||
|
||||
|
||||
su_home_t *_su_home_ref_by(
|
||||
su_home_t *home, char const *file, unsigned line, char const *by);
|
||||
int _su_home_unref_by(
|
||||
su_home_t *home, char const *file, unsigned line, char const *by);
|
||||
|
||||
#define su_home_ref(home) \
|
||||
_su_home_ref_by((home), __FILE__, __LINE__, __func__)
|
||||
#define su_home_unref(home) \
|
||||
_su_home_unref_by((home), __FILE__, __LINE__, __func__)
|
||||
|
||||
#else
|
||||
SU_DLL void *su_home_ref(su_home_t const *);
|
||||
SU_DLL int su_home_unref(su_home_t *);
|
||||
#endif
|
||||
|
||||
SU_DLL size_t su_home_refcount(su_home_t *home);
|
||||
|
||||
@@ -107,9 +132,11 @@ SU_DLL void su_home_check(su_home_t const *home);
|
||||
|
||||
SU_DLL int su_home_check_alloc(su_home_t const *home, void const *data);
|
||||
|
||||
#if (!defined(HAVE_MEMLEAK_LOG) || (HAVE_MEMLEAK_LOG != 1))
|
||||
SU_DLL int su_home_mutex_lock(su_home_t *home);
|
||||
|
||||
SU_DLL int su_home_mutex_unlock(su_home_t *home);
|
||||
#endif
|
||||
|
||||
SU_DLL int su_home_lock(su_home_t *home);
|
||||
SU_DLL int su_home_trylock(su_home_t *home);
|
||||
|
||||
@@ -569,28 +569,6 @@ void *su_home_new(isize_t size)
|
||||
return home;
|
||||
}
|
||||
|
||||
/** Create a new reference to a home object. */
|
||||
void *su_home_ref(su_home_t const *home)
|
||||
{
|
||||
if (home) {
|
||||
su_block_t *sub = MEMLOCK(home);
|
||||
|
||||
if (sub == NULL || sub->sub_ref == 0) {
|
||||
assert(sub && sub->sub_ref != 0);
|
||||
UNLOCK(home);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (sub->sub_ref != REF_MAX)
|
||||
sub->sub_ref++;
|
||||
UNLOCK(home);
|
||||
}
|
||||
else
|
||||
su_seterrno(EFAULT);
|
||||
|
||||
return (void *)home;
|
||||
}
|
||||
|
||||
/** Set destructor function.
|
||||
*
|
||||
* The destructor function is called after the reference count of a
|
||||
@@ -637,6 +615,123 @@ int su_home_desctructor(su_home_t *home, void (*destructor)(void *))
|
||||
return su_home_destructor(home, destructor);
|
||||
}
|
||||
|
||||
|
||||
#if (defined(HAVE_MEMLEAK_LOG) && (HAVE_MEMLEAK_LOG != 1))
|
||||
#include "sofia-sip/su_debug.h"
|
||||
|
||||
|
||||
static void *real_su_home_ref(su_home_t const *home)
|
||||
{
|
||||
if (home) {
|
||||
su_block_t *sub = MEMLOCK(home);
|
||||
|
||||
if (sub == NULL || sub->sub_ref == 0) {
|
||||
assert(sub && sub->sub_ref != 0);
|
||||
UNLOCK(home);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (sub->sub_ref != REF_MAX)
|
||||
sub->sub_ref++;
|
||||
UNLOCK(home);
|
||||
}
|
||||
else
|
||||
su_seterrno(EFAULT);
|
||||
|
||||
return (void *)home;
|
||||
}
|
||||
|
||||
|
||||
static int real_su_home_unref(su_home_t *home)
|
||||
{
|
||||
su_block_t *sub;
|
||||
|
||||
if (home == NULL)
|
||||
return 0;
|
||||
|
||||
sub = MEMLOCK(home);
|
||||
|
||||
if (sub == NULL) {
|
||||
/* Xyzzy */
|
||||
return 0;
|
||||
}
|
||||
else if (sub->sub_ref == REF_MAX) {
|
||||
UNLOCK(home);
|
||||
return 0;
|
||||
}
|
||||
else if (--sub->sub_ref > 0) {
|
||||
UNLOCK(home);
|
||||
return 0;
|
||||
}
|
||||
else if (sub->sub_parent) {
|
||||
su_home_t *parent = sub->sub_parent;
|
||||
UNLOCK(home);
|
||||
su_free(parent, home);
|
||||
return 1;
|
||||
}
|
||||
else {
|
||||
int hauto = sub->sub_hauto;
|
||||
_su_home_deinit(home);
|
||||
if (!hauto)
|
||||
safefree(home);
|
||||
/* UNLOCK(home); */
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
su_home_t *
|
||||
_su_home_ref_by(su_home_t *home,
|
||||
char const *file, unsigned line,
|
||||
char const *function)
|
||||
{
|
||||
if (home)
|
||||
SU_DEBUG_0(("%ld %p - su_home_ref() => "MOD_ZU" by %s:%u: %s()\n", pthread_self(),
|
||||
home, su_home_refcount(home) + 1, file, line, function));
|
||||
return (su_home_t *)real_su_home_ref(home);
|
||||
}
|
||||
|
||||
int
|
||||
_su_home_unref_by(su_home_t *home,
|
||||
char const *file, unsigned line,
|
||||
char const *function)
|
||||
{
|
||||
if (home) {
|
||||
size_t refcount = su_home_refcount(home) - 1;
|
||||
int freed = real_su_home_unref(home);
|
||||
|
||||
if (freed) refcount = 0;
|
||||
SU_DEBUG_0(("%ld %p - su_home_unref() => "MOD_ZU" by %s:%u: %s()\n", pthread_self(),
|
||||
home, refcount, file, line, function));
|
||||
return freed;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
#else
|
||||
|
||||
/** Create a new reference to a home object. */
|
||||
void *su_home_ref(su_home_t const *home)
|
||||
{
|
||||
if (home) {
|
||||
su_block_t *sub = MEMLOCK(home);
|
||||
|
||||
if (sub == NULL || sub->sub_ref == 0) {
|
||||
assert(sub && sub->sub_ref != 0);
|
||||
UNLOCK(home);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (sub->sub_ref != REF_MAX)
|
||||
sub->sub_ref++;
|
||||
UNLOCK(home);
|
||||
}
|
||||
else
|
||||
su_seterrno(EFAULT);
|
||||
|
||||
return (void *)home;
|
||||
}
|
||||
|
||||
|
||||
/**Unreference a su_home_t object.
|
||||
*
|
||||
* Decrements the reference count on home object and destroys and frees it
|
||||
@@ -683,6 +778,7 @@ int su_home_unref(su_home_t *home)
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
/** Return reference count of home. */
|
||||
size_t su_home_refcount(su_home_t *home)
|
||||
@@ -1546,14 +1642,24 @@ int su_home_is_threadsafe(su_home_t const *home)
|
||||
* Otherwise the su_home_mutex_lock() will just increase the reference
|
||||
* count.
|
||||
*/
|
||||
|
||||
#if (defined(HAVE_MEMLEAK_LOG) && (HAVE_MEMLEAK_LOG != 1))
|
||||
int _su_home_mutex_lock(su_home_t *home, const char *file, unsigned int line, const char *function)
|
||||
#else
|
||||
int su_home_mutex_lock(su_home_t *home)
|
||||
#endif
|
||||
|
||||
{
|
||||
int error;
|
||||
|
||||
if (home == NULL)
|
||||
return su_seterrno(EFAULT);
|
||||
|
||||
#if (defined(HAVE_MEMLEAK_LOG) && (HAVE_MEMLEAK_LOG != 1))
|
||||
if (home->suh_blocks == NULL || !_su_home_ref_by(home, file, line, function))
|
||||
#else
|
||||
if (home->suh_blocks == NULL || !su_home_ref(home))
|
||||
#endif
|
||||
return su_seterrno(EINVAL); /* Uninitialized home */
|
||||
|
||||
if (!home->suh_lock)
|
||||
@@ -1570,7 +1676,12 @@ int su_home_mutex_lock(su_home_t *home)
|
||||
*
|
||||
* @sa su_home_unlock().
|
||||
*/
|
||||
|
||||
#if (defined(HAVE_MEMLEAK_LOG) && (HAVE_MEMLEAK_LOG != 1))
|
||||
int _su_home_mutex_unlock(su_home_t *home, const char *file, unsigned int line, const char *function)
|
||||
#else
|
||||
int su_home_mutex_unlock(su_home_t *home)
|
||||
#endif
|
||||
{
|
||||
if (home == NULL)
|
||||
return su_seterrno(EFAULT);
|
||||
@@ -1584,7 +1695,11 @@ int su_home_mutex_unlock(su_home_t *home)
|
||||
if (home->suh_blocks == NULL)
|
||||
return su_seterrno(EINVAL), -1; /* Uninitialized home */
|
||||
|
||||
#if (defined(HAVE_MEMLEAK_LOG) && (HAVE_MEMLEAK_LOG != 1))
|
||||
_su_home_unref_by(home, file, line, function);
|
||||
#else
|
||||
su_home_unref(home);
|
||||
#endif
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -69,6 +69,8 @@ SPAN_DECLARE(SNDFILE *) sf_open_telephony_read(const char *name, int channels);
|
||||
|
||||
SPAN_DECLARE(SNDFILE *) sf_open_telephony_write(const char *name, int channels);
|
||||
|
||||
SPAN_DECLARE(int) sf_close_telephony(SNDFILE *handle);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -70,6 +70,16 @@ static int circle_init = FALSE;
|
||||
static complex_t icircle[MAX_FFT_LEN/2];
|
||||
static int icircle_init = FALSE;
|
||||
|
||||
#define SF_MAX_HANDLE 32
|
||||
static int sf_close_at_exit_registered = FALSE;
|
||||
static SNDFILE *sf_close_at_exit_list[SF_MAX_HANDLE] =
|
||||
{
|
||||
NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
|
||||
NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
|
||||
NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
|
||||
NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL
|
||||
};
|
||||
|
||||
SPAN_DECLARE(complexify_state_t *) complexify_init(void)
|
||||
{
|
||||
complexify_state_t *s;
|
||||
@@ -349,6 +359,42 @@ SPAN_DECLARE(void) codec_munge(codec_munge_state_t *s, int16_t amp[], int len)
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
static void sf_close_at_exit(void)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < SF_MAX_HANDLE; i++)
|
||||
{
|
||||
if (sf_close_at_exit_list[i])
|
||||
{
|
||||
sf_close(sf_close_at_exit_list[i]);
|
||||
sf_close_at_exit_list[i] = NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
static int sf_record_handle(SNDFILE *handle)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < SF_MAX_HANDLE; i++)
|
||||
{
|
||||
if (sf_close_at_exit_list[i] == NULL)
|
||||
break;
|
||||
}
|
||||
if (i >= SF_MAX_HANDLE)
|
||||
return -1;
|
||||
sf_close_at_exit_list[i] = handle;
|
||||
if (!sf_close_at_exit_registered)
|
||||
{
|
||||
atexit(sf_close_at_exit);
|
||||
sf_close_at_exit_registered = TRUE;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(SNDFILE *) sf_open_telephony_read(const char *name, int channels)
|
||||
{
|
||||
SNDFILE *handle;
|
||||
@@ -370,7 +416,7 @@ SPAN_DECLARE(SNDFILE *) sf_open_telephony_read(const char *name, int channels)
|
||||
printf(" Unexpected number of channels in audio file '%s'\n", name);
|
||||
exit(2);
|
||||
}
|
||||
|
||||
sf_record_handle(handle);
|
||||
return handle;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
@@ -393,8 +439,29 @@ SPAN_DECLARE(SNDFILE *) sf_open_telephony_write(const char *name, int channels)
|
||||
fprintf(stderr, " Cannot open audio file '%s' for writing\n", name);
|
||||
exit(2);
|
||||
}
|
||||
|
||||
sf_record_handle(handle);
|
||||
return handle;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(int) sf_close_telephony(SNDFILE *handle)
|
||||
{
|
||||
int res;
|
||||
int i;
|
||||
|
||||
if ((res = sf_close(handle)) == 0)
|
||||
{
|
||||
for (i = 0; i < SF_MAX_HANDLE; i++)
|
||||
{
|
||||
if (sf_close_at_exit_list[i] == handle)
|
||||
{
|
||||
sf_close(sf_close_at_exit_list[i]);
|
||||
sf_close_at_exit_list[i] = NULL;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
return res;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
/*- End of file ------------------------------------------------------------*/
|
||||
@@ -22,6 +22,7 @@ AM_LDFLAGS = $(COMP_VENDOR_LDFLAGS)
|
||||
MAINTAINERCLEANFILES = Makefile.in
|
||||
|
||||
DISTCLEANFILES = $(srcdir)/at_interpreter_dictionary.h \
|
||||
$(srcdir)/math_fixed_tables.h \
|
||||
$(srcdir)/v17_v32bis_rx_fixed_rrc.h \
|
||||
$(srcdir)/v17_v32bis_rx_floating_rrc.h \
|
||||
$(srcdir)/v17_v32bis_tx_fixed_rrc.h \
|
||||
@@ -55,6 +56,7 @@ EXTRA_DIST = floating_fudge.h \
|
||||
libtiff.2008.vcproj \
|
||||
filter_tools.c \
|
||||
make_at_dictionary.c \
|
||||
make_math_fixed_tables.c \
|
||||
make_modem_filter.c \
|
||||
msvc/config.h \
|
||||
msvc/Download_TIFF.2005.vcproj \
|
||||
@@ -123,6 +125,7 @@ libspandsp_la_SOURCES = adsi.c \
|
||||
lpc10_encode.c \
|
||||
lpc10_placev.c \
|
||||
lpc10_voicing.c \
|
||||
math_fixed.c \
|
||||
modem_echo.c \
|
||||
modem_connect_tones.c \
|
||||
noise.c \
|
||||
@@ -204,6 +207,7 @@ nobase_include_HEADERS = spandsp/adsi.h \
|
||||
spandsp/image_translate.h \
|
||||
spandsp/logging.h \
|
||||
spandsp/lpc10.h \
|
||||
spandsp/math_fixed.h \
|
||||
spandsp/modem_echo.h \
|
||||
spandsp/modem_connect_tones.h \
|
||||
spandsp/noise.h \
|
||||
@@ -329,6 +333,9 @@ noinst_HEADERS = faxfont.h \
|
||||
make_at_dictionary$(EXEEXT): $(top_srcdir)/src/make_at_dictionary.c
|
||||
$(CC_FOR_BUILD) -o make_at_dictionary$(EXEEXT) $(top_srcdir)/src/make_at_dictionary.c -DHAVE_CONFIG_H -I$(top_builddir)/src
|
||||
|
||||
make_math_fixed_tables$(EXEEXT): $(top_srcdir)/src/make_math_fixed_tables.c
|
||||
$(CC_FOR_BUILD) -o make_math_fixed_tables$(EXEEXT) $(top_srcdir)/src/make_math_fixed_tables.c -DHAVE_CONFIG_H -I$(top_builddir)/src -lm
|
||||
|
||||
make_modem_filter$(EXEEXT): $(top_srcdir)/src/make_modem_filter.c $(top_srcdir)/src/filter_tools.c
|
||||
$(CC_FOR_BUILD) -o make_modem_filter$(EXEEXT) $(top_srcdir)/src/make_modem_filter.c $(top_srcdir)/src/filter_tools.c -DHAVE_CONFIG_H -I$(top_builddir)/src -lm
|
||||
|
||||
@@ -342,6 +349,13 @@ at_interpreter.lo: at_interpreter_dictionary.h
|
||||
at_interpreter_dictionary.h: make_at_dictionary$(EXEEXT)
|
||||
./make_at_dictionary$(EXEEXT) >at_interpreter_dictionary.h
|
||||
|
||||
math_fixed.$(OBJEXT): math_fixed_tables.h
|
||||
|
||||
math_fixed.lo: math_fixed_tables.h
|
||||
|
||||
math_fixed_tables.h: make_math_fixed_tables$(EXEEXT)
|
||||
./make_math_fixed_tables$(EXEEXT) >math_fixed_tables.h
|
||||
|
||||
t4_rx.$(OBJEXT): spandsp/version.h
|
||||
|
||||
t4_rx.lo: spandsp/version.h
|
||||
|
||||
@@ -69,6 +69,12 @@ SPAN_DECLARE(const char *) signal_status_to_str(int status)
|
||||
return "Poor signal quality";
|
||||
case SIG_STATUS_MODEM_RETRAIN_OCCURRED:
|
||||
return "Modem retrain occurred";
|
||||
case SIG_STATUS_LINK_CONNECTED:
|
||||
return "Link connected";
|
||||
case SIG_STATUS_LINK_DISCONNECTED:
|
||||
return "Link disconnected";
|
||||
case SIG_STATUS_LINK_ERROR:
|
||||
return "Link error";
|
||||
}
|
||||
return "???";
|
||||
}
|
||||
|
||||
@@ -5311,7 +5311,7 @@ static const char *at_cmd_plus_WSTL(at_state_t *s, const char *t)
|
||||
|
||||
#include "at_interpreter_dictionary.h"
|
||||
|
||||
static int command_search(const char *u, int len, int *matched)
|
||||
static int command_search(const char *u, int *matched)
|
||||
{
|
||||
int i;
|
||||
int index;
|
||||
@@ -5445,7 +5445,7 @@ SPAN_DECLARE(void) at_interpreter(at_state_t *s, const char *cmd, int len)
|
||||
t = s->line + 2;
|
||||
while (t && *t)
|
||||
{
|
||||
if ((entry = command_search(t, 15, &matched)) <= 0)
|
||||
if ((entry = command_search(t, &matched)) <= 0)
|
||||
break;
|
||||
if ((t = at_commands[entry - 1](s, t)) == NULL)
|
||||
break;
|
||||
|
||||
@@ -56,7 +56,7 @@
|
||||
/* This is a simple set of direct digital synthesis (DDS) functions to generate sine
|
||||
waves. This version uses a 128 entry sin/cos table to cover one quadrant. */
|
||||
|
||||
static const int16_t sine_table[DDS_STEPS] =
|
||||
static const int16_t sine_table[DDS_STEPS + 1] =
|
||||
{
|
||||
201,
|
||||
603,
|
||||
@@ -186,6 +186,7 @@ static const int16_t sine_table[DDS_STEPS] =
|
||||
32753,
|
||||
32762,
|
||||
32767,
|
||||
32767
|
||||
};
|
||||
|
||||
SPAN_DECLARE(int32_t) dds_phase_rate(float frequency)
|
||||
@@ -220,7 +221,7 @@ SPAN_DECLARE(int16_t) dds_lookup(uint32_t phase)
|
||||
phase >>= DDS_SHIFT;
|
||||
step = phase & (DDS_STEPS - 1);
|
||||
if ((phase & DDS_STEPS))
|
||||
step = (DDS_STEPS - 1) - step;
|
||||
step = DDS_STEPS - step;
|
||||
amp = sine_table[step];
|
||||
if ((phase & (2*DDS_STEPS)))
|
||||
amp = -amp;
|
||||
@@ -254,7 +255,7 @@ SPAN_DECLARE(int16_t) dds_mod(uint32_t *phase_acc, int32_t phase_rate, int16_t s
|
||||
{
|
||||
int16_t amp;
|
||||
|
||||
amp = (int16_t) (((int32_t) dds_lookup(*phase_acc + phase)*(int32_t) scale) >> 15);
|
||||
amp = (int16_t) (((int32_t) dds_lookup(*phase_acc + phase)*scale) >> 15);
|
||||
*phase_acc += phase_rate;
|
||||
return amp;
|
||||
}
|
||||
@@ -280,8 +281,8 @@ SPAN_DECLARE(complexi_t) dds_complexi_mod(uint32_t *phase_acc, int32_t phase_rat
|
||||
{
|
||||
complexi_t amp;
|
||||
|
||||
amp = complex_seti(((int32_t) dds_lookup(*phase_acc + phase + (1 << 30))*(int32_t) scale) >> 15,
|
||||
((int32_t) dds_lookup(*phase_acc + phase)*(int32_t) scale) >> 15);
|
||||
amp = complex_seti(((int32_t) dds_lookup(*phase_acc + phase + (1 << 30))*scale) >> 15,
|
||||
((int32_t) dds_lookup(*phase_acc + phase)*scale) >> 15);
|
||||
*phase_acc += phase_rate;
|
||||
return amp;
|
||||
}
|
||||
@@ -307,8 +308,8 @@ SPAN_DECLARE(complexi16_t) dds_complexi16_mod(uint32_t *phase_acc, int32_t phase
|
||||
{
|
||||
complexi16_t amp;
|
||||
|
||||
amp = complex_seti16((int16_t) (((int32_t) dds_lookup(*phase_acc + phase + (1 << 30))*(int32_t) scale) >> 15),
|
||||
(int16_t) (((int32_t) dds_lookup(*phase_acc + phase)*(int32_t) scale) >> 15));
|
||||
amp = complex_seti16((int16_t) (((int32_t) dds_lookup(*phase_acc + phase + (1 << 30))*scale) >> 15),
|
||||
(int16_t) (((int32_t) dds_lookup(*phase_acc + phase)*scale) >> 15));
|
||||
*phase_acc += phase_rate;
|
||||
return amp;
|
||||
}
|
||||
@@ -334,8 +335,8 @@ SPAN_DECLARE(complexi32_t) dds_complexi32_mod(uint32_t *phase_acc, int32_t phase
|
||||
{
|
||||
complexi32_t amp;
|
||||
|
||||
amp = complex_seti32(((int32_t) dds_lookup(*phase_acc + phase + (1 << 30))*(int32_t) scale) >> 15,
|
||||
((int32_t) dds_lookup(*phase_acc + phase)*(int32_t) scale) >> 15);
|
||||
amp = complex_seti32(((int32_t) dds_lookup(*phase_acc + phase + (1 << 30))*scale) >> 15,
|
||||
((int32_t) dds_lookup(*phase_acc + phase)*scale) >> 15);
|
||||
*phase_acc += phase_rate;
|
||||
return amp;
|
||||
}
|
||||
|
||||
@@ -220,7 +220,7 @@ SPAN_DECLARE(void) fsk_tx_set_get_bit(fsk_tx_state_t *s, get_bit_func_t get_bit,
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(void) fsk_tx_set_modem_status_handler(fsk_tx_state_t *s, modem_tx_status_func_t handler, void *user_data)
|
||||
SPAN_DECLARE(void) fsk_tx_set_modem_status_handler(fsk_tx_state_t *s, modem_status_func_t handler, void *user_data)
|
||||
{
|
||||
s->status_handler = handler;
|
||||
s->status_user_data = user_data;
|
||||
@@ -248,7 +248,7 @@ SPAN_DECLARE(void) fsk_rx_set_put_bit(fsk_rx_state_t *s, put_bit_func_t put_bit,
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(void) fsk_rx_set_modem_status_handler(fsk_rx_state_t *s, modem_tx_status_func_t handler, void *user_data)
|
||||
SPAN_DECLARE(void) fsk_rx_set_modem_status_handler(fsk_rx_state_t *s, modem_status_func_t handler, void *user_data)
|
||||
{
|
||||
s->status_handler = handler;
|
||||
s->status_user_data = user_data;
|
||||
|
||||
@@ -91,15 +91,16 @@ void gsm0610_preprocess(gsm0610_state_t *s, const int16_t amp[GSM0610_FRAME_LEN]
|
||||
/* 4.2.1 Downscaling of the input signal */
|
||||
SO = (amp[k] >> 1) & ~3;
|
||||
|
||||
assert(SO >= -0x4000); // downscaled by
|
||||
assert(SO <= 0x3FFC); // previous routine.
|
||||
/* This is supposed to have been downscaled by previous routine. */
|
||||
assert(SO >= -0x4000);
|
||||
assert(SO <= 0x3FFC);
|
||||
|
||||
/* 4.2.2 Offset compensation */
|
||||
|
||||
/* This part implements a high-pass filter and requires extended
|
||||
arithmetic precision for the recursive part of this filter.
|
||||
The input of this procedure is the array so[0...159] and the
|
||||
output the array sof[ 0...159 ].
|
||||
output the array sof[0...159].
|
||||
*/
|
||||
/* Compute the non-recursive part */
|
||||
s1 = SO - z1;
|
||||
|
||||
@@ -332,7 +332,7 @@ SPAN_DECLARE(void) hdlc_rx_set_frame_handler(hdlc_rx_state_t *s, hdlc_frame_hand
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(void) hdlc_rx_set_status_handler(hdlc_rx_state_t *s, modem_rx_status_func_t handler, void *user_data)
|
||||
SPAN_DECLARE(void) hdlc_rx_set_status_handler(hdlc_rx_state_t *s, modem_status_func_t handler, void *user_data)
|
||||
{
|
||||
s->status_handler = handler;
|
||||
s->status_user_data = user_data;
|
||||
|
||||
@@ -144,14 +144,14 @@ static int image_resize_row(image_translate_state_t *s, uint8_t buf[], size_t le
|
||||
int output_length;
|
||||
int input_width;
|
||||
int input_length;
|
||||
int x;
|
||||
double c1;
|
||||
double c2;
|
||||
double int_part;
|
||||
int x;
|
||||
#if defined(SPANDSP_USE_FIXED_POINT)
|
||||
int frac_row;
|
||||
int frac_col;
|
||||
#else
|
||||
double int_part;
|
||||
double frac_row;
|
||||
double frac_col;
|
||||
#endif
|
||||
@@ -198,7 +198,7 @@ static int image_resize_row(image_translate_state_t *s, uint8_t buf[], size_t le
|
||||
x = i*input_width/output_width;
|
||||
frac_col = x - x*output_width;
|
||||
c1 = s->raw_pixel_row[0][x] + (s->raw_pixel_row[0][x + 1] - s->raw_pixel_row[0][x])*frac_col;
|
||||
c1 = s->raw_pixel_row[1][x] + (s->raw_pixel_row[1][x + 1] - s->raw_pixel_row[1][x])*frac_col;
|
||||
c2 = s->raw_pixel_row[1][x] + (s->raw_pixel_row[1][x + 1] - s->raw_pixel_row[1][x])*frac_col;
|
||||
buf[i] = saturateu8(c1 + (c2 - c1)*frac_row);
|
||||
}
|
||||
#else
|
||||
|
||||
@@ -86,7 +86,7 @@ static __inline__ int32_t pow_ii(int32_t x, int32_t n)
|
||||
if (n == 0 || x == 1)
|
||||
return 1;
|
||||
if (x != -1)
|
||||
return (x == 0) ? 1/x : 0;
|
||||
return (x != 0) ? 1/x : 0;
|
||||
n = -n;
|
||||
}
|
||||
u = n;
|
||||
|
||||
@@ -0,0 +1,116 @@
|
||||
/*
|
||||
* SpanDSP - a series of DSP components for telephony
|
||||
*
|
||||
* make_fixed_point_math_tables.c - Generate lookup tables for some of the
|
||||
* fixed point maths functions.
|
||||
*
|
||||
* Written by Steve Underwood <steveu@coppice.org>
|
||||
*
|
||||
* Copyright (C) 2010 Steve Underwood
|
||||
*
|
||||
* All rights reserved.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2, as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
*/
|
||||
|
||||
#if defined(HAVE_CONFIG_H)
|
||||
#include "config.h"
|
||||
#endif
|
||||
|
||||
#include <inttypes.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <fcntl.h>
|
||||
#include <memory.h>
|
||||
#include <math.h>
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
int i;
|
||||
double val;
|
||||
int ival;
|
||||
|
||||
printf("static const uint16_t fixed_reciprocal_table[129] =\n");
|
||||
printf("{\n");
|
||||
for (i = 0; i < 129; i++)
|
||||
{
|
||||
val = 32768.0*128.0/(128 + i) + 0.5;
|
||||
ival = val;
|
||||
if (i < 128)
|
||||
printf(" %6d,\n", ival);
|
||||
else
|
||||
printf(" %6d\n", ival);
|
||||
}
|
||||
printf("};\n\n");
|
||||
|
||||
printf("static const uint16_t fixed_sqrt_table[193] =\n");
|
||||
printf("{\n");
|
||||
for (i = 64; i <= 256; i++)
|
||||
{
|
||||
ival = sqrt(i/256.0)*65536.0 + 0.5;
|
||||
if (ival > 65535)
|
||||
ival = 65535;
|
||||
if (i < 256)
|
||||
printf(" %6d,\n", ival);
|
||||
else
|
||||
printf(" %6d\n", ival);
|
||||
}
|
||||
printf("};\n\n");
|
||||
|
||||
printf("static const int16_t fixed_log10_table[129] =\n");
|
||||
printf("{\n");
|
||||
for (i = 128; i <= 256; i++)
|
||||
{
|
||||
ival = log10(i/256.0)*32768.0 - 0.5;
|
||||
if (i <= 255)
|
||||
printf(" %6d,\n", ival);
|
||||
else
|
||||
printf(" %6d\n", ival);
|
||||
}
|
||||
printf("};\n\n");
|
||||
|
||||
printf("static const int16_t fixed_sine_table[257] =\n");
|
||||
printf("{\n");
|
||||
for (i = 0; i <= 256; i++)
|
||||
{
|
||||
val = sin(i*3.1415926535/512.0)*32768.0;
|
||||
ival = val + 0.5;
|
||||
if (ival > 32767)
|
||||
ival = 32767;
|
||||
if (i <= 255)
|
||||
printf(" %6d,\n", ival);
|
||||
else
|
||||
printf(" %6d\n", ival);
|
||||
}
|
||||
printf("};\n\n");
|
||||
|
||||
printf("static const uint16_t fixed_arctan_table[257] =\n");
|
||||
printf("{\n");
|
||||
for (i = 0; i <= 256; i++)
|
||||
{
|
||||
val = atan(i/256.0)*65536.0/(2.0*3.1415926535);
|
||||
ival = val + 0.5;
|
||||
/* Nudge the result away from zero, so things sit consistently on
|
||||
the correct side of the axes. */
|
||||
if (ival == 0)
|
||||
ival = 1;
|
||||
if (i <= 255)
|
||||
printf(" %6d,\n", ival);
|
||||
else
|
||||
printf(" %6d\n", ival);
|
||||
}
|
||||
printf("};\n\n");
|
||||
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,255 @@
|
||||
/*
|
||||
* SpanDSP - a series of DSP components for telephony
|
||||
*
|
||||
* math_fixed.c
|
||||
*
|
||||
* Written by Steve Underwood <steveu@coppice.org>
|
||||
*
|
||||
* Copyright (C) 2010 Steve Underwood
|
||||
*
|
||||
* All rights reserved.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License version 2.1,
|
||||
* as published by the Free Software Foundation.
|
||||
*
|
||||
* 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 Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
*/
|
||||
|
||||
/*! \file */
|
||||
|
||||
#if defined(HAVE_CONFIG_H)
|
||||
#include "config.h"
|
||||
#endif
|
||||
|
||||
#include <inttypes.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <fcntl.h>
|
||||
#include <string.h>
|
||||
#include <float.h>
|
||||
#if defined(HAVE_TGMATH_H)
|
||||
#include <tgmath.h>
|
||||
#endif
|
||||
#if defined(HAVE_MATH_H)
|
||||
#include <math.h>
|
||||
#endif
|
||||
#include "floating_fudge.h"
|
||||
#include <assert.h>
|
||||
|
||||
#include "math_fixed_tables.h"
|
||||
|
||||
#include "spandsp/telephony.h"
|
||||
#include "spandsp/bit_operations.h"
|
||||
#include "spandsp/math_fixed.h"
|
||||
|
||||
#if defined(SPANDSP_USE_FIXED_POINT)
|
||||
SPAN_DECLARE(uint16_t) sqrtu32_u16(uint32_t x)
|
||||
{
|
||||
uint16_t zz;
|
||||
uint16_t z;
|
||||
uint16_t i;
|
||||
|
||||
z = 0;
|
||||
for (i = 0x8000; i; i >>= 1)
|
||||
{
|
||||
zz = z | i;
|
||||
if (((int32_t) zz*zz) <= x)
|
||||
z = zz;
|
||||
}
|
||||
return z;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
#endif
|
||||
|
||||
SPAN_DECLARE(uint16_t) fixed_reciprocal16(uint16_t x, int *shift)
|
||||
{
|
||||
if (x == 0)
|
||||
{
|
||||
*shift = 0;
|
||||
return 0xFFFF;
|
||||
}
|
||||
*shift = 15 - top_bit(x);
|
||||
x <<= *shift;
|
||||
return fixed_reciprocal_table[((x + 0x80) >> 8) - 128];
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(uint16_t) fixed_divide16(uint16_t y, uint16_t x)
|
||||
{
|
||||
int shift;
|
||||
uint32_t z;
|
||||
uint16_t recip;
|
||||
|
||||
if (x == 0)
|
||||
return 0xFFFF;
|
||||
recip = fixed_reciprocal16(x, &shift);
|
||||
z = (((uint32_t) y*recip) >> 15) << shift;
|
||||
return z;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(uint16_t) fixed_divide32(uint32_t y, uint16_t x)
|
||||
{
|
||||
int shift;
|
||||
uint32_t z;
|
||||
uint16_t recip;
|
||||
|
||||
if (x == 0)
|
||||
return 0xFFFF;
|
||||
recip = fixed_reciprocal16(x, &shift);
|
||||
z = (((uint32_t) y*recip) >> 15) << shift;
|
||||
return z;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(int16_t) fixed_log10_16(uint16_t x)
|
||||
{
|
||||
int shift;
|
||||
|
||||
if (x == 0)
|
||||
return 0;
|
||||
shift = 14 - top_bit(x);
|
||||
x <<= shift;
|
||||
return (fixed_log10_table[((x + 0x40) >> 7) - 128] >> 3) - shift*1233;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(int32_t) fixed_log10_32(uint32_t x)
|
||||
{
|
||||
int shift;
|
||||
|
||||
if (x == 0)
|
||||
return 0;
|
||||
shift = 30 - top_bit(x);
|
||||
x <<= shift;
|
||||
return (fixed_log10_table[((x + 0x400000) >> 23) - 128] >> 3) - shift*1233;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(uint16_t) fixed_sqrt16(uint16_t x)
|
||||
{
|
||||
int shift;
|
||||
|
||||
if (x == 0)
|
||||
return 0;
|
||||
shift = 14 - (top_bit(x) & ~1);
|
||||
x <<= shift;
|
||||
//return fixed_sqrt_table[(((x + 0x80) >> 8) & 0xFF) - 64] >> (shift >> 1);
|
||||
return fixed_sqrt_table[((x >> 8) & 0xFF) - 64] >> (shift >> 1);
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(uint16_t) fixed_sqrt32(uint32_t x)
|
||||
{
|
||||
int shift;
|
||||
|
||||
if (x == 0)
|
||||
return 0;
|
||||
shift = 30 - (top_bit(x) & ~1);
|
||||
x <<= shift;
|
||||
//return fixed_sqrt_table[(((x + 0x800000) >> 24) & 0xFF) - 64] >> (shift >> 1);
|
||||
return fixed_sqrt_table[((x >> 24) & 0xFF) - 64] >> (shift >> 1);
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(int16_t) fixed_sin(uint16_t x)
|
||||
{
|
||||
int step;
|
||||
int step_after;
|
||||
int16_t frac;
|
||||
int16_t z;
|
||||
|
||||
step = (x & 0x3FFF) >> 6;
|
||||
frac = x & 0x3F;
|
||||
if ((x & 0x4000))
|
||||
{
|
||||
step = 256 - step;
|
||||
step_after = step - 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
step_after = step + 1;
|
||||
}
|
||||
z = fixed_sine_table[step] + ((frac*(fixed_sine_table[step_after] - fixed_sine_table[step])) >> 6);
|
||||
if ((x & 0x8000))
|
||||
z = -z;
|
||||
return z;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(int16_t) fixed_cos(uint16_t x)
|
||||
{
|
||||
int step;
|
||||
int step_after;
|
||||
int16_t frac;
|
||||
int16_t z;
|
||||
|
||||
x += 0x4000;
|
||||
step = (x & 0x3FFF) >> 6;
|
||||
frac = x & 0x3F;
|
||||
if ((x & 0x4000))
|
||||
{
|
||||
step = 256 - step;
|
||||
step_after = step - 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
step_after = step + 1;
|
||||
}
|
||||
z = fixed_sine_table[step] + ((frac*(fixed_sine_table[step_after] - fixed_sine_table[step])) >> 6);
|
||||
if ((x & 0x8000))
|
||||
z = -z;
|
||||
return z;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(uint16_t) fixed_atan2(int16_t y, int16_t x)
|
||||
{
|
||||
int16_t abs_x;
|
||||
int16_t abs_y;
|
||||
uint16_t angle;
|
||||
uint16_t recip;
|
||||
uint32_t z;
|
||||
int step;
|
||||
int shift;
|
||||
|
||||
if (y == 0)
|
||||
return (x & 0x8000);
|
||||
if (x == 0)
|
||||
return ((y & 0x8000) | 0x4000);
|
||||
abs_x = abs(x);
|
||||
abs_y = abs(y);
|
||||
|
||||
if (abs_y < abs_x)
|
||||
{
|
||||
recip = fixed_reciprocal16(abs_x, &shift);
|
||||
z = (((uint32_t) recip*abs_y) >> 15) << shift;
|
||||
step = z >> 7;
|
||||
angle = fixed_arctan_table[step];
|
||||
}
|
||||
else
|
||||
{
|
||||
recip = fixed_reciprocal16(abs_y, &shift);
|
||||
z = (((uint32_t) recip*abs_x) >> 15) << shift;
|
||||
step = z >> 7;
|
||||
angle = 0x4000 - fixed_arctan_table[step];
|
||||
}
|
||||
/* If we are in quadrant II or III, flip things around */
|
||||
if (x < 0)
|
||||
angle = 0x8000 - angle;
|
||||
/* If we are in quadrant III or IV, negate to return an
|
||||
answer in the full circle range. */
|
||||
if (y < 0)
|
||||
angle = -angle;
|
||||
return (uint16_t) angle;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
/*- End of file ------------------------------------------------------------*/
|
||||
@@ -165,10 +165,8 @@ SPAN_DECLARE(int) plc_fillin(plc_state_t *s, int16_t amp[], int len)
|
||||
float old_weight;
|
||||
float new_weight;
|
||||
float gain;
|
||||
//int16_t *orig_amp;
|
||||
int orig_len;
|
||||
|
||||
//orig_amp = amp;
|
||||
orig_len = len;
|
||||
if (s->missing_samples == 0)
|
||||
{
|
||||
|
||||
@@ -122,7 +122,7 @@ SPAN_DECLARE(float) power_meter_current_dbm0(power_meter_t *s)
|
||||
if (s->reading <= 0)
|
||||
return -96.329f + DBM0_MAX_POWER;
|
||||
/* This is based on A-law, but u-law is only 0.03dB different, so don't worry. */
|
||||
return log10f((float) s->reading/(32767.0f*32767.0f))*10.0f + DBM0_MAX_POWER;
|
||||
return 10.0f*log10f((float) s->reading/(32767.0f*32767.0f) + 1.0e-10f) + DBM0_MAX_POWER;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
@@ -130,7 +130,7 @@ SPAN_DECLARE(float) power_meter_current_dbov(power_meter_t *s)
|
||||
{
|
||||
if (s->reading <= 0)
|
||||
return -96.329f;
|
||||
return log10f((float) s->reading/(32767.0f*32767.0f))*10.0f;
|
||||
return 10.0f*log10f((float) s->reading/(32767.0f*32767.0f) + 1.0e-10f);
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
|
||||
@@ -108,7 +108,7 @@ SPAN_DECLARE(int) silence_gen_generated(silence_gen_state_t *s)
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(void) silence_gen_status_handler(silence_gen_state_t *s, modem_tx_status_func_t handler, void *user_data)
|
||||
SPAN_DECLARE(void) silence_gen_status_handler(silence_gen_state_t *s, modem_status_func_t handler, void *user_data)
|
||||
{
|
||||
s->status_handler = handler;
|
||||
s->status_user_data = user_data;
|
||||
|
||||
@@ -49,9 +49,19 @@ static __inline__ int32_t arctan2(float y, float x)
|
||||
float abs_y;
|
||||
float angle;
|
||||
|
||||
if (x == 0.0f || y == 0.0f)
|
||||
return 0;
|
||||
|
||||
if (y == 0.0f)
|
||||
{
|
||||
if (x < 0.0f)
|
||||
return 0x80000000;
|
||||
return 0x00000000;
|
||||
}
|
||||
if (x == 0.0f)
|
||||
{
|
||||
if (y < 0.0f)
|
||||
return 0xc0000000;
|
||||
return 0x40000000;
|
||||
}
|
||||
|
||||
abs_y = fabsf(y);
|
||||
|
||||
/* If we are in quadrant II or III, flip things around */
|
||||
@@ -77,8 +87,18 @@ static __inline__ float arctan2f(float y, float x)
|
||||
float fx;
|
||||
float fy;
|
||||
|
||||
if (x == 0.0f || y == 0.0f)
|
||||
return 0;
|
||||
if (y == 0.0f)
|
||||
{
|
||||
if (x < 0.0f)
|
||||
return 3.1415926f;
|
||||
return 0.0f;
|
||||
}
|
||||
if (x == 0.0f)
|
||||
{
|
||||
if (y < 0.0f)
|
||||
return 3.1415926f*1.5f;
|
||||
return 3.1415926f*0.5f;
|
||||
}
|
||||
fx = fabsf(x);
|
||||
fy = fabsf(y);
|
||||
/* Deal with the octants */
|
||||
|
||||
@@ -80,7 +80,13 @@ enum
|
||||
/*! \brief Notification that a modem has detected signal quality degradation. */
|
||||
SIG_STATUS_POOR_SIGNAL_QUALITY = -12,
|
||||
/*! \brief Notification that a modem retrain has occurred. */
|
||||
SIG_STATUS_MODEM_RETRAIN_OCCURRED = -13
|
||||
SIG_STATUS_MODEM_RETRAIN_OCCURRED = -13,
|
||||
/*! \brief The link protocol (e.g. V.42) has connected. */
|
||||
SIG_STATUS_LINK_CONNECTED = -14,
|
||||
/*! \brief The link protocol (e.g. V.42) has disconnected. */
|
||||
SIG_STATUS_LINK_DISCONNECTED = -15,
|
||||
/*! \brief An error has occurred in the link protocol (e.g. V.42). */
|
||||
SIG_STATUS_LINK_ERROR = -16
|
||||
};
|
||||
|
||||
/*! Message put function for data pumps */
|
||||
@@ -101,11 +107,8 @@ typedef void (*put_bit_func_t)(void *user_data, int bit);
|
||||
/*! Bit get function for data pumps */
|
||||
typedef int (*get_bit_func_t)(void *user_data);
|
||||
|
||||
/*! Completion callback function for tx data pumps */
|
||||
typedef void (*modem_tx_status_func_t)(void *user_data, int status);
|
||||
|
||||
/*! Completion callback function for rx data pumps */
|
||||
typedef void (*modem_rx_status_func_t)(void *user_data, int status);
|
||||
/*! Status change callback function for data pumps */
|
||||
typedef void (*modem_status_func_t)(void *user_data, int status);
|
||||
|
||||
enum
|
||||
{
|
||||
|
||||
@@ -225,7 +225,7 @@ SPAN_DECLARE(uint32_t) bit_reverse_4bytes(uint32_t data);
|
||||
SPAN_DECLARE(uint64_t) bit_reverse_8bytes(uint64_t data);
|
||||
#endif
|
||||
|
||||
/*! \brief Bit reverse each bytes in a buffer.
|
||||
/*! \brief Bit reverse each byte in a buffer.
|
||||
\param to The buffer to place the reversed data in.
|
||||
\param from The buffer containing the data to be reversed.
|
||||
\param len The length of the data in the buffer. */
|
||||
|
||||
@@ -477,6 +477,12 @@ static __inline__ complexi32_t complex_conji32(const complexi32_t *x)
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
static __inline__ int32_t poweri16(const complexi16_t *x)
|
||||
{
|
||||
return (int32_t) x->re*x->re + (int32_t) x->im*x->im;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
static __inline__ float powerf(const complexf_t *x)
|
||||
{
|
||||
return x->re*x->re + x->im*x->im;
|
||||
|
||||
@@ -77,6 +77,8 @@
|
||||
#include <spandsp/private/t4_t6_encode.h>
|
||||
/*#include <spandsp/private/t81_t82_arith_coding.h>*/
|
||||
/*#include <spandsp/private/t85.h>*/
|
||||
/*#include <spandsp/private/t42.h>*/
|
||||
/*#include <spandsp/private/t43.h>*/
|
||||
#include <spandsp/private/t4_rx.h>
|
||||
#include <spandsp/private/t4_tx.h>
|
||||
#include <spandsp/private/t30.h>
|
||||
|
||||
@@ -175,7 +175,7 @@ SPAN_DECLARE(void) fsk_tx_set_get_bit(fsk_tx_state_t *s, get_bit_func_t get_bit,
|
||||
\param s The modem context.
|
||||
\param handler The callback routine used to report modem status changes.
|
||||
\param user_data An opaque pointer. */
|
||||
SPAN_DECLARE(void) fsk_tx_set_modem_status_handler(fsk_tx_state_t *s, modem_tx_status_func_t handler, void *user_data);
|
||||
SPAN_DECLARE(void) fsk_tx_set_modem_status_handler(fsk_tx_state_t *s, modem_status_func_t handler, void *user_data);
|
||||
|
||||
/*! Generate a block of FSK modem audio samples.
|
||||
\brief Generate a block of FSK modem audio samples.
|
||||
@@ -243,7 +243,7 @@ SPAN_DECLARE(void) fsk_rx_set_put_bit(fsk_rx_state_t *s, put_bit_func_t put_bit,
|
||||
\param s The modem context.
|
||||
\param handler The callback routine used to report modem status changes.
|
||||
\param user_data An opaque pointer. */
|
||||
SPAN_DECLARE(void) fsk_rx_set_modem_status_handler(fsk_rx_state_t *s, modem_rx_status_func_t handler, void *user_data);
|
||||
SPAN_DECLARE(void) fsk_rx_set_modem_status_handler(fsk_rx_state_t *s, modem_status_func_t handler, void *user_data);
|
||||
|
||||
#if defined(__cplusplus)
|
||||
}
|
||||
|
||||
@@ -113,7 +113,7 @@ SPAN_DECLARE(void) hdlc_rx_set_frame_handler(hdlc_rx_state_t *s, hdlc_frame_hand
|
||||
\param handler The callback routine used to report status changes.
|
||||
\param user_data An opaque parameter for the callback routine.
|
||||
*/
|
||||
SPAN_DECLARE(void) hdlc_rx_set_status_handler(hdlc_rx_state_t *s, modem_rx_status_func_t handler, void *user_data);
|
||||
SPAN_DECLARE(void) hdlc_rx_set_status_handler(hdlc_rx_state_t *s, modem_status_func_t handler, void *user_data);
|
||||
|
||||
/*! Release an HDLC receiver context.
|
||||
\brief Release an HDLC receiver context.
|
||||
|
||||
@@ -0,0 +1,83 @@
|
||||
/*
|
||||
* SpanDSP - a series of DSP components for telephony
|
||||
*
|
||||
* math_fixed.h
|
||||
*
|
||||
* Written by Steve Underwood <steveu@coppice.org>
|
||||
*
|
||||
* Copyright (C) 2010 Steve Underwood
|
||||
*
|
||||
* All rights reserved.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License version 2.1,
|
||||
* as published by the Free Software Foundation.
|
||||
*
|
||||
* 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 Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public
|
||||
* License along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
*/
|
||||
|
||||
#if !defined(_MATH_FIXED_H_)
|
||||
#define _MATH_FIXED_H_
|
||||
|
||||
/*! \page math_fixed_page Fixed point math functions
|
||||
|
||||
\section math_fixed_page_sec_1 What does it do?
|
||||
|
||||
\section math_fixed_page_sec_2 How does it work?
|
||||
*/
|
||||
|
||||
#if defined(__cplusplus)
|
||||
extern "C"
|
||||
{
|
||||
#endif
|
||||
|
||||
#if defined(SPANDSP_USE_FIXED_POINT)
|
||||
SPAN_DECLARE(uint16_t) sqrtu32_u16(uint32_t x);
|
||||
#endif
|
||||
|
||||
SPAN_DECLARE(uint16_t) fixed_reciprocal16(uint16_t x, int *shift);
|
||||
|
||||
SPAN_DECLARE(uint16_t) fixed_divide16(uint16_t y, uint16_t x);
|
||||
|
||||
SPAN_DECLARE(uint16_t) fixed_divide32(uint32_t y, uint16_t x);
|
||||
|
||||
SPAN_DECLARE(int16_t) fixed_log10_16(uint16_t x);
|
||||
|
||||
SPAN_DECLARE(int32_t) fixed_log10_32(uint32_t x);
|
||||
|
||||
SPAN_DECLARE(uint16_t) fixed_sqrt16(uint16_t x);
|
||||
|
||||
SPAN_DECLARE(uint16_t) fixed_sqrt32(uint32_t x);
|
||||
|
||||
/*! Evaluate an approximate 16 bit fixed point sine.
|
||||
\brief Evaluate an approximate 16 bit fixed point sine.
|
||||
\param x A 16 bit unsigned angle, in 360/65536 degree steps.
|
||||
\return sin(x)*32767. */
|
||||
SPAN_DECLARE(int16_t) fixed_sin(uint16_t x);
|
||||
|
||||
/*! Evaluate an approximate 16 bit fixed point cosine.
|
||||
\brief Evaluate an approximate 16 bit fixed point cosine.
|
||||
\param x A 16 bit unsigned angle, in 360/65536 degree steps.
|
||||
\return cos(x)*32767. */
|
||||
SPAN_DECLARE(int16_t) fixed_cos(uint16_t x);
|
||||
|
||||
/*! Evaluate an approximate 16 bit fixed point sine.
|
||||
\brief Evaluate an approximate 16 bit fixed point sine.
|
||||
\param y .
|
||||
\param x .
|
||||
\return The 16 bit unsigned angle, in 360/65536 degree steps. */
|
||||
SPAN_DECLARE(uint16_t) fixed_atan2(int16_t y, int16_t x);
|
||||
|
||||
#if defined(__cplusplus)
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
||||
/*- End of file ------------------------------------------------------------*/
|
||||
@@ -39,7 +39,7 @@ struct fsk_tx_state_s
|
||||
void *get_bit_user_data;
|
||||
|
||||
/*! \brief The callback function used to report modem status changes. */
|
||||
modem_tx_status_func_t status_handler;
|
||||
modem_status_func_t status_handler;
|
||||
/*! \brief A user specified opaque pointer passed to the status function. */
|
||||
void *status_user_data;
|
||||
|
||||
@@ -66,7 +66,7 @@ struct fsk_rx_state_s
|
||||
void *put_bit_user_data;
|
||||
|
||||
/*! \brief The callback function used to report modem status changes. */
|
||||
modem_tx_status_func_t status_handler;
|
||||
modem_status_func_t status_handler;
|
||||
/*! \brief A user specified opaque pointer passed to the status function. */
|
||||
void *status_user_data;
|
||||
|
||||
|
||||
@@ -40,7 +40,7 @@ struct hdlc_rx_state_s
|
||||
/*! \brief An opaque parameter passed to the frame callback routine. */
|
||||
void *frame_user_data;
|
||||
/*! \brief The callback routine called to report status changes. */
|
||||
modem_rx_status_func_t status_handler;
|
||||
modem_status_func_t status_handler;
|
||||
/*! \brief An opaque parameter passed to the status callback routine. */
|
||||
void *status_user_data;
|
||||
/*! \brief TRUE if bad frames are to be reported. */
|
||||
|
||||
@@ -29,7 +29,7 @@
|
||||
struct silence_gen_state_s
|
||||
{
|
||||
/*! \brief The callback function used to report status changes. */
|
||||
modem_tx_status_func_t status_handler;
|
||||
modem_status_func_t status_handler;
|
||||
/*! \brief A user specified opaque pointer passed to the status function. */
|
||||
void *status_user_data;
|
||||
|
||||
|
||||
@@ -66,7 +66,7 @@
|
||||
#define T30_DCS_BIT_200_200 15
|
||||
|
||||
#define T30_DIS_BIT_2D_CAPABLE 16
|
||||
#define T30_DCS_BIT_2D_CODING 16
|
||||
#define T30_DCS_BIT_2D_MODE 16
|
||||
|
||||
/* Standard facsimile terminals conforming to ITU-T Rec. T.4 must have the following capability:
|
||||
Paper length = 297 mm. */
|
||||
@@ -101,7 +101,7 @@
|
||||
#define T30_DIS_BIT_POLLED_SUBADDRESSING_CAPABLE 35
|
||||
|
||||
#define T30_DIS_BIT_T43_CAPABLE 36
|
||||
#define T30_DCS_BIT_T43_CODING 36
|
||||
#define T30_DCS_BIT_T43_MODE 36
|
||||
|
||||
#define T30_DIS_BIT_PLANE_INTERLEAVE_CAPABLE 37
|
||||
#define T30_DCS_BIT_PLANE_INTERLEAVE 37
|
||||
@@ -270,11 +270,11 @@
|
||||
bits 49, 102 and 50 in DCS or bits 47, 101, 50 and 35 in DTC shall be set to "1" with the following
|
||||
meaning:
|
||||
Bit DIS DTC DCS
|
||||
35 Polled SubAddress capability Polled SubAddress transmission Not allowed – set to "0"
|
||||
47 Selective polling capability Selective polling transmission Not allowed – set to "0"
|
||||
35 Polled SubAddress capability Polled SubAddress transmission Not allowed - set to "0"
|
||||
47 Selective polling capability Selective polling transmission Not allowed - set to "0"
|
||||
49 Subaddressing capability Not allowed (Set to "0") Subaddressing transmission
|
||||
50 Password Password transmission Sender Identification transmission
|
||||
101 Internet Selective Polling Address capability Internet Selective Polling Address transmission Not allowed – set to "0"
|
||||
101 Internet Selective Polling Address capability Internet Selective Polling Address transmission Not allowed - set to "0"
|
||||
102 Internet Routing Address capability Not allowed (Set to "0") Internet Routing Address transmission
|
||||
|
||||
Terminals conforming to the 1993 version of T.30 may set the above bits to "0" even though PWD/SEP/SUB
|
||||
|
||||
@@ -42,6 +42,10 @@ struct t4_state_s
|
||||
/*! \brief The time at which handling of the current page began. */
|
||||
time_t page_start_time;
|
||||
|
||||
/*! \brief TRUE for FAX page headers to overlay (i.e. replace) the beginning of the
|
||||
page image. FALSE for FAX page headers to add to the overall length of
|
||||
the page. */
|
||||
int header_overlays_image;
|
||||
/*! \brief The text which will be used in FAX page header. No text results
|
||||
in no header line. */
|
||||
const char *header_info;
|
||||
|
||||
@@ -61,7 +61,7 @@ struct v17_rx_state_s
|
||||
void *put_bit_user_data;
|
||||
|
||||
/*! \brief The callback function used to report modem status changes. */
|
||||
modem_rx_status_func_t status_handler;
|
||||
modem_status_func_t status_handler;
|
||||
/*! \brief A user specified opaque pointer passed to the status function. */
|
||||
void *status_user_data;
|
||||
|
||||
@@ -86,7 +86,7 @@ struct v17_rx_state_s
|
||||
/*! \brief The register for the data scrambler. */
|
||||
uint32_t scramble_reg;
|
||||
/*! \brief Scrambler tap */
|
||||
//int scrambler_tap;
|
||||
int scrambler_tap;
|
||||
|
||||
/*! \brief TRUE if the short training sequence is to be used. */
|
||||
int short_train;
|
||||
|
||||
@@ -45,7 +45,7 @@ struct v17_tx_state_s
|
||||
void *get_bit_user_data;
|
||||
|
||||
/*! \brief The callback function used to report modem status changes. */
|
||||
modem_tx_status_func_t status_handler;
|
||||
modem_status_func_t status_handler;
|
||||
/*! \brief A user specified opaque pointer passed to the status function. */
|
||||
void *status_user_data;
|
||||
|
||||
@@ -58,9 +58,13 @@ struct v17_tx_state_s
|
||||
|
||||
/*! \brief The route raised cosine (RRC) pulse shaping filter buffer. */
|
||||
#if defined(SPANDSP_USE_FIXED_POINT)
|
||||
complexi16_t rrc_filter[2*V17_TX_FILTER_STEPS];
|
||||
/*! \brief The root raised cosine (RRC) pulse shaping filter buffer. */
|
||||
int16_t rrc_filter_re[V17_TX_FILTER_STEPS];
|
||||
int16_t rrc_filter_im[V17_TX_FILTER_STEPS];
|
||||
#else
|
||||
complexf_t rrc_filter[2*V17_TX_FILTER_STEPS];
|
||||
/*! \brief The root raised cosine (RRC) pulse shaping filter buffer. */
|
||||
float rrc_filter_re[V17_TX_FILTER_STEPS];
|
||||
float rrc_filter_im[V17_TX_FILTER_STEPS];
|
||||
#endif
|
||||
/*! \brief Current offset into the RRC pulse shaping filter buffer. */
|
||||
int rrc_filter_step;
|
||||
@@ -75,7 +79,7 @@ struct v17_tx_state_s
|
||||
/*! \brief The register for the data scrambler. */
|
||||
uint32_t scramble_reg;
|
||||
/*! \brief Scrambler tap */
|
||||
//int scrambler_tap;
|
||||
int scrambler_tap;
|
||||
/*! \brief TRUE if transmitting the training sequence. FALSE if transmitting user data. */
|
||||
int in_training;
|
||||
/*! \brief TRUE if the short training sequence is to be used. */
|
||||
|
||||
@@ -84,7 +84,7 @@ struct v22bis_state_s
|
||||
/*! \brief A user specified opaque pointer passed to the put_bit callback routine. */
|
||||
void *put_bit_user_data;
|
||||
/*! \brief The callback function used to report modem status changes. */
|
||||
modem_rx_status_func_t status_handler;
|
||||
modem_status_func_t status_handler;
|
||||
/*! \brief A user specified opaque pointer passed to the status function. */
|
||||
void *status_user_data;
|
||||
|
||||
|
||||
@@ -58,7 +58,7 @@ struct v27ter_rx_state_s
|
||||
void *put_bit_user_data;
|
||||
|
||||
/*! \brief The callback function used to report modem status changes. */
|
||||
modem_rx_status_func_t status_handler;
|
||||
modem_status_func_t status_handler;
|
||||
/*! \brief A user specified opaque pointer passed to the status function. */
|
||||
void *status_user_data;
|
||||
|
||||
|
||||
@@ -43,7 +43,7 @@ struct v27ter_tx_state_s
|
||||
void *get_bit_user_data;
|
||||
|
||||
/*! \brief The callback function used to report modem status changes. */
|
||||
modem_tx_status_func_t status_handler;
|
||||
modem_status_func_t status_handler;
|
||||
/*! \brief A user specified opaque pointer passed to the status function. */
|
||||
void *status_user_data;
|
||||
|
||||
|
||||
@@ -50,7 +50,7 @@ struct v29_rx_state_s
|
||||
void *put_bit_user_data;
|
||||
|
||||
/*! \brief The callback function used to report modem status changes. */
|
||||
modem_rx_status_func_t status_handler;
|
||||
modem_status_func_t status_handler;
|
||||
/*! \brief A user specified opaque pointer passed to the status function. */
|
||||
void *status_user_data;
|
||||
|
||||
|
||||
@@ -43,7 +43,7 @@ struct v29_tx_state_s
|
||||
void *get_bit_user_data;
|
||||
|
||||
/*! \brief The callback function used to report modem status changes. */
|
||||
modem_tx_status_func_t status_handler;
|
||||
modem_status_func_t status_handler;
|
||||
/*! \brief A user specified opaque pointer passed to the status function. */
|
||||
void *status_user_data;
|
||||
|
||||
@@ -68,7 +68,7 @@ struct v29_tx_state_s
|
||||
int rrc_filter_step;
|
||||
|
||||
/*! \brief The register for the data scrambler. */
|
||||
unsigned int scramble_reg;
|
||||
uint32_t scramble_reg;
|
||||
/*! \brief The register for the training scrambler. */
|
||||
uint8_t training_scramble_reg;
|
||||
/*! \brief TRUE if transmitting the training sequence, or shutting down transmission.
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
*
|
||||
* Written by Steve Underwood <steveu@coppice.org>
|
||||
*
|
||||
* Copyright (C) 2003 Steve Underwood
|
||||
* Copyright (C) 2003, 2011 Steve Underwood
|
||||
*
|
||||
* All rights reserved.
|
||||
*
|
||||
@@ -26,75 +26,94 @@
|
||||
#if !defined(_SPANDSP_PRIVATE_V42_H_)
|
||||
#define _SPANDSP_PRIVATE_V42_H_
|
||||
|
||||
/*! Max retries (9.2.2) */
|
||||
#define V42_DEFAULT_N_400 5
|
||||
/*! Default for max octets in an information field (9.2.3) */
|
||||
#define V42_DEFAULT_N_401 128
|
||||
/*! Maximum supported value for max octets in an information field */
|
||||
#define V42_MAX_N_401 128
|
||||
/*! Default window size (k) (9.2.4) */
|
||||
#define V42_DEFAULT_WINDOW_SIZE_K 15
|
||||
/*! Maximum supported window size (k) */
|
||||
#define V42_MAX_WINDOW_SIZE_K 15
|
||||
|
||||
/*! The number of info frames to allocate */
|
||||
#define V42_INFO_FRAMES (V42_MAX_WINDOW_SIZE_K + 1)
|
||||
/*! The number of control frames to allocate */
|
||||
#define V42_CTRL_FRAMES 8
|
||||
|
||||
typedef struct
|
||||
{
|
||||
/* V.42 LAP.M parameters */
|
||||
uint8_t v42_tx_window_size_k;
|
||||
uint8_t v42_rx_window_size_k;
|
||||
uint16_t v42_tx_n401;
|
||||
uint16_t v42_rx_n401;
|
||||
|
||||
/* V.42bis compressor parameters */
|
||||
uint8_t comp;
|
||||
int comp_dict_size;
|
||||
int comp_max_string;
|
||||
} v42_config_parameters_t;
|
||||
|
||||
typedef struct frame_s
|
||||
{
|
||||
int len;
|
||||
uint8_t buf[4 + V42_MAX_N_401];
|
||||
} v42_frame_t;
|
||||
|
||||
/*!
|
||||
LAP-M descriptor. This defines the working state for a single instance of LAP-M.
|
||||
*/
|
||||
struct lapm_state_s
|
||||
typedef struct
|
||||
{
|
||||
int handle;
|
||||
get_msg_func_t iframe_get;
|
||||
void *iframe_get_user_data;
|
||||
|
||||
put_msg_func_t iframe_put;
|
||||
void *iframe_put_user_data;
|
||||
|
||||
modem_status_func_t status_handler;
|
||||
void *status_user_data;
|
||||
|
||||
hdlc_rx_state_t hdlc_rx;
|
||||
hdlc_tx_state_t hdlc_tx;
|
||||
|
||||
v42_frame_handler_t iframe_receive;
|
||||
void *iframe_receive_user_data;
|
||||
|
||||
v42_status_func_t status_callback;
|
||||
void *status_callback_user_data;
|
||||
/*! Negotiated values for the window and maximum info sizes */
|
||||
uint8_t tx_window_size_k;
|
||||
uint8_t rx_window_size_k;
|
||||
uint16_t tx_n401;
|
||||
uint16_t rx_n401;
|
||||
|
||||
uint8_t cmd_addr;
|
||||
uint8_t rsp_addr;
|
||||
uint8_t vs;
|
||||
uint8_t va;
|
||||
uint8_t vr;
|
||||
int state;
|
||||
int tx_waiting;
|
||||
int debug;
|
||||
/*! TRUE if originator. FALSE if answerer */
|
||||
int we_are_originator;
|
||||
/*! Remote network type (unknown, answerer. originator) */
|
||||
int peer_is_originator;
|
||||
/*! Next N(S) for transmission */
|
||||
int next_tx_frame;
|
||||
/*! The last of our frames which the peer acknowledged */
|
||||
int last_frame_peer_acknowledged;
|
||||
/*! Next N(R) for reception */
|
||||
int next_expected_frame;
|
||||
/*! The last of the peer's frames which we acknowledged */
|
||||
int last_frame_we_acknowledged;
|
||||
/*! TRUE if we sent an I or S frame with the F-bit set */
|
||||
int solicit_f_bit;
|
||||
/*! Retransmission count */
|
||||
int retransmissions;
|
||||
/*! TRUE if peer is busy */
|
||||
int busy;
|
||||
int configuring;
|
||||
int local_busy;
|
||||
int far_busy;
|
||||
int rejected;
|
||||
int retry_count;
|
||||
|
||||
/*! Acknowledgement timer */
|
||||
int t401_timer;
|
||||
/*! Reply delay timer - optional */
|
||||
int t402_timer;
|
||||
/*! Inactivity timer - optional */
|
||||
int t403_timer;
|
||||
/*! Maximum number of octets in an information field */
|
||||
int n401;
|
||||
/*! Window size */
|
||||
int window_size_k;
|
||||
|
||||
lapm_frame_queue_t *txqueue;
|
||||
lapm_frame_queue_t *tx_next;
|
||||
lapm_frame_queue_t *tx_last;
|
||||
queue_state_t *tx_queue;
|
||||
|
||||
span_sched_state_t sched;
|
||||
/*! \brief Error and flow logging control */
|
||||
logging_state_t logging;
|
||||
};
|
||||
/* The control frame buffer, and its pointers */
|
||||
int ctrl_put;
|
||||
int ctrl_get;
|
||||
v42_frame_t ctrl_buf[V42_CTRL_FRAMES];
|
||||
|
||||
/*!
|
||||
V.42 descriptor. This defines the working state for a single instance of V.42.
|
||||
*/
|
||||
struct v42_state_s
|
||||
/* The info frame buffer, and its pointers */
|
||||
int info_put;
|
||||
int info_get;
|
||||
int info_acked;
|
||||
v42_frame_t info_buf[V42_INFO_FRAMES];
|
||||
|
||||
void (*packer_process)(v42_state_t *m, int bits);
|
||||
} lapm_state_t;
|
||||
|
||||
/*! V.42 support negotiation parameters */
|
||||
typedef struct
|
||||
{
|
||||
/*! TRUE if we are the calling party, otherwise FALSE */
|
||||
int calling_party;
|
||||
/*! TRUE if we should detect whether the far end is V.42 capable. FALSE if we go
|
||||
directly to protocol establishment */
|
||||
int detect;
|
||||
|
||||
/*! Stage in negotiating V.42 support */
|
||||
int rx_negotiation_step;
|
||||
int rxbits;
|
||||
@@ -104,11 +123,30 @@ struct v42_state_s
|
||||
int txbits;
|
||||
int txstream;
|
||||
int txadps;
|
||||
/*! The LAP.M context */
|
||||
} v42_negotiation_t;
|
||||
|
||||
/*!
|
||||
V.42 descriptor. This defines the working state for a single
|
||||
instance of a V.42 error corrector.
|
||||
*/
|
||||
struct v42_state_s
|
||||
{
|
||||
/*! TRUE if we are the calling party, otherwise FALSE. */
|
||||
int calling_party;
|
||||
/*! TRUE if we should detect whether the far end is V.42 capable. FALSE if we go
|
||||
directly to protocol establishment. */
|
||||
int detect;
|
||||
|
||||
/*! The bit rate, used to time events */
|
||||
int tx_bit_rate;
|
||||
|
||||
v42_config_parameters_t config;
|
||||
v42_negotiation_t neg;
|
||||
lapm_state_t lapm;
|
||||
|
||||
/*! V.42 support detection timer */
|
||||
int t400_timer;
|
||||
int bit_timer;
|
||||
void (*bit_timer_func)(v42_state_t *m);
|
||||
|
||||
/*! \brief Error and flow logging control */
|
||||
logging_state_t logging;
|
||||
};
|
||||
|
||||
@@ -28,100 +28,85 @@
|
||||
|
||||
/*!
|
||||
V.42bis dictionary node.
|
||||
Note that 0 is not a valid node to point to (0 is always a control code), so 0 is used
|
||||
as a "no such value" marker in this structure.
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
/*! \brief The prior code for each defined code. */
|
||||
uint16_t parent_code;
|
||||
/*! \brief The number of leaf nodes this node has */
|
||||
int16_t leaves;
|
||||
/*! \brief This leaf octet for each defined code. */
|
||||
/*! \brief The value of the octet represented by the current dictionary node */
|
||||
uint8_t node_octet;
|
||||
/*! \brief Bit map of the children which exist */
|
||||
uint32_t children[8];
|
||||
/*! \brief The parent of this node */
|
||||
uint16_t parent;
|
||||
/*! \brief The first child of this node */
|
||||
uint16_t child;
|
||||
/*! \brief The next node at the same depth */
|
||||
uint16_t next;
|
||||
} v42bis_dict_node_t;
|
||||
|
||||
/*!
|
||||
V.42bis compression. This defines the working state for a single instance
|
||||
of V.42bis compression.
|
||||
V.42bis compression or decompression. This defines the working state for a single instance
|
||||
of V.42bis compression or decompression.
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
/*! \brief Compression enabled. */
|
||||
int v42bis_parm_p0;
|
||||
/*! \brief Compression mode. */
|
||||
int compression_mode;
|
||||
/*! \brief Callback function to handle received frames. */
|
||||
v42bis_frame_handler_t handler;
|
||||
/*! \brief An opaque pointer passed in calls to frame_handler. */
|
||||
/*! \brief Callback function to handle output data. */
|
||||
put_msg_func_t handler;
|
||||
/*! \brief An opaque pointer passed in calls to the data handler. */
|
||||
void *user_data;
|
||||
/*! \brief The maximum frame length allowed */
|
||||
int max_len;
|
||||
/*! \brief The maximum amount to be passed to the data handler. */
|
||||
int max_output_len;
|
||||
|
||||
uint32_t string_code;
|
||||
uint32_t latest_code;
|
||||
/*! \brief TRUE if we are in transparent (i.e. uncompressable) mode */
|
||||
int transparent;
|
||||
/*! \brief Next empty dictionary entry */
|
||||
uint16_t v42bis_parm_c1;
|
||||
/*! \brief Current codeword size */
|
||||
uint16_t v42bis_parm_c2;
|
||||
/*! \brief Threshold for codeword size change */
|
||||
uint16_t v42bis_parm_c3;
|
||||
/*! \brief The current update point in the dictionary */
|
||||
uint16_t update_at;
|
||||
/*! \brief The last entry matched in the dictionary */
|
||||
uint16_t last_matched;
|
||||
/*! \brief The last entry added to the dictionary */
|
||||
uint16_t last_added;
|
||||
/*! \brief Total number of codewords in the dictionary */
|
||||
int v42bis_parm_n2;
|
||||
/*! \brief Maximum permitted string length */
|
||||
int v42bis_parm_n7;
|
||||
/*! \brief The dictionary */
|
||||
v42bis_dict_node_t dict[V42BIS_MAX_CODEWORDS];
|
||||
|
||||
/*! \brief The octet string in progress */
|
||||
uint8_t string[V42BIS_MAX_STRING_SIZE];
|
||||
/*! \brief The current length of the octet string in progress */
|
||||
int string_length;
|
||||
uint32_t output_bit_buffer;
|
||||
int output_bit_count;
|
||||
/*! \brief The amount of the octet string in progress which has already
|
||||
been flushed out of the buffer */
|
||||
int flushed_length;
|
||||
|
||||
/*! \brief Compression performance metric */
|
||||
uint16_t compression_performance;
|
||||
|
||||
/*! \brief Outgoing bit buffer (compression), or incoming bit buffer (decompression) */
|
||||
uint32_t bit_buffer;
|
||||
/*! \brief Outgoing bit count (compression), or incoming bit count (decompression) */
|
||||
int bit_count;
|
||||
|
||||
/*! \brief The output composition buffer */
|
||||
uint8_t output_buf[V42BIS_MAX_OUTPUT_LENGTH];
|
||||
/*! \brief The length of the contents of the output composition buffer */
|
||||
int output_octet_count;
|
||||
uint8_t output_buf[1024];
|
||||
v42bis_dict_node_t dict[V42BIS_MAX_CODEWORDS];
|
||||
/*! \brief TRUE if we are in transparent (i.e. uncompressable) mode */
|
||||
int transparent;
|
||||
int change_transparency;
|
||||
/*! \brief IIR filter state, used in assessing compressibility. */
|
||||
int compressibility_filter;
|
||||
int compressibility_persistence;
|
||||
|
||||
/*! \brief Next empty dictionary entry */
|
||||
uint32_t v42bis_parm_c1;
|
||||
/*! \brief Current codeword size */
|
||||
int v42bis_parm_c2;
|
||||
/*! \brief Threshold for codeword size change */
|
||||
uint32_t v42bis_parm_c3;
|
||||
|
||||
/*! \brief Mark that this is the first octet/code to be processed */
|
||||
int first;
|
||||
uint8_t escape_code;
|
||||
} v42bis_compress_state_t;
|
||||
|
||||
/*!
|
||||
V.42bis decompression. This defines the working state for a single instance
|
||||
of V.42bis decompression.
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
/*! \brief Callback function to handle decompressed data. */
|
||||
v42bis_data_handler_t handler;
|
||||
/*! \brief An opaque pointer passed in calls to data_handler. */
|
||||
void *user_data;
|
||||
/*! \brief The maximum decompressed data block length allowed */
|
||||
int max_len;
|
||||
|
||||
uint32_t old_code;
|
||||
uint32_t last_old_code;
|
||||
uint32_t input_bit_buffer;
|
||||
int input_bit_count;
|
||||
int octet;
|
||||
int last_length;
|
||||
int output_octet_count;
|
||||
uint8_t output_buf[1024];
|
||||
v42bis_dict_node_t dict[V42BIS_MAX_CODEWORDS];
|
||||
/*! \brief TRUE if we are in transparent (i.e. uncompressable) mode */
|
||||
int transparent;
|
||||
|
||||
int last_extra_octet;
|
||||
|
||||
/*! \brief Next empty dictionary entry */
|
||||
uint32_t v42bis_parm_c1;
|
||||
/*! \brief Current codeword size */
|
||||
int v42bis_parm_c2;
|
||||
/*! \brief Threshold for codeword size change */
|
||||
uint32_t v42bis_parm_c3;
|
||||
|
||||
/*! \brief Mark that this is the first octet/code to be processed */
|
||||
int first;
|
||||
/*! \brief The current value of the escape code */
|
||||
uint8_t escape_code;
|
||||
/*! \brief TRUE if we just hit an escape code, and are waiting for the following octet */
|
||||
int escaped;
|
||||
} v42bis_decompress_state_t;
|
||||
} v42bis_comp_state_t;
|
||||
|
||||
/*!
|
||||
V.42bis compression/decompression descriptor. This defines the working state for a
|
||||
@@ -129,20 +114,13 @@ typedef struct
|
||||
*/
|
||||
struct v42bis_state_s
|
||||
{
|
||||
/*! \brief V.42bis data compression directions. */
|
||||
int v42bis_parm_p0;
|
||||
|
||||
/*! \brief Compression state. */
|
||||
v42bis_compress_state_t compress;
|
||||
v42bis_comp_state_t compress;
|
||||
/*! \brief Decompression state. */
|
||||
v42bis_decompress_state_t decompress;
|
||||
|
||||
/*! \brief Maximum codeword size (bits) */
|
||||
int v42bis_parm_n1;
|
||||
/*! \brief Total number of codewords */
|
||||
uint32_t v42bis_parm_n2;
|
||||
/*! \brief Maximum string length */
|
||||
int v42bis_parm_n7;
|
||||
v42bis_comp_state_t decompress;
|
||||
|
||||
/*! \brief Error and flow logging control */
|
||||
logging_state_t logging;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
@@ -84,7 +84,7 @@ SPAN_DECLARE(int) silence_gen_generated(silence_gen_state_t *s);
|
||||
\param s The silence generator context.
|
||||
\param handler The callback routine used to report status changes.
|
||||
\param user_data An opaque pointer. */
|
||||
SPAN_DECLARE(void) silence_gen_status_handler(silence_gen_state_t *s, modem_tx_status_func_t handler, void *user_data);
|
||||
SPAN_DECLARE(void) silence_gen_status_handler(silence_gen_state_t *s, modem_status_func_t handler, void *user_data);
|
||||
|
||||
/*! Initialise a timed silence generator context.
|
||||
\brief Initialise a timed silence generator context.
|
||||
|
||||
@@ -261,7 +261,7 @@ enum
|
||||
T30_ERR_RX_GOTDCS, /*! DCS received while waiting for DTC */
|
||||
T30_ERR_RX_INVALCMD, /*! Unexpected command after page received */
|
||||
T30_ERR_RX_NOCARRIER, /*! Carrier lost during fax receive */
|
||||
T30_ERR_RX_NOEOL, /*! Timed out while waiting for EOL (end Of line) */
|
||||
T30_ERR_RX_NOEOL, /*! Timed out while waiting for EOL (end of line) */
|
||||
T30_ERR_RX_NOFAX, /*! Timed out while waiting for first line */
|
||||
T30_ERR_RX_T2EXPDCN, /*! Timer T2 expired while waiting for DCN */
|
||||
T30_ERR_RX_T2EXPD, /*! Timer T2 expired while waiting for phase D */
|
||||
@@ -547,12 +547,10 @@ typedef struct
|
||||
int error_correcting_mode_retries;
|
||||
/*! \brief Current status. */
|
||||
int current_status;
|
||||
#if 0
|
||||
/*! \brief The number of RTP events in this call. */
|
||||
int rtp_events;
|
||||
/*! \brief The number of RTN events in this call. */
|
||||
int rtn_events;
|
||||
#endif
|
||||
} t30_stats_t;
|
||||
|
||||
#if defined(__cplusplus)
|
||||
|
||||
@@ -144,6 +144,12 @@ SPAN_DECLARE(void) t4_tx_set_header_info(t4_state_t *s, const char *info);
|
||||
\param info A POSIX timezone description string. */
|
||||
SPAN_DECLARE(void) t4_tx_set_header_tz(t4_state_t *s, const char *tzstring);
|
||||
|
||||
/*! Set page header extends or overlays the image mode.
|
||||
\brief Set page header overlay mode.
|
||||
\param s The T.4 context.
|
||||
\param header_overlays_image TRUE for overlay, or FALSE for extend the page. */
|
||||
SPAN_DECLARE(void) t4_tx_set_header_overlays_image(t4_state_t *s, int header_overlays_image);
|
||||
|
||||
/*! \brief Set the row read handler for a T.4 transmit context.
|
||||
\param s The T.4 transmit context.
|
||||
\param handler A pointer to the handler routine.
|
||||
|
||||
@@ -77,6 +77,27 @@ typedef int (span_tx_handler_t)(void *s, int16_t amp[], int max_len);
|
||||
#define TRUE (!FALSE)
|
||||
#endif
|
||||
|
||||
/* Fixed point constant macros */
|
||||
#define FP_Q_9_7(x) ((int16_t) (128.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
#define FP_Q_8_8(x) ((int16_t) (256.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
#define FP_Q_7_9(x) ((int16_t) (512.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
#define FP_Q_6_10(x) ((int16_t) (1024.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
#define FP_Q_5_11(x) ((int16_t) (2048.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
#define FP_Q_4_12(x) ((int16_t) (4096.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
#define FP_Q_3_13(x) ((int16_t) (8192.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
#define FP_Q_2_14(x) ((int16_t) (16384.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
#define FP_Q_1_15(x) ((int16_t) (32768.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
|
||||
#define FP_Q_9_23(x) ((int32_t) (65536.0*128.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
#define FP_Q_8_24(x) ((int32_t) (65536.0*256.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
#define FP_Q_7_25(x) ((int32_t) (65536.0*512.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
#define FP_Q_6_26(x) ((int32_t) (65536.0*1024.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
#define FP_Q_5_27(x) ((int32_t) (65536.0*2048.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
#define FP_Q_4_28(x) ((int32_t) (65536.0*4096.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
#define FP_Q_3_29(x) ((int32_t) (65536.0*8192.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
#define FP_Q_2_30(x) ((int32_t) (65536.0*16384.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
#define FP_Q_1_31(x) ((int32_t) (65536.0*32768.0*x + ((x >= 0.0) ? 0.5 : -0.5)))
|
||||
|
||||
#if defined(__cplusplus)
|
||||
/* C++ doesn't seem to have sane rounding functions/macros yet */
|
||||
#if !defined(WIN32)
|
||||
|
||||
@@ -267,7 +267,7 @@ SPAN_DECLARE(void) v17_rx_set_put_bit(v17_rx_state_t *s, put_bit_func_t put_bit,
|
||||
\param s The modem context.
|
||||
\param handler The callback routine used to report modem status changes.
|
||||
\param user_data An opaque pointer. */
|
||||
SPAN_DECLARE(void) v17_rx_set_modem_status_handler(v17_rx_state_t *s, modem_rx_status_func_t handler, void *user_data);
|
||||
SPAN_DECLARE(void) v17_rx_set_modem_status_handler(v17_rx_state_t *s, modem_status_func_t handler, void *user_data);
|
||||
|
||||
/*! Process a block of received V.17 modem audio samples.
|
||||
\brief Process a block of received V.17 modem audio samples.
|
||||
|
||||
@@ -146,7 +146,7 @@ SPAN_DECLARE(void) v17_tx_set_get_bit(v17_tx_state_t *s, get_bit_func_t get_bit,
|
||||
\param s The modem context.
|
||||
\param handler The callback routine used to report modem status changes.
|
||||
\param user_data An opaque pointer. */
|
||||
SPAN_DECLARE(void) v17_tx_set_modem_status_handler(v17_tx_state_t *s, modem_tx_status_func_t handler, void *user_data);
|
||||
SPAN_DECLARE(void) v17_tx_set_modem_status_handler(v17_tx_state_t *s, modem_status_func_t handler, void *user_data);
|
||||
|
||||
/*! Generate a block of V.17 modem audio samples.
|
||||
\brief Generate a block of V.17 modem audio samples.
|
||||
|
||||
@@ -213,7 +213,7 @@ SPAN_DECLARE(void) v22bis_set_put_bit(v22bis_state_t *s, put_bit_func_t put_bit,
|
||||
\param s The modem context.
|
||||
\param handler The callback routine used to report modem status changes.
|
||||
\param user_data An opaque pointer. */
|
||||
SPAN_DECLARE(void) v22bis_set_modem_status_handler(v22bis_state_t *s, modem_rx_status_func_t handler, void *user_data);
|
||||
SPAN_DECLARE(void) v22bis_set_modem_status_handler(v22bis_state_t *s, modem_status_func_t handler, void *user_data);
|
||||
|
||||
#if defined(__cplusplus)
|
||||
}
|
||||
|
||||
@@ -102,7 +102,7 @@ SPAN_DECLARE(void) v27ter_rx_set_put_bit(v27ter_rx_state_t *s, put_bit_func_t pu
|
||||
\param s The modem context.
|
||||
\param handler The callback routine used to report modem status changes.
|
||||
\param user_data An opaque pointer. */
|
||||
SPAN_DECLARE(void) v27ter_rx_set_modem_status_handler(v27ter_rx_state_t *s, modem_rx_status_func_t handler, void *user_data);
|
||||
SPAN_DECLARE(void) v27ter_rx_set_modem_status_handler(v27ter_rx_state_t *s, modem_status_func_t handler, void *user_data);
|
||||
|
||||
/*! Process a block of received V.27ter modem audio samples.
|
||||
\brief Process a block of received V.27ter modem audio samples.
|
||||
|
||||
@@ -127,7 +127,7 @@ SPAN_DECLARE(void) v27ter_tx_set_get_bit(v27ter_tx_state_t *s, get_bit_func_t ge
|
||||
\param s The modem context.
|
||||
\param handler The callback routine used to report modem status changes.
|
||||
\param user_data An opaque pointer. */
|
||||
SPAN_DECLARE(void) v27ter_tx_set_modem_status_handler(v27ter_tx_state_t *s, modem_tx_status_func_t handler, void *user_data);
|
||||
SPAN_DECLARE(void) v27ter_tx_set_modem_status_handler(v27ter_tx_state_t *s, modem_status_func_t handler, void *user_data);
|
||||
|
||||
/*! Generate a block of V.27ter modem audio samples.
|
||||
\brief Generate a block of V.27ter modem audio samples.
|
||||
|
||||
@@ -178,7 +178,7 @@ SPAN_DECLARE(void) v29_rx_set_put_bit(v29_rx_state_t *s, put_bit_func_t put_bit,
|
||||
\param s The modem context.
|
||||
\param handler The callback routine used to report modem status changes.
|
||||
\param user_data An opaque pointer. */
|
||||
SPAN_DECLARE(void) v29_rx_set_modem_status_handler(v29_rx_state_t *s, modem_rx_status_func_t handler, void *user_data);
|
||||
SPAN_DECLARE(void) v29_rx_set_modem_status_handler(v29_rx_state_t *s, modem_status_func_t handler, void *user_data);
|
||||
|
||||
/*! Process a block of received V.29 modem audio samples.
|
||||
\brief Process a block of received V.29 modem audio samples.
|
||||
|
||||
@@ -158,7 +158,7 @@ SPAN_DECLARE(void) v29_tx_set_get_bit(v29_tx_state_t *s, get_bit_func_t get_bit,
|
||||
\param s The modem context.
|
||||
\param handler The callback routine used to report modem status changes.
|
||||
\param user_data An opaque pointer. */
|
||||
SPAN_DECLARE(void) v29_tx_set_modem_status_handler(v29_tx_state_t *s, modem_tx_status_func_t handler, void *user_data);
|
||||
SPAN_DECLARE(void) v29_tx_set_modem_status_handler(v29_tx_state_t *s, modem_status_func_t handler, void *user_data);
|
||||
|
||||
/*! Generate a block of V.29 modem audio samples.
|
||||
\brief Generate a block of V.29 modem audio samples.
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
*
|
||||
* Written by Steve Underwood <steveu@coppice.org>
|
||||
*
|
||||
* Copyright (C) 2003 Steve Underwood
|
||||
* Copyright (C) 2003, 2011 Steve Underwood
|
||||
*
|
||||
* All rights reserved.
|
||||
*
|
||||
@@ -36,45 +36,8 @@ far modem supports V.42 is also defined.
|
||||
#if !defined(_SPANDSP_V42_H_)
|
||||
#define _SPANDSP_V42_H_
|
||||
|
||||
enum
|
||||
{
|
||||
LAPM_DETECT = 0,
|
||||
LAPM_ESTABLISH = 1,
|
||||
LAPM_DATA = 2,
|
||||
LAPM_RELEASE = 3,
|
||||
LAPM_SIGNAL = 4,
|
||||
LAPM_SETPARM = 5,
|
||||
LAPM_TEST = 6,
|
||||
LAPM_UNSUPPORTED = 7
|
||||
};
|
||||
|
||||
typedef void (*v42_status_func_t)(void *user_data, int status);
|
||||
typedef void (*v42_frame_handler_t)(void *user_data, const uint8_t *pkt, int len);
|
||||
|
||||
typedef struct lapm_frame_queue_s
|
||||
{
|
||||
struct lapm_frame_queue_s *next;
|
||||
int len;
|
||||
uint8_t frame[];
|
||||
} lapm_frame_queue_t;
|
||||
|
||||
/*!
|
||||
LAP-M descriptor. This defines the working state for a single instance of LAP-M.
|
||||
*/
|
||||
typedef struct lapm_state_s lapm_state_t;
|
||||
|
||||
/*!
|
||||
V.42 descriptor. This defines the working state for a single instance of V.42.
|
||||
*/
|
||||
typedef struct v42_state_s v42_state_t;
|
||||
|
||||
/*! Log the raw HDLC frames */
|
||||
#define LAPM_DEBUG_LAPM_RAW (1 << 0)
|
||||
/*! Log the interpreted frames */
|
||||
#define LAPM_DEBUG_LAPM_DUMP (1 << 1)
|
||||
/*! Log state machine changes */
|
||||
#define LAPM_DEBUG_LAPM_STATE (1 << 2)
|
||||
|
||||
#if defined(__cplusplus)
|
||||
extern "C"
|
||||
{
|
||||
@@ -82,58 +45,46 @@ extern "C"
|
||||
|
||||
SPAN_DECLARE(const char *) lapm_status_to_str(int status);
|
||||
|
||||
/*! Dump LAP.M frames in a raw and/or decoded forms
|
||||
\param frame The frame itself
|
||||
\param len The length of the frame, in octets
|
||||
\param showraw TRUE if the raw octets should be dumped
|
||||
\param txrx TRUE if tx, FALSE if rx. Used to highlight the packet's direction.
|
||||
*/
|
||||
SPAN_DECLARE(void) lapm_dump(lapm_state_t *s, const uint8_t *frame, int len, int showraw, int txrx);
|
||||
SPAN_DECLARE_NONSTD(void) lapm_receive(void *user_data, const uint8_t *frame, int len, int ok);
|
||||
|
||||
/*! Accept an HDLC packet
|
||||
*/
|
||||
SPAN_DECLARE_NONSTD(void) lapm_receive(void *user_data, const uint8_t *buf, int len, int ok);
|
||||
SPAN_DECLARE(void) v42_start(v42_state_t *s);
|
||||
|
||||
/*! Transmit a LAP.M frame
|
||||
*/
|
||||
SPAN_DECLARE(int) lapm_tx(lapm_state_t *s, const void *buf, int len);
|
||||
SPAN_DECLARE(void) v42_stop(v42_state_t *s);
|
||||
|
||||
/*! Transmit a LAP.M information frame
|
||||
/*! Set the busy status of the local end of a V.42 context.
|
||||
\param s The V.42 context.
|
||||
\param busy The new local end busy status.
|
||||
\return The previous local end busy status.
|
||||
*/
|
||||
SPAN_DECLARE(int) lapm_tx_iframe(lapm_state_t *s, const void *buf, int len, int cr);
|
||||
SPAN_DECLARE(int) v42_set_local_busy_status(v42_state_t *s, int busy);
|
||||
|
||||
/*! Send a break over a LAP.M connection
|
||||
/*! Get the busy status of the far end of a V.42 context.
|
||||
\param s The V.42 context.
|
||||
\return The far end busy status.
|
||||
*/
|
||||
SPAN_DECLARE(int) lapm_break(lapm_state_t *s, int enable);
|
||||
SPAN_DECLARE(int) v42_get_far_busy_status(v42_state_t *s);
|
||||
|
||||
/*! Initiate an orderly release of a LAP.M connection
|
||||
*/
|
||||
SPAN_DECLARE(int) lapm_release(lapm_state_t *s);
|
||||
|
||||
/*! Enable or disable loopback of a LAP.M connection
|
||||
*/
|
||||
SPAN_DECLARE(int) lapm_loopback(lapm_state_t *s, int enable);
|
||||
|
||||
/*! Assign or remove a callback routine used to deal with V.42 status changes.
|
||||
*/
|
||||
SPAN_DECLARE(void) v42_set_status_callback(v42_state_t *s, v42_status_func_t callback, void *user_data);
|
||||
|
||||
/*! Process a newly received bit for a V.42 context.
|
||||
*/
|
||||
SPAN_DECLARE(void) v42_rx_bit(void *user_data, int bit);
|
||||
|
||||
/*! Get the next transmit bit for a V.42 context.
|
||||
*/
|
||||
SPAN_DECLARE(int) v42_tx_bit(void *user_data);
|
||||
|
||||
SPAN_DECLARE(void) v42_set_status_callback(v42_state_t *s, modem_status_func_t callback, void *user_data);
|
||||
|
||||
/*! Initialise a V.42 context.
|
||||
\param s The V.42 context.
|
||||
\param calling_party TRUE if caller mode, else answerer mode.
|
||||
\param frame_handler A callback function to handle received frames of data.
|
||||
\param user_data An opaque pointer passed to the frame handler routine.
|
||||
\param detect TRUE to perform the V.42 detection, else go straight into LAP.M
|
||||
\param iframe_get A callback function to handle received frames of data.
|
||||
\param iframe_put A callback function to get frames of data for transmission.
|
||||
\param user_data An opaque pointer passed to the frame handler routines.
|
||||
\return ???
|
||||
*/
|
||||
SPAN_DECLARE(v42_state_t *) v42_init(v42_state_t *s, int calling_party, int detect, v42_frame_handler_t frame_handler, void *user_data);
|
||||
SPAN_DECLARE(v42_state_t *) v42_init(v42_state_t *s,
|
||||
int calling_party,
|
||||
int detect,
|
||||
get_msg_func_t iframe_get,
|
||||
put_msg_func_t iframe_put,
|
||||
void *user_data);
|
||||
|
||||
/*! Restart a V.42 context.
|
||||
\param s The V.42 context.
|
||||
@@ -143,12 +94,12 @@ SPAN_DECLARE(void) v42_restart(v42_state_t *s);
|
||||
/*! Release a V.42 context.
|
||||
\param s The V.42 context.
|
||||
\return 0 if OK */
|
||||
SPAN_DECLARE(int) v42_release(v42_state_t *s);
|
||||
SPAN_DECLARE(void) v42_release(v42_state_t *s);
|
||||
|
||||
/*! Free a V.42 context.
|
||||
\param s The V.42 context.
|
||||
\return 0 if OK */
|
||||
SPAN_DECLARE(int) v42_free(v42_state_t *s);
|
||||
SPAN_DECLARE(void) v42_free(v42_state_t *s);
|
||||
|
||||
#if defined(__cplusplus)
|
||||
}
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
*
|
||||
* Written by Steve Underwood <steveu@coppice.org>
|
||||
*
|
||||
* Copyright (C) 2005 Steve Underwood
|
||||
* Copyright (C) 2005, 2011 Steve Underwood
|
||||
*
|
||||
* All rights reserved.
|
||||
*
|
||||
@@ -39,7 +39,7 @@ conjunction with the error correction scheme defined in V.42.
|
||||
#define V42BIS_MIN_DICTIONARY_SIZE 512
|
||||
#define V42BIS_MAX_BITS 12
|
||||
#define V42BIS_MAX_CODEWORDS 4096 /* 2^V42BIS_MAX_BITS */
|
||||
#define V42BIS_TABLE_SIZE 5021 /* This should be a prime >(2^V42BIS_MAX_BITS) */
|
||||
#define V42BIS_MAX_OUTPUT_LENGTH 1024
|
||||
|
||||
enum
|
||||
{
|
||||
@@ -56,9 +56,6 @@ enum
|
||||
V42BIS_COMPRESSION_MODE_NEVER
|
||||
};
|
||||
|
||||
typedef void (*v42bis_frame_handler_t)(void *user_data, const uint8_t *pkt, int len);
|
||||
typedef void (*v42bis_data_handler_t)(void *user_data, const uint8_t *buf, int len);
|
||||
|
||||
/*!
|
||||
V.42bis compression/decompression descriptor. This defines the working state for a
|
||||
single instance of V.42bis compress/decompression.
|
||||
@@ -75,7 +72,7 @@ extern "C"
|
||||
\param buf The data to be compressed.
|
||||
\param len The length of the data buffer.
|
||||
\return 0 */
|
||||
SPAN_DECLARE(int) v42bis_compress(v42bis_state_t *s, const uint8_t *buf, int len);
|
||||
SPAN_DECLARE(int) v42bis_compress(v42bis_state_t *s, const uint8_t buf[], int len);
|
||||
|
||||
/*! Flush out any data remaining in a compression buffer.
|
||||
\param s The V.42bis context.
|
||||
@@ -87,7 +84,7 @@ SPAN_DECLARE(int) v42bis_compress_flush(v42bis_state_t *s);
|
||||
\param buf The data to be decompressed.
|
||||
\param len The length of the data buffer.
|
||||
\return 0 */
|
||||
SPAN_DECLARE(int) v42bis_decompress(v42bis_state_t *s, const uint8_t *buf, int len);
|
||||
SPAN_DECLARE(int) v42bis_decompress(v42bis_state_t *s, const uint8_t buf[], int len);
|
||||
|
||||
/*! Flush out any data remaining in the decompression buffer.
|
||||
\param s The V.42bis context.
|
||||
@@ -107,23 +104,23 @@ SPAN_DECLARE(void) v42bis_compression_control(v42bis_state_t *s, int mode);
|
||||
\param negotiated_p0 The negotiated P0 parameter, from the V.42bis spec.
|
||||
\param negotiated_p1 The negotiated P1 parameter, from the V.42bis spec.
|
||||
\param negotiated_p2 The negotiated P2 parameter, from the V.42bis spec.
|
||||
\param frame_handler Frame callback handler.
|
||||
\param frame_user_data An opaque pointer passed to the frame callback handler.
|
||||
\param max_frame_len The maximum length that should be passed to the frame handler.
|
||||
\param data_handler data callback handler.
|
||||
\param data_user_data An opaque pointer passed to the data callback handler.
|
||||
\param max_data_len The maximum length that should be passed to the data handler.
|
||||
\param encode_handler Encode callback handler.
|
||||
\param encode_user_data An opaque pointer passed to the encode callback handler.
|
||||
\param max_encode_len The maximum length that should be passed to the encode handler.
|
||||
\param decode_handler Decode callback handler.
|
||||
\param decode_user_data An opaque pointer passed to the decode callback handler.
|
||||
\param max_decode_len The maximum length that should be passed to the decode handler.
|
||||
\return The V.42bis context. */
|
||||
SPAN_DECLARE(v42bis_state_t *) v42bis_init(v42bis_state_t *s,
|
||||
int negotiated_p0,
|
||||
int negotiated_p1,
|
||||
int negotiated_p2,
|
||||
v42bis_frame_handler_t frame_handler,
|
||||
void *frame_user_data,
|
||||
int max_frame_len,
|
||||
v42bis_data_handler_t data_handler,
|
||||
void *data_user_data,
|
||||
int max_data_len);
|
||||
put_msg_func_t encode_handler,
|
||||
void *encode_user_data,
|
||||
int max_encode_len,
|
||||
put_msg_func_t decode_handler,
|
||||
void *decode_user_data,
|
||||
int max_decode_len);
|
||||
|
||||
/*! Release a V.42bis context.
|
||||
\param s The V.42bis context.
|
||||
|
||||
+106
-8
@@ -60,10 +60,18 @@
|
||||
#include "spandsp/v27ter_tx.h"
|
||||
#include "spandsp/t4_rx.h"
|
||||
#include "spandsp/t4_tx.h"
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
#if defined(SPANDSP_SUPPORT_T42) || defined(SPANDSP_SUPPORT_T43) | defined(SPANDSP_SUPPORT_T85)
|
||||
#include "spandsp/t81_t82_arith_coding.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
#include "spandsp/t85.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T42)
|
||||
#include "spandsp/t42.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T43)
|
||||
#include "spandsp/t43.h"
|
||||
#endif
|
||||
#include "spandsp/t4_t6_decode.h"
|
||||
#include "spandsp/t4_t6_encode.h"
|
||||
#include "spandsp/t30_fcf.h"
|
||||
@@ -73,10 +81,18 @@
|
||||
#include "spandsp/t30_logging.h"
|
||||
|
||||
#include "spandsp/private/logging.h"
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
#if defined(SPANDSP_SUPPORT_T42) || defined(SPANDSP_SUPPORT_T43) | defined(SPANDSP_SUPPORT_T85)
|
||||
#include "spandsp/private/t81_t82_arith_coding.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
#include "spandsp/private/t85.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T42)
|
||||
#include "spandsp/private/t42.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T43)
|
||||
#include "spandsp/private/t43.h"
|
||||
#endif
|
||||
#include "spandsp/private/t4_t6_decode.h"
|
||||
#include "spandsp/private/t4_t6_encode.h"
|
||||
#include "spandsp/private/t4_rx.h"
|
||||
@@ -387,6 +403,7 @@ static void repeat_last_command(t30_state_t *s);
|
||||
static void disconnect(t30_state_t *s);
|
||||
static void decode_20digit_msg(t30_state_t *s, char *msg, const uint8_t *pkt, int len);
|
||||
static void decode_url_msg(t30_state_t *s, char *msg, const uint8_t *pkt, int len);
|
||||
static int decode_nsf_nss_nsc(t30_state_t *s, uint8_t *msg[], const uint8_t *pkt, int len);
|
||||
static int set_min_scan_time_code(t30_state_t *s);
|
||||
static int send_cfr_sequence(t30_state_t *s, int start);
|
||||
static void timer_t2_start(t30_state_t *s);
|
||||
@@ -1312,6 +1329,19 @@ static int build_dcs(t30_state_t *s)
|
||||
/* Select the compression to use. */
|
||||
switch (s->line_encoding)
|
||||
{
|
||||
#if defined(SPANDSP_SUPPORT_T42)
|
||||
case T4_COMPRESSION_ITU_T42:
|
||||
set_ctrl_bit(s->dcs_frame, T30_DCS_BIT_FULL_COLOUR_MODE);
|
||||
set_ctrl_bits(s->dcs_frame, T30_MIN_SCAN_0MS, 21);
|
||||
break;
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T43)
|
||||
case T4_COMPRESSION_ITU_T43:
|
||||
set_ctrl_bit(s->dcs_frame, T30_DCS_BIT_T43_MODE);
|
||||
set_ctrl_bits(s->dcs_frame, T30_MIN_SCAN_0MS, 21);
|
||||
break;
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
case T4_COMPRESSION_ITU_T85:
|
||||
set_ctrl_bit(s->dcs_frame, T30_DCS_BIT_T85_MODE);
|
||||
clr_ctrl_bit(s->dcs_frame, T30_DCS_BIT_T85_L0_MODE);
|
||||
@@ -1322,12 +1352,13 @@ static int build_dcs(t30_state_t *s)
|
||||
set_ctrl_bit(s->dcs_frame, T30_DCS_BIT_T85_L0_MODE);
|
||||
set_ctrl_bits(s->dcs_frame, T30_MIN_SCAN_0MS, 21);
|
||||
break;
|
||||
#endif
|
||||
case T4_COMPRESSION_ITU_T6:
|
||||
set_ctrl_bit(s->dcs_frame, T30_DCS_BIT_T6_MODE);
|
||||
set_ctrl_bits(s->dcs_frame, T30_MIN_SCAN_0MS, 21);
|
||||
break;
|
||||
case T4_COMPRESSION_ITU_T4_2D:
|
||||
set_ctrl_bit(s->dcs_frame, T30_DCS_BIT_2D_CODING);
|
||||
set_ctrl_bit(s->dcs_frame, T30_DCS_BIT_2D_MODE);
|
||||
set_ctrl_bits(s->dcs_frame, s->min_scan_time_code, 21);
|
||||
break;
|
||||
case T4_COMPRESSION_ITU_T4_1D:
|
||||
@@ -1515,7 +1546,7 @@ static int build_dcs(t30_state_t *s)
|
||||
if (bad != T30_ERR_OK)
|
||||
{
|
||||
s->current_status = bad;
|
||||
span_log(&s->logging, SPAN_LOG_FLOW, "Image width (%d pixels) not an acceptable FAX image width\n", s->image_width);
|
||||
span_log(&s->logging, SPAN_LOG_FLOW, "Image width (%d pixels) is not an acceptable FAX image width\n", s->image_width);
|
||||
return -1;
|
||||
}
|
||||
switch (s->image_width)
|
||||
@@ -1557,7 +1588,7 @@ static int build_dcs(t30_state_t *s)
|
||||
if (bad != T30_ERR_OK)
|
||||
{
|
||||
s->current_status = bad;
|
||||
span_log(&s->logging, SPAN_LOG_FLOW, "Image width (%d pixels) not an acceptable FAX image width\n", s->image_width);
|
||||
span_log(&s->logging, SPAN_LOG_FLOW, "Image width (%d pixels) is not an acceptable FAX image width\n", s->image_width);
|
||||
return -1;
|
||||
}
|
||||
/* Deal with the image length */
|
||||
@@ -2132,6 +2163,60 @@ static int process_rx_dis_dtc(t30_state_t *s, const uint8_t *msg, int len)
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
#if 0
|
||||
/* T.4 1D is always available */
|
||||
bi_level_support = T30_SUPPORT_T4_1D_COMPRESSION;
|
||||
if (test_ctrl_bit(s->far_dis_dtc_frame, T30_DIS_BIT_2D_CAPABLE))
|
||||
bi_level_support |= T30_SUPPORT_T4_2D_COMPRESSION;
|
||||
if (test_ctrl_bit(s->far_dis_dtc_frame, T30_DIS_BIT_T6_CAPABLE))
|
||||
bi_level_support |= T30_SUPPORT_T6_COMPRESSION;
|
||||
/* Bit 79 set with bit 78 clear is invalid, so let's completely ignore 79
|
||||
if 78 is clear. */
|
||||
if (test_ctrl_bit(s->far_dis_dtc_frame, T30_DIS_BIT_T85_CAPABLE))
|
||||
{
|
||||
bi_level_support |= T30_SUPPORT_T85_COMPRESSION;
|
||||
if (test_ctrl_bit(s->far_dis_dtc_frame, T30_DIS_BIT_T85_L0_CAPABLE)
|
||||
bi_level_support |= T30_SUPPORT_T85_L0_COMPRESSION;
|
||||
}
|
||||
|
||||
gray_support = 0;
|
||||
colour_support = 0;
|
||||
if (test_ctrl_bit(s->far_dis_dtc_frame, T30_DIS_BIT_200_200_CAPABLE) && test_ctrl_bit(s->far_dis_dtc_frame, T30_DIS_BIT_T81_CAPABLE))
|
||||
{
|
||||
/* Multi-level coding available */
|
||||
gray_support |= T30_SUPPORT_T81_COMPRESSION;
|
||||
if (test_ctrl_bit(s->far_dis_dtc_frame, T30_DIS_BIT_12BIT_CAPABLE))
|
||||
gray_support |= T30_SUPPORT_T81_12BIT_COMPRESSION;
|
||||
if (test_ctrl_bit(s->far_dis_dtc_frame, T30_DIS_BIT_T43_CAPABLE))
|
||||
{
|
||||
gray_support |= T30_SUPPORT_T43_COMPRESSION;
|
||||
if (test_ctrl_bit(s->far_dis_dtc_frame, T30_DIS_BIT_12BIT_CAPABLE))
|
||||
gray_support |= T30_SUPPORT_T43_COMPRESSION_12BIT;
|
||||
}
|
||||
|
||||
if (test_ctrl_bit(s->far_dis_dtc_frame, bit69))
|
||||
{
|
||||
/* Colour coding available */
|
||||
colour_support |= T30_SUPPORT_T81_COMPRESSION;
|
||||
if (test_ctrl_bit(s->far_dis_dtc_frame, T30_DIS_BIT_12BIT_CAPABLE))
|
||||
colour_support |= T30_SUPPORT_T81_12BIT_COMPRESSION;
|
||||
if (!test_ctrl_bit(s->far_dis_dtc_frame, T30_DIS_BIT_NO_SUBSAMPLING))
|
||||
{
|
||||
colour_support |= T30_SUPPORT_T81_SUBSAMPLING_COMPRESSION;
|
||||
if (test_ctrl_bit(s->far_dis_dtc_frame, T30_DIS_BIT_12BIT_CAPABLE))
|
||||
colour_support |= T30_SUPPORT_T81_SUBSAMPLING_COMPRESSION_12BIT;
|
||||
}
|
||||
if (test_ctrl_bit(s->far_dis_dtc_frame, T30_DIS_BIT_T43_CAPABLE))
|
||||
{
|
||||
colour_support |= T30_SUPPORT_T43_COMPRESSION;
|
||||
if (test_ctrl_bit(s->far_dis_dtc_frame, T30_DIS_BIT_12BIT_CAPABLE))
|
||||
colour_support |= T30_SUPPORT_T43_12BIT_COMPRESSION;
|
||||
}
|
||||
}
|
||||
/* bit74 custom illuminant */
|
||||
/* bit75 custom gamut range */
|
||||
}
|
||||
#endif
|
||||
queue_phase(s, T30_PHASE_B_TX);
|
||||
/* Try to send something */
|
||||
if (s->tx_file[0])
|
||||
@@ -2289,7 +2374,7 @@ static int process_rx_dcs(t30_state_t *s, const uint8_t *msg, int len)
|
||||
{
|
||||
s->line_encoding = T4_COMPRESSION_ITU_T6;
|
||||
}
|
||||
else if (test_ctrl_bit(dcs_frame, T30_DCS_BIT_2D_CODING))
|
||||
else if (test_ctrl_bit(dcs_frame, T30_DCS_BIT_2D_MODE))
|
||||
{
|
||||
s->line_encoding = T4_COMPRESSION_ITU_T4_2D;
|
||||
}
|
||||
@@ -4415,11 +4500,13 @@ static void process_rx_control_msg(t30_state_t *s, const uint8_t *msg, int len)
|
||||
span_log(&s->logging, SPAN_LOG_FLOW, "The remote was made by '%s'\n", s->vendor);
|
||||
if (s->model)
|
||||
span_log(&s->logging, SPAN_LOG_FLOW, "The remote is a '%s'\n", s->model);
|
||||
s->rx_info.nsf_len = decode_nsf_nss_nsc(s, &s->rx_info.nsf, &msg[2], len - 2);
|
||||
}
|
||||
else
|
||||
{
|
||||
/* NSC - Non-standard facilities command */
|
||||
/* OK in (NSC) (CIG) DTC */
|
||||
s->rx_info.nsc_len = decode_nsf_nss_nsc(s, &s->rx_info.nsc, &msg[2], len - 2);
|
||||
}
|
||||
break;
|
||||
case (T30_PWD & 0xFE):
|
||||
@@ -4487,6 +4574,7 @@ static void process_rx_control_msg(t30_state_t *s, const uint8_t *msg, int len)
|
||||
break;
|
||||
case (T30_NSS & 0xFE):
|
||||
/* Non-standard facilities set-up */
|
||||
s->rx_info.nss_len = decode_nsf_nss_nsc(s, &s->rx_info.nss, &msg[2], len - 2);
|
||||
break;
|
||||
case (T30_SUB & 0xFE):
|
||||
/* Sub-address */
|
||||
@@ -5209,6 +5297,18 @@ static void decode_url_msg(t30_state_t *s, char *msg, const uint8_t *pkt, int le
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
static int decode_nsf_nss_nsc(t30_state_t *s, uint8_t *msg[], const uint8_t *pkt, int len)
|
||||
{
|
||||
uint8_t *t;
|
||||
|
||||
if ((t = malloc(len - 1)) == NULL)
|
||||
return 0;
|
||||
memcpy(t, pkt + 1, len - 1);
|
||||
*msg = t;
|
||||
return len - 1;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
static void t30_non_ecm_rx_status(void *user_data, int status)
|
||||
{
|
||||
t30_state_t *s;
|
||||
@@ -6175,10 +6275,8 @@ SPAN_DECLARE(void) t30_get_transfer_statistics(t30_state_t *s, t30_stats_t *t)
|
||||
t->encoding = stats.encoding;
|
||||
t->image_size = stats.line_image_size;
|
||||
t->current_status = s->current_status;
|
||||
#if 0
|
||||
t->rtn_events = s->rtn_events;
|
||||
t->rtp_events = s->rtp_events;
|
||||
#endif
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
|
||||
@@ -60,10 +60,18 @@
|
||||
#include "spandsp/v27ter_tx.h"
|
||||
#include "spandsp/t4_rx.h"
|
||||
#include "spandsp/t4_tx.h"
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
#if defined(SPANDSP_SUPPORT_T42) || defined(SPANDSP_SUPPORT_T43) | defined(SPANDSP_SUPPORT_T85)
|
||||
#include "spandsp/t81_t82_arith_coding.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
#include "spandsp/t85.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T42)
|
||||
#include "spandsp/t42.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T43)
|
||||
#include "spandsp/t43.h"
|
||||
#endif
|
||||
#include "spandsp/t4_t6_decode.h"
|
||||
#include "spandsp/t4_t6_encode.h"
|
||||
#include "spandsp/t30_fcf.h"
|
||||
@@ -73,10 +81,18 @@
|
||||
#include "spandsp/t30_logging.h"
|
||||
|
||||
#include "spandsp/private/logging.h"
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
#if defined(SPANDSP_SUPPORT_T42) || defined(SPANDSP_SUPPORT_T43) | defined(SPANDSP_SUPPORT_T85)
|
||||
#include "spandsp/private/t81_t82_arith_coding.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
#include "spandsp/private/t85.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T42)
|
||||
#include "spandsp/private/t42.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T43)
|
||||
#include "spandsp/private/t43.h"
|
||||
#endif
|
||||
#include "spandsp/private/t4_t6_decode.h"
|
||||
#include "spandsp/private/t4_t6_encode.h"
|
||||
#include "spandsp/private/t4_rx.h"
|
||||
@@ -548,10 +564,8 @@ SPAN_DECLARE(size_t) t30_get_rx_csa(t30_state_t *s, int *type, const char *addre
|
||||
|
||||
SPAN_DECLARE(int) t30_set_tx_page_header_overlays_image(t30_state_t *s, int header_overlays_image)
|
||||
{
|
||||
#if 0
|
||||
s->header_overlays_image = header_overlays_image;
|
||||
t4_tx_set_header_overlays_image(&s->t4.tx, s->header_overlays_image);
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
@@ -686,12 +700,17 @@ SPAN_DECLARE(int) t30_set_supported_compressions(t30_state_t *s, int supported_c
|
||||
mask = T30_SUPPORT_T4_1D_COMPRESSION
|
||||
| T30_SUPPORT_T4_2D_COMPRESSION
|
||||
| T30_SUPPORT_T6_COMPRESSION
|
||||
#if defined(SPANDSP_SUPPORT_T42)
|
||||
| T30_SUPPORT_T42_COMPRESSION
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T43)
|
||||
| T30_SUPPORT_T43_COMPRESSION
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
| T30_SUPPORT_T85_COMPRESSION
|
||||
| T30_SUPPORT_T85_L0_COMPRESSION;
|
||||
#else
|
||||
| 0;
|
||||
| T30_SUPPORT_T85_L0_COMPRESSION
|
||||
#endif
|
||||
| 0;
|
||||
s->supported_compressions = supported_compressions & mask;
|
||||
t30_build_dis_or_dtc(s);
|
||||
return 0;
|
||||
|
||||
@@ -60,10 +60,18 @@
|
||||
#include "spandsp/v27ter_tx.h"
|
||||
#include "spandsp/t4_rx.h"
|
||||
#include "spandsp/t4_tx.h"
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
#if defined(SPANDSP_SUPPORT_T42) || defined(SPANDSP_SUPPORT_T43) | defined(SPANDSP_SUPPORT_T85)
|
||||
#include "spandsp/t81_t82_arith_coding.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
#include "spandsp/t85.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T42)
|
||||
#include "spandsp/t42.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T43)
|
||||
#include "spandsp/t43.h"
|
||||
#endif
|
||||
#include "spandsp/t4_t6_decode.h"
|
||||
#include "spandsp/t4_t6_encode.h"
|
||||
#include "spandsp/t30_fcf.h"
|
||||
@@ -72,10 +80,18 @@
|
||||
#include "spandsp/t30_logging.h"
|
||||
|
||||
#include "spandsp/private/logging.h"
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
#if defined(SPANDSP_SUPPORT_T42) || defined(SPANDSP_SUPPORT_T43) | defined(SPANDSP_SUPPORT_T85)
|
||||
#include "spandsp/private/t81_t82_arith_coding.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
#include "spandsp/private/t85.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T42)
|
||||
#include "spandsp/private/t42.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T43)
|
||||
#include "spandsp/private/t43.h"
|
||||
#endif
|
||||
#include "spandsp/private/t4_t6_decode.h"
|
||||
#include "spandsp/private/t4_t6_encode.h"
|
||||
#include "spandsp/private/t4_rx.h"
|
||||
|
||||
@@ -2167,6 +2167,9 @@ SPAN_DECLARE(int) t31_at_rx(t31_state_t *s, const char *t, int len)
|
||||
}
|
||||
dle_unstuff(s, t, len);
|
||||
break;
|
||||
case AT_MODE_CONNECTED:
|
||||
/* TODO: Implement for data modem operation */
|
||||
break;
|
||||
}
|
||||
return len;
|
||||
}
|
||||
|
||||
@@ -73,10 +73,18 @@
|
||||
#include "spandsp/modem_connect_tones.h"
|
||||
#include "spandsp/t4_rx.h"
|
||||
#include "spandsp/t4_tx.h"
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
#if defined(SPANDSP_SUPPORT_T42) || defined(SPANDSP_SUPPORT_T43) | defined(SPANDSP_SUPPORT_T85)
|
||||
#include "spandsp/t81_t82_arith_coding.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
#include "spandsp/t85.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T42)
|
||||
#include "spandsp/t42.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T43)
|
||||
#include "spandsp/t43.h"
|
||||
#endif
|
||||
#include "spandsp/t4_t6_decode.h"
|
||||
#include "spandsp/t4_t6_encode.h"
|
||||
#include "spandsp/t30_fcf.h"
|
||||
@@ -100,10 +108,18 @@
|
||||
#include "spandsp/private/modem_connect_tones.h"
|
||||
#include "spandsp/private/hdlc.h"
|
||||
#include "spandsp/private/fax_modems.h"
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
#if defined(SPANDSP_SUPPORT_T42) || defined(SPANDSP_SUPPORT_T43) | defined(SPANDSP_SUPPORT_T85)
|
||||
#include "spandsp/private/t81_t82_arith_coding.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T85)
|
||||
#include "spandsp/private/t85.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T42)
|
||||
#include "spandsp/private/t42.h"
|
||||
#endif
|
||||
#if defined(SPANDSP_SUPPORT_T43)
|
||||
#include "spandsp/private/t43.h"
|
||||
#endif
|
||||
#include "spandsp/private/t4_t6_decode.h"
|
||||
#include "spandsp/private/t4_t6_encode.h"
|
||||
#include "spandsp/private/t4_rx.h"
|
||||
@@ -519,7 +535,7 @@ static int set_next_tx_type(t38_gateway_state_t *s)
|
||||
t->tx_bit_rate = 2400;
|
||||
break;
|
||||
case T38_IND_V27TER_4800_TRAINING:
|
||||
t->tx_bit_rate = 2400;
|
||||
t->tx_bit_rate = 4800;
|
||||
break;
|
||||
}
|
||||
/*endswitch*/
|
||||
@@ -930,7 +946,7 @@ static void monitor_control_messages(t38_gateway_state_t *s,
|
||||
case T30_EOS | 1:
|
||||
#if 0
|
||||
/* If we are hitting one of these conditions, it will take another DCS/DTC to select
|
||||
the fast modem again, so abandon our idea of t. */
|
||||
the fast modem again, so abandon our idea of it. */
|
||||
s->core.fast_bit_rate = 0;
|
||||
s->core.fast_rx_modem = T38_NONE;
|
||||
s->core.image_data_mode = FALSE;
|
||||
|
||||
@@ -399,7 +399,7 @@ static void make_header(t4_state_t *s, char *header)
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
static int t4_tx_put_fax_header(t4_state_t *s)
|
||||
static int t4_tx_put_fax_header(t4_state_t *s, int *rows)
|
||||
{
|
||||
int row;
|
||||
int i;
|
||||
@@ -435,6 +435,7 @@ static int t4_tx_put_fax_header(t4_state_t *s)
|
||||
repeats = 1;
|
||||
break;
|
||||
}
|
||||
*rows = 16*repeats;
|
||||
for (row = 0; row < 16; row++)
|
||||
{
|
||||
t = header;
|
||||
@@ -1285,6 +1286,7 @@ SPAN_DECLARE(int) t4_tx_start_page(t4_state_t *s)
|
||||
int run_space;
|
||||
int len;
|
||||
int old_image_width;
|
||||
int header_rows;
|
||||
uint8_t *bufptr8;
|
||||
uint32_t *bufptr;
|
||||
|
||||
@@ -1336,7 +1338,7 @@ SPAN_DECLARE(int) t4_tx_start_page(t4_state_t *s)
|
||||
|
||||
if (s->header_info && s->header_info[0])
|
||||
{
|
||||
if (t4_tx_put_fax_header(s))
|
||||
if (t4_tx_put_fax_header(s, &header_rows))
|
||||
return -1;
|
||||
}
|
||||
if (s->t4_t6_tx.row_read_handler)
|
||||
@@ -1501,6 +1503,12 @@ SPAN_DECLARE(void) t4_tx_set_min_bits_per_row(t4_state_t *s, int bits)
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(void) t4_tx_set_header_overlays_image(t4_state_t *s, int header_overlays_image)
|
||||
{
|
||||
s->header_overlays_image = header_overlays_image;
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(void) t4_tx_set_local_ident(t4_state_t *s, const char *ident)
|
||||
{
|
||||
s->tiff.local_ident = (ident && ident[0]) ? ident : NULL;
|
||||
|
||||
@@ -114,11 +114,11 @@ static const int year_lengths[2] =
|
||||
|
||||
static int increment_overflow(int *number, int delta)
|
||||
{
|
||||
int number0;
|
||||
int last_number;
|
||||
|
||||
number0 = *number;
|
||||
last_number = *number;
|
||||
*number += delta;
|
||||
return (*number < number0) != (delta < 0);
|
||||
return (*number < last_number) != (delta < 0);
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
@@ -164,6 +164,10 @@ static struct tm *time_sub(const time_t * const timep, const long int offset, co
|
||||
int y;
|
||||
int hit;
|
||||
int i;
|
||||
int newy;
|
||||
time_t tdelta;
|
||||
int idelta;
|
||||
int leapdays;
|
||||
|
||||
corr = 0;
|
||||
hit = 0;
|
||||
@@ -198,11 +202,6 @@ static struct tm *time_sub(const time_t * const timep, const long int offset, co
|
||||
rem = *timep - tdays*SECS_PER_DAY;
|
||||
while (tdays < 0 || tdays >= year_lengths[isleap(y)])
|
||||
{
|
||||
int newy;
|
||||
time_t tdelta;
|
||||
int idelta;
|
||||
int leapdays;
|
||||
|
||||
tdelta = tdays / DAYS_PER_LEAP_YEAR;
|
||||
idelta = tdelta;
|
||||
if (tdelta - idelta >= 1 || idelta - tdelta >= 1)
|
||||
|
||||
@@ -44,6 +44,9 @@
|
||||
|
||||
#include "spandsp/telephony.h"
|
||||
#include "spandsp/logging.h"
|
||||
#include "spandsp/fast_convert.h"
|
||||
#include "spandsp/math_fixed.h"
|
||||
#include "spandsp/saturated.h"
|
||||
#include "spandsp/complex.h"
|
||||
#include "spandsp/vector_float.h"
|
||||
#include "spandsp/complex_vector_float.h"
|
||||
@@ -62,13 +65,13 @@
|
||||
#include "spandsp/private/logging.h"
|
||||
#include "spandsp/private/v17rx.h"
|
||||
|
||||
#include "v17_v32bis_tx_constellation_maps.h"
|
||||
#include "v17_v32bis_rx_constellation_maps.h"
|
||||
#if defined(SPANDSP_USE_FIXED_POINT)
|
||||
#include "v17_v32bis_rx_fixed_rrc.h"
|
||||
#else
|
||||
#include "v17_v32bis_rx_floating_rrc.h"
|
||||
#endif
|
||||
#include "v17_v32bis_tx_constellation_maps.h"
|
||||
#include "v17_v32bis_rx_constellation_maps.h"
|
||||
|
||||
/*! The nominal frequency of the carrier, in Hertz */
|
||||
#define CARRIER_NOMINAL_FREQ 1800.0f
|
||||
@@ -295,8 +298,7 @@ static int descramble(v17_rx_state_t *s, int in_bit)
|
||||
{
|
||||
int out_bit;
|
||||
|
||||
//out_bit = (in_bit ^ (s->scramble_reg >> s->scrambler_tap) ^ (s->scramble_reg >> (23 - 1))) & 1;
|
||||
out_bit = (in_bit ^ (s->scramble_reg >> (18 - 1)) ^ (s->scramble_reg >> (23 - 1))) & 1;
|
||||
out_bit = (in_bit ^ (s->scramble_reg >> s->scrambler_tap) ^ (s->scramble_reg >> (23 - 1))) & 1;
|
||||
s->scramble_reg <<= 1;
|
||||
if (s->training_stage > TRAINING_STAGE_NORMAL_OPERATION && s->training_stage < TRAINING_STAGE_TCM_WINDUP)
|
||||
s->scramble_reg |= out_bit;
|
||||
@@ -1248,7 +1250,7 @@ SPAN_DECLARE(void) v17_rx_set_put_bit(v17_rx_state_t *s, put_bit_func_t put_bit,
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(void) v17_rx_set_modem_status_handler(v17_rx_state_t *s, modem_tx_status_func_t handler, void *user_data)
|
||||
SPAN_DECLARE(void) v17_rx_set_modem_status_handler(v17_rx_state_t *s, modem_status_func_t handler, void *user_data)
|
||||
{
|
||||
s->status_handler = handler;
|
||||
s->status_user_data = user_data;
|
||||
@@ -1425,7 +1427,7 @@ SPAN_DECLARE(v17_rx_state_t *) v17_rx_init(v17_rx_state_t *s, int bit_rate, put_
|
||||
s->put_bit = put_bit;
|
||||
s->put_bit_user_data = user_data;
|
||||
s->short_train = FALSE;
|
||||
//s->scrambler_tap = 18 - 1;
|
||||
s->scrambler_tap = 18 - 1;
|
||||
v17_rx_signal_cutoff(s, -45.5f);
|
||||
s->carrier_phase_rate_save = dds_phase_ratef(CARRIER_NOMINAL_FREQ);
|
||||
v17_rx_restart(s, bit_rate, s->short_train);
|
||||
|
||||
+33
-33
@@ -100,8 +100,7 @@ static __inline__ int scramble(v17_tx_state_t *s, int in_bit)
|
||||
{
|
||||
int out_bit;
|
||||
|
||||
//out_bit = (in_bit ^ (s->scramble_reg >> s->scrambler_tap) ^ (s->scramble_reg >> (23 - 1))) & 1;
|
||||
out_bit = (in_bit ^ (s->scramble_reg >> (18 - 1)) ^ (s->scramble_reg >> (23 - 1))) & 1;
|
||||
out_bit = (in_bit ^ (s->scramble_reg >> s->scrambler_tap) ^ (s->scramble_reg >> (23 - 1))) & 1;
|
||||
s->scramble_reg = (s->scramble_reg << 1) | out_bit;
|
||||
return out_bit;
|
||||
}
|
||||
@@ -287,13 +286,16 @@ static __inline__ complexf_t getbaud(v17_tx_state_t *s)
|
||||
SPAN_DECLARE_NONSTD(int) v17_tx(v17_tx_state_t *s, int16_t amp[], int len)
|
||||
{
|
||||
#if defined(SPANDSP_USE_FIXED_POINT)
|
||||
complexi_t x;
|
||||
complexi_t z;
|
||||
complexi16_t v;
|
||||
complexi32_t x;
|
||||
complexi32_t z;
|
||||
int16_t iamp;
|
||||
#else
|
||||
complexf_t v;
|
||||
complexf_t x;
|
||||
complexf_t z;
|
||||
float famp;
|
||||
#endif
|
||||
int i;
|
||||
int sample;
|
||||
|
||||
if (s->training_step >= V17_TRAINING_SHUTDOWN_END)
|
||||
@@ -306,37 +308,30 @@ SPAN_DECLARE_NONSTD(int) v17_tx(v17_tx_state_t *s, int16_t amp[], int len)
|
||||
if ((s->baud_phase += 3) >= 10)
|
||||
{
|
||||
s->baud_phase -= 10;
|
||||
s->rrc_filter[s->rrc_filter_step] =
|
||||
s->rrc_filter[s->rrc_filter_step + V17_TX_FILTER_STEPS] = getbaud(s);
|
||||
v = getbaud(s);
|
||||
s->rrc_filter_re[s->rrc_filter_step] = v.re;
|
||||
s->rrc_filter_im[s->rrc_filter_step] = v.im;
|
||||
if (++s->rrc_filter_step >= V17_TX_FILTER_STEPS)
|
||||
s->rrc_filter_step = 0;
|
||||
}
|
||||
/* Root raised cosine pulse shaping at baseband */
|
||||
#if defined(SPANDSP_USE_FIXED_POINT)
|
||||
x = complex_seti(0, 0);
|
||||
for (i = 0; i < V17_TX_FILTER_STEPS; i++)
|
||||
{
|
||||
x.re += (int32_t) tx_pulseshaper[TX_PULSESHAPER_COEFF_SETS - 1 - s->baud_phase][i]*(int32_t) s->rrc_filter[i + s->rrc_filter_step].re;
|
||||
x.im += (int32_t) tx_pulseshaper[TX_PULSESHAPER_COEFF_SETS - 1 - s->baud_phase][i]*(int32_t) s->rrc_filter[i + s->rrc_filter_step].im;
|
||||
}
|
||||
/* Root raised cosine pulse shaping at baseband */
|
||||
x.re = vec_circular_dot_prodi16(s->rrc_filter_re, tx_pulseshaper[TX_PULSESHAPER_COEFF_SETS - 1 - s->baud_phase], V17_TX_FILTER_STEPS, s->rrc_filter_step) >> 4;
|
||||
x.im = vec_circular_dot_prodi16(s->rrc_filter_im, tx_pulseshaper[TX_PULSESHAPER_COEFF_SETS - 1 - s->baud_phase], V17_TX_FILTER_STEPS, s->rrc_filter_step) >> 4;
|
||||
/* Now create and modulate the carrier */
|
||||
x.re >>= 4;
|
||||
x.im >>= 4;
|
||||
z = dds_complexi(&(s->carrier_phase), s->carrier_phase_rate);
|
||||
z = dds_complexi32(&s->carrier_phase, s->carrier_phase_rate);
|
||||
iamp = ((int32_t) x.re*z.re - x.im*z.im) >> 15;
|
||||
/* Don't bother saturating. We should never clip. */
|
||||
i = (x.re*z.re - x.im*z.im) >> 15;
|
||||
amp[sample] = (int16_t) ((i*s->gain) >> 15);
|
||||
amp[sample] = (int16_t) (((int32_t) iamp*s->gain) >> 11);
|
||||
#else
|
||||
x = complex_setf(0.0f, 0.0f);
|
||||
for (i = 0; i < V17_TX_FILTER_STEPS; i++)
|
||||
{
|
||||
x.re += tx_pulseshaper[TX_PULSESHAPER_COEFF_SETS - 1 - s->baud_phase][i]*s->rrc_filter[i + s->rrc_filter_step].re;
|
||||
x.im += tx_pulseshaper[TX_PULSESHAPER_COEFF_SETS - 1 - s->baud_phase][i]*s->rrc_filter[i + s->rrc_filter_step].im;
|
||||
}
|
||||
/* Root raised cosine pulse shaping at baseband */
|
||||
x.re = vec_circular_dot_prodf(s->rrc_filter_re, tx_pulseshaper[TX_PULSESHAPER_COEFF_SETS - 1 - s->baud_phase], V17_TX_FILTER_STEPS, s->rrc_filter_step);
|
||||
x.im = vec_circular_dot_prodf(s->rrc_filter_im, tx_pulseshaper[TX_PULSESHAPER_COEFF_SETS - 1 - s->baud_phase], V17_TX_FILTER_STEPS, s->rrc_filter_step);
|
||||
/* Now create and modulate the carrier */
|
||||
z = dds_complexf(&(s->carrier_phase), s->carrier_phase_rate);
|
||||
z = dds_complexf(&s->carrier_phase, s->carrier_phase_rate);
|
||||
famp = x.re*z.re - x.im*z.im;
|
||||
/* Don't bother saturating. We should never clip. */
|
||||
amp[sample] = (int16_t) lfastrintf((x.re*z.re - x.im*z.im)*s->gain);
|
||||
amp[sample] = (int16_t) lfastrintf(famp*s->gain);
|
||||
#endif
|
||||
}
|
||||
return sample;
|
||||
@@ -345,12 +340,15 @@ SPAN_DECLARE_NONSTD(int) v17_tx(v17_tx_state_t *s, int16_t amp[], int len)
|
||||
|
||||
SPAN_DECLARE(void) v17_tx_power(v17_tx_state_t *s, float power)
|
||||
{
|
||||
float gain;
|
||||
|
||||
/* The constellation design seems to keep the average power the same, regardless
|
||||
of which bit rate is in use. */
|
||||
gain = 0.223f*powf(10.0f, (power - DBM0_MAX_POWER)/20.0f)*32768.0f/TX_PULSESHAPER_GAIN;
|
||||
#if defined(SPANDSP_USE_FIXED_POINT)
|
||||
s->gain = 0.223f*powf(10.0f, (power - DBM0_MAX_POWER)/20.0f)*16.0f*(32767.0f/30672.52f)*32768.0f/TX_PULSESHAPER_GAIN;
|
||||
s->gain = (int16_t) gain;
|
||||
#else
|
||||
s->gain = 0.223f*powf(10.0f, (power - DBM0_MAX_POWER)/20.0f)*32768.0f/TX_PULSESHAPER_GAIN;
|
||||
s->gain = gain;
|
||||
#endif
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
@@ -364,7 +362,7 @@ SPAN_DECLARE(void) v17_tx_set_get_bit(v17_tx_state_t *s, get_bit_func_t get_bit,
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(void) v17_tx_set_modem_status_handler(v17_tx_state_t *s, modem_tx_status_func_t handler, void *user_data)
|
||||
SPAN_DECLARE(void) v17_tx_set_modem_status_handler(v17_tx_state_t *s, modem_status_func_t handler, void *user_data)
|
||||
{
|
||||
s->status_handler = handler;
|
||||
s->status_user_data = user_data;
|
||||
@@ -410,9 +408,11 @@ SPAN_DECLARE(int) v17_tx_restart(v17_tx_state_t *s, int bit_rate, int tep, int s
|
||||
/* NB: some modems seem to use 3 instead of 1 for long training */
|
||||
s->diff = (short_train) ? 0 : 1;
|
||||
#if defined(SPANDSP_USE_FIXED_POINT)
|
||||
cvec_zeroi16(s->rrc_filter, sizeof(s->rrc_filter)/sizeof(s->rrc_filter[0]));
|
||||
vec_zeroi16(s->rrc_filter_re, sizeof(s->rrc_filter_re)/sizeof(s->rrc_filter_re[0]));
|
||||
vec_zeroi16(s->rrc_filter_im, sizeof(s->rrc_filter_im)/sizeof(s->rrc_filter_im[0]));
|
||||
#else
|
||||
cvec_zerof(s->rrc_filter, sizeof(s->rrc_filter)/sizeof(s->rrc_filter[0]));
|
||||
vec_zerof(s->rrc_filter_re, sizeof(s->rrc_filter_re)/sizeof(s->rrc_filter_re[0]));
|
||||
vec_zerof(s->rrc_filter_im, sizeof(s->rrc_filter_im)/sizeof(s->rrc_filter_im[0]));
|
||||
#endif
|
||||
s->rrc_filter_step = 0;
|
||||
s->convolution = 0;
|
||||
@@ -452,7 +452,7 @@ SPAN_DECLARE(v17_tx_state_t *) v17_tx_init(v17_tx_state_t *s, int bit_rate, int
|
||||
span_log_set_protocol(&s->logging, "V.17 TX");
|
||||
s->get_bit = get_bit;
|
||||
s->get_bit_user_data = user_data;
|
||||
//s->scrambler_tap = 18 - 1;
|
||||
s->scrambler_tap = 18 - 1;
|
||||
s->carrier_phase_rate = dds_phase_ratef(CARRIER_NOMINAL_FREQ);
|
||||
v17_tx_power(s, -14.0f);
|
||||
v17_tx_restart(s, bit_rate, tep, FALSE);
|
||||
|
||||
@@ -552,7 +552,7 @@ SPAN_DECLARE(void) v22bis_set_put_bit(v22bis_state_t *s, put_bit_func_t put_bit,
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(void) v22bis_set_modem_status_handler(v22bis_state_t *s, modem_tx_status_func_t handler, void *user_data)
|
||||
SPAN_DECLARE(void) v22bis_set_modem_status_handler(v22bis_state_t *s, modem_status_func_t handler, void *user_data)
|
||||
{
|
||||
s->status_handler = handler;
|
||||
s->status_user_data = user_data;
|
||||
|
||||
@@ -1019,7 +1019,7 @@ SPAN_DECLARE(void) v27ter_rx_set_put_bit(v27ter_rx_state_t *s, put_bit_func_t pu
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(void) v27ter_rx_set_modem_status_handler(v27ter_rx_state_t *s, modem_tx_status_func_t handler, void *user_data)
|
||||
SPAN_DECLARE(void) v27ter_rx_set_modem_status_handler(v27ter_rx_state_t *s, modem_status_func_t handler, void *user_data)
|
||||
{
|
||||
s->status_handler = handler;
|
||||
s->status_user_data = user_data;
|
||||
|
||||
@@ -374,7 +374,7 @@ SPAN_DECLARE(void) v27ter_tx_set_get_bit(v27ter_tx_state_t *s, get_bit_func_t ge
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(void) v27ter_tx_set_modem_status_handler(v27ter_tx_state_t *s, modem_tx_status_func_t handler, void *user_data)
|
||||
SPAN_DECLARE(void) v27ter_tx_set_modem_status_handler(v27ter_tx_state_t *s, modem_status_func_t handler, void *user_data)
|
||||
{
|
||||
s->status_handler = handler;
|
||||
s->status_user_data = user_data;
|
||||
|
||||
@@ -1052,7 +1052,7 @@ SPAN_DECLARE(void) v29_rx_set_put_bit(v29_rx_state_t *s, put_bit_func_t put_bit,
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(void) v29_rx_set_modem_status_handler(v29_rx_state_t *s, modem_tx_status_func_t handler, void *user_data)
|
||||
SPAN_DECLARE(void) v29_rx_set_modem_status_handler(v29_rx_state_t *s, modem_status_func_t handler, void *user_data)
|
||||
{
|
||||
s->status_handler = handler;
|
||||
s->status_user_data = user_data;
|
||||
|
||||
@@ -316,7 +316,7 @@ SPAN_DECLARE(void) v29_tx_set_get_bit(v29_tx_state_t *s, get_bit_func_t get_bit,
|
||||
}
|
||||
/*- End of function --------------------------------------------------------*/
|
||||
|
||||
SPAN_DECLARE(void) v29_tx_set_modem_status_handler(v29_tx_state_t *s, modem_tx_status_func_t handler, void *user_data)
|
||||
SPAN_DECLARE(void) v29_tx_set_modem_status_handler(v29_tx_state_t *s, modem_status_func_t handler, void *user_data)
|
||||
{
|
||||
s->status_handler = handler;
|
||||
s->status_user_data = user_data;
|
||||
|
||||
Loaded 100 of 398 files, more files were not shown because too many files have changed in this diff.
Show more
Reference in new issue
Block a user