Merge branch 'nsg-4.3'
This commit is contained in:
commit
c425955670
|
@ -0,0 +1,15 @@
|
|||
# gitattributes
|
||||
*.exe -diff binary executable windows dfsg-nonfree debian-ignore
|
||||
*.wav -diff binary sound
|
||||
*.gif -diff binary image
|
||||
*.jpg -diff binary image
|
||||
*.jpeg -diff binary image
|
||||
*.pbm -diff binary image
|
||||
/clients/flex* dfsg-nonfree
|
||||
/debian* debian-ignore
|
||||
/freeswitch.xcodeproj debian-ignore
|
||||
/libs/ilbc* dfsg-nonfree
|
||||
/libs/libg722_1* dfsg-nonfree
|
||||
/libs/win32* windows debian-ignore
|
||||
/htdocs* dfsg-nonfree debian-ignore
|
||||
/w32* windows debian-ignore
|
|
@ -43,6 +43,7 @@ configure.lineno
|
|||
config.log
|
||||
config.status
|
||||
core.*
|
||||
TAGS
|
||||
*.2010.log
|
||||
*.Build.CppClean.log
|
||||
*.tlog
|
||||
|
@ -201,3 +202,23 @@ src/mod/formats/mod_shout/*/*/mod_shout.log
|
|||
/src/mod/languages/mod_managed/x64/Release_CLR/FREESWITCH.MANAGED.DLL.metagen
|
||||
/src/mod/languages/mod_managed/x64/Release_CLR/RSAENH.DLL.bi
|
||||
/src/mod/languages/mod_managed/x64/Release_CLR/TZRES.DLL.bi
|
||||
libs/apr-util/a.out.dSYM/Contents/Info.plist
|
||||
libs/apr-util/a.out.dSYM/Contents/Resources/DWARF/a.out
|
||||
libs/apr/a.out.dSYM/Contents/Info.plist
|
||||
libs/apr/a.out.dSYM/Contents/Resources/DWARF/a.out
|
||||
libs/iksemel/a.out.dSYM/Contents/Info.plist
|
||||
libs/iksemel/a.out.dSYM/Contents/Resources/DWARF/a.out
|
||||
libs/ilbc/a.out.dSYM/Contents/Info.plist
|
||||
libs/ilbc/a.out.dSYM/Contents/Resources/DWARF/a.out
|
||||
libs/libedit/a.out.dSYM/Contents/Info.plist
|
||||
libs/libedit/a.out.dSYM/Contents/Resources/DWARF/a.out
|
||||
libs/pcre/a.out.dSYM/Contents/Info.plist
|
||||
libs/pcre/a.out.dSYM/Contents/Resources/DWARF/a.out
|
||||
libs/sqlite/lemon.dSYM/Contents/Info.plist
|
||||
libs/sqlite/lemon.dSYM/Contents/Resources/DWARF/lemon
|
||||
libs/sqlite/mkkeywordhash.dSYM/Contents/Info.plist
|
||||
libs/sqlite/mkkeywordhash.dSYM/Contents/Resources/DWARF/mkkeywordhash
|
||||
libs/sqlite/sqlite3.dSYM/Contents/Info.plist
|
||||
libs/sqlite/sqlite3.dSYM/Contents/Resources/DWARF/sqlite3
|
||||
libs/srtp/a.out.dSYM/Contents/Info.plist
|
||||
libs/srtp/a.out.dSYM/Contents/Resources/DWARF/a.out
|
||||
|
|
|
@ -320,6 +320,8 @@ Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "ldns", "libs\win32\ldns\ldn
|
|||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libpcre Generate pcre_chartables.c", "libs\win32\pcre\pcre_chartables.c.2010.vcxproj", "{1CED5987-A529-46DC-B30F-870D85FF9C94}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libzrtp", "libs\libzrtp\projects\win\libzrtp.2010.vcxproj", "{C13CC324-0032-4492-9A30-310A6BD64FF5}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
All|Win32 = All|Win32
|
||||
|
@ -1989,6 +1991,17 @@ Global
|
|||
{1CED5987-A529-46DC-B30F-870D85FF9C94}.Release|Win32.ActiveCfg = Release|Win32
|
||||
{1CED5987-A529-46DC-B30F-870D85FF9C94}.Release|Win32.Build.0 = Release|Win32
|
||||
{1CED5987-A529-46DC-B30F-870D85FF9C94}.Release|x64.ActiveCfg = Release|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.All|Win32.ActiveCfg = Release|x64
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.All|x64.ActiveCfg = Release|x64
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.All|x64.Build.0 = Release|x64
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Debug|Win32.ActiveCfg = Debug|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Debug|Win32.Build.0 = Debug|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Debug|x64.Build.0 = Debug|x64
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Release|Win32.ActiveCfg = Release|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Release|Win32.Build.0 = Release|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Release|x64.ActiveCfg = Release|x64
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Release|x64.Build.0 = Release|x64
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
|
@ -2089,6 +2102,7 @@ Global
|
|||
{ABB71A76-42B0-47A4-973A-42E3D920C6FD} = {EB910B0D-F27D-4B62-B67B-DE834C99AC5B}
|
||||
{9778F1C0-09BC-4698-8EBC-BD982247209A} = {EB910B0D-F27D-4B62-B67B-DE834C99AC5B}
|
||||
{56B91D01-9150-4BBF-AFA1-5B68AB991B76} = {EB910B0D-F27D-4B62-B67B-DE834C99AC5B}
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5} = {EB910B0D-F27D-4B62-B67B-DE834C99AC5B}
|
||||
{EC3E5C7F-EE09-47E2-80FE-546363D14A98} = {B8F5B47B-8568-46EB-B320-64C17D2A98BC}
|
||||
{1AD3F51E-BBB6-4090-BA39-9DFAB1EF1F5F} = {0C808854-54D1-4230-BFF5-77B5FD905000}
|
||||
{ACFFF684-4D19-4D48-AF12-88EA1D778BDF} = {0C808854-54D1-4230-BFF5-77B5FD905000}
|
||||
|
|
|
@ -525,6 +525,8 @@ Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "gsmlib", "src\mod\endpoints
|
|||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "mod_gsmopen", "src\mod\endpoints\mod_gsmopen\mod_gsmopen.2010.vcxproj", "{74B120FF-6935-4DFE-A142-CDB6BEA99C90}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libzrtp", "libs\libzrtp\projects\win\libzrtp.2010.vcxproj", "{C13CC324-0032-4492-9A30-310A6BD64FF5}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
All|Win32 = All|Win32
|
||||
|
@ -3574,6 +3576,23 @@ Global
|
|||
{74B120FF-6935-4DFE-A142-CDB6BEA99C90}.Release|x64.ActiveCfg = Release|x64
|
||||
{74B120FF-6935-4DFE-A142-CDB6BEA99C90}.Release|x64 Setup.ActiveCfg = Release|x64
|
||||
{74B120FF-6935-4DFE-A142-CDB6BEA99C90}.Release|x86 Setup.ActiveCfg = Release|x64
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.All|Win32.ActiveCfg = Release|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.All|Win32.Build.0 = Release|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.All|x64.ActiveCfg = Release|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.All|x64 Setup.ActiveCfg = Release|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.All|x86 Setup.ActiveCfg = Release|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Debug|Win32.ActiveCfg = Debug|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Debug|Win32.Build.0 = Debug|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Debug|x64.Build.0 = Debug|x64
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Debug|x64 Setup.ActiveCfg = Debug|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Debug|x86 Setup.ActiveCfg = Debug|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Release|Win32.ActiveCfg = Release|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Release|Win32.Build.0 = Release|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Release|x64.ActiveCfg = Release|x64
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Release|x64.Build.0 = Release|x64
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Release|x64 Setup.ActiveCfg = Release|Win32
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5}.Release|x86 Setup.ActiveCfg = Release|Win32
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
|
@ -3687,6 +3706,7 @@ Global
|
|||
{70A49BC2-7500-41D0-B75D-EDCC5BE987A0} = {EB910B0D-F27D-4B62-B67B-DE834C99AC5B}
|
||||
{23B4D303-79FC-49E0-89E2-2280E7E28940} = {EB910B0D-F27D-4B62-B67B-DE834C99AC5B}
|
||||
{26C82FCE-E0CF-4D10-A00C-D8E582FFEB53} = {EB910B0D-F27D-4B62-B67B-DE834C99AC5B}
|
||||
{C13CC324-0032-4492-9A30-310A6BD64FF5} = {EB910B0D-F27D-4B62-B67B-DE834C99AC5B}
|
||||
{EC3E5C7F-EE09-47E2-80FE-546363D14A98} = {B8F5B47B-8568-46EB-B320-64C17D2A98BC}
|
||||
{1AD3F51E-BBB6-4090-BA39-9DFAB1EF1F5F} = {0C808854-54D1-4230-BFF5-77B5FD905000}
|
||||
{ACFFF684-4D19-4D48-AF12-88EA1D778BDF} = {0C808854-54D1-4230-BFF5-77B5FD905000}
|
||||
|
|
21
Makefile.am
21
Makefile.am
|
@ -20,11 +20,18 @@ DEFAULT_SOUNDS=en-us-callie-8000
|
|||
sounds_version=`grep $$base_sound_dir $(switch_srcdir)/build/sounds_version.txt | cut -d ' ' -f2`;\
|
||||
soundfile=`echo freeswitch-sounds-$$full_sound_dir-$$moh_version.tar.gz`; \
|
||||
echo $$full_sound_dir | grep music >/dev/null || soundfile=`echo freeswitch-sounds-$$full_sound_dir-$$sounds_version.tar.gz`; \
|
||||
if test "$$target" = "install"; then $(MAKE) $(AM_MAKEFLAGS) core_install; else $(MAKE) $(AM_MAKEFLAGS) core ; fi; \
|
||||
if test "$$target_prefix" = "sounds"; then \
|
||||
if test "$$target" = "install"; then $(GETSOUNDS) $$soundfile $(DESTDIR)$(soundsdir)/; else $(GETSOUNDS) $$soundfile ; fi; \
|
||||
if test "$$target" = "install"; then \
|
||||
$(GETSOUNDS) $$soundfile $(DESTDIR)$(soundsdir)/;\
|
||||
else \
|
||||
$(GETSOUNDS) $$soundfile ; \
|
||||
fi; \
|
||||
else \
|
||||
cd src/mod && $(MAKE) $(AM_MAKEFLAGS) $@ ;\
|
||||
if test "$$target" = "install"; then \
|
||||
$(MAKE) $(AM_MAKEFLAGS) core_install && cd src/mod && $(MAKE) $(AM_MAKEFLAGS) $@ ; \
|
||||
else \
|
||||
$(MAKE) $(AM_MAKEFLAGS) core && cd src/mod && $(MAKE) $(AM_MAKEFLAGS) $@ ;\
|
||||
fi; \
|
||||
fi
|
||||
|
||||
sounds: sounds-en-us-callie-8000
|
||||
|
@ -150,8 +157,8 @@ if ENABLE_ZRTP
|
|||
CORE_CFLAGS += -I$(switch_srcdir)/libs/libzrtp/third_party/bgaes
|
||||
CORE_CFLAGS += -I$(switch_srcdir)/libs/libzrtp/third_party/bnlib
|
||||
CORE_CFLAGS += -isystem $(switch_srcdir)/libs/libzrtp/include
|
||||
ZRTP_LDFLAGS = -Llibs/libzrtp/third_party/bnlib
|
||||
ZRTP_LDFLAGS += -Llibs/libzrtp/projects/gnu/build
|
||||
ZRTP_LDFLAGS = -L$(switch_srcdir)/libs/libzrtp/third_party/bnlib
|
||||
ZRTP_LDFLAGS += -L$(switch_srcdir)/libs/libzrtp/projects/gnu/build
|
||||
ZRTP_LIBS = -lbn -lzrtp
|
||||
libfreeswitch_la_LDFLAGS += $(ZRTP_LDFLAGS)
|
||||
libfreeswitch_la_LIBADD += $(ZRTP_LIBS)
|
||||
|
@ -411,8 +418,8 @@ $(switch_builddir)/quiet_libtool: $(switch_builddir)/libtool
|
|||
src/include/switch_version.h: src/include/switch_version.h.in .version $(libfreeswitch_la_SOURCES) $(library_include_HEADERS)
|
||||
@have_version=1 ; \
|
||||
force=0 ; \
|
||||
grep "@SWITCH_VERSION_REVISION@" src/include/switch_version.h.in > /dev/null && have_version=0 ; \
|
||||
test ! -f src/include/switch_version.h || grep "@SWITCH_VERSION_REVISION@" src/include/switch_version.h > /dev/null && force=1 ; \
|
||||
grep -- "@SWITCH_VERSION_REVISION@" src/include/switch_version.h.in > /dev/null || have_version=0 ; \
|
||||
test ! -f src/include/switch_version.h || grep -- "@SWITCH_VERSION_REVISION@" src/include/switch_version.h > /dev/null && force=1 ; \
|
||||
if test $$have_version = 1 ; then \
|
||||
cat src/include/switch_version.h.in > src/include/switch_version.h ; \
|
||||
touch .version ; \
|
||||
|
|
10
bootstrap.sh
10
bootstrap.sh
|
@ -343,11 +343,7 @@ bootstrap_apr() {
|
|||
|
||||
echo "Entering directory ${LIBDIR}/apr-util"
|
||||
cd ${LIBDIR}/apr-util
|
||||
if ! ${BGJOB}; then
|
||||
./buildconf
|
||||
else
|
||||
./buildconf &
|
||||
fi
|
||||
./buildconf
|
||||
}
|
||||
|
||||
bootstrap_libzrtp() {
|
||||
|
@ -454,9 +450,10 @@ bootstrap_libs() {
|
|||
if ! ${BGJOB}; then
|
||||
libbootstrap ${i} ; bootstrap_libs_post ${i}
|
||||
else
|
||||
((libbootstrap ${i} ; bootstrap_libs_post ${i}) &)
|
||||
(libbootstrap ${i} ; bootstrap_libs_post ${i}) &
|
||||
fi
|
||||
done
|
||||
${BGJOB} && wait
|
||||
}
|
||||
|
||||
run() {
|
||||
|
@ -471,7 +468,6 @@ run() {
|
|||
check_libtoolize
|
||||
print_autotools_vers
|
||||
bootstrap_libs
|
||||
${BGJOB} && wait
|
||||
return 0
|
||||
}
|
||||
|
||||
|
|
|
@ -46,12 +46,7 @@
|
|||
# Voice Platform
|
||||
### END INIT INFO
|
||||
#
|
||||
# Check for missing binaries (stale symlinks should not happen)
|
||||
# Note: Special treatment of stop for LSB conformance
|
||||
FREESWITCH_BIN=/opt/freeswitch/bin/freeswitch
|
||||
test -x $FREESWITCH_BIN || { echo "$FREESWITCH_BIN not installed";
|
||||
if [ "$1" = "stop" ]; then exit 0;
|
||||
else exit 5; fi; }
|
||||
|
||||
# Check for existence of needed config file and read it
|
||||
FREESWITCH_CONFIG=/etc/sysconfig/freeswitch
|
||||
|
@ -62,6 +57,12 @@ test -r $FREESWITCH_CONFIG || { echo "$FREESWITCH_CONFIG not existing";
|
|||
# Read config
|
||||
. $FREESWITCH_CONFIG
|
||||
|
||||
# Check for missing binaries (stale symlinks should not happen)
|
||||
# Note: Special treatment of stop for LSB conformance
|
||||
test -x $FREESWITCH_BIN || { echo "$FREESWITCH_BIN not installed";
|
||||
if [ "$1" = "stop" ]; then exit 0;
|
||||
else exit 5; fi; }
|
||||
|
||||
# Source LSB init functions
|
||||
# providing start_daemon, killproc, pidofproc,
|
||||
# log_success_msg, log_failure_msg and log_warning_msg.
|
||||
|
@ -202,7 +203,7 @@ case "$1" in
|
|||
## argument to this init script which is required for a reload.
|
||||
## Note: probe is not (yet) part of LSB (as of 1.9)
|
||||
|
||||
test /opt/freeswitch/conf/freeswitch.xml -nt /opt/freeswitch/run/freeswitch.pid && echo reload
|
||||
test ${FREESWITCH_HOME}/conf/freeswitch.xml -nt ${FREESWITCH_HOME}/run/freeswitch.pid && echo reload
|
||||
;;
|
||||
*)
|
||||
echo "Usage: $0 {start|stop|status|try-restart|restart|force-reload|reload|probe}"
|
||||
|
|
|
@ -1,4 +1,5 @@
|
|||
#!/bin/sh
|
||||
##### -*- mode:shell-script; indent-tabs-mode:nil; sh-basic-offset:2 -*-
|
||||
|
||||
TAR=@TAR@
|
||||
ZCAT=@ZCAT@
|
||||
|
@ -8,39 +9,39 @@ WGET=@WGET@
|
|||
CURL=@CURL@
|
||||
|
||||
if [ -f "$WGET" ]; then
|
||||
DOWNLOAD_CMD=$WGET
|
||||
DOWNLOAD_CMD=$WGET
|
||||
elif [ -f "$CURL" ]; then
|
||||
DOWNLOAD_CMD="$CURL -O"
|
||||
DOWNLOAD_CMD="$CURL -O"
|
||||
fi
|
||||
|
||||
if [ -n "`echo $1 | grep '://'`" ]; then
|
||||
base=$1/
|
||||
tarfile=$2
|
||||
base=$1/
|
||||
tarfile=$2
|
||||
else
|
||||
base=http://files.freeswitch.org/downloads/libs/
|
||||
tarfile=$1
|
||||
base=http://files.freeswitch.org/downloads/libs/
|
||||
tarfile=$1
|
||||
fi
|
||||
|
||||
uncompressed=`echo $tarfile | sed 's/\(\(\.tar\.gz\|\.tar\.bz2\|\.tar\.xz\)\|\(\.tgz\|\.tbz2\)\)$//'`
|
||||
|
||||
case `echo $tarfile | sed 's/^.*\.//'` in
|
||||
bz2|tbz2) UNZIPPER=$BZIP ;;
|
||||
xz) UNZIPPER=$XZ ;;
|
||||
gz|tgz|*) UNZIPPER=$ZCAT ;;
|
||||
bz2|tbz2) UNZIPPER=$BZIP ;;
|
||||
xz) UNZIPPER=$XZ ;;
|
||||
gz|tgz|*) UNZIPPER=$ZCAT ;;
|
||||
esac
|
||||
|
||||
if [ ! -d $tarfile ]; then
|
||||
if [ ! -f $tarfile ]; then
|
||||
rm -fr $uncompressed
|
||||
$DOWNLOAD_CMD $base$tarfile
|
||||
if [ ! -f $tarfile ]; then
|
||||
rm -fr $uncompressed
|
||||
$DOWNLOAD_CMD $base$tarfile
|
||||
if [ ! -f $tarfile ]; then
|
||||
echo cannot find $tarfile
|
||||
exit 1
|
||||
fi
|
||||
fi
|
||||
if [ ! -d $uncompressed ]; then
|
||||
$UNZIPPER -c -d $tarfile | $TAR -xf -
|
||||
echo cannot find $tarfile
|
||||
exit 1
|
||||
fi
|
||||
fi
|
||||
if [ ! -d $uncompressed ]; then
|
||||
$UNZIPPER -c -d $tarfile | $TAR -xf -
|
||||
fi
|
||||
fi
|
||||
|
||||
exit 0
|
||||
|
|
|
@ -1,132 +1,18 @@
|
|||
#applications/mod_abstraction
|
||||
#applications/mod_avmd
|
||||
#applications/mod_blacklist
|
||||
#applications/mod_callcenter
|
||||
#applications/mod_cidlookup
|
||||
applications/mod_cluechoo
|
||||
applications/mod_commands
|
||||
applications/mod_conference
|
||||
#applications/mod_curl
|
||||
applications/mod_db
|
||||
#applications/mod_directory
|
||||
#applications/mod_distributor
|
||||
applications/mod_dptools
|
||||
#applications/mod_easyroute
|
||||
applications/mod_enum
|
||||
applications/mod_esf
|
||||
#applications/mod_esl
|
||||
applications/mod_expr
|
||||
applications/mod_fifo
|
||||
#applications/mod_fsk
|
||||
applications/mod_fsv
|
||||
applications/mod_hash
|
||||
applications/mod_httapi
|
||||
#applications/mod_http_cache
|
||||
#applications/mod_ladspa
|
||||
#applications/mod_lcr
|
||||
#applications/mod_memcache
|
||||
#applications/mod_mongo
|
||||
#applications/mod_nibblebill
|
||||
#applications/mod_osp
|
||||
#applications/mod_redis
|
||||
#applications/mod_rss
|
||||
applications/mod_sms
|
||||
#applications/mod_snapshot
|
||||
#applications/mod_snipe_hunt
|
||||
#applications/mod_snom
|
||||
#applications/mod_soundtouch
|
||||
applications/mod_spandsp
|
||||
#applications/mod_spy
|
||||
#applications/mod_stress
|
||||
applications/mod_valet_parking
|
||||
#applications/mod_vmd
|
||||
applications/mod_voicemail
|
||||
#applications/mod_voicemail_ivr
|
||||
#asr_tts/mod_cepstral
|
||||
#asr_tts/mod_flite
|
||||
#asr_tts/mod_pocketsphinx
|
||||
#asr_tts/mod_tts_commandline
|
||||
#asr_tts/mod_unimrcp
|
||||
codecs/mod_amr
|
||||
#codecs/mod_amrwb
|
||||
codecs/mod_bv
|
||||
#codecs/mod_celt
|
||||
#codecs/mod_codec2
|
||||
#codecs/mod_com_g729
|
||||
#codecs/mod_dahdi_codec
|
||||
codecs/mod_g723_1
|
||||
codecs/mod_g729
|
||||
codecs/mod_h26x
|
||||
codecs/mod_ilbc
|
||||
#codecs/mod_isac
|
||||
#codecs/mod_opus
|
||||
#codecs/mod_sangoma_codec
|
||||
#codecs/mod_silk
|
||||
codecs/mod_siren
|
||||
codecs/mod_speex
|
||||
dialplans/mod_dialplan_asterisk
|
||||
#dialplans/mod_dialplan_directory
|
||||
dialplans/mod_dialplan_xml
|
||||
#directories/mod_ldap
|
||||
#endpoints/mod_alsa
|
||||
#endpoints/mod_dingaling
|
||||
#endpoints/mod_h323
|
||||
#endpoints/mod_khomp
|
||||
endpoints/mod_loopback
|
||||
#endpoints/mod_opal
|
||||
#endpoints/mod_portaudio
|
||||
#endpoints/mod_rtmp
|
||||
#endpoints/mod_skinny
|
||||
#endpoints/mod_skypopen
|
||||
endpoints/mod_sofia
|
||||
event_handlers/mod_cdr_csv
|
||||
#event_handlers/mod_cdr_mongodb
|
||||
#event_handlers/mod_cdr_pg_csv
|
||||
event_handlers/mod_cdr_sqlite
|
||||
#event_handlers/mod_erlang_event
|
||||
#event_handlers/mod_event_multicast
|
||||
event_handlers/mod_event_socket
|
||||
#event_handlers/mod_event_zmq
|
||||
#event_handlers/mod_radius_cdr
|
||||
#event_handlers/mod_snmp
|
||||
formats/mod_local_stream
|
||||
formats/mod_native_file
|
||||
#formats/mod_portaudio_stream
|
||||
#formats/mod_shell_stream
|
||||
#formats/mod_shout
|
||||
formats/mod_sndfile
|
||||
formats/mod_tone_stream
|
||||
#languages/mod_java
|
||||
languages/mod_lua
|
||||
#languages/mod_managed
|
||||
#languages/mod_perl
|
||||
#languages/mod_python
|
||||
languages/mod_spidermonkey
|
||||
#languages/mod_yaml
|
||||
loggers/mod_console
|
||||
loggers/mod_logfile
|
||||
loggers/mod_syslog
|
||||
#say/mod_say_de
|
||||
say/mod_say_en
|
||||
#say/mod_say_es
|
||||
#say/mod_say_fr
|
||||
#say/mod_say_he
|
||||
#say/mod_say_hu
|
||||
#say/mod_say_it
|
||||
#say/mod_say_nl
|
||||
#say/mod_say_pt
|
||||
#say/mod_say_ru
|
||||
#say/mod_say_th
|
||||
#say/mod_say_zh
|
||||
#timers/mod_posix_timer
|
||||
#timers/mod_timerfd
|
||||
applications/mod_dptools
|
||||
applications/mod_commands
|
||||
applications/mod_hash
|
||||
applications/mod_spandsp
|
||||
applications/mod_distributor
|
||||
dialplans/mod_dialplan_xml
|
||||
endpoints/mod_sofia
|
||||
endpoints/mod_opal
|
||||
endpoints/mod_media_gateway
|
||||
../../libs/freetdm/mod_freetdm
|
||||
xml_int/mod_xml_cdr
|
||||
#xml_int/mod_xml_curl
|
||||
#xml_int/mod_xml_ldap
|
||||
xml_int/mod_xml_rpc
|
||||
|
||||
#../../libs/freetdm/mod_freetdm
|
||||
#../../libs/openzap/mod_openzap
|
||||
|
||||
## Experimental Modules (don't cry if they're broken)
|
||||
#../../contrib/mod/xml_int/mod_xml_odbc
|
||||
event_handlers/mod_event_socket
|
||||
codecs/mod_sangoma_codec
|
||||
event_handlers/mod_radius_cdr
|
||||
applications/mod_rad_auth
|
||||
|
|
|
@ -0,0 +1 @@
|
|||
1.2-rc3
|
|
@ -0,0 +1,16 @@
|
|||
#!/bin/sh
|
||||
##### -*- mode:shell-script; indent-tabs-mode:nil; sh-basic-offset:2 -*-
|
||||
|
||||
sdir="."
|
||||
[ -n "${0%/*}" ] && sdir="${0%/*}"
|
||||
. $sdir/../scripts/ci/common.sh
|
||||
|
||||
check_pwd
|
||||
check_input_ver_build $@
|
||||
in_ver="$1"
|
||||
if [ "$in_ver" = "auto" ]; then
|
||||
in_ver="$(cat build/next-release.txt)"
|
||||
fi
|
||||
eval $(parse_version "$in_ver")
|
||||
set_fs_ver "$gver" "$gmajor" "$gminor" "$gmicro" "$grev"
|
||||
|
|
@ -60,7 +60,7 @@
|
|||
<load module="mod_g723_1"/>
|
||||
<load module="mod_g729"/>
|
||||
<load module="mod_amr"/>
|
||||
<load module="mod_ilbc"/>
|
||||
<!--<load module="mod_ilbc"/>-->
|
||||
<load module="mod_speex"/>
|
||||
<load module="mod_h26x"/>
|
||||
<!--<load module="mod_siren"/>-->
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
<!-- http://wiki.freeswitch.org/wiki/Sofia_Configuration_Files -->
|
||||
<!-- http://wiki.freeswitch.org/wiki/Sofia_Configuration_Files -->
|
||||
<profile name="external">
|
||||
<!-- This profile is only for outbound registrations to providers -->
|
||||
<gateways>
|
||||
|
@ -29,10 +29,10 @@
|
|||
<!-- This could be set to "passive" -->
|
||||
<param name="manage-presence" value="passive"/>
|
||||
|
||||
<!-- used to share presence info across sofia profiles
|
||||
manage-presence needs to be set to passive on this profile
|
||||
if you want it to behave as if it were the internal profile
|
||||
for presence.
|
||||
<!-- used to share presence info across sofia profiles
|
||||
manage-presence needs to be set to passive on this profile
|
||||
if you want it to behave as if it were the internal profile
|
||||
for presence.
|
||||
-->
|
||||
<!-- Name of the db to use for this profile -->
|
||||
<param name="dbname" value="$${domain}"/>
|
||||
|
@ -47,8 +47,10 @@
|
|||
<param name="nonce-ttl" value="60"/>
|
||||
<param name="auth-calls" value="false"/>
|
||||
<param name="rtp-timeout-sec" value="1800"/>
|
||||
<param name="inbound-late-negotiation" value="true"/>
|
||||
<param name="inbound-zrtp-passthru" value="true"/>
|
||||
<!--
|
||||
DO NOT USE HOSTNAMES, ONLY IP ADDRESSES IN THESE SETTINGS!
|
||||
DO NOT USE HOSTNAMES, ONLY IP ADDRESSES IN THESE SETTINGS!
|
||||
-->
|
||||
<param name="rtp-ip" value="$${local_ip_v4}"/>
|
||||
<param name="sip-ip" value="$${local_ip_v4}"/>
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
<!--/// domain to use in from: *optional* same as realm, if blank ///-->
|
||||
<!--<param name="from-domain" value="asterlink.com"/>-->
|
||||
<!--/// account password *required* ///-->
|
||||
<!--<param name="password" value="2007"/>-->
|
||||
<!--<param name="password" value="2007"/>-->
|
||||
<!--/// extension for inbound calls: *optional* same as username, if blank ///-->
|
||||
<!--<param name="extension" value="cluecon"/>-->
|
||||
<!--/// proxy host: *optional* same as realm, if blank ///-->
|
||||
|
|
|
@ -53,36 +53,39 @@
|
|||
<param name="tls-cert-dir" value="$${internal_ssl_dir}"/>
|
||||
<!-- TLS version ("sslv23" (default), "tlsv1"). NOTE: Phones may not work with TLSv1 -->
|
||||
<param name="tls-version" value="$${sip_tls_version}"/>
|
||||
|
||||
|
||||
<!--If you don't want to pass through timestampes from 1 RTP call to another (on a per call basis with rtp_rewrite_timestamps chanvar)-->
|
||||
<!--<param name="rtp-rewrite-timestamps" value="true"/>-->
|
||||
<!--<param name="pass-rfc2833" value="true"/>-->
|
||||
<!--If you have ODBC support and a working dsn you can use it instead of SQLite-->
|
||||
<!--<param name="odbc-dsn" value="dsn:user:pass"/>-->
|
||||
|
||||
|
||||
<!--Uncomment to set all inbound calls to no media mode-->
|
||||
<!--<param name="inbound-bypass-media" value="true"/>-->
|
||||
|
||||
<!--Uncomment to set all inbound calls to proxy media mode-->
|
||||
<!--<param name="inbound-proxy-media" value="true"/>-->
|
||||
|
||||
<!--Uncomment to let calls hit the dialplan *before* you decide if the codec is ok-->
|
||||
<!--<param name="inbound-late-negotiation" value="true"/>-->
|
||||
|
||||
|
||||
<!-- Let calls hit the dialplan before selecting codec for the a-leg -->
|
||||
<param name="inbound-late-negotiation" value="true"/>
|
||||
|
||||
<!-- Allow ZRTP clients to negotiate end-to-end security associations -->
|
||||
<param name="inbound-zrtp-passthru" value="true"/>
|
||||
|
||||
<!-- this lets anything register -->
|
||||
<!-- comment the next line and uncomment one or both of the other 2 lines for call authentication -->
|
||||
<!-- <param name="accept-blind-reg" value="true"/> -->
|
||||
|
||||
<!-- accept any authentication without actually checking (not a good feature for most people) -->
|
||||
<!-- <param name="accept-blind-auth" value="true"/> -->
|
||||
|
||||
|
||||
<!-- suppress CNG on this profile or per call with the 'suppress_cng' variable -->
|
||||
<!-- <param name="suppress-cng" value="true"/> -->
|
||||
|
||||
|
||||
<!--TTL for nonce in sip auth-->
|
||||
<param name="nonce-ttl" value="60"/>
|
||||
<!--Uncomment if you want to force the outbound leg of a bridge to only offer the codec
|
||||
that the originator is using-->
|
||||
<!--Uncomment if you want to force the outbound leg of a bridge to only offer the codec
|
||||
that the originator is using-->
|
||||
<!--<param name="disable-transcoding" value="true"/>-->
|
||||
<!-- Used for when phones respond to a challenged ACK with method INVITE in the hash -->
|
||||
<!--<param name="NDLB-broken-auth-hash" value="true"/>-->
|
||||
|
@ -128,4 +131,3 @@
|
|||
|
||||
</settings>
|
||||
</profile>
|
||||
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
<!--
|
||||
This is a sofia sip profile/user agent. This will service exactly one ip and port.
|
||||
In FreeSWITCH you can run multiple sip user agents on their own ip and port.
|
||||
|
||||
|
||||
When you hear someone say "sofia profile" this is what they are talking about.
|
||||
-->
|
||||
|
||||
|
@ -16,24 +16,24 @@
|
|||
<gateways>
|
||||
<X-PRE-PROCESS cmd="include" data="internal/*.xml"/>
|
||||
</gateways>
|
||||
|
||||
|
||||
<domains>
|
||||
<!-- indicator to parse the directory for domains with parse="true" to get gateways-->
|
||||
<!--<domain name="$${domain}" parse="true"/>-->
|
||||
<!-- indicator to parse the directory for domains with parse="true" to get gateways and alias every domain to this profile -->
|
||||
<!--<domain name="all" alias="true" parse="true"/>-->
|
||||
<domain name="all" alias="true" parse="false"/>
|
||||
<domain name="all" alias="true" parse="false"/>
|
||||
</domains>
|
||||
|
||||
|
||||
<settings>
|
||||
<!--
|
||||
When calls are in no media this will bring them back to media
|
||||
when you press the hold button.
|
||||
When calls are in no media this will bring them back to media
|
||||
when you press the hold button.
|
||||
-->
|
||||
<!--<param name="media-option" value="resume-media-on-hold"/> -->
|
||||
<!--
|
||||
This will allow a call after an attended transfer go back to
|
||||
bypass media after an attended transfer.
|
||||
This will allow a call after an attended transfer go back to
|
||||
bypass media after an attended transfer.
|
||||
-->
|
||||
<!--<param name="media-option" value="bypass-media-after-att-xfer"/>-->
|
||||
<!-- <param name="user-agent-string" value="FreeSWITCH Rocks!"/> -->
|
||||
|
@ -63,7 +63,7 @@
|
|||
<!--<param name="dtmf-type" value="info"/>-->
|
||||
<param name="record-template" value="$${base_dir}/recordings/${caller_id_number}.${target_domain}.${strftime(%Y-%m-%d-%H-%M-%S)}.wav"/>
|
||||
|
||||
|
||||
|
||||
<!-- This setting is for AAL2 bitpacking on G726 -->
|
||||
<!-- <param name="bitpacking" value="aal2"/> -->
|
||||
<!--max number of open dialogs in proceeding -->
|
||||
|
@ -88,36 +88,39 @@
|
|||
<param name="tls-cert-dir" value="$${internal_ssl_dir}"/>
|
||||
<!-- TLS version ("sslv23" (default), "tlsv1"). NOTE: Phones may not work with TLSv1 -->
|
||||
<param name="tls-version" value="$${sip_tls_version}"/>
|
||||
|
||||
|
||||
<!--If you don't want to pass through timestamps from 1 RTP call to another (on a per call basis with rtp_rewrite_timestamps chanvar)-->
|
||||
<!--<param name="rtp-rewrite-timestamps" value="true"/>-->
|
||||
<!--<param name="pass-rfc2833" value="true"/>-->
|
||||
<!--If you have ODBC support and a working dsn you can use it instead of SQLite-->
|
||||
<!--<param name="odbc-dsn" value="dsn:user:pass"/>-->
|
||||
|
||||
|
||||
<!--Uncomment to set all inbound calls to no media mode-->
|
||||
<!--<param name="inbound-bypass-media" value="true"/>-->
|
||||
|
||||
<!--Uncomment to set all inbound calls to proxy media mode-->
|
||||
<!--<param name="inbound-proxy-media" value="true"/>-->
|
||||
|
||||
<!--Uncomment to let calls hit the dialplan *before* you decide if the codec is ok-->
|
||||
<!--<param name="inbound-late-negotiation" value="true"/>-->
|
||||
|
||||
|
||||
<!-- Let calls hit the dialplan before selecting codec for the a-leg -->
|
||||
<param name="inbound-late-negotiation" value="true"/>
|
||||
|
||||
<!-- Allow ZRTP clients to negotiate end-to-end security associations -->
|
||||
<param name="inbound-zrtp-passthru" value="true"/>
|
||||
|
||||
<!-- this lets anything register -->
|
||||
<!-- comment the next line and uncomment one or both of the other 2 lines for call authentication -->
|
||||
<!-- <param name="accept-blind-reg" value="true"/> -->
|
||||
|
||||
<!-- accept any authentication without actually checking (not a good feature for most people) -->
|
||||
<!-- <param name="accept-blind-auth" value="true"/> -->
|
||||
|
||||
|
||||
<!-- suppress CNG on this profile or per call with the 'suppress_cng' variable -->
|
||||
<!-- <param name="suppress-cng" value="true"/> -->
|
||||
|
||||
|
||||
<!--TTL for nonce in sip auth-->
|
||||
<param name="nonce-ttl" value="60"/>
|
||||
<!--Uncomment if you want to force the outbound leg of a bridge to only offer the codec
|
||||
that the originator is using-->
|
||||
<!--Uncomment if you want to force the outbound leg of a bridge to only offer the codec
|
||||
that the originator is using-->
|
||||
<!--<param name="disable-transcoding" value="true"/>-->
|
||||
<!-- Used for when phones respond to a challenged ACK with method INVITE in the hash -->
|
||||
<!--<param name="NDLB-broken-auth-hash" value="true"/>-->
|
||||
|
@ -138,7 +141,7 @@
|
|||
<!-- <param name="vad" value="out"/> -->
|
||||
<!-- <param name="vad" value="both"/> -->
|
||||
<!--<param name="alias" value="sip:10.0.1.251:5555"/>-->
|
||||
|
||||
|
||||
<!--all inbound reg will look in this domain for the users -->
|
||||
<param name="force-register-domain" value="$${domain}"/>
|
||||
<!--all inbound reg will stored in the db using this domain -->
|
||||
|
@ -158,24 +161,24 @@
|
|||
<!--<param name="disable-transfer" value="true"/>-->
|
||||
<!--<param name="disable-register" value="true"/>-->
|
||||
|
||||
<!-- enable-3pcc can be set to either 'true' or 'proxy', true accepts the call right away, proxy waits until the call has been answered then sends accepts -->
|
||||
<!-- enable-3pcc can be set to either 'true' or 'proxy', true accepts the call right away, proxy waits until the call has been answered then sends accepts -->
|
||||
<!--<param name="enable-3pcc" value="true"/>-->
|
||||
|
||||
|
||||
<!-- use at your own risk or if you know what this does.-->
|
||||
<!--<param name="NDLB-force-rport" value="true"/>-->
|
||||
<!--
|
||||
Choose the realm challenge key. Default is auto_to if not set.
|
||||
|
||||
auto_from - uses the from field as the value for the sip realm.
|
||||
auto_to - uses the to field as the value for the sip realm.
|
||||
<anyvalue> - you can input any value to use for the sip realm.
|
||||
Choose the realm challenge key. Default is auto_to if not set.
|
||||
|
||||
If you want URL dialing to work you'll want to set this to auto_from.
|
||||
|
||||
If you use any other value besides auto_to or auto_from you'll loose
|
||||
the ability to do multiple domains.
|
||||
|
||||
Note: comment out to restore the behavior before 2008-09-29
|
||||
auto_from - uses the from field as the value for the sip realm.
|
||||
auto_to - uses the to field as the value for the sip realm.
|
||||
<anyvalue> - you can input any value to use for the sip realm.
|
||||
|
||||
If you want URL dialing to work you'll want to set this to auto_from.
|
||||
|
||||
If you use any other value besides auto_to or auto_from you'll loose
|
||||
the ability to do multiple domains.
|
||||
|
||||
Note: comment out to restore the behavior before 2008-09-29
|
||||
|
||||
-->
|
||||
<param name="challenge-realm" value="auto_from"/>
|
||||
|
@ -186,4 +189,3 @@
|
|||
<!--<param name="outbound-use-uuid-as-callid" value="true"/>-->
|
||||
</settings>
|
||||
</profile>
|
||||
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
<!--/// domain to use in from: *optional* same as realm, if blank ///-->
|
||||
<!--<param name="from-domain" value="asterlink.com"/>-->
|
||||
<!--/// account password *required* ///-->
|
||||
<!--<param name="password" value="2007"/>-->
|
||||
<!--<param name="password" value="2007"/>-->
|
||||
<!--/// extension for inbound calls: *optional* same as username, if blank ///-->
|
||||
<!--<param name="extension" value="cluecon"/>-->
|
||||
<!--/// proxy host: *optional* same as realm, if blank ///-->
|
||||
|
|
|
@ -39,7 +39,7 @@
|
|||
<load module="mod_g723_1"/>
|
||||
<load module="mod_g729"/>
|
||||
<load module="mod_amr"/>
|
||||
<load module="mod_ilbc"/>
|
||||
<!--<load module="mod_ilbc"/>-->
|
||||
<load module="mod_speex"/>
|
||||
<load module="mod_h26x"/>
|
||||
<!--<load module="mod_siren"/>-->
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
<!-- http://wiki.freeswitch.org/wiki/Sofia_Configuration_Files -->
|
||||
<!-- http://wiki.freeswitch.org/wiki/Sofia_Configuration_Files -->
|
||||
<profile name="external">
|
||||
<!-- This profile is only for outbound registrations to providers -->
|
||||
<gateways>
|
||||
|
@ -7,7 +7,7 @@
|
|||
|
||||
<aliases>
|
||||
<alias name="outbound"/>
|
||||
<alias name="nat"/> <!-- for backwards compatibility -->
|
||||
<alias name="nat"/> <!-- for backwards compatibility -->
|
||||
</aliases>
|
||||
|
||||
<domains>
|
||||
|
@ -30,10 +30,10 @@
|
|||
<!-- This could be set to "passive" -->
|
||||
<param name="manage-presence" value="false"/>
|
||||
|
||||
<!-- used to share presence info across sofia profiles
|
||||
manage-presence needs to be set to passive on this profile
|
||||
if you want it to behave as if it were the internal profile
|
||||
for presence.
|
||||
<!-- used to share presence info across sofia profiles
|
||||
manage-presence needs to be set to passive on this profile
|
||||
if you want it to behave as if it were the internal profile
|
||||
for presence.
|
||||
-->
|
||||
<!-- Name of the db to use for this profile -->
|
||||
<!--<param name="dbname" value="share_presence"/>-->
|
||||
|
@ -48,8 +48,10 @@
|
|||
<param name="nonce-ttl" value="60"/>
|
||||
<param name="auth-calls" value="false"/>
|
||||
<param name="rtp-timeout-sec" value="1800"/>
|
||||
<param name="inbound-late-negotiation" value="true"/>
|
||||
<param name="inbound-zrtp-passthru" value="true"/>
|
||||
<!--
|
||||
DO NOT USE HOSTNAMES, ONLY IP ADDRESSES IN THESE SETTINGS!
|
||||
DO NOT USE HOSTNAMES, ONLY IP ADDRESSES IN THESE SETTINGS!
|
||||
-->
|
||||
<param name="rtp-ip" value="$${local_ip_v4}"/>
|
||||
<param name="sip-ip" value="$${local_ip_v4}"/>
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
<!--/// domain to use in from: *optional* same as realm, if blank ///-->
|
||||
<!--<param name="from-domain" value="asterlink.com"/>-->
|
||||
<!--/// account password *required* ///-->
|
||||
<!--<param name="password" value="2007"/>-->
|
||||
<!--<param name="password" value="2007"/>-->
|
||||
<!--/// extension for inbound calls: *optional* same as username, if blank ///-->
|
||||
<!--<param name="extension" value="cluecon"/>-->
|
||||
<!--/// proxy host: *optional* same as realm, if blank ///-->
|
||||
|
|
|
@ -53,36 +53,39 @@
|
|||
<param name="tls-cert-dir" value="$${internal_ssl_dir}"/>
|
||||
<!-- TLS version ("sslv23" (default), "tlsv1"). NOTE: Phones may not work with TLSv1 -->
|
||||
<param name="tls-version" value="$${sip_tls_version}"/>
|
||||
|
||||
|
||||
<!--If you don't want to pass through timestampes from 1 RTP call to another (on a per call basis with rtp_rewrite_timestamps chanvar)-->
|
||||
<!--<param name="rtp-rewrite-timestamps" value="true"/>-->
|
||||
<!--<param name="pass-rfc2833" value="true"/>-->
|
||||
<!--If you have ODBC support and a working dsn you can use it instead of SQLite-->
|
||||
<!--<param name="odbc-dsn" value="dsn:user:pass"/>-->
|
||||
|
||||
|
||||
<!--Uncomment to set all inbound calls to no media mode-->
|
||||
<!--<param name="inbound-bypass-media" value="true"/>-->
|
||||
|
||||
<!--Uncomment to set all inbound calls to proxy media mode-->
|
||||
<!--<param name="inbound-proxy-media" value="true"/>-->
|
||||
|
||||
<!--Uncomment to let calls hit the dialplan *before* you decide if the codec is ok-->
|
||||
<!--<param name="inbound-late-negotiation" value="true"/>-->
|
||||
|
||||
|
||||
<!-- Let calls hit the dialplan before selecting codec for the a-leg -->
|
||||
<param name="inbound-late-negotiation" value="true"/>
|
||||
|
||||
<!-- Allow ZRTP clients to negotiate end-to-end security associations -->
|
||||
<param name="inbound-zrtp-passthru" value="true"/>
|
||||
|
||||
<!-- this lets anything register -->
|
||||
<!-- comment the next line and uncomment one or both of the other 2 lines for call authentication -->
|
||||
<!-- <param name="accept-blind-reg" value="true"/> -->
|
||||
|
||||
<!-- accept any authentication without actually checking (not a good feature for most people) -->
|
||||
<!-- <param name="accept-blind-auth" value="true"/> -->
|
||||
|
||||
|
||||
<!-- suppress CNG on this profile or per call with the 'suppress_cng' variable -->
|
||||
<!-- <param name="suppress-cng" value="true"/> -->
|
||||
|
||||
|
||||
<!--TTL for nonce in sip auth-->
|
||||
<param name="nonce-ttl" value="60"/>
|
||||
<!--Uncomment if you want to force the outbound leg of a bridge to only offer the codec
|
||||
that the originator is using-->
|
||||
<!--Uncomment if you want to force the outbound leg of a bridge to only offer the codec
|
||||
that the originator is using-->
|
||||
<!--<param name="disable-transcoding" value="true"/>-->
|
||||
<!-- Used for when phones respond to a challenged ACK with method INVITE in the hash -->
|
||||
<!--<param name="NDLB-broken-auth-hash" value="true"/>-->
|
||||
|
@ -128,4 +131,3 @@
|
|||
|
||||
</settings>
|
||||
</profile>
|
||||
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
<!--
|
||||
This is a sofia sip profile/user agent. This will service exactly one ip and port.
|
||||
In FreeSWITCH you can run multiple sip user agents on their own ip and port.
|
||||
|
||||
|
||||
When you hear someone say "sofia profile" this is what they are talking about.
|
||||
-->
|
||||
|
||||
|
@ -15,24 +15,24 @@
|
|||
<gateways>
|
||||
<X-PRE-PROCESS cmd="include" data="internal/*.xml"/>
|
||||
</gateways>
|
||||
|
||||
|
||||
<domains>
|
||||
<!-- indicator to parse the directory for domains with parse="true" to get gateways-->
|
||||
<!--<domain name="$${domain}" parse="true"/>-->
|
||||
<!-- indicator to parse the directory for domains with parse="true" to get gateways and alias every domain to this profile -->
|
||||
<!--<domain name="all" alias="true" parse="true"/>-->
|
||||
<domain name="all" alias="true" parse="false"/>
|
||||
<domain name="all" alias="true" parse="false"/>
|
||||
</domains>
|
||||
|
||||
|
||||
<settings>
|
||||
<!--
|
||||
When calls are in no media this will bring them back to media
|
||||
when you press the hold button.
|
||||
When calls are in no media this will bring them back to media
|
||||
when you press the hold button.
|
||||
-->
|
||||
<!--<param name="media-option" value="resume-media-on-hold"/> -->
|
||||
<!--
|
||||
This will allow a call after an attended transfer go back to
|
||||
bypass media after an attended transfer.
|
||||
This will allow a call after an attended transfer go back to
|
||||
bypass media after an attended transfer.
|
||||
-->
|
||||
<!--<param name="media-option" value="bypass-media-after-att-xfer"/>-->
|
||||
<!-- <param name="user-agent-string" value="FreeSWITCH Rocks!"/> -->
|
||||
|
@ -69,7 +69,7 @@
|
|||
<!--<param name="dbname" value="share_presence"/>-->
|
||||
<!--<param name="presence-hosts" value="$${domain}"/>-->
|
||||
<!-- ************************************************* -->
|
||||
|
||||
|
||||
<!-- This setting is for AAL2 bitpacking on G726 -->
|
||||
<!-- <param name="bitpacking" value="aal2"/> -->
|
||||
<!--max number of open dialogs in proceeding -->
|
||||
|
@ -94,36 +94,39 @@
|
|||
<param name="tls-cert-dir" value="$${internal_ssl_dir}"/>
|
||||
<!-- TLS version ("sslv23" (default), "tlsv1"). NOTE: Phones may not work with TLSv1 -->
|
||||
<param name="tls-version" value="$${sip_tls_version}"/>
|
||||
|
||||
|
||||
<!--If you don't want to pass through timestamps from 1 RTP call to another (on a per call basis with rtp_rewrite_timestamps chanvar)-->
|
||||
<!--<param name="rtp-rewrite-timestamps" value="true"/>-->
|
||||
<!--<param name="pass-rfc2833" value="true"/>-->
|
||||
<!--If you have ODBC support and a working dsn you can use it instead of SQLite-->
|
||||
<!--<param name="odbc-dsn" value="dsn:user:pass"/>-->
|
||||
|
||||
|
||||
<!--Uncomment to set all inbound calls to no media mode-->
|
||||
<!--<param name="inbound-bypass-media" value="true"/>-->
|
||||
|
||||
<!--Uncomment to set all inbound calls to proxy media mode-->
|
||||
<!--<param name="inbound-proxy-media" value="true"/>-->
|
||||
|
||||
<!--Uncomment to let calls hit the dialplan *before* you decide if the codec is ok-->
|
||||
<!--<param name="inbound-late-negotiation" value="true"/>-->
|
||||
|
||||
|
||||
<!-- Let calls hit the dialplan before selecting codec for the a-leg -->
|
||||
<param name="inbound-late-negotiation" value="true"/>
|
||||
|
||||
<!-- Allow ZRTP clients to negotiate end-to-end security associations -->
|
||||
<param name="inbound-zrtp-passthru" value="true"/>
|
||||
|
||||
<!-- this lets anything register -->
|
||||
<!-- comment the next line and uncomment one or both of the other 2 lines for call authentication -->
|
||||
<!-- <param name="accept-blind-reg" value="true"/> -->
|
||||
|
||||
<!-- accept any authentication without actually checking (not a good feature for most people) -->
|
||||
<!-- <param name="accept-blind-auth" value="true"/> -->
|
||||
|
||||
|
||||
<!-- suppress CNG on this profile or per call with the 'suppress_cng' variable -->
|
||||
<!-- <param name="suppress-cng" value="true"/> -->
|
||||
|
||||
|
||||
<!--TTL for nonce in sip auth-->
|
||||
<param name="nonce-ttl" value="60"/>
|
||||
<!--Uncomment if you want to force the outbound leg of a bridge to only offer the codec
|
||||
that the originator is using-->
|
||||
<!--Uncomment if you want to force the outbound leg of a bridge to only offer the codec
|
||||
that the originator is using-->
|
||||
<!--<param name="disable-transcoding" value="true"/>-->
|
||||
<!-- Used for when phones respond to a challenged ACK with method INVITE in the hash -->
|
||||
<!--<param name="NDLB-broken-auth-hash" value="true"/>-->
|
||||
|
@ -154,24 +157,24 @@
|
|||
<!--<param name="disable-transfer" value="true"/>-->
|
||||
<!--<param name="disable-register" value="true"/>-->
|
||||
|
||||
<!-- enable-3pcc can be set to either 'true' or 'proxy', true accepts the call right away, proxy waits until the call has been answered then sends accepts -->
|
||||
<!-- enable-3pcc can be set to either 'true' or 'proxy', true accepts the call right away, proxy waits until the call has been answered then sends accepts -->
|
||||
<!--<param name="enable-3pcc" value="true"/>-->
|
||||
|
||||
|
||||
<!-- use at your own risk or if you know what this does.-->
|
||||
<!--<param name="NDLB-force-rport" value="true"/>-->
|
||||
<!--
|
||||
Choose the realm challenge key. Default is auto_to if not set.
|
||||
|
||||
auto_from - uses the from field as the value for the sip realm.
|
||||
auto_to - uses the to field as the value for the sip realm.
|
||||
<anyvalue> - you can input any value to use for the sip realm.
|
||||
Choose the realm challenge key. Default is auto_to if not set.
|
||||
|
||||
If you want URL dialing to work you'll want to set this to auto_from.
|
||||
|
||||
If you use any other value besides auto_to or auto_from you'll loose
|
||||
the ability to do multiple domains.
|
||||
|
||||
Note: comment out to restore the behavior before 2008-09-29
|
||||
auto_from - uses the from field as the value for the sip realm.
|
||||
auto_to - uses the to field as the value for the sip realm.
|
||||
<anyvalue> - you can input any value to use for the sip realm.
|
||||
|
||||
If you want URL dialing to work you'll want to set this to auto_from.
|
||||
|
||||
If you use any other value besides auto_to or auto_from you'll loose
|
||||
the ability to do multiple domains.
|
||||
|
||||
Note: comment out to restore the behavior before 2008-09-29
|
||||
|
||||
-->
|
||||
<param name="challenge-realm" value="auto_from"/>
|
||||
|
@ -182,4 +185,3 @@
|
|||
<!--<param name="outbound-use-uuid-as-callid" value="true"/>-->
|
||||
</settings>
|
||||
</profile>
|
||||
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
<!--/// domain to use in from: *optional* same as realm, if blank ///-->
|
||||
<!--<param name="from-domain" value="asterlink.com"/>-->
|
||||
<!--/// account password *required* ///-->
|
||||
<!--<param name="password" value="2007"/>-->
|
||||
<!--<param name="password" value="2007"/>-->
|
||||
<!--/// extension for inbound calls: *optional* same as username, if blank ///-->
|
||||
<!--<param name="extension" value="cluecon"/>-->
|
||||
<!--/// proxy host: *optional* same as realm, if blank ///-->
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
<X-PRE-PROCESS cmd="set" data="auto_answer=false"/>
|
||||
<X-PRE-PROCESS cmd="set" data="domain=$${local_ip_v4}"/>
|
||||
<X-PRE-PROCESS cmd="set" data="hold_music=local_stream://moh"/>
|
||||
<X-PRE-PROCESS cmd="set" data="codec_prefs=CELT@48000h,G7221@32000h,G7221@16000h,G722,PCMU,PCMA,GSM"/>
|
||||
<X-PRE-PROCESS cmd="set" data="codec_prefs=CELT@48000h,G722,PCMU,PCMA,GSM"/>
|
||||
<X-PRE-PROCESS cmd="set" data="external_rtp_ip=stun:stun.freeswitch.org"/>
|
||||
<X-PRE-PROCESS cmd="set" data="external_sip_ip=stun:stun.freeswitch.org"/>
|
||||
<X-PRE-PROCESS cmd="set" data="outbound_caller_name=FreeSWITCH"/>
|
||||
|
@ -86,10 +86,8 @@
|
|||
<load module="mod_dptools"/>
|
||||
<load module="mod_dialplan_xml"/>
|
||||
<load module="mod_voipcodecs"/>
|
||||
<load module="mod_ilbc"/>
|
||||
<load module="mod_speex"/>
|
||||
<load module="mod_celt"/>
|
||||
<load module="mod_siren"/>
|
||||
<load module="mod_sndfile"/>
|
||||
<load module="mod_tone_stream"/>
|
||||
<load module="mod_local_stream"/>
|
||||
|
|
|
@ -16,6 +16,7 @@
|
|||
<!-- <load module="mod_xml_rpc"/> -->
|
||||
<!-- <load module="mod_xml_curl"/> -->
|
||||
<!-- <load module="mod_xml_cdr"/> -->
|
||||
<!-- <load module="mod_xml_scgi"/> -->
|
||||
|
||||
<!-- Event Handlers -->
|
||||
<load module="mod_cdr_csv"/>
|
||||
|
@ -62,6 +63,7 @@
|
|||
<load module="mod_valet_parking"/>
|
||||
<!--<load module="mod_fsk"/>-->
|
||||
<!--<load module="mod_spy"/>-->
|
||||
<!--<load module="mod_random"/>-->
|
||||
<load module="mod_httapi"/>
|
||||
|
||||
<!-- SNOM Module -->
|
||||
|
@ -80,10 +82,10 @@
|
|||
<load module="mod_g723_1"/>
|
||||
<load module="mod_g729"/>
|
||||
<load module="mod_amr"/>
|
||||
<load module="mod_ilbc"/>
|
||||
<!--<load module="mod_ilbc"/>-->
|
||||
<load module="mod_speex"/>
|
||||
<load module="mod_h26x"/>
|
||||
<load module="mod_siren"/>
|
||||
<!--<load module="mod_siren"/>-->
|
||||
<!--<load module="mod_isac"/>-->
|
||||
<!--<load module="mod_celt"/>-->
|
||||
<!--<load module="mod_opus"/>-->
|
||||
|
|
|
@ -0,0 +1,12 @@
|
|||
<configuration name="xml_scgi.conf" description="SCGI XML Gateway">
|
||||
<bindings>
|
||||
<binding name="example">
|
||||
<!-- one or more |-delim of configuration|directory|dialplan -->
|
||||
<!-- <param name="host" value="127.0.0.1" bindings="dialplan"/> -->
|
||||
<!-- <param name="port" value="8080"/> -->
|
||||
<!-- <param name="timeout" value="10"/> -->
|
||||
<!-- one or more of these imply you want to pick the exact variables that are transmitted -->
|
||||
<!--<param name="enable-post-var" value="Unique-ID"/>-->
|
||||
</binding>
|
||||
</bindings>
|
||||
</configuration>
|
|
@ -29,7 +29,7 @@
|
|||
<macro name="voicemail_change_pass_success">
|
||||
<input pattern="(.*)">
|
||||
<match>
|
||||
<action function="play-file" data="ivr/ivr-Thank_you.wav"/>
|
||||
<action function="play-file" data="voicemail/vm-password_has_been_changed.wav"/>
|
||||
</match>
|
||||
</input>
|
||||
</macro>
|
||||
|
@ -37,7 +37,7 @@
|
|||
<macro name="voicemail_change_pass_fail">
|
||||
<input pattern="(.*)">
|
||||
<match>
|
||||
<action function="play-file" data="voicemail/vm-fail_auth.wav"/>
|
||||
<action function="play-file" data="voicemail/vm-password_not_valid.wav"/>
|
||||
</match>
|
||||
</input>
|
||||
</macro>
|
||||
|
|
|
@ -1,14 +1,14 @@
|
|||
<profile name="external">
|
||||
<!-- http://wiki.freeswitch.org/wiki/Sofia_Configuration_Files -->
|
||||
<!-- http://wiki.freeswitch.org/wiki/Sofia_Configuration_Files -->
|
||||
<!-- This profile is only for outbound registrations to providers -->
|
||||
<gateways>
|
||||
<X-PRE-PROCESS cmd="include" data="external/*.xml"/>
|
||||
</gateways>
|
||||
|
||||
<aliases>
|
||||
<!--
|
||||
<alias name="outbound"/>
|
||||
<alias name="nat"/>
|
||||
<!--
|
||||
<alias name="outbound"/>
|
||||
<alias name="nat"/>
|
||||
-->
|
||||
</aliases>
|
||||
|
||||
|
@ -18,10 +18,10 @@
|
|||
|
||||
<settings>
|
||||
<param name="debug" value="0"/>
|
||||
<!-- If you want FreeSWITCH to shutdown if this profile fails to load, uncomment the next line. -->
|
||||
<!-- <param name="shutdown-on-fail" value="true"/> -->
|
||||
<!-- If you want FreeSWITCH to shutdown if this profile fails to load, uncomment the next line. -->
|
||||
<!-- <param name="shutdown-on-fail" value="true"/> -->
|
||||
<param name="sip-trace" value="no"/>
|
||||
<param name="sip-capture" value="no"/>
|
||||
<param name="sip-capture" value="no"/>
|
||||
<param name="rfc2833-pt" value="101"/>
|
||||
<!-- RFC 5626 : Send reg-id and sip.instance -->
|
||||
<!--<param name="enable-rfc-5626" value="true"/> -->
|
||||
|
@ -34,15 +34,15 @@
|
|||
<param name="hold-music" value="$${hold_music}"/>
|
||||
<param name="rtp-timer-name" value="soft"/>
|
||||
<!--<param name="enable-100rel" value="true"/>-->
|
||||
<!--<param name="disable-srv503" value="true"/>-->
|
||||
<!--<param name="disable-srv503" value="true"/>-->
|
||||
<!-- This could be set to "passive" -->
|
||||
<param name="local-network-acl" value="localnet.auto"/>
|
||||
<param name="manage-presence" value="false"/>
|
||||
|
||||
<!-- used to share presence info across sofia profiles
|
||||
manage-presence needs to be set to passive on this profile
|
||||
if you want it to behave as if it were the internal profile
|
||||
for presence.
|
||||
<!-- used to share presence info across sofia profiles
|
||||
manage-presence needs to be set to passive on this profile
|
||||
if you want it to behave as if it were the internal profile
|
||||
for presence.
|
||||
-->
|
||||
<!-- Name of the db to use for this profile -->
|
||||
<!--<param name="dbname" value="share_presence"/>-->
|
||||
|
@ -56,8 +56,10 @@
|
|||
<param name="inbound-codec-negotiation" value="generous"/>
|
||||
<param name="nonce-ttl" value="60"/>
|
||||
<param name="auth-calls" value="false"/>
|
||||
<param name="inbound-late-negotiation" value="true"/>
|
||||
<param name="inbound-zrtp-passthru" value="true"/>
|
||||
<!--
|
||||
DO NOT USE HOSTNAMES, ONLY IP ADDRESSES IN THESE SETTINGS!
|
||||
DO NOT USE HOSTNAMES, ONLY IP ADDRESSES IN THESE SETTINGS!
|
||||
-->
|
||||
<param name="rtp-ip" value="$${local_ip_v4}"/>
|
||||
<param name="sip-ip" value="$${local_ip_v4}"/>
|
||||
|
@ -90,6 +92,5 @@
|
|||
<param name="tls-verify-in-subjects" value=""/>
|
||||
<!-- TLS version ("sslv23" (default), "tlsv1"). NOTE: Phones may not work with TLSv1 -->
|
||||
<param name="tls-version" value="$${sip_tls_version}"/>
|
||||
|
||||
</settings>
|
||||
</profile>
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
<!--/// domain to use in from: *optional* same as realm, if blank ///-->
|
||||
<!--<param name="from-domain" value="asterlink.com"/>-->
|
||||
<!--/// account password *required* ///-->
|
||||
<!--<param name="password" value="2007"/>-->
|
||||
<!--<param name="password" value="2007"/>-->
|
||||
<!--/// extension for inbound calls: *optional* same as username, if blank ///-->
|
||||
<!--<param name="extension" value="cluecon"/>-->
|
||||
<!--/// proxy host: *optional* same as realm, if blank ///-->
|
||||
|
|
|
@ -54,36 +54,39 @@
|
|||
<param name="tls-cert-dir" value="$${internal_ssl_dir}"/>
|
||||
<!-- TLS version ("sslv23" (default), "tlsv1"). NOTE: Phones may not work with TLSv1 -->
|
||||
<param name="tls-version" value="$${sip_tls_version}"/>
|
||||
|
||||
|
||||
<!--If you don't want to pass through timestampes from 1 RTP call to another (on a per call basis with rtp_rewrite_timestamps chanvar)-->
|
||||
<!--<param name="rtp-rewrite-timestamps" value="true"/>-->
|
||||
<!--<param name="pass-rfc2833" value="true"/>-->
|
||||
<!--If you have ODBC support and a working dsn you can use it instead of SQLite-->
|
||||
<!--<param name="odbc-dsn" value="dsn:user:pass"/>-->
|
||||
|
||||
|
||||
<!--Uncomment to set all inbound calls to no media mode-->
|
||||
<!--<param name="inbound-bypass-media" value="true"/>-->
|
||||
|
||||
<!--Uncomment to set all inbound calls to proxy media mode-->
|
||||
<!--<param name="inbound-proxy-media" value="true"/>-->
|
||||
|
||||
<!--Uncomment to let calls hit the dialplan *before* you decide if the codec is ok-->
|
||||
<!--<param name="inbound-late-negotiation" value="true"/>-->
|
||||
|
||||
|
||||
<!-- Let calls hit the dialplan before selecting codec for the a-leg -->
|
||||
<param name="inbound-late-negotiation" value="true"/>
|
||||
|
||||
<!-- Allow ZRTP clients to negotiate end-to-end security associations -->
|
||||
<param name="inbound-zrtp-passthru" value="true"/>
|
||||
|
||||
<!-- this lets anything register -->
|
||||
<!-- comment the next line and uncomment one or both of the other 2 lines for call authentication -->
|
||||
<!-- <param name="accept-blind-reg" value="true"/> -->
|
||||
|
||||
<!-- accept any authentication without actually checking (not a good feature for most people) -->
|
||||
<!-- <param name="accept-blind-auth" value="true"/> -->
|
||||
|
||||
|
||||
<!-- suppress CNG on this profile or per call with the 'suppress_cng' variable -->
|
||||
<!-- <param name="suppress-cng" value="true"/> -->
|
||||
|
||||
|
||||
<!--TTL for nonce in sip auth-->
|
||||
<param name="nonce-ttl" value="60"/>
|
||||
<!--Uncomment if you want to force the outbound leg of a bridge to only offer the codec
|
||||
that the originator is using-->
|
||||
<!--Uncomment if you want to force the outbound leg of a bridge to only offer the codec
|
||||
that the originator is using-->
|
||||
<!--<param name="disable-transcoding" value="true"/>-->
|
||||
<!-- Used for when phones respond to a challenged ACK with method INVITE in the hash -->
|
||||
<!--<param name="NDLB-broken-auth-hash" value="true"/>-->
|
||||
|
@ -103,8 +106,8 @@
|
|||
<!-- <param name="vad" value="both"/> -->
|
||||
<!--<param name="alias" value="sip:10.0.1.251:5555"/>-->
|
||||
<!--
|
||||
These are enabled to make the default config work better out of the box.
|
||||
If you need more than ONE domain you'll need to not use these options.
|
||||
These are enabled to make the default config work better out of the box.
|
||||
If you need more than ONE domain you'll need to not use these options.
|
||||
|
||||
-->
|
||||
<!--all inbound reg will look in this domain for the users -->
|
||||
|
@ -121,10 +124,9 @@
|
|||
<!-- set to true to have the profile determine stun is not useful and turn it off globally-->
|
||||
<!--<param name="stun-auto-disable" value="true"/>-->
|
||||
|
||||
<!-- the following can be used as workaround with bogus SRV/NAPTR records -->
|
||||
<!--<param name="disable-srv" value="false" />-->
|
||||
<!--<param name="disable-naptr" value="false" />-->
|
||||
<!-- the following can be used as workaround with bogus SRV/NAPTR records -->
|
||||
<!--<param name="disable-srv" value="false" />-->
|
||||
<!--<param name="disable-naptr" value="false" />-->
|
||||
|
||||
</settings>
|
||||
</profile>
|
||||
|
||||
|
|
|
@ -2,30 +2,30 @@
|
|||
<!--
|
||||
This is a sofia sip profile/user agent. This will service exactly one ip and port.
|
||||
In FreeSWITCH you can run multiple sip user agents on their own ip and port.
|
||||
|
||||
|
||||
When you hear someone say "sofia profile" this is what they are talking about.
|
||||
-->
|
||||
|
||||
|
||||
<!-- http://wiki.freeswitch.org/wiki/Sofia_Configuration_Files -->
|
||||
<!--aliases are other names that will work as a valid profile name for this profile-->
|
||||
<aliases>
|
||||
<!--
|
||||
<alias name="default"/>
|
||||
<alias name="default"/>
|
||||
-->
|
||||
</aliases>
|
||||
<!-- Outbound Registrations -->
|
||||
<gateways>
|
||||
<X-PRE-PROCESS cmd="include" data="internal/*.xml"/>
|
||||
</gateways>
|
||||
|
||||
|
||||
<domains>
|
||||
<!-- indicator to parse the directory for domains with parse="true" to get gateways-->
|
||||
<!--<domain name="$${domain}" parse="true"/>-->
|
||||
<!-- indicator to parse the directory for domains with parse="true" to get gateways and alias every domain to this profile -->
|
||||
<!--<domain name="all" alias="true" parse="true"/>-->
|
||||
<domain name="all" alias="true" parse="false"/>
|
||||
<domain name="all" alias="true" parse="false"/>
|
||||
</domains>
|
||||
|
||||
|
||||
<settings>
|
||||
|
||||
|
||||
|
@ -33,31 +33,31 @@
|
|||
<!-- <param name="rtp-digit-delay" value="40"/>-->
|
||||
|
||||
<!--
|
||||
When calls are in no media this will bring them back to media
|
||||
when you press the hold button.
|
||||
When calls are in no media this will bring them back to media
|
||||
when you press the hold button.
|
||||
-->
|
||||
<!--<param name="media-option" value="resume-media-on-hold"/> -->
|
||||
<!--
|
||||
This will allow a call after an attended transfer go back to
|
||||
bypass media after an attended transfer.
|
||||
This will allow a call after an attended transfer go back to
|
||||
bypass media after an attended transfer.
|
||||
-->
|
||||
<!--<param name="media-option" value="bypass-media-after-att-xfer"/>-->
|
||||
<!-- <param name="user-agent-string" value="FreeSWITCH Rocks!"/> -->
|
||||
<param name="debug" value="0"/>
|
||||
<!-- If you want FreeSWITCH to shutdown if this profile fails to load, uncomment the next line. -->
|
||||
<!-- <param name="shutdown-on-fail" value="true"/> -->
|
||||
<!-- If you want FreeSWITCH to shutdown if this profile fails to load, uncomment the next line. -->
|
||||
<!-- <param name="shutdown-on-fail" value="true"/> -->
|
||||
<param name="sip-trace" value="no"/>
|
||||
<param name="sip-capture" value="no"/>
|
||||
|
||||
<!-- Use presence_map.conf.xml to convert extension regex to presence protos for routing -->
|
||||
<!-- <param name="presence-proto-lookup" value="true"/> -->
|
||||
|
||||
|
||||
|
||||
<!-- Don't be picky about negotiated DTMF just always offer 2833 and accept both 2833 and INFO -->
|
||||
<!--<param name="liberal-dtmf" value="true"/>-->
|
||||
|
||||
|
||||
<!--
|
||||
<!--
|
||||
Sometimes, in extremely rare edge cases, the Sofia SIP stack may stop
|
||||
responding. These options allow you to enable and control a watchdog
|
||||
on the Sofia SIP stack so that if it stops responding for the
|
||||
|
@ -70,7 +70,7 @@
|
|||
through the FreeSWITCH CLI either on an individual profile basis or
|
||||
globally for all profiles. So, if you run in an HA environment with a
|
||||
master and slave, you should use the CLI to make sure the watchdog is
|
||||
only enabled on the master.
|
||||
only enabled on the master.
|
||||
If such crash occurs, FreeSWITCH will dump core if allowed. The
|
||||
stacktrace will include function watchdog_triggered_abort().
|
||||
-->
|
||||
|
@ -106,26 +106,26 @@
|
|||
|
||||
<!--<param name="aggressive-nat-detection" value="true"/>-->
|
||||
<!--
|
||||
There are known issues (asserts and segfaults) when 100rel is enabled.
|
||||
It is not recommended to enable 100rel at this time.
|
||||
There are known issues (asserts and segfaults) when 100rel is enabled.
|
||||
It is not recommended to enable 100rel at this time.
|
||||
-->
|
||||
<!--<param name="enable-100rel" value="true"/>-->
|
||||
|
||||
<!-- uncomment if you don't wish to try a next SRV destination on 503 response -->
|
||||
<!-- RFC3263 Section 4.3 -->
|
||||
<!--<param name="disable-srv503" value="true"/>-->
|
||||
|
||||
<!-- RFC3263 Section 4.3 -->
|
||||
<!--<param name="disable-srv503" value="true"/>-->
|
||||
|
||||
<!-- Enable Compact SIP headers. -->
|
||||
<!--<param name="enable-compact-headers" value="true"/>-->
|
||||
<!--
|
||||
enable/disable session timers
|
||||
enable/disable session timers
|
||||
-->
|
||||
<!--<param name="enable-timer" value="false"/>-->
|
||||
<!--<param name="minimum-session-expires" value="120"/>-->
|
||||
<param name="apply-inbound-acl" value="domains"/>
|
||||
<!--
|
||||
This defines your local network, by default we detect your local network
|
||||
and create this localnet.auto ACL for this.
|
||||
This defines your local network, by default we detect your local network
|
||||
and create this localnet.auto ACL for this.
|
||||
-->
|
||||
<param name="local-network-acl" value="localnet.auto"/>
|
||||
<!--<param name="apply-register-acl" value="domains"/>-->
|
||||
|
@ -134,10 +134,10 @@
|
|||
|
||||
<!-- 'true' means every time 'first-only' means on the first register -->
|
||||
<!--<param name="send-message-query-on-register" value="true"/>-->
|
||||
|
||||
|
||||
<!-- 'true' means every time 'first-only' means on the first register -->
|
||||
<!--<param name="send-presence-on-register" value="first-only"/> -->
|
||||
|
||||
|
||||
|
||||
<!-- Caller-ID type (choose one, can be overridden by inbound call type and/or sip_cid_type channel variable -->
|
||||
<!-- Remote-Party-ID header -->
|
||||
|
@ -164,7 +164,7 @@
|
|||
<param name="presence-hosts" value="$${domain},$${local_ip_v4}"/>
|
||||
<param name="presence-privacy" value="$${presence_privacy}"/>
|
||||
<!-- ************************************************* -->
|
||||
|
||||
|
||||
<!-- This setting is for AAL2 bitpacking on G726 -->
|
||||
<!-- <param name="bitpacking" value="aal2"/> -->
|
||||
<!--max number of open dialogs in proceeding -->
|
||||
|
@ -203,39 +203,42 @@
|
|||
<!-- TLS version ("sslv23" (default), "tlsv1"). NOTE: Phones may not work with TLSv1 -->
|
||||
<param name="tls-version" value="$${sip_tls_version}"/>
|
||||
|
||||
<!-- turn on auto-flush during bridge (skip timer sleep when the socket already has data)
|
||||
(reduces delay on latent connections default true, must be disabled explicitly)-->
|
||||
<!-- turn on auto-flush during bridge (skip timer sleep when the socket already has data)
|
||||
(reduces delay on latent connections default true, must be disabled explicitly)-->
|
||||
<!--<param name="rtp-autoflush-during-bridge" value="false"/>-->
|
||||
|
||||
|
||||
<!--If you don't want to pass through timestamps from 1 RTP call to another (on a per call basis with rtp_rewrite_timestamps chanvar)-->
|
||||
<!--<param name="rtp-rewrite-timestamps" value="true"/>-->
|
||||
<!--<param name="pass-rfc2833" value="true"/>-->
|
||||
<!--If you have ODBC support and a working dsn you can use it instead of SQLite-->
|
||||
<!--<param name="odbc-dsn" value="dsn:user:pass"/>-->
|
||||
|
||||
|
||||
<!--Uncomment to set all inbound calls to no media mode-->
|
||||
<!--<param name="inbound-bypass-media" value="true"/>-->
|
||||
|
||||
<!--Uncomment to set all inbound calls to proxy media mode-->
|
||||
<!--<param name="inbound-proxy-media" value="true"/>-->
|
||||
|
||||
<!--Uncomment to let calls hit the dialplan *before* you decide if the codec is ok-->
|
||||
<!--<param name="inbound-late-negotiation" value="true"/>-->
|
||||
|
||||
|
||||
<!-- Let calls hit the dialplan before selecting codec for the a-leg -->
|
||||
<param name="inbound-late-negotiation" value="true"/>
|
||||
|
||||
<!-- Allow ZRTP clients to negotiate end-to-end security associations -->
|
||||
<param name="inbound-zrtp-passthru" value="true"/>
|
||||
|
||||
<!-- this lets anything register -->
|
||||
<!-- comment the next line and uncomment one or both of the other 2 lines for call authentication -->
|
||||
<!-- <param name="accept-blind-reg" value="true"/> -->
|
||||
|
||||
<!-- accept any authentication without actually checking (not a good feature for most people) -->
|
||||
<!-- <param name="accept-blind-auth" value="true"/> -->
|
||||
|
||||
|
||||
<!-- suppress CNG on this profile or per call with the 'suppress_cng' variable -->
|
||||
<!-- <param name="suppress-cng" value="true"/> -->
|
||||
|
||||
|
||||
<!--TTL for nonce in sip auth-->
|
||||
<param name="nonce-ttl" value="60"/>
|
||||
<!--Uncomment if you want to force the outbound leg of a bridge to only offer the codec
|
||||
that the originator is using-->
|
||||
<!--Uncomment if you want to force the outbound leg of a bridge to only offer the codec
|
||||
that the originator is using-->
|
||||
<!--<param name="disable-transcoding" value="true"/>-->
|
||||
<!-- Handle 302 Redirect in the dialplan -->
|
||||
<!--<param name="manual-redirect" value="true"/> -->
|
||||
|
@ -252,16 +255,16 @@
|
|||
<param name="inbound-reg-force-matching-username" value="true"/>
|
||||
<!-- on authed calls, authenticate *all* the packets not just invite -->
|
||||
<param name="auth-all-packets" value="false"/>
|
||||
|
||||
|
||||
<!-- external_sip_ip
|
||||
Used as the public IP address for SDP.
|
||||
Can be an one of:
|
||||
ip address - "12.34.56.78"
|
||||
a stun server lookup - "stun:stun.server.com"
|
||||
a DNS name - "host:host.server.com"
|
||||
auto - Use guessed ip.
|
||||
auto-nat - Use ip learned from NAT-PMP or UPNP
|
||||
-->
|
||||
Used as the public IP address for SDP.
|
||||
Can be an one of:
|
||||
ip address - "12.34.56.78"
|
||||
a stun server lookup - "stun:stun.server.com"
|
||||
a DNS name - "host:host.server.com"
|
||||
auto - Use guessed ip.
|
||||
auto-nat - Use ip learned from NAT-PMP or UPNP
|
||||
-->
|
||||
<param name="ext-rtp-ip" value="auto-nat"/>
|
||||
<param name="ext-sip-ip" value="auto-nat"/>
|
||||
|
||||
|
@ -274,8 +277,8 @@
|
|||
<!-- <param name="vad" value="both"/> -->
|
||||
<!--<param name="alias" value="sip:10.0.1.251:5555"/>-->
|
||||
<!--
|
||||
These are enabled to make the default config work better out of the box.
|
||||
If you need more than ONE domain you'll need to not use these options.
|
||||
These are enabled to make the default config work better out of the box.
|
||||
If you need more than ONE domain you'll need to not use these options.
|
||||
|
||||
-->
|
||||
<!--all inbound reg will look in this domain for the users -->
|
||||
|
@ -297,28 +300,27 @@
|
|||
<!--<param name="disable-transfer" value="true"/>-->
|
||||
<!--<param name="disable-register" value="true"/>-->
|
||||
|
||||
<!--
|
||||
enable-3pcc can be set to either 'true' or 'proxy', true accepts the call
|
||||
right away, proxy waits until the call has been answered then sends accepts
|
||||
<!--
|
||||
enable-3pcc can be set to either 'true' or 'proxy', true accepts the call
|
||||
right away, proxy waits until the call has been answered then sends accepts
|
||||
-->
|
||||
<!--<param name="enable-3pcc" value="true"/>-->
|
||||
|
||||
|
||||
<!-- use at your own risk or if you know what this does.-->
|
||||
<!--<param name="NDLB-force-rport" value="true"/>-->
|
||||
<!--
|
||||
Choose the realm challenge key. Default is auto_to if not set.
|
||||
|
||||
auto_from - uses the from field as the value for the sip realm.
|
||||
auto_to - uses the to field as the value for the sip realm.
|
||||
<anyvalue> - you can input any value to use for the sip realm.
|
||||
Choose the realm challenge key. Default is auto_to if not set.
|
||||
|
||||
If you want URL dialing to work you'll want to set this to auto_from.
|
||||
|
||||
If you use any other value besides auto_to or auto_from you'll loose
|
||||
the ability to do multiple domains.
|
||||
|
||||
Note: comment out to restore the behavior before 2008-09-29
|
||||
auto_from - uses the from field as the value for the sip realm.
|
||||
auto_to - uses the to field as the value for the sip realm.
|
||||
<anyvalue> - you can input any value to use for the sip realm.
|
||||
|
||||
If you want URL dialing to work you'll want to set this to auto_from.
|
||||
|
||||
If you use any other value besides auto_to or auto_from you'll
|
||||
loose the ability to do multiple domains.
|
||||
|
||||
Note: comment out to restore the behavior before 2008-09-29
|
||||
-->
|
||||
<param name="challenge-realm" value="auto_from"/>
|
||||
<!--<param name="disable-rtp-auto-adjust" value="true"/>-->
|
||||
|
@ -332,59 +334,58 @@
|
|||
<!-- set this param to false if your gateway for some reason hates X- headers that it is supposed to ignore-->
|
||||
<!--<param name="pass-callee-id" value="false"/>-->
|
||||
|
||||
<!-- clear clears them all or supply the name to add or the name prefixed with ~ to remove
|
||||
valid values:
|
||||
<!-- clear clears them all or supply the name to add or the name
|
||||
prefixed with ~ to remove valid values:
|
||||
|
||||
clear
|
||||
CISCO_SKIP_MARK_BIT_2833
|
||||
SONUS_SEND_INVALID_TIMESTAMP_2833
|
||||
clear
|
||||
CISCO_SKIP_MARK_BIT_2833
|
||||
SONUS_SEND_INVALID_TIMESTAMP_2833
|
||||
|
||||
-->
|
||||
<!--<param name="auto-rtp-bugs" data="clear"/>-->
|
||||
|
||||
<!-- the following can be used as workaround with bogus SRV/NAPTR records -->
|
||||
<!--<param name="disable-srv" value="false" />-->
|
||||
<!--<param name="disable-naptr" value="false" />-->
|
||||
<!-- the following can be used as workaround with bogus SRV/NAPTR records -->
|
||||
<!--<param name="disable-srv" value="false" />-->
|
||||
<!--<param name="disable-naptr" value="false" />-->
|
||||
|
||||
<!-- The following can be used to fine-tune timers within sofia's transport layer
|
||||
Those settings are for advanced users and can safely be left as-is -->
|
||||
|
||||
<!-- Initial retransmission interval (in milliseconds).
|
||||
Set the T1 retransmission interval used by the SIP transaction engine.
|
||||
The T1 is the initial duration used by request retransmission timers A and E (UDP) as well as response retransmission timer G. -->
|
||||
<!-- <param name="timer-T1" value="500" /> -->
|
||||
|
||||
<!-- Transaction timeout (defaults to T1 * 64).
|
||||
Set the T1x64 timeout value used by the SIP transaction engine.
|
||||
The T1x64 is duration used for timers B, F, H, and J (UDP) by the SIP transaction engine.
|
||||
The timeout value T1x64 can be adjusted separately from the initial retransmission interval T1. -->
|
||||
<!-- <param name="timer-T1X64" value="32000" /> -->
|
||||
|
||||
|
||||
<!-- Maximum retransmission interval (in milliseconds).
|
||||
Set the maximum retransmission interval used by the SIP transaction engine.
|
||||
The T2 is the maximum duration used for the timers E (UDP) and G by the SIP transaction engine.
|
||||
Note that the timer A is not capped by T2. Retransmission interval of INVITE requests grows exponentially
|
||||
until the timer B fires. -->
|
||||
<!-- <param name="timer-T2" value="4000" /> -->
|
||||
|
||||
<!--
|
||||
Transaction lifetime (in milliseconds).
|
||||
Set the lifetime for completed transactions used by the SIP transaction engine.
|
||||
A completed transaction is kept around for the duration of T4 in order to catch late responses.
|
||||
The T4 is the maximum duration for the messages to stay in the network and the duration of SIP timer K. -->
|
||||
<!-- <param name="timer-T4" value="4000" /> -->
|
||||
<!-- The following can be used to fine-tune timers within sofia's transport layer
|
||||
Those settings are for advanced users and can safely be left as-is -->
|
||||
|
||||
<!-- Turn on a jitterbuffer for every call -->
|
||||
<!-- <param name="auto-jitterbuffer-msec" value="60"/> -->
|
||||
<!-- Initial retransmission interval (in milliseconds).
|
||||
Set the T1 retransmission interval used by the SIP transaction engine.
|
||||
The T1 is the initial duration used by request retransmission timers A and E (UDP) as well as response retransmission timer G. -->
|
||||
<!-- <param name="timer-T1" value="500" /> -->
|
||||
|
||||
<!-- Transaction timeout (defaults to T1 * 64).
|
||||
Set the T1x64 timeout value used by the SIP transaction engine.
|
||||
The T1x64 is duration used for timers B, F, H, and J (UDP) by the SIP transaction engine.
|
||||
The timeout value T1x64 can be adjusted separately from the initial retransmission interval T1. -->
|
||||
<!-- <param name="timer-T1X64" value="32000" /> -->
|
||||
|
||||
|
||||
<!-- By default mod_sofia will ignore the codecs in the sdp for hold/unhold operations
|
||||
Set this to true if you want to actually parse the sdp and re-negotiate the codec during hold/unhold.
|
||||
It's probably not what you want so stick with the default unless you really need to change this.
|
||||
-->
|
||||
<!--<param name="renegotiate-codec-on-hold" value="true"/>-->
|
||||
|
||||
<!-- Maximum retransmission interval (in milliseconds).
|
||||
Set the maximum retransmission interval used by the SIP transaction engine.
|
||||
The T2 is the maximum duration used for the timers E (UDP) and G by the SIP transaction engine.
|
||||
Note that the timer A is not capped by T2. Retransmission interval of INVITE requests grows exponentially
|
||||
until the timer B fires. -->
|
||||
<!-- <param name="timer-T2" value="4000" /> -->
|
||||
|
||||
<!--
|
||||
Transaction lifetime (in milliseconds).
|
||||
Set the lifetime for completed transactions used by the SIP transaction engine.
|
||||
A completed transaction is kept around for the duration of T4 in order to catch late responses.
|
||||
The T4 is the maximum duration for the messages to stay in the network and the duration of SIP timer K. -->
|
||||
<!-- <param name="timer-T4" value="4000" /> -->
|
||||
|
||||
<!-- Turn on a jitterbuffer for every call -->
|
||||
<!-- <param name="auto-jitterbuffer-msec" value="60"/> -->
|
||||
|
||||
|
||||
<!-- By default mod_sofia will ignore the codecs in the sdp for hold/unhold operations
|
||||
Set this to true if you want to actually parse the sdp and re-negotiate the codec during hold/unhold.
|
||||
It's probably not what you want so stick with the default unless you really need to change this.
|
||||
-->
|
||||
<!--<param name="renegotiate-codec-on-hold" value="true"/>-->
|
||||
|
||||
</settings>
|
||||
</profile>
|
||||
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
<!--/// domain to use in from: *optional* same as realm, if blank ///-->
|
||||
<!--<param name="from-domain" value="asterlink.com"/>-->
|
||||
<!--/// account password *required* ///-->
|
||||
<!--<param name="password" value="2007"/>-->
|
||||
<!--<param name="password" value="2007"/>-->
|
||||
<!--/// extension for inbound calls: *optional* same as username, if blank ///-->
|
||||
<!--<param name="extension" value="cluecon"/>-->
|
||||
<!--/// proxy host: *optional* same as realm, if blank ///-->
|
||||
|
|
|
@ -123,7 +123,7 @@
|
|||
127 - BV32
|
||||
|
||||
-->
|
||||
<X-PRE-PROCESS cmd="set" data="global_codec_prefs=G7221@32000h,G7221@16000h,G722,PCMU,PCMA,GSM"/>
|
||||
<X-PRE-PROCESS cmd="set" data="global_codec_prefs=G722,PCMU,PCMA,GSM"/>
|
||||
<X-PRE-PROCESS cmd="set" data="outbound_codec_prefs=PCMU,PCMA,GSM"/>
|
||||
|
||||
<!--
|
||||
|
|
11
configure.in
11
configure.in
|
@ -3,11 +3,11 @@
|
|||
|
||||
# Must change all of the below together
|
||||
# For a release, set revision for that tagged release as well and uncomment
|
||||
AC_INIT([freeswitch], [1.1.beta1], BUG-REPORT-ADDRESS)
|
||||
AC_SUBST(SWITCH_VERSION_MAJOR, [1])
|
||||
AC_SUBST(SWITCH_VERSION_MINOR, [1])
|
||||
AC_SUBST(SWITCH_VERSION_MICRO, [beta1])
|
||||
#AC_SUBST(SWITCH_VERSION_REVISION, [])
|
||||
AC_INIT([freeswitch], [4.3.0], BUG-REPORT-ADDRESS)
|
||||
AC_SUBST(SWITCH_VERSION_MAJOR, [4])
|
||||
AC_SUBST(SWITCH_VERSION_MINOR, [3])
|
||||
AC_SUBST(SWITCH_VERSION_MICRO, [0])
|
||||
AC_SUBST(SWITCH_VERSION_REVISION, [3e39945d73bc55c9bae492161e968bed239a4f4f])
|
||||
|
||||
AC_CONFIG_FILES([src/include/switch_version.h.in:src/include/switch_version.h.template])
|
||||
AC_CONFIG_FILES([.version:.version.in])
|
||||
|
@ -993,7 +993,6 @@ AC_CONFIG_FILES([Makefile
|
|||
src/Makefile
|
||||
src/mod/Makefile
|
||||
src/mod/applications/mod_expr/Makefile
|
||||
src/mod/applications/mod_fax/Makefile
|
||||
src/mod/applications/mod_spandsp/Makefile
|
||||
src/mod/applications/mod_osp/Makefile
|
||||
src/mod/applications/mod_stress/Makefile
|
||||
|
|
|
@ -20,7 +20,6 @@
|
|||
/freeswitch-dbg/
|
||||
/freeswitch-dev/
|
||||
/freeswitch-doc/
|
||||
/freeswitch-htdocs-slim*/
|
||||
/freeswitch-init*/
|
||||
/freeswitch-meta*/
|
||||
/freeswitch-mod-*/
|
||||
|
@ -28,3 +27,4 @@
|
|||
/freeswitch-sounds*/
|
||||
/freeswitch-systemd/
|
||||
/freeswitch-sysvinit/
|
||||
/libfreeswitch*/
|
||||
|
|
|
@ -48,10 +48,17 @@ The format of debian/modules.conf is:
|
|||
To build this package, I recommend running the following from the root
|
||||
directory of your FS git working tree:
|
||||
|
||||
mkdir ../sounds
|
||||
export FS_SOUNDS_DIR=$(pwd)/../sounds
|
||||
distro=sid
|
||||
ver="$(cat build/next-release.txt | sed -e 's/-/~/g')~n$(date +%Y%m%dT%H%M%SZ)-1~${distro}+1"
|
||||
git clean -fdx && git reset --hard HEAD
|
||||
(cd debian && ./bootstrap.sh)
|
||||
schedtool -B -e git-buildpackage --git-verbose -us -uc
|
||||
./build/set-fs-version.sh "$ver"
|
||||
git add configure.in && git commit -m "bump to custom v$ver"
|
||||
(cd debian && ./bootstrap.sh -c $distro)
|
||||
dch -b -m -v "$ver" --force-distribution -D "$suite" "Custom build."
|
||||
git-buildpackage -b -us -uc \
|
||||
--git-verbose \
|
||||
--git-pbuilder --git-dist=$distro \
|
||||
--git-compression-level=1v --git-compression=xz
|
||||
git reset --hard HEAD^
|
||||
|
||||
-- Travis Cross <tc@traviscross.com>, Sat, 5 May 2012 23:32:53 +0000
|
||||
-- Travis Cross <tc@traviscross.com>, Thu, 24 May 2012 16:35:57 +0000
|
||||
|
|
|
@ -6,38 +6,47 @@ mod_dir="../src/mod"
|
|||
conf_dir="../conf"
|
||||
fs_description="FreeSWITCH is a scalable open source cross-platform telephony platform designed to route and interconnect popular communication protocols using audio, video, text or any other form of media."
|
||||
mod_build_depends="."
|
||||
supported_distros="squeeze wheezy sid"
|
||||
avoid_mods=(
|
||||
applications/mod_fax
|
||||
applications/mod_ladspa
|
||||
applications/mod_limit
|
||||
applications/mod_mongo
|
||||
applications/mod_mp4
|
||||
applications/mod_osp
|
||||
applications/mod_rad_auth
|
||||
applications/mod_skel
|
||||
applications/mod_soundtouch
|
||||
asr_tts/mod_cepstral
|
||||
asr_tts/mod_flite
|
||||
codecs/mod_com_g729
|
||||
codecs/mod_ilbc
|
||||
codecs/mod_sangoma_codec
|
||||
codecs/mod_siren
|
||||
codecs/mod_skel_codec
|
||||
codecs/mod_voipcodecs
|
||||
endpoints/mod_gsmopen
|
||||
endpoints/mod_h323
|
||||
endpoints/mod_khomp
|
||||
endpoints/mod_opal
|
||||
endpoints/mod_portaudio
|
||||
endpoints/mod_reference
|
||||
endpoints/mod_unicall
|
||||
event_handlers/mod_snmp
|
||||
formats/mod_portaudio_stream
|
||||
formats/mod_shout
|
||||
formats/mod_vlc
|
||||
languages/mod_java
|
||||
languages/mod_managed
|
||||
languages/mod_spidermonkey
|
||||
languages/mod_yaml
|
||||
sdk/autotools
|
||||
xml_int/mod_xml_ldap
|
||||
)
|
||||
avoid_mods_sid=(
|
||||
endpoints/mod_portaudio
|
||||
formats/mod_portaudio_stream
|
||||
)
|
||||
avoid_mods_wheezy=(
|
||||
endpoints/mod_portaudio
|
||||
formats/mod_portaudio_stream
|
||||
)
|
||||
avoid_mods_squeeze=(
|
||||
formats/mod_vlc
|
||||
languages/mod_managed
|
||||
)
|
||||
|
||||
err () {
|
||||
echo "$0 error: $1" >&2
|
||||
|
@ -54,15 +63,23 @@ xread () {
|
|||
}
|
||||
|
||||
avoid_mod_filter () {
|
||||
for x in "${avoid_mods[@]}"; do
|
||||
[ "$1" = "$x" ] && return 1
|
||||
local x="avoid_mods_$codename[@]"
|
||||
local -a mods=("${avoid_mods[@]}" "${!x}")
|
||||
for x in "${mods[@]}"; do
|
||||
if [ "$1" = "$x" ]; then
|
||||
[ "$2" = "show" ] && echo "excluding module $x" >&2
|
||||
return 1
|
||||
fi
|
||||
done
|
||||
return 0
|
||||
}
|
||||
|
||||
modconf_filter () {
|
||||
while xread line; do
|
||||
[ "$1" = "$line" ] && return 0
|
||||
while xread l; do
|
||||
if [ "$1" = "$l" ]; then
|
||||
[ "$2" = "show" ] && echo "including module $l" >&2
|
||||
return 0
|
||||
fi
|
||||
done < modules.conf
|
||||
return 1
|
||||
}
|
||||
|
@ -75,6 +92,10 @@ mod_filter () {
|
|||
fi
|
||||
}
|
||||
|
||||
mod_filter_show () {
|
||||
mod_filter "$1" show
|
||||
}
|
||||
|
||||
map_fs_modules () {
|
||||
local filterfn="$1" percatfns="$2" permodfns="$3"
|
||||
for x in $mod_dir/*; do
|
||||
|
@ -106,18 +127,23 @@ map_modules () {
|
|||
module=${y##*/} module_path=$y
|
||||
$filterfn $category/$module || continue
|
||||
module="" category="" module_name=""
|
||||
description="" long_description=""
|
||||
section="" description="" long_description=""
|
||||
build_depends="" depends="" recommends="" suggests=""
|
||||
distro_conflicts=""
|
||||
distro_vars=""
|
||||
for x in $supported_distros; do
|
||||
distro_vars="$distro_vars build_depends_$x"
|
||||
eval build_depends_$x=""
|
||||
done
|
||||
. $y
|
||||
[ -n "$description" ] || description="$module_name"
|
||||
[ -n "$long_description" ] || description="Adds ${module_name}."
|
||||
for f in $permodfns; do $f; done
|
||||
unset \
|
||||
module module_name module_path \
|
||||
description long_description \
|
||||
section description long_description \
|
||||
build_depends depends recommends suggests \
|
||||
distro_conflicts
|
||||
distro_conflicts $distro_vars
|
||||
done
|
||||
unset category category_path
|
||||
done
|
||||
|
@ -150,7 +176,7 @@ Build-Depends:
|
|||
wget, pkg-config,
|
||||
# configure options
|
||||
libssl-dev, unixodbc-dev,
|
||||
libncurses5-dev, libjpeg8-dev,
|
||||
libncurses5-dev, libjpeg62-dev,
|
||||
python-dev, erlang-dev,
|
||||
# documentation
|
||||
doxygen,
|
||||
|
@ -172,7 +198,8 @@ print_core_control () {
|
|||
cat <<EOF
|
||||
Package: freeswitch
|
||||
Architecture: any
|
||||
Depends: \${shlibs:Depends}, \${perl:Depends}, \${misc:Depends}
|
||||
Depends: \${shlibs:Depends}, \${perl:Depends}, \${misc:Depends},
|
||||
libfreeswitch1 (= \${binary:Version})
|
||||
Recommends:
|
||||
Suggests: freeswitch-dbg
|
||||
Description: Cross-Platform Scalable Multi-Protocol Soft Switch
|
||||
|
@ -180,12 +207,21 @@ Description: Cross-Platform Scalable Multi-Protocol Soft Switch
|
|||
.
|
||||
This package contains the FreeSWITCH core.
|
||||
|
||||
Package: libfreeswitch1
|
||||
Architecture: any
|
||||
Depends: \${shlibs:Depends}, \${misc:Depends}
|
||||
Recommends:
|
||||
Suggests: libfreeswitch1-dbg
|
||||
Description: Cross-Platform Scalable Multi-Protocol Soft Switch
|
||||
$(debian_wrap "${fs_description}")
|
||||
.
|
||||
This package contains the FreeSWITCH core library.
|
||||
|
||||
Package: freeswitch-meta-bare
|
||||
Architecture: any
|
||||
Depends: \${misc:Depends}, freeswitch (= \${binary:Version})
|
||||
Recommends:
|
||||
freeswitch-doc (= \${binary:Version}),
|
||||
freeswitch-htdocs-slim (= \${binary:Version}),
|
||||
freeswitch-mod-commands (= \${binary:Version}),
|
||||
freeswitch-init (= \${binary:Version}),
|
||||
freeswitch-music (= \${binary:Version}),
|
||||
|
@ -264,10 +300,8 @@ Depends: \${misc:Depends}, freeswitch (= \${binary:Version}),
|
|||
freeswitch-mod-g723-1 (= \${binary:Version}),
|
||||
freeswitch-mod-g729 (= \${binary:Version}),
|
||||
freeswitch-mod-amr (= \${binary:Version}),
|
||||
freeswitch-mod-ilbc (= \${binary:Version}),
|
||||
freeswitch-mod-speex (= \${binary:Version}),
|
||||
freeswitch-mod-h26x (= \${binary:Version}),
|
||||
freeswitch-mod-siren (= \${binary:Version}),
|
||||
freeswitch-mod-sndfile (= \${binary:Version}),
|
||||
freeswitch-mod-native-file (= \${binary:Version}),
|
||||
freeswitch-mod-local-stream (= \${binary:Version}),
|
||||
|
@ -298,13 +332,15 @@ Depends: \${misc:Depends}, freeswitch (= \${binary:Version}),
|
|||
freeswitch-mod-g723-1 (= \${binary:Version}),
|
||||
freeswitch-mod-g729 (= \${binary:Version}),
|
||||
freeswitch-mod-h26x (= \${binary:Version}),
|
||||
freeswitch-mod-ilbc (= \${binary:Version}),
|
||||
freeswitch-mod-mp4v (= \${binary:Version}),
|
||||
freeswitch-mod-opus (= \${binary:Version}),
|
||||
freeswitch-mod-silk (= \${binary:Version}),
|
||||
freeswitch-mod-siren (= \${binary:Version}),
|
||||
freeswitch-mod-spandsp (= \${binary:Version}),
|
||||
freeswitch-mod-speex (= \${binary:Version}),
|
||||
freeswitch-mod-theora (= \${binary:Version})
|
||||
Suggests:
|
||||
freeswitch-mod-ilbc (= \${binary:Version}),
|
||||
freeswitch-mod-siren (= \${binary:Version})
|
||||
Description: Cross-Platform Scalable Multi-Protocol Soft Switch
|
||||
$(debian_wrap "${fs_description}")
|
||||
.
|
||||
|
@ -321,7 +357,17 @@ Description: debugging symbols for FreeSWITCH
|
|||
.
|
||||
This package contains debugging symbols for FreeSWITCH.
|
||||
|
||||
Package: freeswitch-dev
|
||||
Package: libfreeswitch1-dbg
|
||||
Section: debug
|
||||
Priority: extra
|
||||
Architecture: any
|
||||
Depends: \${misc:Depends}, libfreeswitch1 (= \${binary:Version})
|
||||
Description: debugging symbols for FreeSWITCH
|
||||
$(debian_wrap "${fs_description}")
|
||||
.
|
||||
This package contains debugging symbols for libfreeswitch1.
|
||||
|
||||
Package: libfreeswitch-dev
|
||||
Section: libdevel
|
||||
Architecture: any
|
||||
Depends: \${misc:Depends}, freeswitch
|
||||
|
@ -369,40 +415,18 @@ Description: FreeSWITCH systemd configuration
|
|||
|
||||
## misc
|
||||
|
||||
Package: freeswitch-htdocs-slim
|
||||
Architecture: all
|
||||
Depends: \${misc:Depends}
|
||||
Description: FreeSWITCH htdocs slim player
|
||||
$(debian_wrap "${fs_description}")
|
||||
.
|
||||
This package contains the slim SWF player for FreeSWITCH.
|
||||
|
||||
## sounds
|
||||
|
||||
Package: freeswitch-music
|
||||
Architecture: all
|
||||
Depends: \${misc:Depends},
|
||||
freeswitch-music-default (= \${binary:Version})
|
||||
freeswitch-music-default (>= 1.0.8)
|
||||
Description: Music on hold audio for FreeSWITCH
|
||||
$(debian_wrap "${fs_description}")
|
||||
.
|
||||
This is a metapackage which depends on the default music on hold
|
||||
packages for FreeSWITCH.
|
||||
|
||||
Package: freeswitch-music-default
|
||||
Architecture: all
|
||||
Depends: \${misc:Depends},
|
||||
freeswitch-music-default-8k (= \${binary:Version})
|
||||
Recommends:
|
||||
freeswitch-music-default-16k (= \${binary:Version}),
|
||||
freeswitch-music-default-32k (= \${binary:Version}),
|
||||
freeswitch-music-default-48k (= \${binary:Version})
|
||||
Description: Music on hold audio for FreeSWITCH
|
||||
$(debian_wrap "${fs_description}")
|
||||
.
|
||||
This is a metapackage which depends on the default music on hold
|
||||
packages for FreeSWITCH at various sampling rates.
|
||||
|
||||
Package: freeswitch-sounds
|
||||
Architecture: all
|
||||
Depends: \${misc:Depends},
|
||||
|
@ -426,33 +450,21 @@ Description: English sounds for FreeSWITCH
|
|||
Package: freeswitch-sounds-en-us
|
||||
Architecture: all
|
||||
Depends: \${misc:Depends},
|
||||
freeswitch-sounds-en-us-callie (= \${binary:Version})
|
||||
freeswitch-sounds-en-us-callie (>= 1.0.18)
|
||||
Description: US English sounds for FreeSWITCH
|
||||
$(debian_wrap "${fs_description}")
|
||||
.
|
||||
This is a metapackage which depends on the default US/English sound
|
||||
packages for FreeSWITCH.
|
||||
|
||||
Package: freeswitch-sounds-en-us-callie
|
||||
Architecture: all
|
||||
Depends: \${misc:Depends},
|
||||
freeswitch-sounds-en-us-callie-8k (= \${binary:Version})
|
||||
Recommends:
|
||||
freeswitch-sounds-en-us-callie-16k (= \${binary:Version}),
|
||||
freeswitch-sounds-en-us-callie-32k (= \${binary:Version}),
|
||||
freeswitch-sounds-en-us-callie-48k (= \${binary:Version})
|
||||
Description: US English sounds for FreeSWITCH
|
||||
$(debian_wrap "${fs_description}")
|
||||
.
|
||||
This is a metapackage which depends on the US/English Callie sound
|
||||
packages for FreeSWITCH at various sampling rates.
|
||||
|
||||
EOF
|
||||
}
|
||||
|
||||
print_mod_control () {
|
||||
local m_section="${section:-comm}"
|
||||
cat <<EOF
|
||||
Package: freeswitch-${module_name//_/-}
|
||||
Section: ${m_section}
|
||||
Architecture: any
|
||||
$(debian_wrap "Depends: \${shlibs:Depends}, \${misc:Depends}, freeswitch, ${depends}")
|
||||
$(debian_wrap "Recommends: ${recommends}")
|
||||
|
@ -482,7 +494,6 @@ EOF
|
|||
|
||||
print_mod_install () {
|
||||
cat <<EOF
|
||||
/usr/lib/freeswitch/mod/${1}.la
|
||||
/usr/lib/freeswitch/mod/${1}.so
|
||||
EOF
|
||||
}
|
||||
|
@ -508,6 +519,15 @@ ${p}: possible-gpl-code-linked-with-openssl
|
|||
EOF
|
||||
}
|
||||
|
||||
print_itp_override () {
|
||||
local p="$1"
|
||||
cat <<EOF
|
||||
# We're not in Debian (yet) so we don't have an ITP bug to close.
|
||||
${p}: new-package-should-close-itp-bug
|
||||
|
||||
EOF
|
||||
}
|
||||
|
||||
print_common_overrides () {
|
||||
print_long_filename_override "$1"
|
||||
}
|
||||
|
@ -521,14 +541,6 @@ print_conf_overrides () {
|
|||
print_common_overrides "$1"
|
||||
}
|
||||
|
||||
print_sound_overrides () {
|
||||
print_common_overrides "$1"
|
||||
}
|
||||
|
||||
print_music_overrides () {
|
||||
print_common_overrides "$1"
|
||||
}
|
||||
|
||||
print_conf_control () {
|
||||
cat <<EOF
|
||||
Package: freeswitch-conf-${conf//_/-}
|
||||
|
@ -548,46 +560,6 @@ conf/${conf} /usr/share/freeswitch/conf
|
|||
EOF
|
||||
}
|
||||
|
||||
print_music_control () {
|
||||
cat <<EOF
|
||||
Package: freeswitch-music-default-${rate_k}
|
||||
Architecture: all
|
||||
Depends: \${misc:Depends}
|
||||
Description: Music on hold audio for FreeSWITCH
|
||||
$(debian_wrap "${fs_description}")
|
||||
.
|
||||
This package contains the default music on hold audio for FreeSWITCH
|
||||
at a sampling rate of ${rate}Hz.
|
||||
|
||||
EOF
|
||||
}
|
||||
|
||||
print_music_install () {
|
||||
cat <<EOF
|
||||
/usr/share/freeswitch/sounds/music/${rate}
|
||||
EOF
|
||||
}
|
||||
|
||||
print_sound_control () {
|
||||
cat <<EOF
|
||||
Package: freeswitch-sounds-${sound//\//-}-${rate_k}
|
||||
Architecture: all
|
||||
Depends: \${misc:Depends}
|
||||
Description: ${sound} sounds for FreeSWITCH
|
||||
$(debian_wrap "${fs_description}")
|
||||
.
|
||||
This package contains the ${sound} sounds for FreeSWITCH at a
|
||||
sampling rate of ${rate}Hz.
|
||||
|
||||
EOF
|
||||
}
|
||||
|
||||
print_sound_install () {
|
||||
cat <<EOF
|
||||
/usr/share/freeswitch/sounds/${sound_path}/*/${rate}
|
||||
EOF
|
||||
}
|
||||
|
||||
print_edit_warning () {
|
||||
echo "#### Do not edit! This file is auto-generated from debian/bootstrap.sh."; echo
|
||||
}
|
||||
|
@ -631,41 +603,18 @@ genconf () {
|
|||
test -f $f.tmpl && cat $f.tmpl >> $f
|
||||
}
|
||||
|
||||
genmusic () {
|
||||
rate="$1" rate_k="${rate%%000}k"
|
||||
print_music_control >> control
|
||||
local p=freeswitch-music-default-${rate_k}
|
||||
local f=$p.install
|
||||
(print_edit_warning; print_music_install) > $f
|
||||
test -f $f.tmpl && cat $f.tmpl >> $f
|
||||
local f=$p.lintian-overrides
|
||||
(print_edit_warning; print_music_overrides "$p") > $f
|
||||
test -f $f.tmpl && cat $f.tmpl >> $f
|
||||
unset rate rate_k
|
||||
}
|
||||
|
||||
gensound () {
|
||||
rate="$1" rate_k="${rate%%000}k" sound_path="$2" sound="${2,,}"
|
||||
language=$(echo $sound | cut -d/ -f1)
|
||||
country=$(echo $sound | cut -d/ -f2)
|
||||
speaker=$(echo $sound | cut -d/ -f3)
|
||||
print_sound_control >> control
|
||||
local p=freeswitch-sounds-${sound//\//-}-${rate_k}
|
||||
local f=$p.install
|
||||
(print_edit_warning; print_sound_install) > $f
|
||||
test -f $f.tmpl && cat $f.tmpl >> $f
|
||||
local f=$p.lintian-overrides
|
||||
(print_edit_warning; print_sound_overrides "$p") > $f
|
||||
test -f $f.tmpl && cat $f.tmpl >> $f
|
||||
unset rate rate_k sound sound_path language country speaker
|
||||
}
|
||||
|
||||
accumulate_build_depends () {
|
||||
if [ -n "$build_depends" ]; then
|
||||
local x=""
|
||||
if [ -n "$(eval echo \$build_depends_$codename)" ]; then
|
||||
x="$(eval echo \$build_depends_$codename)"
|
||||
else
|
||||
x="${build_depends}"
|
||||
fi
|
||||
if [ -n "$x" ]; then
|
||||
if [ ! "$mod_build_depends" = "." ]; then
|
||||
mod_build_depends="${mod_build_depends}, ${build_depends}"
|
||||
mod_build_depends="${mod_build_depends}, ${x}"
|
||||
else
|
||||
mod_build_depends="${build_depends}"
|
||||
mod_build_depends="${x}"
|
||||
fi
|
||||
fi
|
||||
}
|
||||
|
@ -775,12 +724,17 @@ genmodctl_cat () {
|
|||
|
||||
genmodctl_mod () {
|
||||
echo "Module: $module"
|
||||
[ -n "$section" ] && echo "Section: $section"
|
||||
echo "Description: $description"
|
||||
echo "$long_description" | fold -s -w 69 | while xread l; do
|
||||
local v="$(echo "$l" | sed -e 's/ *$//g')"
|
||||
echo " $v"
|
||||
done
|
||||
[ -n "$build_depends" ] && debian_wrap "Build-Depends: $build_depends"
|
||||
for x in $supported_distros; do
|
||||
[ -n "$(eval echo \$build_depends_$x)" ] \
|
||||
&& debian_wrap "Build-Depends-$x: $(eval echo \$build_depends_$x)"
|
||||
done
|
||||
[ -n "$depends" ] && debian_wrap "Depends: $depends"
|
||||
[ -n "$reccomends" ] && debian_wrap "Recommends: $recommends"
|
||||
[ -n "$suggests" ] && debian_wrap "Suggests: $suggests"
|
||||
|
@ -788,42 +742,68 @@ genmodctl_mod () {
|
|||
echo
|
||||
}
|
||||
|
||||
codename="sid"
|
||||
while getopts "c:" o; do
|
||||
case "$o" in
|
||||
c) codename="$OPTARG" ;;
|
||||
esac
|
||||
done
|
||||
shift $(($OPTIND-1))
|
||||
|
||||
echo "Bootstrapping debian/ for ${codename}" >&2
|
||||
echo >&2
|
||||
echo "Please wait, this takes a few seconds..." >&2
|
||||
|
||||
echo "Adding any new modules to control-modules..." >&2
|
||||
parse_dir=control-modules.parse
|
||||
map_fs_modules ':' 'genmodctl_new_cat' 'genmodctl_new_mod' >> control-modules
|
||||
echo "Parsing control-modules..." >&2
|
||||
parse_mod_control
|
||||
(echo "# -*- mode:debian-control -*-"; echo; \
|
||||
echo "Displaying includes/excludes..." >&2
|
||||
map_modules 'mod_filter_show' '' ''
|
||||
echo "Generating control-modules.gen as sanity check..." >&2
|
||||
(echo "# -*- mode:debian-control -*-"; \
|
||||
echo "##### Author: Travis Cross <tc@traviscross.com>"; echo; \
|
||||
map_modules ':' 'genmodctl_cat' 'genmodctl_mod' \
|
||||
) > control-modules.gen
|
||||
|
||||
print_edit_warning > modules_.conf
|
||||
echo "Accumulating build dependencies from modules..." >&2
|
||||
map_modules 'mod_filter' '' 'accumulate_build_depends'
|
||||
echo "Generating debian/..." >&2
|
||||
> control
|
||||
(print_edit_warning; print_source_control; print_core_control) >> control
|
||||
for r in 8000 16000 32000 48000; do genmusic $r; done
|
||||
for x in 'en/us/callie'; do
|
||||
for r in 8000 16000 32000 48000; do
|
||||
gensound $r $x
|
||||
done
|
||||
done
|
||||
echo "Generating debian/ (conf)..." >&2
|
||||
(echo "### conf"; echo) >> control
|
||||
map_confs 'genconf'
|
||||
echo "Generating debian/ (modules)..." >&2
|
||||
(echo "### modules"; echo) >> control
|
||||
print_edit_warning > modules_.conf
|
||||
map_modules "mod_filter" \
|
||||
"gencontrol_per_cat genmodules_per_cat" \
|
||||
"gencontrol_per_mod geninstall_per_mod genoverrides_per_mod genmodules_per_mod"
|
||||
|
||||
echo "Generating additional lintian overrides..." >&2
|
||||
grep -e '^Package:' control | while xread l; do
|
||||
m="${l#*: }"
|
||||
f=$m.lintian-overrides
|
||||
if [ ! -s $f ] || ! grep -e 'package-has-long-file-name' $f >/dev/null; then
|
||||
[ -s $f ] || print_edit_warning >> $f
|
||||
[ -s $f ] || print_edit_warning >> $f
|
||||
if ! grep -e 'package-has-long-file-name' $f >/dev/null; then
|
||||
print_long_filename_override "$m" >> $f
|
||||
fi
|
||||
if ! grep -e 'new-package-should-close-itp-bug' $f >/dev/null; then
|
||||
print_itp_override "$m" >> $f
|
||||
fi
|
||||
done
|
||||
for p in freeswitch libfreeswitch1; do
|
||||
f=$p.lintian-overrides
|
||||
[ -s $f ] || print_edit_warning >> $f
|
||||
print_gpl_openssl_override "$p" >> $f
|
||||
done
|
||||
f=freeswitch.lintian-overrides
|
||||
[ -s $f ] || print_edit_warning >> $f
|
||||
print_gpl_openssl_override "freeswitch" >> $f
|
||||
|
||||
echo "Cleaning up..." >&2
|
||||
rm -f control-modules.preparse
|
||||
rm -rf control-modules.parse
|
||||
diff control-modules control-modules.gen >/dev/null && rm -f control-modules.gen
|
||||
|
||||
echo "Done bootstrapping debian/" >&2
|
||||
touch .stamp-bootstrap
|
||||
|
|
|
@ -1,3 +1,10 @@
|
|||
freeswitch (1.2~rc2-1) unstable; urgency=low
|
||||
|
||||
* Bump version.
|
||||
* Sounds and music have been moved to their own source packaging.
|
||||
|
||||
-- Travis Cross <tc@traviscross.com> Thu, 24 May 2012 15:15:10 +0000
|
||||
|
||||
freeswitch (1.2~alpha1-1) unstable; urgency=low
|
||||
|
||||
* Initial release of FreeSWITCH in new debian packaging.
|
||||
|
|
|
@ -114,6 +114,8 @@ Description: HTTP GET with caching
|
|||
Module: applications/mod_ladspa
|
||||
Description: LADSPA
|
||||
This module provides an API for accessing LADSPA plugins.
|
||||
Build-Depends: ladspa-sdk
|
||||
Suggests: tap-plugins, swh-plugins, autotalent
|
||||
|
||||
Module: applications/mod_lcr
|
||||
Description: LCR
|
||||
|
@ -133,13 +135,12 @@ Description: MongoDB
|
|||
This module provides an interface to MongoDB.
|
||||
Build-Depends: scons, libboost-dev, libboost-system-dev,
|
||||
libboost-date-time-dev, libboost-thread-dev, libboost-filesystem-dev
|
||||
Depends: libicu44, libboost-system1.42.0, libboost-date-time1.42.0,
|
||||
libboost-serialization1.42.0, libboost-thread1.42.0,
|
||||
libboost-filesystem1.42.0
|
||||
|
||||
Module: applications/mod_mp4
|
||||
Section: contrib/comm
|
||||
Description: MP4 video support
|
||||
This module adds support for MP4 video playback.
|
||||
Build-Depends: libmp4v2-dev
|
||||
|
||||
Module: applications/mod_nibblebill
|
||||
Description: Nibblebill
|
||||
|
@ -149,11 +150,17 @@ Description: Nibblebill
|
|||
Module: applications/mod_osp
|
||||
Description: Open Settlement Protocol
|
||||
This module adds support for the Open Settlement Protocol (OSP).
|
||||
Build-Depends: libosptk3-dev
|
||||
|
||||
Module: applications/mod_rad_auth
|
||||
Description: RADIUS AA
|
||||
This module implements RADIUS Authentication and Authorization.
|
||||
|
||||
Module: applications/mod_random
|
||||
Description: Entropy extraction
|
||||
This module extracts entropy from FreeSWITCH and feeds it into
|
||||
/dev/random.
|
||||
|
||||
Module: applications/mod_redis
|
||||
Description: Redis limit backend
|
||||
This module provides a mechanism to use Redis as a backend data
|
||||
|
@ -282,6 +289,7 @@ Description: mod_h26x
|
|||
Adds mod_h26x.
|
||||
|
||||
Module: codecs/mod_ilbc
|
||||
Section: non-free/comm
|
||||
Description: mod_ilbc
|
||||
Adds mod_ilbc.
|
||||
|
||||
|
@ -306,6 +314,7 @@ Description: mod_silk
|
|||
Adds mod_silk.
|
||||
|
||||
Module: codecs/mod_siren
|
||||
Section: non-free/comm
|
||||
Description: mod_siren
|
||||
Adds mod_siren.
|
||||
|
||||
|
@ -317,7 +326,6 @@ Module: codecs/mod_speex
|
|||
Description: mod_speex
|
||||
Adds mod_speex.
|
||||
Build-Depends: libogg-dev
|
||||
Depends: libogg0
|
||||
|
||||
Module: codecs/mod_theora
|
||||
Description: mod_theora
|
||||
|
@ -353,7 +361,6 @@ Module: endpoints/mod_alsa
|
|||
Description: mod_alsa
|
||||
Adds mod_alsa.
|
||||
Build-Depends: libasound2-dev
|
||||
Depends: libasound2
|
||||
|
||||
Module: endpoints/mod_dingaling
|
||||
Description: mod_dingaling
|
||||
|
@ -362,10 +369,12 @@ Description: mod_dingaling
|
|||
Module: endpoints/mod_gsmopen
|
||||
Description: mod_gsmopen
|
||||
Adds mod_gsmopen.
|
||||
Build-Depends: libx11-dev
|
||||
|
||||
Module: endpoints/mod_h323
|
||||
Description: mod_h323
|
||||
Adds mod_h323.
|
||||
Build-Depends: libopenh323-dev, libpt-dev
|
||||
|
||||
Module: endpoints/mod_khomp
|
||||
Description: mod_khomp
|
||||
|
@ -399,7 +408,6 @@ Module: endpoints/mod_skypopen
|
|||
Description: mod_skypopen
|
||||
Adds mod_skypopen.
|
||||
Build-Depends: libx11-dev
|
||||
Depends: libpthread-stubs0
|
||||
|
||||
Module: endpoints/mod_sofia
|
||||
Description: mod_sofia
|
||||
|
@ -423,7 +431,6 @@ Module: event_handlers/mod_cdr_pg_csv
|
|||
Description: mod_cdr_pg_csv
|
||||
Adds mod_cdr_pg_csv.
|
||||
Build-Depends: libpq-dev
|
||||
Depends: libpq5
|
||||
|
||||
Module: event_handlers/mod_cdr_sqlite
|
||||
Description: mod_cdr_sqlite
|
||||
|
@ -432,10 +439,12 @@ Description: mod_cdr_sqlite
|
|||
Module: event_handlers/mod_erlang_event
|
||||
Description: mod_erlang_event
|
||||
Adds mod_erlang_event.
|
||||
Build-Depends: erlang-dev
|
||||
|
||||
Module: event_handlers/mod_event_multicast
|
||||
Description: mod_event_multicast
|
||||
Adds mod_event_multicast.
|
||||
Build-Depends: libssl-dev
|
||||
|
||||
Module: event_handlers/mod_event_socket
|
||||
Description: mod_event_socket
|
||||
|
@ -460,6 +469,7 @@ Description: mod_radius_cdr
|
|||
Module: event_handlers/mod_snmp
|
||||
Description: mod_snmp
|
||||
Adds mod_snmp.
|
||||
Build-Depends: libsnmp-dev
|
||||
|
||||
## mod/formats
|
||||
|
||||
|
@ -483,8 +493,6 @@ Module: formats/mod_shout
|
|||
Description: mod_shout
|
||||
Adds mod_shout.
|
||||
Build-Depends: libogg-dev, libvorbis-dev
|
||||
Depends: libogg0, libvorbis0a, libvorbisenc2, libvorbisfile3,
|
||||
libvorbisidec1
|
||||
|
||||
Module: formats/mod_sndfile
|
||||
Description: mod_sndfile
|
||||
|
@ -498,7 +506,6 @@ Module: formats/mod_vlc
|
|||
Description: VLC streaming
|
||||
This module provides VLC streaming.
|
||||
Build-Depends: libvlc-dev (>= 2.0.0)
|
||||
Depends: libvlc5
|
||||
Distro-Conflicts: squeeze
|
||||
|
||||
## mod/languages
|
||||
|
@ -506,6 +513,7 @@ Distro-Conflicts: squeeze
|
|||
Module: languages/mod_java
|
||||
Description: mod_java
|
||||
Adds mod_java.
|
||||
Build-Depends: default-jdk, gcj-jdk
|
||||
|
||||
Module: languages/mod_lua
|
||||
Description: mod_lua
|
||||
|
@ -514,24 +522,27 @@ Description: mod_lua
|
|||
Module: languages/mod_managed
|
||||
Description: mod_managed
|
||||
Adds mod_managed.
|
||||
Build-Depends: libmono-2.0-dev, mono-gmcs
|
||||
|
||||
Module: languages/mod_perl
|
||||
Description: mod_perl
|
||||
Adds mod_perl.
|
||||
Build-Depends: libperl-dev
|
||||
Depends: libperl5.10
|
||||
|
||||
Module: languages/mod_python
|
||||
Description: mod_python
|
||||
Adds mod_python.
|
||||
Build-Depends: python-dev
|
||||
|
||||
Module: languages/mod_spidermonkey
|
||||
Description: mod_spidermonkey
|
||||
Adds mod_spidermonkey.
|
||||
Build-Depends: unixodbc-dev
|
||||
|
||||
Module: languages/mod_yaml
|
||||
Description: mod_yaml
|
||||
Adds mod_yaml.
|
||||
Build-Depends: libyaml-dev
|
||||
|
||||
## mod/loggers
|
||||
|
||||
|
@ -561,6 +572,10 @@ Module: say/mod_say_es
|
|||
Description: mod_say_es
|
||||
Adds mod_say_es.
|
||||
|
||||
Module: say/mod_say_fa
|
||||
Description: mod_say_fa
|
||||
Adds mod_say_fa.
|
||||
|
||||
Module: say/mod_say_fr
|
||||
Description: mod_say_fr
|
||||
Adds mod_say_fr.
|
||||
|
@ -635,9 +650,12 @@ Module: xml_int/mod_xml_ldap
|
|||
Description: mod_xml_ldap
|
||||
Adds mod_xml_ldap.
|
||||
Build-Depends: libsasl2-dev
|
||||
Depends: libsasl2-modules
|
||||
|
||||
Module: xml_int/mod_xml_rpc
|
||||
Description: mod_xml_rpc
|
||||
Adds mod_xml_rpc.
|
||||
|
||||
Module: xml_int/mod_xml_scgi
|
||||
Description: mod_xml_scgi
|
||||
Adds mod_xml_scgi.
|
||||
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -1,3 +0,0 @@
|
|||
/usr/share/freeswitch/htdocs/license.txt
|
||||
/usr/share/freeswitch/htdocs/slim.swf
|
||||
/usr/share/freeswitch/htdocs/slimtest.htm
|
|
@ -0,0 +1 @@
|
|||
/usr/share/freeswitch/scripts/freeswitch.jar
|
|
@ -1,3 +1 @@
|
|||
/usr/bin
|
||||
/usr/lib/libfreeswitch.so.*
|
||||
/usr/share/freeswitch/scripts
|
||||
|
|
|
@ -7,7 +7,6 @@ upstream-branch=master
|
|||
debian-branch=master
|
||||
upstream-tree=branch
|
||||
tag=False
|
||||
force-create=True
|
||||
compression=xz
|
||||
compression-level=9ev
|
||||
builder=debuild --prepend-path=/usr/lib/ccache -eFS_* -eCCACHE_* -i\.git -I.git -Zxz -z9
|
||||
|
|
|
@ -1,6 +1,4 @@
|
|||
/usr/include
|
||||
/usr/lib/freeswitch/mod/*.la
|
||||
/usr/lib/libfreeswitch.so
|
||||
/usr/lib/*.a
|
||||
/usr/lib/*.la
|
||||
/usr/lib/pkgconfig
|
|
@ -0,0 +1 @@
|
|||
/usr/lib/libfreeswitch.so.*
|
|
@ -1,11 +1,12 @@
|
|||
#!/usr/bin/make -f
|
||||
# -*- mode:makefile -*-
|
||||
##### Author: Travis Cross <tc@traviscross.com>
|
||||
|
||||
#export DH_VERBOSE=1
|
||||
|
||||
FS_CFLAGS?=-ggdb3 -O2
|
||||
FS_CPPFLAGS?=
|
||||
FS_CXXFLAGS?=$(FS_CFLAGS)
|
||||
FS_INSTALL_SOUNDS?=true
|
||||
export PATH?=/usr/lib/ccache:/usr/sbin:/usr/bin:/sbin:/bin
|
||||
export CFLAGS=$(FS_CFLAGS)
|
||||
export CPPFLAGS=$(FS_CPPFLAGS)
|
||||
|
@ -18,7 +19,6 @@ show_vars= \
|
|||
echo "CFLAGS='$(CFLAGS)'"; \
|
||||
echo "CXXFLAGS='$(CXXFLAGS)'"; \
|
||||
echo "CCACHE_DIR='$(CCACHE_DIR)'"; \
|
||||
echo "FS_INSTALL_SOUNDS='$(FS_INSTALL_SOUNDS)'"; \
|
||||
echo;
|
||||
|
||||
binary:
|
||||
|
@ -88,9 +88,9 @@ override_dh_strip:
|
|||
|
||||
override_dh_auto_install:
|
||||
dh_auto_install
|
||||
-$(FS_INSTALL_SOUNDS) && DESTDIR=debian/tmp make cd-sounds-install cd-moh-install
|
||||
mkdir -p debian/tmp/lib/systemd/system
|
||||
install -m0644 debian/freeswitch-systemd.freeswitch.service debian/tmp/lib/systemd/system/freeswitch.service
|
||||
rm -f debian/tmp/usr/share/freeswitch/grammar/model/communicator/COPYING
|
||||
|
||||
override_dh_installinit:
|
||||
dh_installinit -pfreeswitch-sysvinit --name=freeswitch
|
||||
|
@ -115,13 +115,5 @@ binary-quicktest:
|
|||
@$(call show_vars)
|
||||
echo "applications/mod_commands" > debian/modules.conf
|
||||
(cd debian && ./bootstrap.sh)
|
||||
env FS_INSTALL_SOUNDS=false dh binary \
|
||||
-Nfreeswitch-sounds-music-8k \
|
||||
-Nfreeswitch-sounds-music-16k \
|
||||
-Nfreeswitch-sounds-music-32k \
|
||||
-Nfreeswitch-sounds-music-48k \
|
||||
-Nfreeswitch-sounds-en-us-callie-8k \
|
||||
-Nfreeswitch-sounds-en-us-callie-16k \
|
||||
-Nfreeswitch-sounds-en-us-callie-32k \
|
||||
-Nfreeswitch-sounds-en-us-callie-48k
|
||||
dh binary
|
||||
|
||||
|
|
|
@ -2,14 +2,29 @@
|
|||
##### -*- mode:shell-script; indent-tabs-mode:nil; sh-basic-offset:2 -*-
|
||||
##### Author: Travis Cross <tc@traviscross.com>
|
||||
|
||||
set -e
|
||||
|
||||
ddir="."
|
||||
[ -n "${0%/*}" ] && ddir="${0%/*}"
|
||||
cd $ddir/../
|
||||
|
||||
#### lib
|
||||
|
||||
err () {
|
||||
echo "$0 error: $1" >&2
|
||||
exit 1
|
||||
}
|
||||
|
||||
announce () {
|
||||
cat >&2 <<EOF
|
||||
|
||||
########################################################################
|
||||
## $1
|
||||
########################################################################
|
||||
|
||||
EOF
|
||||
}
|
||||
|
||||
xread () {
|
||||
local xIFS="$IFS"
|
||||
IFS=''
|
||||
|
@ -19,6 +34,35 @@ xread () {
|
|||
return $ret
|
||||
}
|
||||
|
||||
mk_dver () { echo "$1" | sed -e 's/-/~/g'; }
|
||||
mk_uver () { echo "$1" | sed -e 's/-.*$//' -e 's/~/-/'; }
|
||||
dsc_source () { dpkg-parsechangelog | grep '^Source:' | awk '{print $2}'; }
|
||||
dsc_ver () { dpkg-parsechangelog | grep '^Version:' | awk '{print $2}'; }
|
||||
up_ver () { mk_uver "$(dsc_ver)"; }
|
||||
dsc_base () { echo "$(dsc_source)_$(dsc_ver)"; }
|
||||
up_base () { echo "$(dsc_source)-$(up_ver)"; }
|
||||
|
||||
find_distro () {
|
||||
case "$1" in
|
||||
experimental) echo "sid";;
|
||||
unstable) echo "sid";;
|
||||
testing) echo "wheezy";;
|
||||
stable) echo "squeeze";;
|
||||
*) echo "$1";;
|
||||
esac
|
||||
}
|
||||
|
||||
find_suite () {
|
||||
case "$1" in
|
||||
sid) echo "unstable";;
|
||||
wheezy) echo "testing";;
|
||||
squeeze) echo "stable";;
|
||||
*) echo "$1";;
|
||||
esac
|
||||
}
|
||||
|
||||
#### debian/rules helpers
|
||||
|
||||
create_dbg_pkgs () {
|
||||
for x in $ddir/*; do
|
||||
test ! -d $x && continue
|
||||
|
@ -30,51 +74,275 @@ create_dbg_pkgs () {
|
|||
done
|
||||
}
|
||||
|
||||
list_build_depends () {
|
||||
test -f $ddir/.stamp-bootstrap || (cd $ddir && ./bootstrap.sh)
|
||||
local deps="" found=false
|
||||
while xread l; do
|
||||
if [ "${l%%:*}" = "Build-Depends" ]; then
|
||||
deps="${l#*:}"
|
||||
found=true
|
||||
continue
|
||||
elif $found; then
|
||||
if [ -z "$l" ]; then
|
||||
# is newline
|
||||
break
|
||||
elif [ -z "${l##\#*}" ]; then
|
||||
# is comment
|
||||
continue
|
||||
elif [ -z "${l## *}" ]; then
|
||||
# is continuation line
|
||||
deps="$deps $(echo "$l" | sed -e 's/^ *//' -e 's/ *([^)]*)//g' -e 's/,//g')"
|
||||
else
|
||||
# is a new header
|
||||
break
|
||||
fi
|
||||
cwget () {
|
||||
local url="$1" f="${1##*/}"
|
||||
echo "fetching: $url to $f" >&2
|
||||
if [ -n "$FS_FILES_DIR" ]; then
|
||||
if ! [ -s "$FS_FILES_DIR/$f" ]; then
|
||||
(cd $FS_FILES_DIR && wget -N "$url")
|
||||
fi
|
||||
done < $ddir/control
|
||||
echo "${deps# }"
|
||||
cp -a $FS_FILES_DIR/$f .
|
||||
else
|
||||
wget -N "$url"
|
||||
fi
|
||||
}
|
||||
|
||||
install_build_depends () {
|
||||
local apt=""
|
||||
if [ -n "$(which aptitude)" ]; then
|
||||
apt=$(which aptitude)
|
||||
elif [ -n "$(which apt-get)" ]; then
|
||||
apt=$(which apt-get)
|
||||
else
|
||||
err "Can't find apt-get or aptitude; are you running on debian?"
|
||||
fi
|
||||
$apt install -y $(list_build_depends)
|
||||
touch $ddir/.stamp-build-depends
|
||||
getlib () {
|
||||
local url="$1" f="${1##*/}"
|
||||
cwget "$url"
|
||||
tar -xv --no-same-owner --no-same-permissions -f "$f"
|
||||
rm -f "$f" && mkdir -p $f && touch $f/.download-stamp
|
||||
}
|
||||
|
||||
getlibs () {
|
||||
# get pinned libraries
|
||||
getlib http://downloads.mongodb.org/cxx-driver/mongodb-linux-x86_64-v1.8-latest.tgz
|
||||
getlib http://files.freeswitch.org/downloads/libs/json-c-0.9.tar.gz
|
||||
getlib http://files.freeswitch.org/downloads/libs/libmemcached-0.32.tar.gz
|
||||
getlib http://files.freeswitch.org/downloads/libs/soundtouch-1.6.0.tar.gz
|
||||
getlib http://files.freeswitch.org/downloads/libs/flite-1.5.4-current.tar.bz2
|
||||
getlib http://files.freeswitch.org/downloads/libs/sphinxbase-0.7.tar.gz
|
||||
getlib http://files.freeswitch.org/downloads/libs/pocketsphinx-0.7.tar.gz
|
||||
getlib http://files.freeswitch.org/downloads/libs/communicator_semi_6000_20080321.tar.gz
|
||||
getlib http://files.freeswitch.org/downloads/libs/celt-0.10.0.tar.gz
|
||||
getlib http://files.freeswitch.org/downloads/libs/opus-0.9.0.tar.gz
|
||||
getlib http://files.freeswitch.org/downloads/libs/openldap-2.4.19.tar.gz
|
||||
getlib http://download.zeromq.org/zeromq-2.1.9.tar.gz \
|
||||
|| getlib http://download.zeromq.org/historic/zeromq-2.1.9.tar.gz
|
||||
getlib http://files.freeswitch.org/downloads/libs/freeradius-client-1.1.6.tar.gz
|
||||
getlib http://files.freeswitch.org/downloads/libs/lame-3.98.4.tar.gz
|
||||
getlib http://files.freeswitch.org/downloads/libs/libshout-2.2.2.tar.gz
|
||||
getlib http://files.freeswitch.org/downloads/libs/mpg123-1.13.2.tar.gz
|
||||
# cleanup mongo
|
||||
(
|
||||
cd mongo-cxx-driver-v1.8
|
||||
rm -rf config.log .sconf_temp *Test *Example
|
||||
find . -name "*.o" -exec rm -f {} \;
|
||||
)
|
||||
}
|
||||
|
||||
check_repo_clean () {
|
||||
git diff-index --quiet --cached HEAD \
|
||||
|| err "uncommitted changes present"
|
||||
git diff-files --quiet \
|
||||
|| err "unclean working tree"
|
||||
git diff-index --quiet HEAD \
|
||||
|| err "unclean repository"
|
||||
! git ls-files --other --error-unmatch . >/dev/null 2>&1 \
|
||||
|| err "untracked files or build products present"
|
||||
}
|
||||
|
||||
create_orig () {
|
||||
{
|
||||
set -e
|
||||
local OPTIND OPTARG
|
||||
local uver="" bundle_deps=false zl=9e
|
||||
while getopts 'bnv:z:' o "$@"; do
|
||||
case "$o" in
|
||||
b) bundle_deps=true;;
|
||||
n) uver="nightly";;
|
||||
v) uver="$OPTARG";;
|
||||
z) zl="$OPTARG";;
|
||||
esac
|
||||
done
|
||||
shift $(($OPTIND-1))
|
||||
[ -z "$uver" ] || [ "$uver" = "nightly" ] \
|
||||
&& uver="$(cat build/next-release.txt)-n$(date +%Y%m%dT%H%M%SZ)"
|
||||
local treeish="$1" dver="$(mk_dver "$uver")"
|
||||
local orig="../freeswitch_$dver.orig.tar.xz"
|
||||
[ -n "$treeish" ] || treeish="HEAD"
|
||||
check_repo_clean
|
||||
git reset --hard "$treeish"
|
||||
mv .gitattributes .gitattributes.orig
|
||||
grep .gitattributes.orig \
|
||||
-e '\bdebian-ignore\b' \
|
||||
-e '\bdfsg-nonfree\b' \
|
||||
| while xread l; do
|
||||
echo "$l export-ignore" >> .gitattributes
|
||||
done
|
||||
if $bundle_deps; then
|
||||
(cd libs && getlibs)
|
||||
git add -f libs
|
||||
fi
|
||||
./build/set-fs-version.sh "$uver" && git add configure.in
|
||||
git commit --allow-empty -m "nightly v$uver"
|
||||
git archive -v \
|
||||
--worktree-attributes \
|
||||
--format=tar \
|
||||
--prefix=freeswitch-$uver/ \
|
||||
HEAD \
|
||||
| xz -c -${zl}v > $orig
|
||||
mv .gitattributes.orig .gitattributes
|
||||
git reset --hard HEAD^ && git clean -fdx
|
||||
} 1>&2
|
||||
echo $orig
|
||||
}
|
||||
|
||||
set_modules_quicktest () {
|
||||
cat > debian/modules.conf <<EOF
|
||||
applications/mod_commands
|
||||
EOF
|
||||
}
|
||||
|
||||
create_dsc () {
|
||||
{
|
||||
set -e
|
||||
local OPTIND OPTARG modules_list="" speed="normal"
|
||||
while getopts 'm:s:' o "$@"; do
|
||||
case "$o" in
|
||||
m) modules_list="$OPTARG";;
|
||||
s) speed="$OPTARG";;
|
||||
esac
|
||||
done
|
||||
shift $(($OPTIND-1))
|
||||
local distro="$(find_distro $1)" orig="$2"
|
||||
local suite="$(find_suite $distro)"
|
||||
local orig_ver="$(echo "$orig" | sed -e 's/^.*_//' -e 's/\.orig\.tar.*$//')"
|
||||
local dver="${orig_ver}-1~${distro}+1"
|
||||
[ -x "$(which dch)" ] \
|
||||
|| err "package devscripts isn't installed"
|
||||
if [ -n "$modules_list" ]; then
|
||||
set_modules_${modules_list}
|
||||
fi
|
||||
(cd debian && ./bootstrap.sh -c $distro)
|
||||
case "$speed" in
|
||||
paranoid) sed -i ./debian/rules \
|
||||
-e '/\.stamp-bootstrap:/{:l2 n; /\.\/bootstrap.sh -j/{s/ -j//; :l3 n; b l3}; b l2};' ;;
|
||||
reckless) sed -i ./debian/rules \
|
||||
-e '/\.stamp-build:/{:l2 n; /make/{s/$/ -j/; :l3 n; b l3}; b l2};' ;;
|
||||
esac
|
||||
git add debian/rules
|
||||
dch -b -m -v "$dver" --force-distribution -D "$suite" "Nightly build."
|
||||
git add debian/changelog && git commit -m "nightly v$orig_ver"
|
||||
dpkg-source -i.* -Zxz -z9 -b .
|
||||
dpkg-genchanges -S > ../$(dsc_base)_source.changes
|
||||
local dsc="../$(dsc_base).dsc"
|
||||
git reset --hard HEAD^ && git clean -fdx
|
||||
} 1>&2
|
||||
echo $dsc
|
||||
}
|
||||
|
||||
fmt_debug_hook () {
|
||||
cat <<'EOF'
|
||||
#!/bin/bash
|
||||
export debian_chroot="cow"
|
||||
cd /tmp/buildd/*/debian/..
|
||||
/bin/bash < /dev/tty > /dev/tty 2> /dev/tty
|
||||
EOF
|
||||
}
|
||||
|
||||
build_debs () {
|
||||
{
|
||||
set -e
|
||||
local OPTIND OPTARG debug_hook=false hookdir=""
|
||||
while getopts 'd' o "$@"; do
|
||||
case "$o" in
|
||||
d) debug_hook=true;;
|
||||
esac
|
||||
done
|
||||
shift $(($OPTIND-1))
|
||||
local distro="$(find_distro $1)" dsc="$2" arch="$3"
|
||||
if [ -z "$distro" ] || [ "$distro" = "auto" ]; then
|
||||
if ! (echo "$dsc" | grep -e '-[0-9]*~[a-z]*+[0-9]*'); then
|
||||
err "no distro specified or found"
|
||||
fi
|
||||
local x="$(echo $dsc | sed -e 's/^[^-]*-[0-9]*~//' -e 's/+[^+]*$//')"
|
||||
distro="$(find_distro $x)"
|
||||
fi
|
||||
[ -n "$arch" ] || arch="$(dpkg-architecture | grep '^DEB_BUILD_ARCH=' | cut -d'=' -f2)"
|
||||
[ -x "$(which cowbuilder)" ] \
|
||||
|| err "package cowbuilder isn't installed"
|
||||
local cow_img=/var/cache/pbuilder/base-$distro-$arch.cow
|
||||
cow () {
|
||||
cowbuilder "$@" \
|
||||
--distribution $distro \
|
||||
--architecture $arch \
|
||||
--basepath $cow_img
|
||||
}
|
||||
if ! [ -d $cow_img ]; then
|
||||
announce "Creating base $distro-$arch image..."
|
||||
cow --create
|
||||
fi
|
||||
announce "Updating base $distro-$arch image..."
|
||||
cow --update
|
||||
announce "Building $distro-$arch DEBs from $dsc..."
|
||||
if $debug_hook; then
|
||||
mkdir -p .hooks
|
||||
fmt_debug_hook > .hooks/C10shell
|
||||
chmod +x .hooks/C10shell
|
||||
hookdir=$(pwd)/.hooks
|
||||
fi
|
||||
cow --build $dsc \
|
||||
--hookdir "$hookdir" \
|
||||
--buildresult ../
|
||||
} 1>&2
|
||||
echo ${dsc}_${arch}.changes
|
||||
}
|
||||
|
||||
build_all () {
|
||||
local OPTIND OPTARG
|
||||
local orig_opts="" dsc_opts="" deb_opts=""
|
||||
local archs="" distros="" par=false
|
||||
while getopts 'a:bc:djnm:s:v:z:' o "$@"; do
|
||||
case "$o" in
|
||||
a) archs="$archs $OPTARG";;
|
||||
b) orig_opts="$orig_opts -b";;
|
||||
c) distros="$distros $OPTARG";;
|
||||
d) deb_opts="$deb_opts -d";;
|
||||
j) par=true;;
|
||||
n) orig_opts="$orig_opts -n";;
|
||||
m) dsc_opts="$dsc_opts -m$OPTARG";;
|
||||
s) dsc_opts="$dsc_opts -s$OPTARG";;
|
||||
v) orig_opts="$orig_opts -v$OPTARG";;
|
||||
z) orig_opts="$orig_opts -z$OPTARG";;
|
||||
esac
|
||||
done
|
||||
shift $(($OPTIND-1))
|
||||
[ -n "$archs" ] || archs="amd64 i386"
|
||||
[ -n "$distros" ] || distros="sid wheezy squeeze"
|
||||
local orig="$(create_orig $orig_opts HEAD | tail -n1)"
|
||||
mkdir -p ../log
|
||||
> ../log/changes
|
||||
echo; echo; echo; echo
|
||||
if [ "${orig:0:2}" = ".." ]; then
|
||||
for distro in $distros; do
|
||||
echo "Creating $distro dsc..." >&2
|
||||
local dsc="$(create_dsc $dsc_opts $distro $orig 2>../log/$distro | tail -n1)"
|
||||
echo "Done creating $distro dsc." >&2
|
||||
if [ "${dsc:0:2}" = ".." ]; then
|
||||
for arch in $archs; do
|
||||
{
|
||||
echo "Building $distro-$arch debs..." >&2
|
||||
local changes="$(build_debs $deb_opts $distro $dsc $arch 2>../log/$distro-$arch | tail -n1)"
|
||||
echo "Done building $distro-$arch debs." >&2
|
||||
if [ "${changes:0:2}" = ".." ]; then
|
||||
echo "$changes" >> ../log/changes
|
||||
fi
|
||||
} &
|
||||
$par || wait
|
||||
done
|
||||
fi
|
||||
done
|
||||
! $par || wait
|
||||
fi
|
||||
cat ../log/changes
|
||||
}
|
||||
|
||||
while getopts 'd' o "$@"; do
|
||||
case "$o" in
|
||||
d) set -vx;;
|
||||
esac
|
||||
done
|
||||
shift $(($OPTIND-1))
|
||||
|
||||
cmd="$1"
|
||||
shift
|
||||
case "$cmd" in
|
||||
archive-orig) archive_orig "$@" ;;
|
||||
build-all) build_all "$@" ;;
|
||||
build-debs) build_debs "$@" ;;
|
||||
create-dbg-pkgs) create_dbg_pkgs ;;
|
||||
list-build-depends) list_build_depends ;;
|
||||
install-build-depends) install_build_depends ;;
|
||||
create-dsc) create_dsc "$@" ;;
|
||||
create-orig) create_orig "$@" ;;
|
||||
esac
|
||||
|
||||
|
|
|
@ -1,3 +1,18 @@
|
|||
freeswitch (1.2.0)
|
||||
config: add screen_confirm macro to lang/en/ivr/sounds.xml (r:9ea3ce66)
|
||||
config: support for --with-logfilesdir, --with-dbdir, --with-htdocsdir, --with-soundsdir, --with-grammardir, --with-scriptdir and --with-recordin
|
||||
gsdir (r:7ae3f5b7/FS-302)
|
||||
core: Add RECORD_STEREO_SWAP to reverse the record channels (r:d5042f2c/FS-3069)
|
||||
core: api_on_startup (r:e164b76c)
|
||||
mod_conference: Add auto-record filename to conference_recording channel variable and ability to pull filename from API (r:b9295fd5/FS-1573)
|
||||
mod_conference: Convenience feature in mod_conference: apply sub cmds to non_moderator members (r:04295ac9/FS-3249)
|
||||
mod_conference: New conference commands: get and set (r:ab5f3f28/FS-3254)
|
||||
mod_commands: allow system API command to capture output from the executed command (r:d7a37e97)
|
||||
mod_posix_timer: New timer module mod_posix_timer (r:9d7e9e67/FS-3731)
|
||||
mod_sofia: Add presence-privacy parameter to exclude extension numbers from the distributed presence string (r:c6633fa3/FS-849)
|
||||
mod_spandsp: Add T31 modem support to mod_spandsp - similar to iaxmodem only wired into FS. Also merge configs into single spandsp.conf.xml --see in tree example-- (r:d91f67d0)
|
||||
mod_valet_parking: add orbit feature to valet_parking similar to mod_fifo (r:09725e2b)
|
||||
|
||||
freeswitch (1.0.7)
|
||||
|
||||
build: Add mod_silk to windows build
|
||||
|
|
|
@ -77,6 +77,7 @@ BuildArch: noarch
|
|||
BuildRequires: sox
|
||||
Requires: freeswitch
|
||||
Requires: freeswitch-sounds-en-us-callie-48000
|
||||
Requires: sox
|
||||
BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root-%(%{__id_u} -n)
|
||||
|
||||
%description
|
||||
|
|
|
@ -1,3 +1,4 @@
|
|||
%define fsname freeswitch
|
||||
%define PREFIX %{_prefix}
|
||||
%define EXECPREFIX %{_exec_prefix}
|
||||
%define BINDIR %{_bindir}
|
||||
|
|
|
@ -15,13 +15,13 @@
|
|||
# This file and all modifications and additions to the pristine package are under the same license as the package itself.
|
||||
#
|
||||
# Contributor(s): Mike Jerris
|
||||
# Brian West
|
||||
# Raul Fragoso
|
||||
# Rupa Shomaker
|
||||
# Marc Olivier Chouinard
|
||||
# Raymond Chandler
|
||||
# Anthony Minessale II <anthm@freeswitch.org>
|
||||
#
|
||||
# Brian West
|
||||
# Anthony Minessale II <anthm@freeswitch.org>
|
||||
# Raul Fragoso
|
||||
# Rupa Shomaker
|
||||
# Marc Olivier Chouinard
|
||||
# Raymond Chandler
|
||||
# Ken Rice <krice@freeswitch.org>
|
||||
#
|
||||
# Maintainer(s): Ken Rice <krice@freeswitch.org>
|
||||
#
|
||||
|
@ -1433,7 +1433,7 @@ export ACLOCAL_FLAGS="-I /usr/share/aclocal"
|
|||
|
||||
if test ! -f Makefile.in
|
||||
then
|
||||
./bootstrap.sh -j
|
||||
./bootstrap.sh
|
||||
fi
|
||||
|
||||
%configure -C \
|
||||
|
@ -1593,6 +1593,7 @@ fi
|
|||
#################################### Basic Directory Structure #######################################################
|
||||
#
|
||||
%dir %attr(0750, freeswitch, daemon) %{sysconfdir}
|
||||
%dir %attr(0750, freeswitch, daemon) %{LOCALSTATEDIR}
|
||||
%dir %attr(0750, freeswitch, daemon) %{DBDIR}
|
||||
%dir %attr(0750, freeswitch, daemon) %{GRAMMARDIR}
|
||||
%dir %attr(0750, freeswitch, daemon) %{HTDOCSDIR}
|
||||
|
@ -1756,6 +1757,7 @@ fi
|
|||
%config(noreplace) %attr(0640, freeswitch, daemon) %{sysconfdir}/autoload_configs/xml_cdr.conf.xml
|
||||
%config(noreplace) %attr(0640, freeswitch, daemon) %{sysconfdir}/autoload_configs/xml_curl.conf.xml
|
||||
%config(noreplace) %attr(0640, freeswitch, daemon) %{sysconfdir}/autoload_configs/xml_rpc.conf.xml
|
||||
%config(noreplace) %attr(0640, freeswitch, daemon) %{sysconfdir}/autoload_configs/xml_scgi.conf.xml
|
||||
%config(noreplace) %attr(0640, freeswitch, daemon) %{sysconfdir}/autoload_configs/zeroconf.conf.xml
|
||||
######################################################################################################################
|
||||
# Chatplans
|
||||
|
|
|
@ -9,6 +9,7 @@
|
|||
#include <getopt.h>
|
||||
|
||||
#define CMD_BUFLEN 1024
|
||||
#define PROMPT_PREFIX "netborder-ss7"
|
||||
|
||||
#ifndef WIN32
|
||||
#include <sys/select.h>
|
||||
|
@ -902,30 +903,19 @@ static const char *basic_gets(int *cnt)
|
|||
return command_buf;
|
||||
}
|
||||
|
||||
static const char *banner =
|
||||
" _____ ____ ____ _ ___ \n"
|
||||
" | ___/ ___| / ___| | |_ _| \n"
|
||||
" | |_ \\___ \\ | | | | | | \n"
|
||||
" | _| ___) | | |___| |___ | | \n"
|
||||
" |_| |____/ \\____|_____|___| \n"
|
||||
"\n"
|
||||
"*******************************************************\n"
|
||||
"* Anthony Minessale II, Ken Rice, *\n"
|
||||
"* Michael Jerris, Travis Cross *\n"
|
||||
"* FreeSWITCH (http://www.freeswitch.org) *\n"
|
||||
"* Paypal Donations Appreciated: paypal@freeswitch.org *\n"
|
||||
"* Brought to you by ClueCon http://www.cluecon.com/ *\n"
|
||||
"*******************************************************\n"
|
||||
"\n"
|
||||
"Type /help <enter> to see a list of commands\n\n\n";
|
||||
|
||||
static void print_banner(FILE *stream)
|
||||
{
|
||||
#ifndef WIN32
|
||||
fprintf(stream, "%s%s", output_text_color, banner);
|
||||
#else
|
||||
fprintf(stream, "%s", banner);
|
||||
#endif
|
||||
fprintf(stream,
|
||||
|
||||
|
||||
"\n"
|
||||
"*******************************************************\n"
|
||||
"* Netborder SS7 Gateway *\n"
|
||||
"* Powered by FreeSWITCH (http://www.freeswitch.org) *\n"
|
||||
"*******************************************************\n"
|
||||
"\n"
|
||||
"Type /help <enter> to see a list of commands\n\n\n"
|
||||
);
|
||||
}
|
||||
|
||||
static void set_fn_keys(cli_profile_t *profile)
|
||||
|
@ -1152,13 +1142,13 @@ int main(int argc, char *argv[])
|
|||
char cmd_str[1024] = "";
|
||||
cli_profile_t *profile = NULL;
|
||||
#ifndef WIN32
|
||||
char hfile[512] = "/tmp/fs_cli_history";
|
||||
char cfile[512] = "/etc/fs_cli.conf";
|
||||
char dft_cfile[512] = "/etc/fs_cli.conf";
|
||||
char hfile[512] = "/etc/nbess7_cli_history";
|
||||
char cfile[512] = "/etc/nbess7_cli.conf";
|
||||
char dft_cfile[512] = "/etc/nbess7_cli.conf";
|
||||
#else
|
||||
char hfile[512] = "fs_cli_history";
|
||||
char cfile[512] = "fs_cli.conf";
|
||||
char dft_cfile[512] = "fs_cli.conf";
|
||||
char hfile[512] = "nbess7_cli_history";
|
||||
char cfile[512] = "nbess7_cli.conf";
|
||||
char dft_cfile[512] = "nbess7_cli.conf";
|
||||
#endif
|
||||
char *home = getenv("HOME");
|
||||
/* Vars for optargs */
|
||||
|
@ -1203,18 +1193,19 @@ int main(int argc, char *argv[])
|
|||
#else
|
||||
feature_level = 1;
|
||||
#endif
|
||||
feature_level = 0;
|
||||
|
||||
strncpy(internal_profile.host, "127.0.0.1", sizeof(internal_profile.host));
|
||||
strncpy(internal_profile.pass, "ClueCon", sizeof(internal_profile.pass));
|
||||
strncpy(internal_profile.name, "internal", sizeof(internal_profile.name));
|
||||
internal_profile.port = 8021;
|
||||
internal_profile.port = 8821;
|
||||
set_fn_keys(&internal_profile);
|
||||
esl_set_string(internal_profile.prompt_color, prompt_color);
|
||||
esl_set_string(internal_profile.input_text_color, input_text_color);
|
||||
esl_set_string(internal_profile.output_text_color, output_text_color);
|
||||
if (home) {
|
||||
snprintf(hfile, sizeof(hfile), "%s/.fs_cli_history", home);
|
||||
snprintf(cfile, sizeof(cfile), "%s/.fs_cli_conf", home);
|
||||
snprintf(hfile, sizeof(hfile), "%s/.nbess7_cli_history", home);
|
||||
snprintf(cfile, sizeof(cfile), "%s/.nbess7_cli_conf", home);
|
||||
}
|
||||
signal(SIGINT, handle_SIGINT);
|
||||
#ifdef SIGTSTP
|
||||
|
@ -1335,20 +1326,24 @@ int main(int argc, char *argv[])
|
|||
esl_set_string(input_text_color, profile->input_text_color);
|
||||
esl_set_string(output_text_color, profile->output_text_color);
|
||||
if (argv_host) {
|
||||
if (argv_port && profile->port != 8021) {
|
||||
snprintf(bare_prompt_str, sizeof(bare_prompt_str), "freeswitch@%s:%u@%s> ", profile->host, profile->port, profile->name);
|
||||
if (argv_port && profile->port != 8821) {
|
||||
snprintf(prompt_str, sizeof(prompt_str), PROMPT_PREFIX "@%s:%u@%s> ", profile->host, profile->port, profile->name);
|
||||
} else {
|
||||
snprintf(bare_prompt_str, sizeof(bare_prompt_str), "freeswitch@%s@%s> ", profile->host, profile->name);
|
||||
snprintf(prompt_str, sizeof(prompt_str), PROMPT_PREFIX "@%s@%s> ", profile->host, profile->name);
|
||||
}
|
||||
} else {
|
||||
snprintf(bare_prompt_str, sizeof(bare_prompt_str), "freeswitch@%s> ", profile->name);
|
||||
snprintf(prompt_str, sizeof(prompt_str), PROMPT_PREFIX "@%s> ", profile->name);
|
||||
}
|
||||
bare_prompt_str_len = (int)strlen(bare_prompt_str);
|
||||
if (feature_level) {
|
||||
snprintf(prompt_str, sizeof(prompt_str), "%s%s%s", prompt_color, bare_prompt_str, input_text_color);
|
||||
} else {
|
||||
}
|
||||
/*
|
||||
else {
|
||||
|
||||
snprintf(prompt_str, sizeof(prompt_str), "%s", bare_prompt_str);
|
||||
}
|
||||
}
|
||||
*/
|
||||
connect:
|
||||
connected = 0;
|
||||
while (--loops > 0) {
|
||||
|
@ -1470,8 +1465,10 @@ int main(int argc, char *argv[])
|
|||
setvbuf(stdout, (char*)NULL, _IONBF, 0);
|
||||
}
|
||||
print_banner(stdout);
|
||||
esl_log(ESL_LOG_INFO, "FS CLI Ready.\nenter /help for a list of commands.\n");
|
||||
|
||||
esl_log(ESL_LOG_INFO, "Netborder SS7 CLI Ready.\nenter /help for a list of commands.\n");
|
||||
output_printf("%s\n", handle.last_sr_reply);
|
||||
|
||||
while (running > 0) {
|
||||
int r;
|
||||
#ifdef HAVE_EDITLINE
|
||||
|
|
|
@ -4,7 +4,7 @@
|
|||
|
||||
host => 127.0.0.1
|
||||
password => ClueCon
|
||||
port => 8021
|
||||
port => 8821
|
||||
debug => 2
|
||||
|
||||
key_f1 => help
|
||||
|
|
|
@ -213,6 +213,8 @@ ftmod_sangoma_ss7_la_SOURCES = \
|
|||
$(SRC)/ftmod/ftmod_sangoma_ss7/ftmod_sangoma_ss7_sta.c \
|
||||
$(SRC)/ftmod/ftmod_sangoma_ss7/ftmod_sangoma_ss7_sts.c \
|
||||
$(SRC)/ftmod/ftmod_sangoma_ss7/ftmod_sangoma_ss7_logger.c \
|
||||
$(SRC)/ftmod/ftmod_sangoma_ss7/ftmod_sangoma_ss7_m2ua_xml.c \
|
||||
$(SRC)/ftmod/ftmod_sangoma_ss7/ftmod_sangoma_ss7_m2ua.c \
|
||||
$(SRC)/ftmod/ftmod_sangoma_ss7/ftmod_sangoma_ss7_relay.c
|
||||
|
||||
ftmod_sangoma_ss7_la_CFLAGS = $(FTDM_CFLAGS) $(AM_CFLAGS) -D_GNU_SOURCE
|
||||
|
|
|
@ -13,7 +13,7 @@ cpu_monitoring_interval => 1000
|
|||
cpu_set_alarm_threshold => 80
|
||||
|
||||
; At what CPU percentage stop the CPU alarm
|
||||
cpu_reset_alarm_threshold => 70
|
||||
cpu_clear_alarm_threshold => 70
|
||||
|
||||
; Which action to take when the CPU alarm is raised
|
||||
; it can be warn and/or reject calls
|
||||
|
|
|
@ -0,0 +1,43 @@
|
|||
SS7 Native Bridge
|
||||
|
||||
Native bridge is enabled on 2 conditions:
|
||||
|
||||
* The SIP header FreeTDM-TransUUID is set in the originating leg and matches a freetdm channel
|
||||
* The variable freetdm_native_sigbridge is true and the originating leg is also a freetdm channel
|
||||
|
||||
Some coding rules apply to this feature:
|
||||
|
||||
- Each channel is responsible for clearning its own peer_data and event queue
|
||||
at the end of the call (when moving to DOWN state)
|
||||
|
||||
- Each channel dequeues messages only from its own queue and enqueues messages
|
||||
in the peer's queue, with the only exception being messages received before
|
||||
the bridge is stablished (IAM for sure and possible SAM messages) because
|
||||
if the bridge is not yet stablished the messages must be queued by the channel
|
||||
in its own queue temporarily until the bridge is ready
|
||||
|
||||
- When the bridge is ready it is the responsibility of the incoming channel to
|
||||
move the messages that stored temporarily in its own queue to the bridged peer queue
|
||||
|
||||
- During hangup, each channel is responsible for moving itself to DOWN. The procedure
|
||||
however differs slightly depending on the hangup conditions
|
||||
|
||||
If the user requests hangup (ie, FreeSWITCH) the request will be noted by setting the
|
||||
FTDM_CHANNEL_USER_HANGUP flag but will not be processed yet because call control is
|
||||
driven only by the link messages (so no hangup from ESL or command line allowed)
|
||||
|
||||
When REL message comes, the channel receiving it must move to TERMINATING state and:
|
||||
|
||||
- If the user has not hangup yet (FTDM_CHANNEL_USER_HANGUP flag not set) then
|
||||
notify the user via SIGEVENT_STOP and wait for the user to move to HANGUP
|
||||
state by calling ftdm_channel_call_hangup() before sending RLC
|
||||
|
||||
- If the user did hangup already (FTDM_CHANNEL_USER_HANGUP flag is set) then
|
||||
skip user notification and move to HANGUP state directly where the RLC message
|
||||
will be sent
|
||||
|
||||
- On HANGUP state the RLC is sent and the channel is moved to DOWN, final state
|
||||
The peer channel will forward the REL message and wait for RLC from the network, when
|
||||
RLC is received the channel can move straight to DOWN itself because the peer channel
|
||||
is completing its own shutdown procedure when it received the REL message
|
||||
|
|
@ -4,6 +4,7 @@ BASE=../../..
|
|||
FT_DIR=..
|
||||
VERBOSE=1
|
||||
FTLA=$(FT_DIR)/libfreetdm.la
|
||||
LOCAL_OBJS=tdm.o
|
||||
LOCAL_CFLAGS=-I$(FT_DIR)/src/include -I$(FT_DIR)/src/isdn/include $(FT_CFLAGS)
|
||||
LOCAL_LDFLAGS=-L$(FT_DIR) -lfreetdm
|
||||
include $(BASE)/build/modmake.rules
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,712 @@
|
|||
/*
|
||||
* FreeSWITCH Modular Media Switching Software Library / Soft-Switch Application
|
||||
* Copyright (C) 2005-2011, Anthony Minessale II <anthm@freeswitch.org>
|
||||
*
|
||||
* Version: MPL 1.1
|
||||
*
|
||||
* The contents of this file are subject to the Mozilla Public License Version
|
||||
* 1.1 (the "License"); you may not use this file except in compliance with
|
||||
* the License. You may obtain a copy of the License at
|
||||
* http://www.mozilla.org/MPL/
|
||||
*
|
||||
* Software distributed under the License is distributed on an "AS IS" basis,
|
||||
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
||||
* for the specific language governing rights and limitations under the
|
||||
* License.
|
||||
*
|
||||
* The Original Code is FreeSWITCH Modular Media Switching Software Library / Soft-Switch Application
|
||||
*
|
||||
* The Initial Developer of the Original Code is
|
||||
* Anthony Minessale II <anthm@freeswitch.org>
|
||||
* Portions created by the Initial Developer are Copyright (C)
|
||||
* the Initial Developer. All Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
*
|
||||
* Mathieu Rene <mrene@avgs.ca>
|
||||
*
|
||||
* tdm.c -- FreeTDM Controllable Channel Module
|
||||
*
|
||||
*/
|
||||
|
||||
#include <switch.h>
|
||||
#include "freetdm.h"
|
||||
|
||||
void ctdm_init(switch_loadable_module_interface_t *module_interface);
|
||||
|
||||
/* Parameters */
|
||||
|
||||
#define kSPAN_ID "span"
|
||||
#define kCHAN_ID "chan"
|
||||
#define kSPAN_NAME "span_name"
|
||||
#define kPREBUFFER_LEN "prebuffer_len"
|
||||
#define kECHOCANCEL "echo_cancel"
|
||||
|
||||
|
||||
static struct {
|
||||
switch_memory_pool_t *pool;
|
||||
switch_endpoint_interface_t *endpoint_interface;
|
||||
} ctdm;
|
||||
|
||||
typedef struct {
|
||||
int span_id;
|
||||
int chan_id;
|
||||
ftdm_channel_t *ftdm_channel;
|
||||
switch_core_session_t *session;
|
||||
switch_codec_t read_codec, write_codec;
|
||||
switch_frame_t read_frame;
|
||||
int prebuffer_len;
|
||||
|
||||
unsigned char databuf[SWITCH_RECOMMENDED_BUFFER_SIZE];
|
||||
} ctdm_private_t;
|
||||
|
||||
static switch_status_t channel_on_init(switch_core_session_t *session);
|
||||
static switch_status_t channel_on_destroy(switch_core_session_t *session);
|
||||
static switch_call_cause_t channel_outgoing_channel(switch_core_session_t *session, switch_event_t *var_event,
|
||||
switch_caller_profile_t *outbound_profile,
|
||||
switch_core_session_t **new_session,
|
||||
switch_memory_pool_t **pool,
|
||||
switch_originate_flag_t flags, switch_call_cause_t *cancel_cause);
|
||||
static switch_status_t channel_read_frame(switch_core_session_t *session, switch_frame_t **frame, switch_io_flag_t flags, int stream_id);
|
||||
static switch_status_t channel_write_frame(switch_core_session_t *session, switch_frame_t *frame, switch_io_flag_t flags, int stream_id);
|
||||
static switch_status_t channel_receive_message(switch_core_session_t *session, switch_core_session_message_t *msg);
|
||||
static switch_status_t channel_receive_event(switch_core_session_t *session, switch_event_t *event);
|
||||
static switch_status_t channel_send_dtmf(switch_core_session_t *session, const switch_dtmf_t *dtmf);
|
||||
|
||||
|
||||
static ftdm_status_t ctdm_span_prepare(ftdm_span_t *span);
|
||||
|
||||
switch_state_handler_table_t ctdm_state_handlers = {
|
||||
.on_init = channel_on_init,
|
||||
.on_destroy = channel_on_destroy
|
||||
};
|
||||
|
||||
switch_io_routines_t ctdm_io_routines = {
|
||||
.send_dtmf = channel_send_dtmf,
|
||||
.outgoing_channel = channel_outgoing_channel,
|
||||
.read_frame = channel_read_frame,
|
||||
.write_frame = channel_write_frame,
|
||||
.receive_message = channel_receive_message,
|
||||
.receive_event = channel_receive_event
|
||||
};
|
||||
|
||||
static void ctdm_report_alarms(ftdm_channel_t *channel)
|
||||
{
|
||||
switch_event_t *event = NULL;
|
||||
ftdm_alarm_flag_t alarmflag = 0;
|
||||
|
||||
if (switch_event_create(&event, SWITCH_EVENT_TRAP) != SWITCH_STATUS_SUCCESS) {
|
||||
ftdm_log(FTDM_LOG_ERROR, "failed to create alarms events\n");
|
||||
return;
|
||||
}
|
||||
|
||||
if (ftdm_channel_get_alarms(channel, &alarmflag) != FTDM_SUCCESS) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Failed to retrieve alarms %s:%d\n", ftdm_channel_get_span_name(channel), ftdm_channel_get_id(channel));
|
||||
return;
|
||||
}
|
||||
|
||||
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "span-name", "%s", ftdm_channel_get_span_name(channel));
|
||||
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "span-number", "%d", ftdm_channel_get_span_id(channel));
|
||||
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "chan-number", "%d", ftdm_channel_get_id(channel));
|
||||
|
||||
if (alarmflag) {
|
||||
switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "condition", "ftdm-alarm-trap");
|
||||
} else {
|
||||
switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "condition", "ftdm-alarm-clear");
|
||||
}
|
||||
|
||||
if (alarmflag & FTDM_ALARM_RED) {
|
||||
switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "alarm", "red");
|
||||
}
|
||||
if (alarmflag & FTDM_ALARM_YELLOW) {
|
||||
switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "alarm", "yellow");
|
||||
}
|
||||
if (alarmflag & FTDM_ALARM_RAI) {
|
||||
switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "alarm", "rai");
|
||||
}
|
||||
if (alarmflag & FTDM_ALARM_BLUE) {
|
||||
switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "alarm", "blue");
|
||||
}
|
||||
if (alarmflag & FTDM_ALARM_AIS) {
|
||||
switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "alarm", "ais");
|
||||
}
|
||||
if (alarmflag & FTDM_ALARM_GENERAL) {
|
||||
switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "alarm", "general");
|
||||
}
|
||||
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Reporting [%s] alarms for %s:%d\n",
|
||||
(alarmflag?"ftdm-alarm-trap":"ftdm-alarm-clear"), ftdm_channel_get_span_name(channel), ftdm_channel_get_id(channel));
|
||||
|
||||
switch_event_fire(&event);
|
||||
return;
|
||||
}
|
||||
|
||||
static ftdm_channel_t *ctdm_get_channel_from_event(switch_event_t *event, ftdm_span_t *span)
|
||||
{
|
||||
uint32_t chan_id = 0;
|
||||
const char *chan_number = NULL;
|
||||
|
||||
chan_number = switch_event_get_header(event, "chan-number");
|
||||
|
||||
if (zstr(chan_number)) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "No channel number specified\n");
|
||||
return NULL;
|
||||
}
|
||||
chan_id = atoi(chan_number);
|
||||
if (!chan_id) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Invalid channel number:%s\n", chan_number);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return ftdm_span_get_channel_ph(span, chan_id);
|
||||
}
|
||||
|
||||
|
||||
static void ctdm_event_handler(switch_event_t *event)
|
||||
{
|
||||
ftdm_status_t status = FTDM_FAIL;
|
||||
switch(event->event_id) {
|
||||
case SWITCH_EVENT_TRAP:
|
||||
{
|
||||
ftdm_span_t *span = NULL;
|
||||
ftdm_channel_t *channel = NULL;
|
||||
const char *span_name = NULL;
|
||||
|
||||
const char *cond = switch_event_get_header(event, "condition");
|
||||
const char *command = switch_event_get_header(event, "command");
|
||||
if (zstr(cond)) {
|
||||
return;
|
||||
}
|
||||
|
||||
span_name = switch_event_get_header(event, "span-name");
|
||||
|
||||
if (ftdm_span_find_by_name(span_name, &span) != FTDM_SUCCESS) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Cannot find span [%s]\n", span_name);
|
||||
return;
|
||||
}
|
||||
|
||||
if (!strcmp(cond, "mg-tdm-prepare")) {
|
||||
status = ctdm_span_prepare(span);
|
||||
if (status == FTDM_SUCCESS) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "%s:prepared successfully\n", span_name);
|
||||
} else if (status != FTDM_EINVAL) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "%s:Failed to prepare span\n", span_name);
|
||||
}
|
||||
} else if (!strcmp(cond, "mg-tdm-check")) {
|
||||
channel = ctdm_get_channel_from_event(event, span);
|
||||
if (!channel) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Could not find channel\n");
|
||||
return;
|
||||
}
|
||||
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Requesting alarm status for %s:%d\n",
|
||||
ftdm_channel_get_span_name(channel), ftdm_channel_get_id(channel));
|
||||
|
||||
ctdm_report_alarms(channel);
|
||||
} else if (!strcmp(cond, "mg-tdm-dtmfremoval")) {
|
||||
uint8_t enable = 0;
|
||||
channel = ctdm_get_channel_from_event(event, span);
|
||||
if (!channel) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Could not find channel\n");
|
||||
return;
|
||||
}
|
||||
|
||||
if (zstr(command)) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "%s:No command specified for mg-tdm-dtmfremoval\n", span_name);
|
||||
return;
|
||||
}
|
||||
|
||||
if (!strcmp(command, "enable")) {
|
||||
enable = 1;
|
||||
}
|
||||
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "%s DTMF-removal for %s:%d\n",
|
||||
enable ? "Enabling" : "Disabling", ftdm_channel_get_span_name(channel), ftdm_channel_get_id(channel));
|
||||
|
||||
ftdm_channel_command(channel, enable ? FTDM_COMMAND_ENABLE_DTMF_REMOVAL : FTDM_COMMAND_DISABLE_DTMF_REMOVAL, 0);
|
||||
}
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
void ctdm_init(switch_loadable_module_interface_t *module_interface)
|
||||
{
|
||||
switch_endpoint_interface_t *endpoint_interface;
|
||||
ctdm.pool = module_interface->pool;
|
||||
endpoint_interface = switch_loadable_module_create_interface(module_interface, SWITCH_ENDPOINT_INTERFACE);
|
||||
endpoint_interface->interface_name = "tdm";
|
||||
endpoint_interface->io_routines = &ctdm_io_routines;
|
||||
endpoint_interface->state_handler = &ctdm_state_handlers;
|
||||
ctdm.endpoint_interface = endpoint_interface;
|
||||
|
||||
switch_event_bind("mod_freetdm", SWITCH_EVENT_TRAP, SWITCH_EVENT_SUBCLASS_ANY, ctdm_event_handler, NULL);
|
||||
}
|
||||
|
||||
static FIO_SIGNAL_CB_FUNCTION(on_signal_cb)
|
||||
{
|
||||
uint32_t chanid, spanid;
|
||||
switch_event_t *event = NULL;
|
||||
ftdm_alarm_flag_t alarmbits = FTDM_ALARM_NONE;
|
||||
|
||||
chanid = ftdm_channel_get_id(sigmsg->channel);
|
||||
spanid = ftdm_channel_get_span_id(sigmsg->channel);
|
||||
|
||||
switch(sigmsg->event_id) {
|
||||
case FTDM_SIGEVENT_ALARM_CLEAR:
|
||||
case FTDM_SIGEVENT_ALARM_TRAP:
|
||||
{
|
||||
if (ftdm_channel_get_alarms(sigmsg->channel, &alarmbits) != FTDM_SUCCESS) {
|
||||
ftdm_log(FTDM_LOG_ERROR, "failed to retrieve alarms\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
if (switch_event_create(&event, SWITCH_EVENT_TRAP) != SWITCH_STATUS_SUCCESS) {
|
||||
ftdm_log(FTDM_LOG_ERROR, "failed to create alarms events\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
if (sigmsg->event_id == FTDM_SIGEVENT_ALARM_CLEAR) {
|
||||
ftdm_log(FTDM_LOG_NOTICE, "Alarm cleared on channel %d:%d\n", spanid, chanid);
|
||||
switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "condition", "ftdm-alarm-clear");
|
||||
} else {
|
||||
ftdm_log(FTDM_LOG_NOTICE, "Alarm raised on channel %d:%d\n", spanid, chanid);
|
||||
switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "condition", "ftdm-alarm-trap");
|
||||
}
|
||||
}
|
||||
break;
|
||||
default:
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Unhandled event %d\n", sigmsg->event_id);
|
||||
break;
|
||||
}
|
||||
|
||||
if (event) {
|
||||
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "span-name", "%s", ftdm_channel_get_span_name(sigmsg->channel));
|
||||
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "span-number", "%d", ftdm_channel_get_span_id(sigmsg->channel));
|
||||
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "chan-number", "%d", ftdm_channel_get_id(sigmsg->channel));
|
||||
|
||||
if (alarmbits & FTDM_ALARM_RED) {
|
||||
switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "alarm", "red");
|
||||
}
|
||||
if (alarmbits & FTDM_ALARM_YELLOW) {
|
||||
switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "alarm", "yellow");
|
||||
}
|
||||
if (alarmbits & FTDM_ALARM_RAI) {
|
||||
switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "alarm", "rai");
|
||||
}
|
||||
if (alarmbits & FTDM_ALARM_BLUE) {
|
||||
switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "alarm", "blue");
|
||||
}
|
||||
if (alarmbits & FTDM_ALARM_AIS) {
|
||||
switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "alarm", "ais");
|
||||
}
|
||||
if (alarmbits & FTDM_ALARM_GENERAL) {
|
||||
switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "alarm", "general");
|
||||
}
|
||||
|
||||
switch_event_fire(&event);
|
||||
}
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
static ftdm_status_t ctdm_span_prepare(ftdm_span_t *span)
|
||||
{
|
||||
if (ftdm_span_register_signal_cb(span, on_signal_cb) != FTDM_SUCCESS) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't register signal CB\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
return ftdm_span_start(span);
|
||||
}
|
||||
|
||||
static switch_call_cause_t channel_outgoing_channel(switch_core_session_t *session, switch_event_t *var_event,
|
||||
switch_caller_profile_t *outbound_profile,
|
||||
switch_core_session_t **new_session,
|
||||
switch_memory_pool_t **pool,
|
||||
switch_originate_flag_t flags, switch_call_cause_t *cancel_cause)
|
||||
{
|
||||
const char *szchanid = switch_event_get_header(var_event, kCHAN_ID),
|
||||
*span_name = switch_event_get_header(var_event, kSPAN_NAME),
|
||||
*szprebuffer_len = switch_event_get_header(var_event, kPREBUFFER_LEN);
|
||||
int chan_id;
|
||||
int span_id;
|
||||
switch_caller_profile_t *caller_profile;
|
||||
ftdm_span_t *span;
|
||||
ftdm_channel_t *chan;
|
||||
switch_channel_t *channel;
|
||||
char name[128];
|
||||
const char *dname;
|
||||
ftdm_codec_t codec;
|
||||
uint32_t interval;
|
||||
ctdm_private_t *tech_pvt = NULL;
|
||||
|
||||
if (zstr(szchanid) || zstr(span_name)) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Both ["kSPAN_ID"] and ["kCHAN_ID"] have to be set.\n");
|
||||
goto fail;
|
||||
}
|
||||
|
||||
chan_id = atoi(szchanid);
|
||||
|
||||
if (ftdm_span_find_by_name(span_name, &span) == FTDM_SUCCESS) {
|
||||
span_id = ftdm_span_get_id(span);
|
||||
} else {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Cannot find span [%s]\n", span_name);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
if (!(*new_session = switch_core_session_request(ctdm.endpoint_interface, SWITCH_CALL_DIRECTION_OUTBOUND, 0, pool))) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't request session.\n");
|
||||
goto fail;
|
||||
}
|
||||
|
||||
channel = switch_core_session_get_channel(*new_session);
|
||||
|
||||
if (ftdm_channel_open_ph(span_id, chan_id, &chan) != FTDM_SUCCESS) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't open span or channel.\n");
|
||||
goto fail;
|
||||
}
|
||||
|
||||
span = ftdm_channel_get_span(chan);
|
||||
|
||||
tech_pvt = switch_core_session_alloc(*new_session, sizeof *tech_pvt);
|
||||
tech_pvt->chan_id = chan_id;
|
||||
tech_pvt->span_id = span_id;
|
||||
tech_pvt->ftdm_channel = chan;
|
||||
tech_pvt->session = *new_session;
|
||||
tech_pvt->read_frame.buflen = sizeof(tech_pvt->databuf);
|
||||
tech_pvt->read_frame.data = tech_pvt->databuf;
|
||||
tech_pvt->prebuffer_len = zstr(szprebuffer_len) ? 0 : atoi(szprebuffer_len);
|
||||
switch_core_session_set_private(*new_session, tech_pvt);
|
||||
|
||||
|
||||
caller_profile = switch_caller_profile_clone(*new_session, outbound_profile);
|
||||
switch_channel_set_caller_profile(channel, caller_profile);
|
||||
|
||||
snprintf(name, sizeof(name), "tdm/%d:%d", span_id, chan_id);
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Connect outbound channel %s\n", name);
|
||||
switch_channel_set_name(channel, name);
|
||||
|
||||
switch_channel_set_state(channel, CS_INIT);
|
||||
|
||||
if (FTDM_SUCCESS != ftdm_channel_command(chan, FTDM_COMMAND_GET_CODEC, &codec)) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Failed to retrieve channel codec.\n");
|
||||
return SWITCH_STATUS_GENERR;
|
||||
}
|
||||
|
||||
if (FTDM_SUCCESS != ftdm_channel_command(chan, FTDM_COMMAND_GET_INTERVAL, &interval)) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Failed to retrieve channel interval.\n");
|
||||
return SWITCH_STATUS_GENERR;
|
||||
}
|
||||
|
||||
if (FTDM_SUCCESS != ftdm_channel_command(chan, FTDM_COMMAND_SET_PRE_BUFFER_SIZE, &tech_pvt->prebuffer_len)) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Failed to set channel pre buffer size.\n");
|
||||
return SWITCH_STATUS_GENERR;
|
||||
}
|
||||
|
||||
if (FTDM_SUCCESS != ftdm_channel_command(tech_pvt->ftdm_channel, FTDM_COMMAND_ENABLE_ECHOCANCEL, NULL)) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_WARNING, "Failed to set enable echo cancellation.\n");
|
||||
}
|
||||
|
||||
switch(codec) {
|
||||
case FTDM_CODEC_ULAW:
|
||||
{
|
||||
dname = "PCMU";
|
||||
}
|
||||
break;
|
||||
case FTDM_CODEC_ALAW:
|
||||
{
|
||||
dname = "PCMA";
|
||||
}
|
||||
break;
|
||||
case FTDM_CODEC_SLIN:
|
||||
{
|
||||
dname = "L16";
|
||||
}
|
||||
break;
|
||||
default:
|
||||
{
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Invalid codec value retrieved from channel, codec value: %d\n", codec);
|
||||
goto fail;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (switch_core_codec_init(&tech_pvt->read_codec,
|
||||
dname,
|
||||
NULL,
|
||||
8000,
|
||||
interval,
|
||||
1,
|
||||
SWITCH_CODEC_FLAG_ENCODE | SWITCH_CODEC_FLAG_DECODE,
|
||||
NULL, switch_core_session_get_pool(tech_pvt->session)) != SWITCH_STATUS_SUCCESS) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Can't load codec?\n");
|
||||
goto fail;
|
||||
} else {
|
||||
if (switch_core_codec_init(&tech_pvt->write_codec,
|
||||
dname,
|
||||
NULL,
|
||||
8000,
|
||||
interval,
|
||||
1,
|
||||
SWITCH_CODEC_FLAG_ENCODE | SWITCH_CODEC_FLAG_DECODE,
|
||||
NULL, switch_core_session_get_pool(tech_pvt->session)) != SWITCH_STATUS_SUCCESS) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Can't load codec?\n");
|
||||
switch_core_codec_destroy(&tech_pvt->read_codec);
|
||||
goto fail;
|
||||
}
|
||||
}
|
||||
|
||||
if (switch_core_session_set_read_codec(*new_session, &tech_pvt->read_codec) != SWITCH_STATUS_SUCCESS) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Can't set read codec?\n");
|
||||
goto fail;
|
||||
}
|
||||
|
||||
if (switch_core_session_set_write_codec(*new_session, &tech_pvt->write_codec) != SWITCH_STATUS_SUCCESS) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Can't set write codec?\n");
|
||||
}
|
||||
|
||||
if (switch_core_session_thread_launch(*new_session) != SWITCH_STATUS_SUCCESS) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't start session thread.\n");
|
||||
goto fail;
|
||||
}
|
||||
|
||||
switch_channel_mark_answered(channel);
|
||||
|
||||
return SWITCH_CAUSE_SUCCESS;
|
||||
|
||||
fail:
|
||||
|
||||
if (tech_pvt) {
|
||||
if (tech_pvt->ftdm_channel) {
|
||||
ftdm_channel_close(&tech_pvt->ftdm_channel);
|
||||
}
|
||||
|
||||
if (tech_pvt->read_codec.implementation) {
|
||||
switch_core_codec_destroy(&tech_pvt->read_codec);
|
||||
}
|
||||
|
||||
if (tech_pvt->write_codec.implementation) {
|
||||
switch_core_codec_destroy(&tech_pvt->write_codec);
|
||||
}
|
||||
}
|
||||
|
||||
if (*new_session) {
|
||||
switch_core_session_destroy(new_session);
|
||||
}
|
||||
return SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER;
|
||||
}
|
||||
|
||||
static switch_status_t channel_on_init(switch_core_session_t *session)
|
||||
{
|
||||
switch_channel_t *channel = switch_core_session_get_channel(session);
|
||||
|
||||
switch_channel_set_state(channel, CS_CONSUME_MEDIA);
|
||||
return SWITCH_STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
static switch_status_t channel_on_destroy(switch_core_session_t *session)
|
||||
{
|
||||
ctdm_private_t *tech_pvt = switch_core_session_get_private(session);
|
||||
|
||||
if ((tech_pvt = switch_core_session_get_private(session))) {
|
||||
|
||||
if (FTDM_SUCCESS != ftdm_channel_command(tech_pvt->ftdm_channel, FTDM_COMMAND_ENABLE_ECHOCANCEL, NULL)) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_WARNING, "Failed to enable echo cancellation.\n");
|
||||
}
|
||||
|
||||
if (tech_pvt->read_codec.implementation) {
|
||||
switch_core_codec_destroy(&tech_pvt->read_codec);
|
||||
}
|
||||
|
||||
if (tech_pvt->write_codec.implementation) {
|
||||
switch_core_codec_destroy(&tech_pvt->write_codec);
|
||||
}
|
||||
|
||||
ftdm_channel_close(&tech_pvt->ftdm_channel);
|
||||
}
|
||||
|
||||
return SWITCH_STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
static switch_status_t channel_read_frame(switch_core_session_t *session, switch_frame_t **frame, switch_io_flag_t flags, int stream_id)
|
||||
{
|
||||
ftdm_wait_flag_t wflags = FTDM_READ;
|
||||
ftdm_status_t status;
|
||||
ctdm_private_t *tech_pvt;
|
||||
const char *name;
|
||||
switch_channel_t *channel;
|
||||
int chunk;
|
||||
uint32_t span_id, chan_id;
|
||||
ftdm_size_t len;
|
||||
char dtmf[128] = "";
|
||||
|
||||
channel = switch_core_session_get_channel(session);
|
||||
assert(channel != NULL);
|
||||
|
||||
tech_pvt = switch_core_session_get_private(session);
|
||||
assert(tech_pvt != NULL);
|
||||
|
||||
name = switch_channel_get_name(channel);
|
||||
|
||||
top:
|
||||
wflags = FTDM_READ;
|
||||
chunk = ftdm_channel_get_io_interval(tech_pvt->ftdm_channel) * 2;
|
||||
status = ftdm_channel_wait(tech_pvt->ftdm_channel, &wflags, chunk);
|
||||
|
||||
|
||||
span_id = ftdm_channel_get_span_id(tech_pvt->ftdm_channel);
|
||||
chan_id = ftdm_channel_get_id(tech_pvt->ftdm_channel);
|
||||
|
||||
if (status == FTDM_FAIL) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Failed to read from channel %s device %d:%d!\n", name, span_id, chan_id);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
if (status == FTDM_TIMEOUT) {
|
||||
goto top;
|
||||
}
|
||||
|
||||
if (!(wflags & FTDM_READ)) {
|
||||
goto top;
|
||||
}
|
||||
|
||||
len = tech_pvt->read_frame.buflen;
|
||||
if (ftdm_channel_read(tech_pvt->ftdm_channel, tech_pvt->read_frame.data, &len) != FTDM_SUCCESS) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_WARNING, "Failed to read from channel %s device %d:%d!\n", name, span_id, chan_id);
|
||||
}
|
||||
|
||||
*frame = &tech_pvt->read_frame;
|
||||
tech_pvt->read_frame.datalen = (uint32_t)len;
|
||||
tech_pvt->read_frame.samples = tech_pvt->read_frame.datalen;
|
||||
tech_pvt->read_frame.codec = &tech_pvt->read_codec;
|
||||
|
||||
if (ftdm_channel_get_codec(tech_pvt->ftdm_channel) == FTDM_CODEC_SLIN) {
|
||||
tech_pvt->read_frame.samples /= 2;
|
||||
}
|
||||
|
||||
while (ftdm_channel_dequeue_dtmf(tech_pvt->ftdm_channel, dtmf, sizeof(dtmf))) {
|
||||
switch_dtmf_t _dtmf = { 0, switch_core_default_dtmf_duration(0) };
|
||||
char *p;
|
||||
for (p = dtmf; p && *p; p++) {
|
||||
if (is_dtmf(*p)) {
|
||||
_dtmf.digit = *p;
|
||||
ftdm_log(FTDM_LOG_DEBUG, "Queuing DTMF [%c] in channel %s device %d:%d\n", *p, name, span_id, chan_id);
|
||||
switch_channel_queue_dtmf(channel, &_dtmf);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return SWITCH_STATUS_SUCCESS;
|
||||
|
||||
fail:
|
||||
return SWITCH_STATUS_GENERR;
|
||||
}
|
||||
|
||||
static switch_status_t channel_write_frame(switch_core_session_t *session, switch_frame_t *frame, switch_io_flag_t flags, int stream_id)
|
||||
{
|
||||
ftdm_wait_flag_t wflags = FTDM_WRITE;
|
||||
ctdm_private_t *tech_pvt;
|
||||
const char *name;
|
||||
switch_channel_t *channel;
|
||||
uint32_t span_id, chan_id;
|
||||
ftdm_size_t len;
|
||||
unsigned char data[SWITCH_RECOMMENDED_BUFFER_SIZE] = {0};
|
||||
|
||||
channel = switch_core_session_get_channel(session);
|
||||
assert(channel != NULL);
|
||||
|
||||
tech_pvt = switch_core_session_get_private(session);
|
||||
assert(tech_pvt != NULL);
|
||||
|
||||
span_id = ftdm_channel_get_span_id(tech_pvt->ftdm_channel);
|
||||
chan_id = ftdm_channel_get_id(tech_pvt->ftdm_channel);
|
||||
|
||||
name = switch_channel_get_name(channel);
|
||||
|
||||
if (switch_test_flag(frame, SFF_CNG)) {
|
||||
frame->data = data;
|
||||
frame->buflen = sizeof(data);
|
||||
if ((frame->datalen = tech_pvt->write_codec.implementation->encoded_bytes_per_packet) > frame->buflen) {
|
||||
goto fail;
|
||||
}
|
||||
memset(data, 255, frame->datalen);
|
||||
}
|
||||
|
||||
wflags = FTDM_WRITE;
|
||||
ftdm_channel_wait(tech_pvt->ftdm_channel, &wflags, ftdm_channel_get_io_interval(tech_pvt->ftdm_channel) * 10);
|
||||
|
||||
if (!(wflags & FTDM_WRITE)) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Dropping frame! (write not ready) in channel %s device %d:%d!\n", name, span_id, chan_id);
|
||||
return SWITCH_STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
len = frame->datalen;
|
||||
if (ftdm_channel_write(tech_pvt->ftdm_channel, frame->data, frame->buflen, &len) != FTDM_SUCCESS) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Failed to write to channel %s device %d:%d!\n", name, span_id, chan_id);
|
||||
}
|
||||
|
||||
return SWITCH_STATUS_SUCCESS;
|
||||
|
||||
fail:
|
||||
return SWITCH_STATUS_GENERR;
|
||||
}
|
||||
|
||||
static switch_status_t channel_send_dtmf(switch_core_session_t *session, const switch_dtmf_t *dtmf)
|
||||
{
|
||||
ctdm_private_t *tech_pvt = NULL;
|
||||
char tmp[2] = "";
|
||||
|
||||
tech_pvt = switch_core_session_get_private(session);
|
||||
assert(tech_pvt != NULL);
|
||||
|
||||
tmp[0] = dtmf->digit;
|
||||
ftdm_channel_command(tech_pvt->ftdm_channel, FTDM_COMMAND_SEND_DTMF, tmp);
|
||||
|
||||
return SWITCH_STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
static switch_status_t channel_receive_message(switch_core_session_t *session, switch_core_session_message_t *msg)
|
||||
{
|
||||
return SWITCH_STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
static switch_status_t channel_receive_event(switch_core_session_t *session, switch_event_t *event)
|
||||
{
|
||||
const char *command = switch_event_get_header(event, "command");
|
||||
ctdm_private_t *tech_pvt = switch_core_session_get_private(session);
|
||||
|
||||
if (!zstr(command)) {
|
||||
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "FreeTDM received %s command \n",command);
|
||||
|
||||
if (!strcasecmp(command, kPREBUFFER_LEN)) {
|
||||
const char *szval = switch_event_get_header(event, kPREBUFFER_LEN);
|
||||
int val = !zstr(szval) ? atoi(szval) : 0;
|
||||
|
||||
if (tech_pvt->prebuffer_len == val) {
|
||||
tech_pvt->prebuffer_len = val;
|
||||
if (FTDM_SUCCESS != ftdm_channel_command(tech_pvt->ftdm_channel, FTDM_COMMAND_SET_PRE_BUFFER_SIZE, &tech_pvt->prebuffer_len)) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Failed to set channel pre buffer size.\n");
|
||||
return SWITCH_STATUS_GENERR;
|
||||
}
|
||||
}
|
||||
} else if (!strcasecmp(command, kECHOCANCEL)) {
|
||||
const char *szval = switch_event_get_header(event, kECHOCANCEL);
|
||||
int enabled = !!switch_true(szval);
|
||||
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "FreeTDM sending echo cancel [%s] command \n",enabled ? "enable" : "disable");
|
||||
|
||||
if (FTDM_SUCCESS != ftdm_channel_command(tech_pvt->ftdm_channel, enabled ? FTDM_COMMAND_ENABLE_ECHOCANCEL : FTDM_COMMAND_DISABLE_ECHOCANCEL, NULL)) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_WARNING, "Failed to %s echo cancellation.\n", enabled ? "enable" : "disable");
|
||||
}
|
||||
|
||||
} else {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "FreeTDM received unknown command [%s] \n",command);
|
||||
}
|
||||
}
|
||||
|
||||
return SWITCH_STATUS_SUCCESS;
|
||||
}
|
||||
|
|
@ -36,10 +36,10 @@
|
|||
* David Yat Sin <dyatsin@sangoma.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#define _GNU_SOURCE
|
||||
#include "private/ftdm_core.h"
|
||||
#include <stdarg.h>
|
||||
#include <ctype.h>
|
||||
#ifdef WIN32
|
||||
#include <io.h>
|
||||
#endif
|
||||
|
@ -52,9 +52,7 @@
|
|||
struct tm *localtime_r(const time_t *clock, struct tm *result);
|
||||
#endif
|
||||
|
||||
#define FORCE_HANGUP_TIMER 3000
|
||||
#define SPAN_PENDING_CHANS_QUEUE_SIZE 1000
|
||||
#define SPAN_PENDING_SIGNALS_QUEUE_SIZE 1000
|
||||
#define FORCE_HANGUP_TIMER 30000
|
||||
#define FTDM_READ_TRACE_INDEX 0
|
||||
#define FTDM_WRITE_TRACE_INDEX 1
|
||||
#define MAX_CALLIDS 6000
|
||||
|
@ -64,11 +62,78 @@ struct tm *localtime_r(const time_t *clock, struct tm *result);
|
|||
ftdm_time_t time_last_throttle_log = 0;
|
||||
ftdm_time_t time_current_throttle_log = 0;
|
||||
|
||||
typedef struct val_str {
|
||||
const char *str;
|
||||
unsigned long long val;
|
||||
} val_str_t;
|
||||
|
||||
static val_str_t channel_flag_strs[] = {
|
||||
{ "configured" , FTDM_CHANNEL_CONFIGURED},
|
||||
{ "ready", FTDM_CHANNEL_READY},
|
||||
{ "open", FTDM_CHANNEL_OPEN},
|
||||
{ "dtmf-detect", FTDM_CHANNEL_DTMF_DETECT},
|
||||
{ "suppress-dtmf", FTDM_CHANNEL_SUPRESS_DTMF},
|
||||
{ "transcode", FTDM_CHANNEL_TRANSCODE},
|
||||
{ "buffer", FTDM_CHANNEL_BUFFER},
|
||||
{ "in-thread", FTDM_CHANNEL_INTHREAD},
|
||||
{ "wink", FTDM_CHANNEL_WINK},
|
||||
{ "flash", FTDM_CHANNEL_FLASH},
|
||||
{ "state-change", FTDM_CHANNEL_STATE_CHANGE},
|
||||
{ "hold", FTDM_CHANNEL_HOLD},
|
||||
{ "in-use", FTDM_CHANNEL_INUSE},
|
||||
{ "off-hook", FTDM_CHANNEL_OFFHOOK},
|
||||
{ "ringing", FTDM_CHANNEL_RINGING},
|
||||
{ "progress-detect", FTDM_CHANNEL_PROGRESS_DETECT},
|
||||
{ "callerid-detect", FTDM_CHANNEL_CALLERID_DETECT},
|
||||
{ "outbound", FTDM_CHANNEL_OUTBOUND},
|
||||
{ "suspended", FTDM_CHANNEL_SUSPENDED},
|
||||
{ "3-way", FTDM_CHANNEL_3WAY},
|
||||
{ "progress", FTDM_CHANNEL_PROGRESS},
|
||||
{ "media", FTDM_CHANNEL_MEDIA},
|
||||
{ "answered", FTDM_CHANNEL_ANSWERED},
|
||||
{ "mute", FTDM_CHANNEL_MUTE},
|
||||
{ "use-rx-gain", FTDM_CHANNEL_USE_RX_GAIN},
|
||||
{ "use-tx-gain", FTDM_CHANNEL_USE_TX_GAIN},
|
||||
{ "in-alarm", FTDM_CHANNEL_IN_ALARM},
|
||||
{ "sig-up", FTDM_CHANNEL_SIG_UP},
|
||||
{ "user-hangup", FTDM_CHANNEL_USER_HANGUP},
|
||||
{ "rx-disabled", FTDM_CHANNEL_RX_DISABLED},
|
||||
{ "tx-disabled", FTDM_CHANNEL_TX_DISABLED},
|
||||
{ "call-started", FTDM_CHANNEL_CALL_STARTED},
|
||||
{ "non-block", FTDM_CHANNEL_NONBLOCK},
|
||||
{ "ind-ack-pending", FTDM_CHANNEL_IND_ACK_PENDING},
|
||||
{ "blocking", FTDM_CHANNEL_BLOCKING},
|
||||
{ "media", FTDM_CHANNEL_DIGITAL_MEDIA},
|
||||
{ "native-sigbridge", FTDM_CHANNEL_NATIVE_SIGBRIDGE},
|
||||
{ "invalid", FTDM_CHANNEL_MAX_FLAG},
|
||||
};
|
||||
|
||||
static val_str_t span_flag_strs[] = {
|
||||
{ "configured", FTDM_SPAN_CONFIGURED},
|
||||
{ "started", FTDM_SPAN_STARTED},
|
||||
{ "state-change", FTDM_SPAN_STATE_CHANGE},
|
||||
{ "suspended", FTDM_SPAN_SUSPENDED},
|
||||
{ "in-thread", FTDM_SPAN_IN_THREAD},
|
||||
{ "stop-thread", FTDM_SPAN_STOP_THREAD},
|
||||
{ "use-chan-queue", FTDM_SPAN_USE_CHAN_QUEUE},
|
||||
{ "suggest-chan-id", FTDM_SPAN_SUGGEST_CHAN_ID},
|
||||
{ "use-av-rate", FTDM_SPAN_USE_AV_RATE},
|
||||
{ "power-saving", FTDM_SPAN_PWR_SAVING},
|
||||
{ "signals-queue", FTDM_SPAN_USE_SIGNALS_QUEUE},
|
||||
{ "proceed-state", FTDM_SPAN_USE_PROCEED_STATE},
|
||||
{ "skip-state", FTDM_SPAN_USE_SKIP_STATES},
|
||||
{ "non-stoppable", FTDM_SPAN_NON_STOPPABLE},
|
||||
{ "use-transfer", FTDM_SPAN_USE_TRANSFER},
|
||||
};
|
||||
|
||||
static ftdm_status_t ftdm_call_set_call_id(ftdm_channel_t *fchan, ftdm_caller_data_t *caller_data);
|
||||
static ftdm_status_t ftdm_call_clear_call_id(ftdm_caller_data_t *caller_data);
|
||||
static ftdm_status_t ftdm_channel_done(ftdm_channel_t *ftdmchan);
|
||||
static ftdm_status_t ftdm_channel_sig_indicate(ftdm_channel_t *ftdmchan, ftdm_channel_indication_t indication, ftdm_usrmsg_t *usrmsg);
|
||||
|
||||
static const char *ftdm_val2str(unsigned long long val, val_str_t *val_str_table, ftdm_size_t array_size, const char *default_str);
|
||||
static unsigned long long ftdm_str2val(const char *str, val_str_t *val_str_table, ftdm_size_t array_size, unsigned long long default_val);
|
||||
|
||||
|
||||
static int time_is_init = 0;
|
||||
|
||||
|
@ -171,7 +236,7 @@ static void stop_chan_io_dump(ftdm_io_dump_t *dump)
|
|||
return;
|
||||
}
|
||||
ftdm_safe_free(dump->buffer);
|
||||
memset(dump, 0, sizeof(dump));
|
||||
memset(dump, 0, sizeof(*dump));
|
||||
}
|
||||
|
||||
static ftdm_status_t start_chan_io_dump(ftdm_channel_t *chan, ftdm_io_dump_t *dump, ftdm_size_t size)
|
||||
|
@ -223,7 +288,7 @@ typedef struct {
|
|||
uint32_t interval;
|
||||
uint8_t alarm_action_flags;
|
||||
uint8_t set_alarm_threshold;
|
||||
uint8_t reset_alarm_threshold;
|
||||
uint8_t clear_alarm_threshold;
|
||||
ftdm_interrupt_t *interrupt;
|
||||
} cpu_monitor_t;
|
||||
|
||||
|
@ -1051,7 +1116,7 @@ FT_DECLARE(ftdm_status_t) ftdm_span_add_channel(ftdm_span_t *span, ftdm_socket_t
|
|||
i++;
|
||||
}
|
||||
|
||||
ftdm_set_flag(new_chan, FTDM_CHANNEL_CONFIGURED | FTDM_CHANNEL_READY);
|
||||
ftdm_set_flag(new_chan, FTDM_CHANNEL_CONFIGURED | FTDM_CHANNEL_READY);
|
||||
new_chan->state = FTDM_CHANNEL_STATE_DOWN;
|
||||
new_chan->state_status = FTDM_STATE_STATUS_COMPLETED;
|
||||
*chan = new_chan;
|
||||
|
@ -1404,13 +1469,24 @@ FT_DECLARE(ftdm_status_t) ftdm_group_channel_use_count(ftdm_group_t *group, uint
|
|||
|
||||
static __inline__ int chan_is_avail(ftdm_channel_t *check)
|
||||
{
|
||||
if (!ftdm_test_flag(check, FTDM_CHANNEL_READY) ||
|
||||
!ftdm_test_flag(check, FTDM_CHANNEL_SIG_UP) ||
|
||||
ftdm_test_flag(check, FTDM_CHANNEL_INUSE) ||
|
||||
ftdm_test_flag(check, FTDM_CHANNEL_SUSPENDED) ||
|
||||
ftdm_test_flag(check, FTDM_CHANNEL_IN_ALARM) ||
|
||||
check->state != FTDM_CHANNEL_STATE_DOWN) {
|
||||
return 0;
|
||||
if ((check->span->signal_type == FTDM_SIGTYPE_M2UA) ||
|
||||
(check->span->signal_type == FTDM_SIGTYPE_NONE)) {
|
||||
if (!ftdm_test_flag(check, FTDM_CHANNEL_READY) ||
|
||||
ftdm_test_flag(check, FTDM_CHANNEL_INUSE) ||
|
||||
ftdm_test_flag(check, FTDM_CHANNEL_SUSPENDED) ||
|
||||
ftdm_test_flag(check, FTDM_CHANNEL_IN_ALARM) ||
|
||||
check->state != FTDM_CHANNEL_STATE_DOWN) {
|
||||
return 0;
|
||||
}
|
||||
} else {
|
||||
if (!ftdm_test_flag(check, FTDM_CHANNEL_READY) ||
|
||||
!ftdm_test_flag(check, FTDM_CHANNEL_SIG_UP) ||
|
||||
ftdm_test_flag(check, FTDM_CHANNEL_INUSE) ||
|
||||
ftdm_test_flag(check, FTDM_CHANNEL_SUSPENDED) ||
|
||||
ftdm_test_flag(check, FTDM_CHANNEL_IN_ALARM) ||
|
||||
check->state != FTDM_CHANNEL_STATE_DOWN) {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
@ -1816,7 +1892,7 @@ done:
|
|||
return status;
|
||||
}
|
||||
|
||||
static ftdm_status_t _ftdm_channel_open(uint32_t span_id, uint32_t chan_id, ftdm_channel_t **ftdmchan)
|
||||
static ftdm_status_t _ftdm_channel_open(uint32_t span_id, uint32_t chan_id, ftdm_channel_t **ftdmchan, uint8_t physical)
|
||||
{
|
||||
ftdm_channel_t *check = NULL;
|
||||
ftdm_span_t *span = NULL;
|
||||
|
@ -1845,14 +1921,46 @@ static ftdm_status_t _ftdm_channel_open(uint32_t span_id, uint32_t chan_id, ftdm
|
|||
goto done;
|
||||
}
|
||||
|
||||
if (chan_id < 1 || chan_id > span->chan_count) {
|
||||
ftdm_log(FTDM_LOG_ERROR, "Invalid channel %d to open in span %d\n", chan_id, span_id);
|
||||
goto done;
|
||||
}
|
||||
if (physical) { /* Open by physical */
|
||||
ftdm_channel_t *fchan = NULL;
|
||||
ftdm_iterator_t *citer = NULL;
|
||||
ftdm_iterator_t *curr = NULL;
|
||||
|
||||
if (!(check = span->channels[chan_id])) {
|
||||
ftdm_log(FTDM_LOG_CRIT, "Wow, no channel %d in span %d\n", chan_id, span_id);
|
||||
goto done;
|
||||
if (chan_id < 1) {
|
||||
ftdm_log(FTDM_LOG_ERROR, "Invalid physical channel %d to open in span %d\n", chan_id, span_id);
|
||||
status = FTDM_FAIL;
|
||||
goto done;
|
||||
}
|
||||
|
||||
citer = ftdm_span_get_chan_iterator(span, NULL);
|
||||
if (!citer) {
|
||||
status = ENOMEM;
|
||||
goto done;
|
||||
}
|
||||
|
||||
for (curr = citer ; curr; curr = ftdm_iterator_next(curr)) {
|
||||
fchan = ftdm_iterator_current(curr);
|
||||
if (fchan->physical_chan_id == chan_id) {
|
||||
check = fchan;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
ftdm_iterator_free(citer);
|
||||
if (!check) {
|
||||
ftdm_log(FTDM_LOG_CRIT, "Wow, no physical channel %d in span %d\n", chan_id, span_id);
|
||||
goto done;
|
||||
}
|
||||
} else { /* Open by logical */
|
||||
if (chan_id < 1 || chan_id > span->chan_count) {
|
||||
ftdm_log(FTDM_LOG_ERROR, "Invalid channel %d to open in span %d\n", chan_id, span_id);
|
||||
goto done;
|
||||
}
|
||||
|
||||
if (!(check = span->channels[chan_id])) {
|
||||
ftdm_log(FTDM_LOG_CRIT, "Wow, no channel %d in span %d\n", chan_id, span_id);
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
|
||||
ftdm_channel_lock(check);
|
||||
|
@ -1923,7 +2031,18 @@ done:
|
|||
FT_DECLARE(ftdm_status_t) ftdm_channel_open(uint32_t span_id, uint32_t chan_id, ftdm_channel_t **ftdmchan)
|
||||
{
|
||||
ftdm_status_t status;
|
||||
status = _ftdm_channel_open(span_id, chan_id, ftdmchan);
|
||||
status = _ftdm_channel_open(span_id, chan_id, ftdmchan, 0);
|
||||
if (status == FTDM_SUCCESS) {
|
||||
ftdm_channel_t *fchan = *ftdmchan;
|
||||
ftdm_channel_unlock(fchan);
|
||||
}
|
||||
return status;
|
||||
}
|
||||
|
||||
FT_DECLARE(ftdm_status_t) ftdm_channel_open_ph(uint32_t span_id, uint32_t chan_id, ftdm_channel_t **ftdmchan)
|
||||
{
|
||||
ftdm_status_t status;
|
||||
status = _ftdm_channel_open(span_id, chan_id, ftdmchan, 1);
|
||||
if (status == FTDM_SUCCESS) {
|
||||
ftdm_channel_t *fchan = *ftdmchan;
|
||||
ftdm_channel_unlock(fchan);
|
||||
|
@ -2205,6 +2324,15 @@ static ftdm_status_t _ftdm_channel_call_hangup_nl(const char *file, const char *
|
|||
{
|
||||
ftdm_status_t status = FTDM_SUCCESS;
|
||||
|
||||
/* In native sigbridge mode we ignore hangup requests from the user and hangup only when the signaling module decides it */
|
||||
if (ftdm_test_flag(chan, FTDM_CHANNEL_NATIVE_SIGBRIDGE) && chan->state != FTDM_CHANNEL_STATE_TERMINATING) {
|
||||
|
||||
ftdm_log_chan_ex(chan, file, func, line, FTDM_LOG_LEVEL_DEBUG,
|
||||
"Ignoring hangup in channel in state %s (native bridge enabled)\n", ftdm_channel_state2str(chan->state));
|
||||
ftdm_set_flag(chan, FTDM_CHANNEL_USER_HANGUP);
|
||||
goto done;
|
||||
}
|
||||
|
||||
if (chan->state != FTDM_CHANNEL_STATE_DOWN) {
|
||||
if (chan->state == FTDM_CHANNEL_STATE_HANGUP) {
|
||||
/* make user's life easier, and just ignore double hangup requests */
|
||||
|
@ -2231,6 +2359,8 @@ static ftdm_status_t _ftdm_channel_call_hangup_nl(const char *file, const char *
|
|||
ftdm_channel_close(&chan);
|
||||
}
|
||||
}
|
||||
|
||||
done:
|
||||
return status;
|
||||
}
|
||||
|
||||
|
@ -2289,6 +2419,39 @@ FT_DECLARE(ftdm_channel_t *) ftdm_span_get_channel(const ftdm_span_t *span, uint
|
|||
return chan;
|
||||
}
|
||||
|
||||
FT_DECLARE(ftdm_channel_t *) ftdm_span_get_channel_ph(const ftdm_span_t *span, uint32_t chanid)
|
||||
{
|
||||
ftdm_channel_t *chan = NULL;
|
||||
ftdm_channel_t *fchan = NULL;
|
||||
ftdm_iterator_t *citer = NULL;
|
||||
ftdm_iterator_t *curr = NULL;
|
||||
|
||||
ftdm_mutex_lock(span->mutex);
|
||||
if (chanid == 0) {
|
||||
ftdm_mutex_unlock(span->mutex);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
citer = ftdm_span_get_chan_iterator(span, NULL);
|
||||
if (!citer) {
|
||||
ftdm_mutex_unlock(span->mutex);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
for (curr = citer ; curr; curr = ftdm_iterator_next(curr)) {
|
||||
fchan = ftdm_iterator_current(curr);
|
||||
if (fchan->physical_chan_id == chanid) {
|
||||
chan = fchan;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
ftdm_iterator_free(citer);
|
||||
|
||||
ftdm_mutex_unlock(span->mutex);
|
||||
return chan;
|
||||
}
|
||||
|
||||
FT_DECLARE(uint32_t) ftdm_span_get_chan_count(const ftdm_span_t *span)
|
||||
{
|
||||
uint32_t count;
|
||||
|
@ -2326,6 +2489,15 @@ FT_DECLARE(ftdm_status_t) _ftdm_channel_call_indicate(const char *file, const ch
|
|||
|
||||
ftdm_channel_lock(ftdmchan);
|
||||
|
||||
if (ftdm_test_flag(ftdmchan, FTDM_CHANNEL_NATIVE_SIGBRIDGE)) {
|
||||
ftdm_log_chan_ex(ftdmchan, file, func, line, FTDM_LOG_LEVEL_DEBUG,
|
||||
"Ignoring indication %s in channel in state %s (native bridge enabled)\n",
|
||||
ftdm_channel_indication2str(indication),
|
||||
ftdm_channel_state2str(ftdmchan->state));
|
||||
status = FTDM_SUCCESS;
|
||||
goto done;
|
||||
}
|
||||
|
||||
if (ftdm_test_flag(ftdmchan, FTDM_CHANNEL_IND_ACK_PENDING)) {
|
||||
ftdm_log_chan_ex(ftdmchan, file, func, line, FTDM_LOG_LEVEL_WARNING, "Cannot indicate %s in channel with indication %s still pending in state %s\n",
|
||||
ftdm_channel_indication2str(indication),
|
||||
|
@ -2426,10 +2598,56 @@ FT_DECLARE(ftdm_status_t) _ftdm_channel_reset(const char *file, const char *func
|
|||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
FT_DECLARE(ftdm_status_t) ftdm_get_channel_from_string(const char *string_id, ftdm_span_t **out_span, ftdm_channel_t **out_channel)
|
||||
{
|
||||
ftdm_status_t status = FTDM_SUCCESS;
|
||||
int rc = 0;
|
||||
ftdm_span_t *span = NULL;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
unsigned span_id = 0;
|
||||
unsigned chan_id = 0;
|
||||
|
||||
*out_span = NULL;
|
||||
*out_channel = NULL;
|
||||
|
||||
if (!string_id) {
|
||||
ftdm_log(FTDM_LOG_ERROR, "Cannot parse NULL channel id string\n");
|
||||
status = FTDM_EINVAL;
|
||||
goto done;
|
||||
}
|
||||
|
||||
rc = sscanf(string_id, "%u:%u", &span_id, &chan_id);
|
||||
if (rc != 2) {
|
||||
ftdm_log(FTDM_LOG_ERROR, "Failed to parse channel id string '%s'\n", string_id);
|
||||
status = FTDM_EINVAL;
|
||||
goto done;
|
||||
}
|
||||
|
||||
status = ftdm_span_find(span_id, &span);
|
||||
if (status != FTDM_SUCCESS || !span) {
|
||||
ftdm_log(FTDM_LOG_ERROR, "Failed to find span for channel id string '%s'\n", string_id);
|
||||
status = FTDM_EINVAL;
|
||||
goto done;
|
||||
}
|
||||
|
||||
if (chan_id > (FTDM_MAX_CHANNELS_SPAN+1) || !(ftdmchan = span->channels[chan_id])) {
|
||||
ftdm_log(FTDM_LOG_ERROR, "Invalid channel id string '%s'\n", string_id);
|
||||
status = FTDM_EINVAL;
|
||||
goto done;
|
||||
}
|
||||
|
||||
status = FTDM_SUCCESS;
|
||||
*out_span = span;
|
||||
*out_channel = ftdmchan;
|
||||
done:
|
||||
return status;
|
||||
}
|
||||
|
||||
/* this function MUST be called with the channel lock held with lock recursivity of 1 exactly,
|
||||
* and the caller must be aware we might unlock the channel for a brief period of time and then lock it again */
|
||||
static ftdm_status_t _ftdm_channel_call_place_nl(const char *file, const char *func, int line, ftdm_channel_t *ftdmchan, ftdm_usrmsg_t *usrmsg)
|
||||
{
|
||||
const char *var = NULL;
|
||||
ftdm_status_t status = FTDM_FAIL;
|
||||
|
||||
ftdm_assert_return(ftdmchan != NULL, FTDM_FAIL, "null channel");
|
||||
|
@ -2465,6 +2683,16 @@ static ftdm_status_t _ftdm_channel_call_place_nl(const char *file, const char *f
|
|||
|
||||
ftdm_set_flag(ftdmchan, FTDM_CHANNEL_CALL_STARTED);
|
||||
ftdm_call_set_call_id(ftdmchan, &ftdmchan->caller_data);
|
||||
var = ftdm_usrmsg_get_var(usrmsg, "sigbridge_peer");
|
||||
if (var) {
|
||||
ftdm_span_t *peer_span = NULL;
|
||||
ftdm_channel_t *peer_chan = NULL;
|
||||
ftdm_set_flag(ftdmchan, FTDM_CHANNEL_NATIVE_SIGBRIDGE);
|
||||
ftdm_get_channel_from_string(var, &peer_span, &peer_chan);
|
||||
if (peer_chan) {
|
||||
ftdm_set_flag(peer_chan, FTDM_CHANNEL_NATIVE_SIGBRIDGE);
|
||||
}
|
||||
}
|
||||
|
||||
/* if the signaling stack left the channel in state down on success, is expecting us to move to DIALING */
|
||||
if (ftdmchan->state == FTDM_CHANNEL_STATE_DOWN) {
|
||||
|
@ -2520,7 +2748,7 @@ FT_DECLARE(ftdm_status_t) _ftdm_call_place(const char *file, const char *func, i
|
|||
status = _ftdm_channel_open_by_group(hunting->mode_data.group.group_id,
|
||||
hunting->mode_data.group.direction, caller_data, &fchan);
|
||||
} else if (hunting->mode == FTDM_HUNT_CHAN) {
|
||||
status = _ftdm_channel_open(hunting->mode_data.chan.span_id, hunting->mode_data.chan.chan_id, &fchan);
|
||||
status = _ftdm_channel_open(hunting->mode_data.chan.span_id, hunting->mode_data.chan.chan_id, &fchan, 0);
|
||||
} else {
|
||||
ftdm_log(FTDM_LOG_ERROR, "Cannot make outbound call with invalid hunting mode %d\n", hunting->mode);
|
||||
return FTDM_EINVAL;
|
||||
|
@ -2668,6 +2896,7 @@ static ftdm_status_t ftdm_channel_done(ftdm_channel_t *ftdmchan)
|
|||
ftdm_clear_flag(ftdmchan, FTDM_CHANNEL_ANSWERED);
|
||||
ftdm_clear_flag(ftdmchan, FTDM_CHANNEL_USER_HANGUP);
|
||||
ftdm_clear_flag(ftdmchan, FTDM_CHANNEL_DIGITAL_MEDIA);
|
||||
ftdm_clear_flag(ftdmchan, FTDM_CHANNEL_NATIVE_SIGBRIDGE);
|
||||
ftdm_mutex_lock(ftdmchan->pre_buffer_mutex);
|
||||
ftdm_buffer_destroy(&ftdmchan->pre_buffer);
|
||||
ftdmchan->pre_buffer_size = 0;
|
||||
|
@ -4264,7 +4493,7 @@ static struct {
|
|||
ftdm_io_interface_t *pika_interface;
|
||||
} interfaces;
|
||||
|
||||
static void print_channels_by_flag(ftdm_stream_handle_t *stream, int32_t flagval, int not, int *count)
|
||||
static void print_channels_by_flag(ftdm_stream_handle_t *stream, ftdm_span_t *inspan, uint32_t inchan_id, int32_t flagval, int not, int *count)
|
||||
{
|
||||
ftdm_hash_iterator_t *i = NULL;
|
||||
ftdm_span_t *span;
|
||||
|
@ -4274,40 +4503,147 @@ static void print_channels_by_flag(ftdm_stream_handle_t *stream, int32_t flagval
|
|||
const void *key = NULL;
|
||||
void *val = NULL;
|
||||
uint32_t flag = (1 << flagval);
|
||||
int mycount = 0;
|
||||
|
||||
*count = 0;
|
||||
|
||||
ftdm_mutex_lock(globals.mutex);
|
||||
|
||||
for (i = hashtable_first(globals.span_hash); i; i = hashtable_next(i)) {
|
||||
hashtable_this(i, &key, NULL, &val);
|
||||
if (!key || !val) {
|
||||
break;
|
||||
}
|
||||
span = val;
|
||||
citer = ftdm_span_get_chan_iterator(span, NULL);
|
||||
if (inspan) {
|
||||
citer = ftdm_span_get_chan_iterator(inspan, NULL);
|
||||
if (!citer) {
|
||||
continue;
|
||||
goto end;
|
||||
}
|
||||
for (curr = citer ; curr; curr = ftdm_iterator_next(curr)) {
|
||||
fchan = ftdm_iterator_current(curr);
|
||||
if (not && !ftdm_test_flag(fchan, flag)) {
|
||||
stream->write_function(stream, "[s%dc%d][%d:%d] has not flag %d\n",
|
||||
fchan->span_id, fchan->chan_id,
|
||||
fchan->physical_span_id, fchan->physical_chan_id,
|
||||
flagval);
|
||||
(*count)++;
|
||||
} else if (!not && ftdm_test_flag(fchan, flag)) {
|
||||
stream->write_function(stream, "[s%dc%d][%d:%d] has flag %d\n",
|
||||
fchan->span_id, fchan->chan_id,
|
||||
fchan->physical_span_id, fchan->physical_chan_id,
|
||||
flagval);
|
||||
(*count)++;
|
||||
if (!inchan_id || inchan_id == fchan->chan_id) {
|
||||
if (not) {
|
||||
if (!ftdm_test_flag(fchan, flag)) {
|
||||
stream->write_function(stream, "[s%dc%d][%d:%d] flag !%d(!%s) ON \n",
|
||||
fchan->span_id, fchan->chan_id,
|
||||
fchan->physical_span_id, fchan->physical_chan_id,
|
||||
flagval, ftdm_val2str(flag, channel_flag_strs, ftdm_array_len(channel_flag_strs), "invalid"));
|
||||
|
||||
mycount++;
|
||||
} else {
|
||||
stream->write_function(stream, "[s%dc%d][%d:%d] flag !%d(!%s) OFF \n",
|
||||
fchan->span_id, fchan->chan_id,
|
||||
fchan->physical_span_id, fchan->physical_chan_id,
|
||||
flagval, ftdm_val2str(flag, channel_flag_strs, ftdm_array_len(channel_flag_strs), "invalid"));
|
||||
}
|
||||
} else {
|
||||
if (ftdm_test_flag(fchan, flag)) {
|
||||
stream->write_function(stream, "[s%dc%d][%d:%d] flag %d(%s) ON\n",
|
||||
fchan->span_id, fchan->chan_id,
|
||||
fchan->physical_span_id, fchan->physical_chan_id,
|
||||
flagval, ftdm_val2str(flag, channel_flag_strs, ftdm_array_len(channel_flag_strs), "invalid"));
|
||||
|
||||
mycount++;
|
||||
} else {
|
||||
stream->write_function(stream, "[s%dc%d][%d:%d] flag %d(%s) OFF \n",
|
||||
fchan->span_id, fchan->chan_id,
|
||||
fchan->physical_span_id, fchan->physical_chan_id,
|
||||
flagval, ftdm_val2str(flag, channel_flag_strs, ftdm_array_len(channel_flag_strs), "invalid"));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
ftdm_iterator_free(citer);
|
||||
}
|
||||
|
||||
} else {
|
||||
for (i = hashtable_first(globals.span_hash); i; i = hashtable_next(i)) {
|
||||
hashtable_this(i, &key, NULL, &val);
|
||||
if (!key || !val) {
|
||||
break;
|
||||
}
|
||||
span = val;
|
||||
citer = ftdm_span_get_chan_iterator(span, NULL);
|
||||
if (!citer) {
|
||||
continue;
|
||||
}
|
||||
for (curr = citer ; curr; curr = ftdm_iterator_next(curr)) {
|
||||
fchan = ftdm_iterator_current(curr);
|
||||
if (not && !ftdm_test_flag(fchan, flag)) {
|
||||
stream->write_function(stream, "[s%dc%d][%d:%d] flag !%d(!%s)\n",
|
||||
fchan->span_id, fchan->chan_id,
|
||||
fchan->physical_span_id, fchan->physical_chan_id,
|
||||
flagval, ftdm_val2str(flag, channel_flag_strs, ftdm_array_len(channel_flag_strs), "invalid"));
|
||||
mycount++;
|
||||
} else if (!not && ftdm_test_flag(fchan, flag)) {
|
||||
stream->write_function(stream, "[s%dc%d][%d:%d] flag %d(%s)\n",
|
||||
fchan->span_id, fchan->chan_id,
|
||||
fchan->physical_span_id, fchan->physical_chan_id,
|
||||
flagval, ftdm_val2str(flag, channel_flag_strs, ftdm_array_len(channel_flag_strs), "invalid"));
|
||||
mycount++;
|
||||
}
|
||||
}
|
||||
ftdm_iterator_free(citer);
|
||||
}
|
||||
}
|
||||
*count = mycount;
|
||||
end:
|
||||
ftdm_mutex_unlock(globals.mutex);
|
||||
}
|
||||
|
||||
static void print_spans_by_flag(ftdm_stream_handle_t *stream, ftdm_span_t *inspan, int32_t flagval, int not, int *count)
|
||||
{
|
||||
ftdm_hash_iterator_t *i = NULL;
|
||||
ftdm_span_t *span;
|
||||
const void *key = NULL;
|
||||
void *val = NULL;
|
||||
uint32_t flag = (1 << flagval);
|
||||
int mycount = 0;
|
||||
|
||||
*count = 0;
|
||||
|
||||
ftdm_mutex_lock(globals.mutex);
|
||||
|
||||
if (inspan) {
|
||||
if (not) {
|
||||
if (!ftdm_test_flag(inspan, flag)) {
|
||||
stream->write_function(stream, "[s%d] flag !%d(!%s) ON \n",
|
||||
inspan->span_id,
|
||||
flagval, ftdm_val2str(flag, span_flag_strs, ftdm_array_len(span_flag_strs), "invalid"));
|
||||
|
||||
mycount++;
|
||||
} else {
|
||||
stream->write_function(stream, "[s%d] flag !%d(!%s) OFF \n",
|
||||
inspan->span_id,
|
||||
flagval, ftdm_val2str(flag, span_flag_strs, ftdm_array_len(span_flag_strs), "invalid"));
|
||||
}
|
||||
} else {
|
||||
if (ftdm_test_flag(inspan, flag)) {
|
||||
stream->write_function(stream, "[s%d] flag %d(%s) ON \n",
|
||||
inspan->span_id,
|
||||
flagval, ftdm_val2str(flag, span_flag_strs, ftdm_array_len(span_flag_strs), "invalid"));
|
||||
mycount++;
|
||||
} else {
|
||||
stream->write_function(stream, "[s%d] flag %d(%s) OFF \n",
|
||||
inspan->span_id,
|
||||
flagval, ftdm_val2str(flag, span_flag_strs, ftdm_array_len(span_flag_strs), "invalid"));
|
||||
}
|
||||
}
|
||||
} else {
|
||||
for (i = hashtable_first(globals.span_hash); i; i = hashtable_next(i)) {
|
||||
hashtable_this(i, &key, NULL, &val);
|
||||
if (!key || !val) {
|
||||
break;
|
||||
}
|
||||
span = val;
|
||||
if (not && !ftdm_test_flag(span, flag)) {
|
||||
stream->write_function(stream, "[s%d] flag !%d(!%s)\n",
|
||||
span->span_id,
|
||||
flagval, ftdm_val2str(flag, span_flag_strs, ftdm_array_len(span_flag_strs), "invalid"));
|
||||
mycount++;
|
||||
} else if (!not && ftdm_test_flag(span, flag)) {
|
||||
stream->write_function(stream, "[s%d] flag %d(%s)\n",
|
||||
span->span_id,
|
||||
flagval, ftdm_val2str(flag, span_flag_strs, ftdm_array_len(span_flag_strs), "invalid"));
|
||||
mycount++;
|
||||
}
|
||||
}
|
||||
}
|
||||
*count = mycount;
|
||||
ftdm_mutex_unlock(globals.mutex);
|
||||
}
|
||||
|
||||
|
@ -4359,12 +4695,52 @@ static void print_core_usage(ftdm_stream_handle_t *stream)
|
|||
{
|
||||
stream->write_function(stream,
|
||||
"--------------------------------------------------------------------------------\n"
|
||||
"ftdm core state [!]<state_name> - List all channels in or not in the given state\n"
|
||||
"ftdm core flag <flag-int-value> - List all channels with the given flag value set\n"
|
||||
"ftdm core state [!]<state-name> - List all channels in or not in the given state\n"
|
||||
"ftdm core flag [!]<flag-int-value|flag-name> [<span_id|span_name>] [<chan_id>] - List all channels with the given flag value set\n"
|
||||
"ftdm core spanflag [!]<flag-int-value|flag-name> [<span_id|span_name>] - List all spans with the given span flag value set\n"
|
||||
"ftdm core calls - List all known calls to the FreeTDM core\n"
|
||||
"--------------------------------------------------------------------------------\n");
|
||||
}
|
||||
|
||||
|
||||
static unsigned long long ftdm_str2val(const char *str, val_str_t *val_str_table, ftdm_size_t array_size, unsigned long long default_val)
|
||||
{
|
||||
int i;
|
||||
for (i = 0; i < array_size; i++) {
|
||||
if (!strcasecmp(val_str_table[i].str, str)) {
|
||||
return val_str_table[i].val;
|
||||
}
|
||||
}
|
||||
return default_val;
|
||||
}
|
||||
|
||||
static const char *ftdm_val2str(unsigned long long val, val_str_t *val_str_table, ftdm_size_t array_size, const char *default_str)
|
||||
{
|
||||
int i;
|
||||
for (i = 0; i < array_size; i++) {
|
||||
if (val_str_table[i].val == val) {
|
||||
return val_str_table[i].str;
|
||||
}
|
||||
}
|
||||
return default_str;
|
||||
}
|
||||
|
||||
static void print_channel_flag_values(ftdm_stream_handle_t *stream)
|
||||
{
|
||||
int i;
|
||||
for (i = 0; i < ftdm_array_len(channel_flag_strs); i++) {
|
||||
stream->write_function(stream, "%s\n", channel_flag_strs[i].str);
|
||||
}
|
||||
}
|
||||
|
||||
static void print_span_flag_values(ftdm_stream_handle_t *stream)
|
||||
{
|
||||
int i;
|
||||
for (i = 0; i < ftdm_array_len(span_flag_strs); i++) {
|
||||
stream->write_function(stream, "%s\n", span_flag_strs[i].str);
|
||||
}
|
||||
}
|
||||
|
||||
static char *handle_core_command(const char *cmd)
|
||||
{
|
||||
char *mycmd = NULL;
|
||||
|
@ -4374,11 +4750,12 @@ static char *handle_core_command(const char *cmd)
|
|||
char *argv[10] = { 0 };
|
||||
char *state = NULL;
|
||||
char *flag = NULL;
|
||||
uint32_t flagval = 0;
|
||||
unsigned long long flagval = 0;
|
||||
uint32_t current_call_id = 0;
|
||||
ftdm_caller_data_t *calldata = NULL;
|
||||
ftdm_channel_t *fchan = NULL;
|
||||
ftdm_channel_state_t i = FTDM_CHANNEL_STATE_INVALID;
|
||||
ftdm_span_t *fspan = NULL;
|
||||
ftdm_stream_handle_t stream = { 0 };
|
||||
|
||||
FTDM_STANDARD_STREAM(stream);
|
||||
|
@ -4419,6 +4796,7 @@ static char *handle_core_command(const char *cmd)
|
|||
print_channels_by_state(&stream, i, not, &count);
|
||||
stream.write_function(&stream, "\nTotal channels %s %s: %d\n", not ? "not in state" : "in state", ftdm_channel_state2str(i), count);
|
||||
} else if (!strcasecmp(argv[0], "flag")) {
|
||||
uint32_t chan_id = 0;
|
||||
if (argc < 2) {
|
||||
stream.write_function(&stream, "core flag command requires an argument\n");
|
||||
print_core_usage(&stream);
|
||||
|
@ -4429,9 +4807,77 @@ static char *handle_core_command(const char *cmd)
|
|||
not = 1;
|
||||
flag++;
|
||||
}
|
||||
flagval = atoi(flag);
|
||||
print_channels_by_flag(&stream, flagval, not, &count);
|
||||
|
||||
if (isalpha(flag[0])) {
|
||||
flagval = ftdm_str2val(flag, channel_flag_strs, ftdm_array_len(channel_flag_strs), FTDM_CHANNEL_MAX_FLAG);
|
||||
if (flagval == FTDM_CHANNEL_MAX_FLAG) {
|
||||
stream.write_function(&stream, "\nInvalid channel flag value. Possible channel flags\n");
|
||||
print_channel_flag_values(&stream);
|
||||
goto done;
|
||||
}
|
||||
flagval = flagval >> 1;
|
||||
} else {
|
||||
flagval = atoi(flag);
|
||||
}
|
||||
|
||||
/* Specific span specified */
|
||||
if (argv[2]) {
|
||||
ftdm_span_find_by_name(argv[2], &fspan);
|
||||
if (!fspan) {
|
||||
stream.write_function(&stream, "-ERR span:%s not found\n", argv[2]);
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
|
||||
/* Specific channel specified */
|
||||
if (argv[3]) {
|
||||
chan_id = atoi(argv[3]);
|
||||
if (chan_id >= ftdm_span_get_chan_count(fspan)) {
|
||||
stream.write_function(&stream, "-ERR invalid channel %d\n", chan_id);
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
|
||||
print_channels_by_flag(&stream, fspan, chan_id, flagval, not, &count);
|
||||
stream.write_function(&stream, "\nTotal channels %s %d: %d\n", not ? "without flag" : "with flag", flagval, count);
|
||||
} else if (!strcasecmp(argv[0], "spanflag")) {
|
||||
if (argc < 2) {
|
||||
stream.write_function(&stream, "core spanflag command requires an argument\n");
|
||||
print_core_usage(&stream);
|
||||
goto done;
|
||||
}
|
||||
|
||||
flag = argv[1];
|
||||
if (argv[1][0] == '!') {
|
||||
not = 1;
|
||||
flag++;
|
||||
}
|
||||
|
||||
if (isalpha(flag[0])) {
|
||||
flagval = ftdm_str2val(flag, span_flag_strs, ftdm_array_len(span_flag_strs), FTDM_SPAN_MAX_FLAG);
|
||||
if (flagval == FTDM_SPAN_MAX_FLAG) {
|
||||
stream.write_function(&stream, "\nInvalid span flag value. Possible span flags\n");
|
||||
print_span_flag_values(&stream);
|
||||
goto done;
|
||||
}
|
||||
flagval = flagval >> 1;
|
||||
} else {
|
||||
flagval = atoi(flag);
|
||||
}
|
||||
|
||||
/* Specific span specified */
|
||||
if (argv[2]) {
|
||||
ftdm_span_find_by_name(argv[2], &fspan);
|
||||
if (!fspan) {
|
||||
stream.write_function(&stream, "-ERR span:%s not found\n", argv[2]);
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
|
||||
print_spans_by_flag(&stream, fspan, flagval, not, &count);
|
||||
if (!fspan) {
|
||||
stream.write_function(&stream, "\nTotal spans %s %d: %d\n", not ? "without flag" : "with flag", flagval, count);
|
||||
}
|
||||
} else if (!strcasecmp(argv[0], "calls")) {
|
||||
ftdm_mutex_lock(globals.call_id_mutex);
|
||||
current_call_id = globals.last_call_id;
|
||||
|
@ -4872,14 +5318,15 @@ static ftdm_status_t load_config(void)
|
|||
} else {
|
||||
ftdm_log(FTDM_LOG_ERROR, "Invalid cpu alarm set threshold %s\n", val);
|
||||
}
|
||||
} else if (!strncasecmp(var, "cpu_reset_alarm_threshold", sizeof("cpu_reset_alarm_threshold")-1)) {
|
||||
} else if (!strncasecmp(var, "cpu_reset_alarm_threshold", sizeof("cpu_reset_alarm_threshold")-1) ||
|
||||
!strncasecmp(var, "cpu_clear_alarm_threshold", sizeof("cpu_clear_alarm_threshold")-1)) {
|
||||
intparam = atoi(val);
|
||||
if (intparam > 0 && intparam < 100) {
|
||||
globals.cpu_monitor.reset_alarm_threshold = (uint8_t)intparam;
|
||||
if (globals.cpu_monitor.reset_alarm_threshold > globals.cpu_monitor.set_alarm_threshold) {
|
||||
globals.cpu_monitor.reset_alarm_threshold = globals.cpu_monitor.set_alarm_threshold - 10;
|
||||
ftdm_log(FTDM_LOG_ERROR, "Cpu alarm reset threshold must be lower than set threshold"
|
||||
", setting threshold to %d\n", globals.cpu_monitor.reset_alarm_threshold);
|
||||
globals.cpu_monitor.clear_alarm_threshold = (uint8_t)intparam;
|
||||
if (globals.cpu_monitor.clear_alarm_threshold > globals.cpu_monitor.set_alarm_threshold) {
|
||||
globals.cpu_monitor.clear_alarm_threshold = globals.cpu_monitor.set_alarm_threshold - 10;
|
||||
ftdm_log(FTDM_LOG_ERROR, "Cpu alarm clear threshold must be lower than set threshold, "
|
||||
"setting clear threshold to %d\n", globals.cpu_monitor.clear_alarm_threshold);
|
||||
}
|
||||
} else {
|
||||
ftdm_log(FTDM_LOG_ERROR, "Invalid cpu alarm reset threshold %s\n", val);
|
||||
|
@ -5247,16 +5694,68 @@ FT_DECLARE(ftdm_status_t) ftdm_configure_span_signaling(ftdm_span_t *span, const
|
|||
return status;
|
||||
}
|
||||
|
||||
static void *ftdm_span_service_events(ftdm_thread_t *me, void *obj)
|
||||
{
|
||||
int i;
|
||||
unsigned waitms;
|
||||
ftdm_event_t *event;
|
||||
ftdm_status_t status = FTDM_SUCCESS;
|
||||
ftdm_span_t *span = (ftdm_span_t*) obj;
|
||||
short *poll_events = ftdm_malloc(sizeof(short) * span->chan_count);
|
||||
|
||||
memset(poll_events, 0, sizeof(short) * span->chan_count);
|
||||
|
||||
for(i = 1; i <= span->chan_count; i++) {
|
||||
poll_events[i] |= FTDM_EVENTS;
|
||||
}
|
||||
|
||||
while (ftdm_running() && !(ftdm_test_flag(span, FTDM_SPAN_STOP_THREAD))) {
|
||||
waitms = 1000;
|
||||
status = ftdm_span_poll_event(span, waitms, poll_events);
|
||||
switch (status) {
|
||||
case FTDM_FAIL:
|
||||
ftdm_log(FTDM_LOG_CRIT, "%s:Failed to poll span for events\n", span->name);
|
||||
break;
|
||||
case FTDM_TIMEOUT:
|
||||
break;
|
||||
case FTDM_SUCCESS:
|
||||
/* Check if there are any channels that have events available */
|
||||
while (ftdm_span_next_event(span, &event) == FTDM_SUCCESS);
|
||||
break;
|
||||
default:
|
||||
ftdm_log(FTDM_LOG_CRIT, "%s:Unhandled IO event\n", span->name);
|
||||
}
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
FT_DECLARE(ftdm_status_t) ftdm_span_register_signal_cb(ftdm_span_t *span, fio_signal_cb_t sig_cb)
|
||||
{
|
||||
span->signal_cb = sig_cb;
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
FT_DECLARE(ftdm_status_t) ftdm_span_start(ftdm_span_t *span)
|
||||
{
|
||||
ftdm_status_t status = FTDM_FAIL;
|
||||
|
||||
ftdm_mutex_lock(span->mutex);
|
||||
|
||||
if (ftdm_test_flag(span, FTDM_SPAN_STARTED)) {
|
||||
status = FTDM_EINVAL;
|
||||
goto done;
|
||||
}
|
||||
if (span->signal_type == FTDM_SIGTYPE_NONE) {
|
||||
/* If there is no signalling component, start a thread to poll events */
|
||||
status = ftdm_thread_create_detached(ftdm_span_service_events, span);
|
||||
if (status != FTDM_SUCCESS) {
|
||||
ftdm_log(FTDM_LOG_CRIT,"Failed to start span event monitor thread!\n");
|
||||
goto done;
|
||||
}
|
||||
|
||||
//ftdm_report_initial_channels_alarms(span);
|
||||
ftdm_set_flag_locked(span, FTDM_SPAN_STARTED);
|
||||
goto done;
|
||||
}
|
||||
|
||||
if (!span->start) {
|
||||
status = FTDM_ENOSYS;
|
||||
|
@ -5272,7 +5771,6 @@ FT_DECLARE(ftdm_status_t) ftdm_span_start(ftdm_span_t *span)
|
|||
if (status == FTDM_SUCCESS) {
|
||||
ftdm_set_flag_locked(span, FTDM_SPAN_STARTED);
|
||||
}
|
||||
|
||||
done:
|
||||
ftdm_mutex_unlock(span->mutex);
|
||||
return status;
|
||||
|
@ -5457,8 +5955,10 @@ FT_DECLARE(ftdm_status_t) ftdm_group_create(ftdm_group_t **group, const char *na
|
|||
|
||||
static ftdm_status_t ftdm_span_trigger_signal(const ftdm_span_t *span, ftdm_sigmsg_t *sigmsg)
|
||||
{
|
||||
ftdm_status_t status = span->signal_cb(sigmsg);
|
||||
return status;
|
||||
if (!span->signal_cb) {
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
return span->signal_cb(sigmsg);
|
||||
}
|
||||
|
||||
static ftdm_status_t ftdm_span_queue_signal(const ftdm_span_t *span, ftdm_sigmsg_t *sigmsg)
|
||||
|
@ -5492,7 +5992,7 @@ static void execute_safety_hangup(void *data)
|
|||
ftdm_channel_lock(fchan);
|
||||
fchan->hangup_timer = 0;
|
||||
if (fchan->state == FTDM_CHANNEL_STATE_TERMINATING) {
|
||||
ftdm_log_chan(fchan, FTDM_LOG_CRIT, "Forcing hangup since the user did not confirmed our hangup after %dms\n", FORCE_HANGUP_TIMER);
|
||||
ftdm_log_chan(fchan, FTDM_LOG_WARNING, "Forcing hangup since the user did not confirmed our hangup after %dms\n", FORCE_HANGUP_TIMER);
|
||||
_ftdm_channel_call_hangup_nl(__FILE__, __FUNCTION__, __LINE__, fchan, NULL);
|
||||
} else {
|
||||
ftdm_log_chan(fchan, FTDM_LOG_CRIT, "Not performing safety hangup, channel state is %s\n", ftdm_channel_state2str(fchan->state));
|
||||
|
@ -5623,28 +6123,32 @@ static void *ftdm_cpu_monitor_run(ftdm_thread_t *me, void *obj)
|
|||
{
|
||||
cpu_monitor_t *monitor = (cpu_monitor_t *)obj;
|
||||
struct ftdm_cpu_monitor_stats *cpu_stats = ftdm_new_cpu_monitor();
|
||||
|
||||
ftdm_log(FTDM_LOG_DEBUG, "CPU monitor thread is now running\n");
|
||||
if (!cpu_stats) {
|
||||
return NULL;
|
||||
goto done;
|
||||
}
|
||||
monitor->running = 1;
|
||||
|
||||
while(ftdm_running()) {
|
||||
double time;
|
||||
if (ftdm_cpu_get_system_idle_time(cpu_stats, &time)) {
|
||||
while (ftdm_running()) {
|
||||
double idle_time = 0.0;
|
||||
int cpu_usage = 0;
|
||||
|
||||
if (ftdm_cpu_get_system_idle_time(cpu_stats, &idle_time)) {
|
||||
break;
|
||||
}
|
||||
|
||||
cpu_usage = (int)(100 - idle_time);
|
||||
if (monitor->alarm) {
|
||||
if ((int)time >= (100 - monitor->set_alarm_threshold)) {
|
||||
ftdm_log(FTDM_LOG_DEBUG, "CPU alarm OFF (idle:%d)\n", (int) time);
|
||||
if (cpu_usage <= monitor->clear_alarm_threshold) {
|
||||
ftdm_log(FTDM_LOG_DEBUG, "CPU alarm is now OFF (cpu usage: %d)\n", cpu_usage);
|
||||
monitor->alarm = 0;
|
||||
}
|
||||
if (monitor->alarm_action_flags & FTDM_CPU_ALARM_ACTION_WARN) {
|
||||
ftdm_log(FTDM_LOG_WARNING, "CPU alarm is ON (cpu usage:%d)\n", (int) (100-time));
|
||||
} else if (monitor->alarm_action_flags & FTDM_CPU_ALARM_ACTION_WARN) {
|
||||
ftdm_log(FTDM_LOG_WARNING, "CPU alarm is still ON (cpu usage: %d)\n", cpu_usage);
|
||||
}
|
||||
} else {
|
||||
if ((int)time <= (100-monitor->reset_alarm_threshold)) {
|
||||
ftdm_log(FTDM_LOG_DEBUG, "CPU alarm ON (idle:%d)\n", (int) time);
|
||||
if (cpu_usage >= monitor->set_alarm_threshold) {
|
||||
ftdm_log(FTDM_LOG_WARNING, "CPU alarm is now ON (cpu usage: %d)\n", cpu_usage);
|
||||
monitor->alarm = 1;
|
||||
}
|
||||
}
|
||||
|
@ -5653,7 +6157,11 @@ static void *ftdm_cpu_monitor_run(ftdm_thread_t *me, void *obj)
|
|||
|
||||
ftdm_delete_cpu_monitor(cpu_stats);
|
||||
monitor->running = 0;
|
||||
|
||||
done:
|
||||
ftdm_log(FTDM_LOG_DEBUG, "CPU monitor thread is now terminating\n");
|
||||
return NULL;
|
||||
|
||||
#ifdef __WINDOWS__
|
||||
UNREFERENCED_PARAMETER(me);
|
||||
#endif
|
||||
|
@ -5755,8 +6263,8 @@ FT_DECLARE(ftdm_status_t) ftdm_global_configuration(void)
|
|||
globals.cpu_monitor.enabled = 0;
|
||||
globals.cpu_monitor.interval = 1000;
|
||||
globals.cpu_monitor.alarm_action_flags = 0;
|
||||
globals.cpu_monitor.set_alarm_threshold = 80;
|
||||
globals.cpu_monitor.reset_alarm_threshold = 70;
|
||||
globals.cpu_monitor.set_alarm_threshold = 92;
|
||||
globals.cpu_monitor.clear_alarm_threshold = 82;
|
||||
|
||||
if (load_config() != FTDM_SUCCESS) {
|
||||
globals.running = 0;
|
||||
|
@ -5765,10 +6273,10 @@ FT_DECLARE(ftdm_status_t) ftdm_global_configuration(void)
|
|||
}
|
||||
|
||||
if (globals.cpu_monitor.enabled) {
|
||||
ftdm_log(FTDM_LOG_INFO, "CPU Monitor is running interval:%d lo-thres:%d hi-thres:%d\n",
|
||||
ftdm_log(FTDM_LOG_INFO, "CPU Monitor is running interval:%d set-thres:%d clear-thres:%d\n",
|
||||
globals.cpu_monitor.interval,
|
||||
globals.cpu_monitor.set_alarm_threshold,
|
||||
globals.cpu_monitor.reset_alarm_threshold);
|
||||
globals.cpu_monitor.clear_alarm_threshold);
|
||||
|
||||
if (ftdm_cpu_monitor_start() != FTDM_SUCCESS) {
|
||||
return FTDM_FAIL;
|
||||
|
|
|
@ -48,9 +48,26 @@ FT_DECLARE(ftdm_status_t) _ftdm_channel_complete_state(const char *file, const c
|
|||
ftdm_time_t diff = 0;
|
||||
ftdm_channel_state_t state = fchan->state;
|
||||
|
||||
#if 0
|
||||
/* I could not perform this sanity check without more disruptive changes. Ideally we should check here if the signaling module completing the state
|
||||
executed a state processor (called ftdm_channel_advance_states() which call fchan->span->state_processor(fchan)) for the state. That is just a
|
||||
sanity check, as in the past we had at least one bug where the signaling module set the state and then accidentally changed the state to a new one
|
||||
without calling ftdm_channel_advance_states(), meaning the state processor for the first state was not executed and that lead to unexpected behavior.
|
||||
|
||||
If we want to be able to perform this kind of sanity check it would be nice to add a new state status (FTDM_STATE_STATUS_PROCESSING), the function
|
||||
ftdm_channel_advance_states() would set the state_status to PROCESSING and then the check below for STATUS_NEW would be valid. Currently is not
|
||||
valid because the signaling module may be completing the state at the end of the state_processor callback and therefore the state will still be
|
||||
in STATUS_NEW, and is perfectly valid ... */
|
||||
|
||||
if (fchan->state_status == FTDM_STATE_STATUS_NEW) {
|
||||
ftdm_log_chan_ex(fchan, file, func, line, FTDM_LOG_LEVEL_CRIT,
|
||||
"Asking to complete state change from %s to %s in %llums, but the state is still unprocessed (this might be a bug!)\n",
|
||||
ftdm_channel_state2str(fchan->last_state), ftdm_channel_state2str(state), diff);
|
||||
}
|
||||
#endif
|
||||
|
||||
if (fchan->state_status == FTDM_STATE_STATUS_COMPLETED) {
|
||||
ftdm_assert_return(!ftdm_test_flag(fchan, FTDM_CHANNEL_STATE_CHANGE), FTDM_FAIL,
|
||||
"State change flag set but state is not completed\n");
|
||||
ftdm_assert_return(!ftdm_test_flag(fchan, FTDM_CHANNEL_STATE_CHANGE), FTDM_FAIL, "State change flag set but state is already completed\n");
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
|
@ -87,6 +104,7 @@ FT_DECLARE(ftdm_status_t) _ftdm_channel_complete_state(const char *file, const c
|
|||
ftdm_assert(!fchan->history[hindex].end_time, "End time should be zero!\n");
|
||||
|
||||
fchan->history[hindex].end_time = ftdm_current_time_in_ms();
|
||||
fchan->last_state_change_time = ftdm_current_time_in_ms();
|
||||
|
||||
fchan->state_status = FTDM_STATE_STATUS_COMPLETED;
|
||||
|
||||
|
@ -262,6 +280,9 @@ static ftdm_status_t ftdm_core_set_state(const char *file, const char *func, int
|
|||
}
|
||||
}
|
||||
|
||||
if (ftdm_test_flag(ftdmchan, FTDM_CHANNEL_NATIVE_SIGBRIDGE)) {
|
||||
goto perform_state_change;
|
||||
}
|
||||
|
||||
if (ftdmchan->span->state_map) {
|
||||
ok = ftdm_parse_state_map(ftdmchan, state, ftdmchan->span->state_map);
|
||||
|
@ -353,6 +374,8 @@ end:
|
|||
goto done;
|
||||
}
|
||||
|
||||
perform_state_change:
|
||||
|
||||
ftdm_log_chan_ex(ftdmchan, file, func, line, FTDM_LOG_LEVEL_DEBUG, "Changed state from %s to %s\n", ftdm_channel_state2str(ftdmchan->state), ftdm_channel_state2str(state));
|
||||
ftdmchan->last_state = ftdmchan->state;
|
||||
ftdmchan->state = state;
|
||||
|
|
|
@ -401,7 +401,7 @@ FT_DECLARE(ftdm_status_t) ftdm_interrupt_wait(ftdm_interrupt_t *interrupt, int m
|
|||
if (interrupt->device != FTDM_INVALID_SOCKET) {
|
||||
num++;
|
||||
ints[1] = interrupt->device;
|
||||
ftdm_log(FTDM_LOG_CRIT, "implement me! (Windows support for device_output_flags member!)\n", size);
|
||||
ftdm_log(FTDM_LOG_CRIT, "implement me! (Windows support for device_output_flags member!)\n");
|
||||
}
|
||||
res = WaitForMultipleObjects(num, ints, FALSE, ms >= 0 ? ms : INFINITE);
|
||||
switch (res) {
|
||||
|
|
|
@ -77,7 +77,9 @@ int ft_to_sngss7_cfg_all(void)
|
|||
int ret = 0;
|
||||
|
||||
/* check if we have done gen_config already */
|
||||
if (!(g_ftdm_sngss7_data.gen_config)) {
|
||||
if (g_ftdm_sngss7_data.gen_config == SNG_GEN_CFG_STATUS_INIT) {
|
||||
/* update the global gen_config so we don't do it again */
|
||||
g_ftdm_sngss7_data.gen_config = SNG_GEN_CFG_STATUS_PENDING;
|
||||
|
||||
/* start of by checking if the license and sig file are valid */
|
||||
if (sng_validate_license(g_ftdm_sngss7_data.cfg.license,
|
||||
|
@ -92,7 +94,7 @@ int ft_to_sngss7_cfg_all(void)
|
|||
/* set the desired procID value */
|
||||
sng_set_procId((uint16_t)g_ftdm_sngss7_data.cfg.procId);
|
||||
}
|
||||
|
||||
|
||||
/* start up the stack manager */
|
||||
if (sng_isup_init_sm()) {
|
||||
SS7_CRITICAL("Failed to start Stack Manager\n");
|
||||
|
@ -207,30 +209,22 @@ int ft_to_sngss7_cfg_all(void)
|
|||
}
|
||||
} /* if (sngss7_test_flag(&g_ftdm_sngss7_data.cfg, SNGSS7_MTP2)) */
|
||||
|
||||
/* update the global gen_config so we don't do it again */
|
||||
g_ftdm_sngss7_data.gen_config = 1;
|
||||
if(SNG_SS7_OPR_MODE_M2UA_SG == g_ftdm_operating_mode){
|
||||
if(FTDM_SUCCESS != ftmod_ss7_m2ua_init()){
|
||||
ftdm_log (FTDM_LOG_ERROR, "ftmod_ss7_m2ua_init FAILED \n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
}
|
||||
|
||||
g_ftdm_sngss7_data.gen_config = SNG_GEN_CFG_STATUS_DONE;
|
||||
|
||||
} /* if (!(g_ftdm_sngss7_data.gen_config)) */
|
||||
|
||||
/* go through all the relays channels and configure it */
|
||||
x = 1;
|
||||
while (x < (MAX_RELAY_CHANNELS)) {
|
||||
/* check if this relay channel has been configured already */
|
||||
if ((g_ftdm_sngss7_data.cfg.relay[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.relay[x].flags & SNGSS7_CONFIGURED))) {
|
||||
|
||||
/* send the specific configuration */
|
||||
if (ftmod_ss7_relay_chan_config(x)) {
|
||||
SS7_CRITICAL("Relay Channel %d configuration FAILED!\n", x);
|
||||
return 1;
|
||||
} else {
|
||||
SS7_INFO("Relay Channel %d configuration DONE!\n", x);
|
||||
}
|
||||
|
||||
/* set the SNGSS7_CONFIGURED flag */
|
||||
g_ftdm_sngss7_data.cfg.relay[x].flags |= SNGSS7_CONFIGURED;
|
||||
} /* if !SNGSS7_CONFIGURED */
|
||||
x++;
|
||||
} /* while (x < (MAX_RELAY_CHANNELS)) */
|
||||
if (g_ftdm_sngss7_data.gen_config != SNG_GEN_CFG_STATUS_DONE) {
|
||||
SS7_CRITICAL("General configuration FAILED!\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
x = 1;
|
||||
while (x < (MAX_MTP_LINKS)) {
|
||||
|
@ -272,160 +266,203 @@ int ft_to_sngss7_cfg_all(void)
|
|||
x++;
|
||||
} /* while (x < (MAX_MTP_LINKS+1)) */
|
||||
|
||||
x = 1;
|
||||
while (x < (MAX_MTP_LINKS)) {
|
||||
/* check if this link has been configured already */
|
||||
if ((g_ftdm_sngss7_data.cfg.mtp3Link[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.mtp3Link[x].flags & SNGSS7_CONFIGURED))) {
|
||||
|
||||
/* configure mtp3 */
|
||||
if (ftmod_ss7_mtp3_dlsap_config(x)) {
|
||||
SS7_CRITICAL("MTP3 DLSAP %d configuration FAILED!\n", x);
|
||||
return 1;;
|
||||
} else {
|
||||
SS7_INFO("MTP3 DLSAP %d configuration DONE!\n", x);
|
||||
}
|
||||
|
||||
/* set the SNGSS7_CONFIGURED flag */
|
||||
g_ftdm_sngss7_data.cfg.mtp3Link[x].flags |= SNGSS7_CONFIGURED;
|
||||
}
|
||||
|
||||
x++;
|
||||
} /* while (x < (MAX_MTP_LINKS+1)) */
|
||||
|
||||
x = 1;
|
||||
while (x < (MAX_NSAPS)) {
|
||||
/* check if this link has been configured already */
|
||||
if ((g_ftdm_sngss7_data.cfg.nsap[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.nsap[x].flags & SNGSS7_CONFIGURED))) {
|
||||
|
||||
ret = ftmod_ss7_mtp3_nsap_config(x);
|
||||
if (ret) {
|
||||
SS7_CRITICAL("MTP3 NSAP %d configuration FAILED!(%s)\n", x, DECODE_LCM_REASON(ret));
|
||||
return 1;
|
||||
} else {
|
||||
SS7_INFO("MTP3 NSAP %d configuration DONE!\n", x);
|
||||
}
|
||||
|
||||
ret = ftmod_ss7_isup_nsap_config(x);
|
||||
if (ret) {
|
||||
SS7_CRITICAL("ISUP NSAP %d configuration FAILED!(%s)\n", x, DECODE_LCM_REASON(ret));
|
||||
return 1;
|
||||
} else {
|
||||
SS7_INFO("ISUP NSAP %d configuration DONE!\n", x);
|
||||
}
|
||||
|
||||
/* set the SNGSS7_CONFIGURED flag */
|
||||
g_ftdm_sngss7_data.cfg.nsap[x].flags |= SNGSS7_CONFIGURED;
|
||||
} /* if !SNGSS7_CONFIGURED */
|
||||
|
||||
x++;
|
||||
} /* while (x < (MAX_NSAPS)) */
|
||||
|
||||
x = 1;
|
||||
while (x < (MAX_MTP_LINKSETS+1)) {
|
||||
/* check if this link has been configured already */
|
||||
if ((g_ftdm_sngss7_data.cfg.mtpLinkSet[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.mtpLinkSet[x].flags & SNGSS7_CONFIGURED))) {
|
||||
|
||||
if (ftmod_ss7_mtp3_linkset_config(x)) {
|
||||
SS7_CRITICAL("MTP3 LINKSET %d configuration FAILED!\n", x);
|
||||
return 1;
|
||||
} else {
|
||||
SS7_INFO("MTP3 LINKSET %d configuration DONE!\n", x);
|
||||
}
|
||||
|
||||
/* set the SNGSS7_CONFIGURED flag */
|
||||
g_ftdm_sngss7_data.cfg.mtpLinkSet[x].flags |= SNGSS7_CONFIGURED;
|
||||
} /* if !SNGSS7_CONFIGURED */
|
||||
|
||||
x++;
|
||||
} /* while (x < (MAX_MTP_LINKSETS+1)) */
|
||||
|
||||
x = 1;
|
||||
while (x < (MAX_MTP_ROUTES+1)) {
|
||||
/* check if this link has been configured already */
|
||||
if ((g_ftdm_sngss7_data.cfg.mtpRoute[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.mtpRoute[x].flags & SNGSS7_CONFIGURED))) {
|
||||
|
||||
if (ftmod_ss7_mtp3_route_config(x)) {
|
||||
SS7_CRITICAL("MTP3 ROUTE %d configuration FAILED!\n", x);
|
||||
return 1;
|
||||
} else {
|
||||
SS7_INFO("MTP3 ROUTE %d configuration DONE!\n",x);
|
||||
}
|
||||
|
||||
/* set the SNGSS7_CONFIGURED flag */
|
||||
g_ftdm_sngss7_data.cfg.mtpRoute[x].flags |= SNGSS7_CONFIGURED;
|
||||
} /* if !SNGSS7_CONFIGURED */
|
||||
|
||||
x++;
|
||||
} /* while (x < (MAX_MTP_ROUTES+1)) */
|
||||
|
||||
x = 1;
|
||||
while (x < (MAX_ISAPS)) {
|
||||
/* check if this link has been configured already */
|
||||
if ((g_ftdm_sngss7_data.cfg.isap[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.isap[x].flags & SNGSS7_CONFIGURED))) {
|
||||
|
||||
if (ftmod_ss7_isup_isap_config(x)) {
|
||||
SS7_CRITICAL("ISUP ISAP %d configuration FAILED!\n", x);
|
||||
return 1;
|
||||
} else {
|
||||
SS7_INFO("ISUP ISAP %d configuration DONE!\n", x);
|
||||
}
|
||||
|
||||
/* set the SNGSS7_CONFIGURED flag */
|
||||
g_ftdm_sngss7_data.cfg.isap[x].flags |= SNGSS7_CONFIGURED;
|
||||
} /* if !SNGSS7_CONFIGURED */
|
||||
|
||||
x++;
|
||||
} /* while (x < (MAX_ISAPS)) */
|
||||
|
||||
if (sngss7_test_flag(&g_ftdm_sngss7_data.cfg, SNGSS7_ISUP_STARTED)) {
|
||||
/* no configs above mtp2 for relay */
|
||||
if (g_ftdm_sngss7_data.cfg.procId == 1) {
|
||||
x = 1;
|
||||
while (x < (MAX_ISUP_INFS)) {
|
||||
while (x < (MAX_MTP_LINKS)) {
|
||||
/* check if this link has been configured already */
|
||||
if ((g_ftdm_sngss7_data.cfg.mtp3Link[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.mtp3Link[x].flags & SNGSS7_CONFIGURED))) {
|
||||
|
||||
/* configure mtp3 */
|
||||
if (ftmod_ss7_mtp3_dlsap_config(x)) {
|
||||
SS7_CRITICAL("MTP3 DLSAP %d configuration FAILED!\n", x);
|
||||
return 1;;
|
||||
} else {
|
||||
SS7_INFO("MTP3 DLSAP %d configuration DONE!\n", x);
|
||||
}
|
||||
|
||||
/* set the SNGSS7_CONFIGURED flag */
|
||||
g_ftdm_sngss7_data.cfg.mtp3Link[x].flags |= SNGSS7_CONFIGURED;
|
||||
}
|
||||
|
||||
x++;
|
||||
} /* while (x < (MAX_MTP_LINKS+1)) */
|
||||
|
||||
/* in M2UA_SG mode there will not be any MTP3 layer */
|
||||
if(SNG_SS7_OPR_MODE_M2UA_SG != g_ftdm_operating_mode){
|
||||
x = 1;
|
||||
while (x < (MAX_NSAPS)) {
|
||||
/* check if this link has been configured already */
|
||||
if ((g_ftdm_sngss7_data.cfg.nsap[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.nsap[x].flags & SNGSS7_CONFIGURED))) {
|
||||
|
||||
ret = ftmod_ss7_mtp3_nsap_config(x);
|
||||
if (ret) {
|
||||
SS7_CRITICAL("MTP3 NSAP %d configuration FAILED!(%s)\n", x, DECODE_LCM_REASON(ret));
|
||||
return 1;
|
||||
} else {
|
||||
SS7_INFO("MTP3 NSAP %d configuration DONE!\n", x);
|
||||
}
|
||||
|
||||
ret = ftmod_ss7_isup_nsap_config(x);
|
||||
if (ret) {
|
||||
SS7_CRITICAL("ISUP NSAP %d configuration FAILED!(%s)\n", x, DECODE_LCM_REASON(ret));
|
||||
return 1;
|
||||
} else {
|
||||
SS7_INFO("ISUP NSAP %d configuration DONE!\n", x);
|
||||
}
|
||||
|
||||
/* set the SNGSS7_CONFIGURED flag */
|
||||
g_ftdm_sngss7_data.cfg.nsap[x].flags |= SNGSS7_CONFIGURED;
|
||||
} /* if !SNGSS7_CONFIGURED */
|
||||
|
||||
x++;
|
||||
} /* while (x < (MAX_NSAPS)) */
|
||||
}
|
||||
|
||||
/* in M2UA_SG mode there will not be any MTP3 layer */
|
||||
if(SNG_SS7_OPR_MODE_M2UA_SG != g_ftdm_operating_mode){
|
||||
x = 1;
|
||||
while (x < (MAX_MTP_LINKSETS+1)) {
|
||||
/* check if this link has been configured already */
|
||||
if ((g_ftdm_sngss7_data.cfg.mtpLinkSet[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.mtpLinkSet[x].flags & SNGSS7_CONFIGURED))) {
|
||||
|
||||
if (ftmod_ss7_mtp3_linkset_config(x)) {
|
||||
SS7_CRITICAL("MTP3 LINKSET %d configuration FAILED!\n", x);
|
||||
return 1;
|
||||
} else {
|
||||
SS7_INFO("MTP3 LINKSET %d configuration DONE!\n", x);
|
||||
}
|
||||
|
||||
/* set the SNGSS7_CONFIGURED flag */
|
||||
g_ftdm_sngss7_data.cfg.mtpLinkSet[x].flags |= SNGSS7_CONFIGURED;
|
||||
} /* if !SNGSS7_CONFIGURED */
|
||||
|
||||
x++;
|
||||
} /* while (x < (MAX_MTP_LINKSETS+1)) */
|
||||
}
|
||||
|
||||
/* in M2UA_SG mode there will not be any MTP3 layer */
|
||||
if(SNG_SS7_OPR_MODE_M2UA_SG != g_ftdm_operating_mode){
|
||||
x = 1;
|
||||
while (x < (MAX_MTP_ROUTES+1)) {
|
||||
/* check if this link has been configured already */
|
||||
if ((g_ftdm_sngss7_data.cfg.mtpRoute[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.mtpRoute[x].flags & SNGSS7_CONFIGURED))) {
|
||||
|
||||
if (ftmod_ss7_mtp3_route_config(x)) {
|
||||
SS7_CRITICAL("MTP3 ROUTE %d configuration FAILED!\n", x);
|
||||
return 1;
|
||||
} else {
|
||||
SS7_INFO("MTP3 ROUTE %d configuration DONE!\n",x);
|
||||
}
|
||||
|
||||
/* set the SNGSS7_CONFIGURED flag */
|
||||
g_ftdm_sngss7_data.cfg.mtpRoute[x].flags |= SNGSS7_CONFIGURED;
|
||||
} /* if !SNGSS7_CONFIGURED */
|
||||
|
||||
x++;
|
||||
} /* while (x < (MAX_MTP_ROUTES+1)) */
|
||||
}
|
||||
|
||||
x = 1;
|
||||
while (x < (MAX_ISAPS)) {
|
||||
/* check if this link has been configured already */
|
||||
if ((g_ftdm_sngss7_data.cfg.isupIntf[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.isupIntf[x].flags & SNGSS7_CONFIGURED))) {
|
||||
|
||||
if (ftmod_ss7_isup_intf_config(x)) {
|
||||
SS7_CRITICAL("ISUP INTF %d configuration FAILED!\n", x);
|
||||
if ((g_ftdm_sngss7_data.cfg.isap[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.isap[x].flags & SNGSS7_CONFIGURED))) {
|
||||
|
||||
if (ftmod_ss7_isup_isap_config(x)) {
|
||||
SS7_CRITICAL("ISUP ISAP %d configuration FAILED!\n", x);
|
||||
return 1;
|
||||
} else {
|
||||
SS7_INFO("ISUP INTF %d configuration DONE!\n", x);
|
||||
/* set the interface to paused */
|
||||
sngss7_set_flag(&g_ftdm_sngss7_data.cfg.isupIntf[x], SNGSS7_PAUSED);
|
||||
SS7_INFO("ISUP ISAP %d configuration DONE!\n", x);
|
||||
}
|
||||
|
||||
|
||||
/* set the SNGSS7_CONFIGURED flag */
|
||||
g_ftdm_sngss7_data.cfg.isupIntf[x].flags |= SNGSS7_CONFIGURED;
|
||||
g_ftdm_sngss7_data.cfg.isap[x].flags |= SNGSS7_CONFIGURED;
|
||||
} /* if !SNGSS7_CONFIGURED */
|
||||
|
||||
x++;
|
||||
} /* while (x < (MAX_ISUP_INFS)) */
|
||||
} /* if (sngss7_test_flag(&g_ftdm_sngss7_data.cfg, SNGSS7_ISUP)) */
|
||||
} /* while (x < (MAX_ISAPS)) */
|
||||
|
||||
x = (g_ftdm_sngss7_data.cfg.procId * 1000) + 1;
|
||||
while (g_ftdm_sngss7_data.cfg.isupCkt[x].id != 0) {
|
||||
/* check if this link has been configured already */
|
||||
if ((g_ftdm_sngss7_data.cfg.isupCkt[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.isupCkt[x].flags & SNGSS7_CONFIGURED))) {
|
||||
if (sngss7_test_flag(&g_ftdm_sngss7_data.cfg, SNGSS7_ISUP_STARTED)) {
|
||||
x = 1;
|
||||
while (x < (MAX_ISUP_INFS)) {
|
||||
/* check if this link has been configured already */
|
||||
if ((g_ftdm_sngss7_data.cfg.isupIntf[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.isupIntf[x].flags & SNGSS7_CONFIGURED))) {
|
||||
|
||||
if (ftmod_ss7_isup_intf_config(x)) {
|
||||
SS7_CRITICAL("ISUP INTF %d configuration FAILED!\n", x);
|
||||
return 1;
|
||||
} else {
|
||||
SS7_INFO("ISUP INTF %d configuration DONE!\n", x);
|
||||
/* set the interface to paused */
|
||||
sngss7_set_flag(&g_ftdm_sngss7_data.cfg.isupIntf[x], SNGSS7_PAUSED);
|
||||
}
|
||||
|
||||
/* set the SNGSS7_CONFIGURED flag */
|
||||
g_ftdm_sngss7_data.cfg.isupIntf[x].flags |= SNGSS7_CONFIGURED;
|
||||
} /* if !SNGSS7_CONFIGURED */
|
||||
|
||||
x++;
|
||||
} /* while (x < (MAX_ISUP_INFS)) */
|
||||
} /* if (sngss7_test_flag(&g_ftdm_sngss7_data.cfg, SNGSS7_ISUP)) */
|
||||
|
||||
if (ftmod_ss7_isup_ckt_config(x)) {
|
||||
SS7_CRITICAL("ISUP CKT %d configuration FAILED!\n", x);
|
||||
x = (g_ftdm_sngss7_data.cfg.procId * 1000) + 1;
|
||||
while (g_ftdm_sngss7_data.cfg.isupCkt[x].id != 0) {
|
||||
|
||||
if (g_ftdm_sngss7_data.cfg.procId > 1) {
|
||||
break;
|
||||
}
|
||||
|
||||
/* check if this link has been configured already */
|
||||
if ((g_ftdm_sngss7_data.cfg.isupCkt[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.isupCkt[x].flags & SNGSS7_CONFIGURED))) {
|
||||
|
||||
if (ftmod_ss7_isup_ckt_config(x)) {
|
||||
SS7_CRITICAL("ISUP CKT %d configuration FAILED!\n", x);
|
||||
return 1;
|
||||
} else {
|
||||
SS7_INFO("ISUP CKT %d configuration DONE!\n", x);
|
||||
}
|
||||
|
||||
/* set the SNGSS7_CONFIGURED flag */
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].flags |= SNGSS7_CONFIGURED;
|
||||
} /* if !SNGSS7_CONFIGURED */
|
||||
|
||||
x++;
|
||||
} /* while (g_ftdm_sngss7_data.cfg.isupCkt[x].id != 0) */
|
||||
}
|
||||
|
||||
/* go through all the relays channels and configure it */
|
||||
x = 1;
|
||||
while (x < (MAX_RELAY_CHANNELS)) {
|
||||
/* check if this relay channel has been configured already */
|
||||
if ((g_ftdm_sngss7_data.cfg.relay[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.relay[x].flags & SNGSS7_CONFIGURED))) {
|
||||
|
||||
/* send the specific configuration */
|
||||
if (ftmod_ss7_relay_chan_config(x)) {
|
||||
SS7_CRITICAL("Relay Channel %d configuration FAILED!\n", x);
|
||||
return 1;
|
||||
} else {
|
||||
SS7_INFO("ISUP CKT %d configuration DONE!\n", x);
|
||||
SS7_INFO("Relay Channel %d configuration DONE!\n", x);
|
||||
}
|
||||
|
||||
/* set the SNGSS7_CONFIGURED flag */
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].flags |= SNGSS7_CONFIGURED;
|
||||
g_ftdm_sngss7_data.cfg.relay[x].flags |= SNGSS7_CONFIGURED;
|
||||
} /* if !SNGSS7_CONFIGURED */
|
||||
|
||||
x++;
|
||||
} /* while (g_ftdm_sngss7_data.cfg.isupCkt[x].id != 0) */
|
||||
} /* while (x < (MAX_RELAY_CHANNELS)) */
|
||||
|
||||
|
||||
if(SNG_SS7_OPR_MODE_M2UA_SG == g_ftdm_operating_mode){
|
||||
return ftmod_ss7_m2ua_cfg();
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -48,35 +48,7 @@ static int ftmod_ss7_enable_isap(int suId);
|
|||
static int ftmod_ss7_enable_nsap(int suId);
|
||||
static int ftmod_ss7_enable_mtpLinkSet(int lnkSetId);
|
||||
|
||||
int ftmod_ss7_inhibit_mtp3link(uint32_t id);
|
||||
int ftmod_ss7_uninhibit_mtp3link(uint32_t id);
|
||||
|
||||
int ftmod_ss7_bind_mtp3link(uint32_t id);
|
||||
int ftmod_ss7_unbind_mtp3link(uint32_t id);
|
||||
int ftmod_ss7_activate_mtp3link(uint32_t id);
|
||||
int ftmod_ss7_deactivate_mtp3link(uint32_t id);
|
||||
int ftmod_ss7_deactivate2_mtp3link(uint32_t id);
|
||||
|
||||
int ftmod_ss7_activate_mtplinkSet(uint32_t id);
|
||||
int ftmod_ss7_deactivate_mtplinkSet(uint32_t id);
|
||||
int ftmod_ss7_deactivate2_mtplinkSet(uint32_t id);
|
||||
|
||||
int ftmod_ss7_lpo_mtp3link(uint32_t id);
|
||||
int ftmod_ss7_lpr_mtp3link(uint32_t id);
|
||||
|
||||
int ftmod_ss7_shutdown_isup(void);
|
||||
int ftmod_ss7_shutdown_mtp3(void);
|
||||
int ftmod_ss7_shutdown_mtp2(void);
|
||||
int ftmod_ss7_shutdown_relay(void);
|
||||
int ftmod_ss7_disable_relay_channel(uint32_t chanId);
|
||||
|
||||
int ftmod_ss7_disable_grp_mtp3Link(uint32_t procId);
|
||||
int ftmod_ss7_enable_grp_mtp3Link(uint32_t procId);
|
||||
|
||||
int ftmod_ss7_disable_grp_mtp2Link(uint32_t procId);
|
||||
|
||||
int ftmod_ss7_block_isup_ckt(uint32_t cktId);
|
||||
int ftmod_ss7_unblock_isup_ckt(uint32_t cktId);
|
||||
/******************************************************************************/
|
||||
|
||||
/* FUNCTIONS ******************************************************************/
|
||||
|
@ -88,7 +60,7 @@ int ft_to_sngss7_activate_all(void)
|
|||
while (x < (MAX_ISAPS)) {
|
||||
/* check if this link has already been actived */
|
||||
if ((g_ftdm_sngss7_data.cfg.isap[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.isap[x].flags & SNGSS7_ACTIVE))) {
|
||||
(!(g_ftdm_sngss7_data.cfg.isap[x].flags & SNGSS7_ACTIVE))) {
|
||||
|
||||
if (ftmod_ss7_enable_isap(x)) {
|
||||
SS7_CRITICAL("ISAP %d Enable: NOT OK\n", x);
|
||||
|
@ -100,15 +72,16 @@ int ft_to_sngss7_activate_all(void)
|
|||
/* set the SNGSS7_ACTIVE flag */
|
||||
g_ftdm_sngss7_data.cfg.isap[x].flags |= SNGSS7_ACTIVE;
|
||||
} /* if !SNGSS7_ACTIVE */
|
||||
|
||||
|
||||
x++;
|
||||
} /* while (x < (MAX_ISAPS)) */
|
||||
|
||||
if(SNG_SS7_OPR_MODE_M2UA_SG != g_ftdm_operating_mode){
|
||||
x = 1;
|
||||
while (x < (MAX_NSAPS)) {
|
||||
/* check if this link has already been actived */
|
||||
if ((g_ftdm_sngss7_data.cfg.nsap[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.nsap[x].flags & SNGSS7_ACTIVE))) {
|
||||
(!(g_ftdm_sngss7_data.cfg.nsap[x].flags & SNGSS7_ACTIVE))) {
|
||||
|
||||
if (ftmod_ss7_enable_nsap(x)) {
|
||||
SS7_CRITICAL("NSAP %d Enable: NOT OK\n", x);
|
||||
|
@ -120,30 +93,35 @@ int ft_to_sngss7_activate_all(void)
|
|||
/* set the SNGSS7_ACTIVE flag */
|
||||
g_ftdm_sngss7_data.cfg.nsap[x].flags |= SNGSS7_ACTIVE;
|
||||
} /* if !SNGSS7_ACTIVE */
|
||||
|
||||
|
||||
x++;
|
||||
} /* while (x < (MAX_NSAPS)) */
|
||||
|
||||
if (g_ftdm_sngss7_data.cfg.mtpRoute[1].id != 0) {
|
||||
x = 1;
|
||||
while (x < (MAX_MTP_LINKSETS+1)) {
|
||||
/* check if this link has already been actived */
|
||||
if ((g_ftdm_sngss7_data.cfg.mtpLinkSet[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.mtpLinkSet[x].flags & SNGSS7_ACTIVE))) {
|
||||
|
||||
if (ftmod_ss7_enable_mtpLinkSet(x)) {
|
||||
SS7_CRITICAL("LinkSet \"%s\" Enable: NOT OK\n", g_ftdm_sngss7_data.cfg.mtpLinkSet[x].name);
|
||||
return 1;
|
||||
} else {
|
||||
SS7_INFO("LinkSet \"%s\" Enable: OK\n", g_ftdm_sngss7_data.cfg.mtpLinkSet[x].name);
|
||||
}
|
||||
|
||||
/* set the SNGSS7_ACTIVE flag */
|
||||
g_ftdm_sngss7_data.cfg.mtpLinkSet[x].flags |= SNGSS7_ACTIVE;
|
||||
} /* if !SNGSS7_ACTIVE */
|
||||
|
||||
x++;
|
||||
} /* while (x < (MAX_MTP_LINKSETS+1)) */
|
||||
if (g_ftdm_sngss7_data.cfg.mtpRoute[1].id != 0) {
|
||||
x = 1;
|
||||
while (x < (MAX_MTP_LINKSETS+1)) {
|
||||
/* check if this link has already been actived */
|
||||
if ((g_ftdm_sngss7_data.cfg.mtpLinkSet[x].id != 0) &&
|
||||
(!(g_ftdm_sngss7_data.cfg.mtpLinkSet[x].flags & SNGSS7_ACTIVE))) {
|
||||
|
||||
if (ftmod_ss7_enable_mtpLinkSet(x)) {
|
||||
SS7_CRITICAL("LinkSet \"%s\" Enable: NOT OK\n", g_ftdm_sngss7_data.cfg.mtpLinkSet[x].name);
|
||||
return 1;
|
||||
} else {
|
||||
SS7_INFO("LinkSet \"%s\" Enable: OK\n", g_ftdm_sngss7_data.cfg.mtpLinkSet[x].name);
|
||||
}
|
||||
|
||||
/* set the SNGSS7_ACTIVE flag */
|
||||
g_ftdm_sngss7_data.cfg.mtpLinkSet[x].flags |= SNGSS7_ACTIVE;
|
||||
} /* if !SNGSS7_ACTIVE */
|
||||
|
||||
x++;
|
||||
} /* while (x < (MAX_MTP_LINKSETS+1)) */
|
||||
}
|
||||
}
|
||||
|
||||
if(SNG_SS7_OPR_MODE_M2UA_SG == g_ftdm_operating_mode){
|
||||
return ftmod_ss7_m2ua_start();
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
@ -779,7 +757,14 @@ int ftmod_ss7_disable_grp_mtp3Link(uint32_t procId)
|
|||
cntrl.t.cntrl.action = AUBND_DIS; /* disable and unbind */
|
||||
cntrl.t.cntrl.subAction = SAGR_DSTPROCID; /* specificed element */
|
||||
|
||||
return (sng_cntrl_mtp3(&pst, &cntrl));
|
||||
if (g_ftdm_sngss7_data.cfg.procId == procId) {
|
||||
SS7_DEBUG("Executing MTP3 cntrl command local pid =%i\n",procId);
|
||||
return (sng_cntrl_mtp3(&pst, &cntrl));
|
||||
} else {
|
||||
SS7_WARN("Executing MTP3 cntrl command different local=%i target=%i\n",
|
||||
g_ftdm_sngss7_data.cfg.procId,procId);
|
||||
return (sng_cntrl_mtp3_nowait(&pst, &cntrl));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
@ -811,7 +796,14 @@ int ftmod_ss7_enable_grp_mtp3Link(uint32_t procId)
|
|||
cntrl.t.cntrl.action = ABND_ENA; /* bind and enable */
|
||||
cntrl.t.cntrl.subAction = SAGR_DSTPROCID; /* specificed element */
|
||||
|
||||
return (sng_cntrl_mtp3(&pst, &cntrl));
|
||||
if (g_ftdm_sngss7_data.cfg.procId == procId) {
|
||||
SS7_DEBUG("Executing MTP3 cntrl command local pid =%i\n",procId);
|
||||
return (sng_cntrl_mtp3(&pst, &cntrl));
|
||||
} else {
|
||||
SS7_WARN("Executing MTP3 cntrl command different local=%i target=%i\n",
|
||||
g_ftdm_sngss7_data.cfg.procId,procId);
|
||||
return (sng_cntrl_mtp3_nowait(&pst, &cntrl));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
@ -848,7 +840,7 @@ int ftmod_ss7_disable_grp_mtp2Link(uint32_t procId)
|
|||
}
|
||||
|
||||
/******************************************************************************/
|
||||
int ftmod_ss7_block_isup_ckt(uint32_t cktId)
|
||||
int __ftmod_ss7_block_isup_ckt(uint32_t cktId, ftdm_bool_t wait)
|
||||
{
|
||||
SiMngmt cntrl;
|
||||
Pst pst;
|
||||
|
@ -876,7 +868,11 @@ int ftmod_ss7_block_isup_ckt(uint32_t cktId)
|
|||
cntrl.t.cntrl.action = ADISIMM; /* block via BLO */
|
||||
cntrl.t.cntrl.subAction = SAELMNT; /* specificed element */
|
||||
|
||||
return (sng_cntrl_isup(&pst, &cntrl));
|
||||
if (wait == FTDM_TRUE) {
|
||||
return (sng_cntrl_isup(&pst, &cntrl));
|
||||
} else {
|
||||
return (sng_cntrl_isup_nowait(&pst, &cntrl));
|
||||
}
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
|
|
|
@ -33,6 +33,7 @@
|
|||
* Contributors:
|
||||
*
|
||||
* Ricardo Barroetaveña <rbarroetavena@anura.com.ar>
|
||||
* James Zhang <jzhang@sangoma.com>
|
||||
*
|
||||
*/
|
||||
|
||||
|
@ -87,6 +88,8 @@ ftdm_status_t handle_olm_msg(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
/* FUNCTIONS ******************************************************************/
|
||||
|
||||
#define ftdm_running_return(var) if (!ftdm_running()) { SS7_ERROR("Error: ftdm_running is not set! Ignoring\n"); return var; }
|
||||
|
||||
ftdm_status_t handle_con_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, SiConEvnt *siConEvnt)
|
||||
{
|
||||
SS7_FUNC_TRACE_ENTER(__FUNCTION__);
|
||||
|
@ -94,9 +97,11 @@ ftdm_status_t handle_con_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
sngss7_chan_data_t *sngss7_info = NULL;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
char var[FTDM_DIGITS_LIMIT];
|
||||
|
||||
|
||||
memset(var, '\0', sizeof(var));
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* get the ftdmchan and ss7_chan_data from the circuit */
|
||||
if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
|
||||
SS7_ERROR("Failed to extract channel data for circuit = %d!\n", circuit);
|
||||
|
@ -118,11 +123,24 @@ ftdm_status_t handle_con_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
/* as per Q.764, 2.8.2.3 xiv ... remove the block from this channel */
|
||||
sngss7_clear_ckt_blk_flag(sngss7_info, FLAG_CKT_MN_BLOCK_RX);
|
||||
sngss7_clear_ckt_blk_flag(sngss7_info, FLAG_CKT_MN_BLOCK_RX_DN);
|
||||
sngss7_clear_ckt_blk_flag(sngss7_info, FLAG_GRP_HW_BLOCK_RX);
|
||||
sngss7_clear_ckt_blk_flag(sngss7_info, FLAG_GRP_HW_BLOCK_RX_DN);
|
||||
sngss7_clear_ckt_blk_flag(sngss7_info, FLAG_GRP_MN_BLOCK_RX);
|
||||
sngss7_clear_ckt_blk_flag(sngss7_info, FLAG_GRP_MN_BLOCK_RX_DN);
|
||||
|
||||
/* KONRAD FIX ME : check in case there is a ckt and grp block */
|
||||
}
|
||||
|
||||
sngss7_clear_ckt_flag(sngss7_info, FLAG_INR_TX);
|
||||
sngss7_clear_ckt_flag(sngss7_info, FLAG_INR_SENT);
|
||||
sngss7_clear_ckt_flag(sngss7_info, FLAG_INR_RX);
|
||||
sngss7_clear_ckt_flag(sngss7_info, FLAG_INR_RX_DN);
|
||||
sngss7_clear_ckt_flag(sngss7_info, FLAG_INF_TX);
|
||||
sngss7_clear_ckt_flag(sngss7_info, FLAG_INF_SENT);
|
||||
sngss7_clear_ckt_flag(sngss7_info, FLAG_INF_RX);
|
||||
sngss7_clear_ckt_flag(sngss7_info, FLAG_INF_RX_DN);
|
||||
sngss7_clear_ckt_flag(sngss7_info, FLAG_FULL_NUMBER);
|
||||
|
||||
/* check whether the ftdm channel is in a state to accept a call */
|
||||
switch (ftdmchan->state) {
|
||||
|
@ -167,6 +185,12 @@ ftdm_status_t handle_con_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
/* fill in ANI */
|
||||
ftdm_set_string(ftdmchan->caller_data.ani.digits, ftdmchan->caller_data.cid_num.digits);
|
||||
}
|
||||
else {
|
||||
if (g_ftdm_sngss7_data.cfg.force_inr) {
|
||||
sngss7_set_ckt_flag(sngss7_info, FLAG_INR_TX);
|
||||
sngss7_clear_ckt_flag(sngss7_info, FLAG_INR_SENT);
|
||||
}
|
||||
}
|
||||
|
||||
if (siConEvnt->cgPtyNum.scrnInd.pres) {
|
||||
/* fill in the screening indication value */
|
||||
|
@ -178,6 +202,11 @@ ftdm_status_t handle_con_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
ftdmchan->caller_data.pres = siConEvnt->cgPtyNum.presRest.val;
|
||||
}
|
||||
} else {
|
||||
if (g_ftdm_sngss7_data.cfg.force_inr) {
|
||||
sngss7_set_ckt_flag(sngss7_info, FLAG_INR_TX);
|
||||
sngss7_clear_ckt_flag(sngss7_info, FLAG_INR_SENT);
|
||||
}
|
||||
|
||||
SS7_INFO_CHAN(ftdmchan,"No Calling party (ANI) information in IAM!%s\n", " ");
|
||||
}
|
||||
|
||||
|
@ -192,12 +221,16 @@ ftdm_status_t handle_con_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
} else {
|
||||
SS7_INFO_CHAN(ftdmchan,"No Called party (DNIS) information in IAM!%s\n", " ");
|
||||
}
|
||||
|
||||
copy_NatureOfConnection_from_sngss7(ftdmchan, &siConEvnt->natConInd);
|
||||
copy_fwdCallInd_hex_from_sngss7(ftdmchan, &siConEvnt->fwdCallInd);
|
||||
copy_access_transport_from_sngss7(ftdmchan, &siConEvnt->accTrnspt);
|
||||
copy_ocn_from_sngss7(ftdmchan, &siConEvnt->origCdNum);
|
||||
copy_redirgNum_from_sngss7(ftdmchan, &siConEvnt->redirgNum);
|
||||
|
||||
copy_redirgInfo_from_sngss7(ftdmchan, &siConEvnt->redirInfo);
|
||||
copy_genNmb_from_sngss7(ftdmchan, &siConEvnt->genNmb);
|
||||
|
||||
copy_cgPtyCat_from_sngss7(ftdmchan, &siConEvnt->cgPtyCat);
|
||||
copy_cdPtyNum_from_sngss7(ftdmchan, &siConEvnt->cdPtyNum);
|
||||
|
||||
/* fill in the TMR/bearer capability */
|
||||
if (siConEvnt->txMedReq.eh.pres) {
|
||||
|
@ -213,9 +246,6 @@ ftdm_status_t handle_con_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
sprintf(var, "%d", siConEvnt->cgPtyNum.natAddrInd.val);
|
||||
sngss7_add_var(sngss7_info, "ss7_clg_nadi", var);
|
||||
|
||||
sprintf(var, "%d", siConEvnt->cdPtyNum.natAddrInd.val);
|
||||
sngss7_add_var(sngss7_info, "ss7_cld_nadi", var);
|
||||
|
||||
/* Retrieve the Location Number if present (see ITU Q.763, 3.30) */
|
||||
if (siConEvnt->cgPtyNum1.eh.pres) {
|
||||
if (siConEvnt->cgPtyNum1.addrSig.pres) {
|
||||
|
@ -247,7 +277,8 @@ ftdm_status_t handle_con_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
sprintf(var, "%d", sngss7_info->circuit->cic);
|
||||
sngss7_add_var(sngss7_info, "ss7_cic", var);
|
||||
|
||||
sprintf(var, "%d", g_ftdm_sngss7_data.cfg.isupIntf[sngss7_info->circuit->infId].spc );
|
||||
|
||||
sprintf(var, "%d", g_ftdm_sngss7_data.cfg.isupIntf[sngss7_info->circuit->infId].dpc );
|
||||
sngss7_add_var(sngss7_info, "ss7_opc", var);
|
||||
|
||||
if (siConEvnt->callRef.callId.pres) {
|
||||
|
@ -308,24 +339,26 @@ handle_glare:
|
|||
|
||||
/* setup the hangup cause */
|
||||
ftdmchan->caller_data.hangup_cause = 34; /* Circuit Congrestion */
|
||||
|
||||
/* this is a remote hangup request */
|
||||
sngss7_set_ckt_flag(sngss7_info, FLAG_REMOTE_REL);
|
||||
|
||||
/* move the state of the channel to Terminating to end the call */
|
||||
|
||||
/* move the state of the channel to Terminating to end the call
|
||||
in TERMINATING state, the release cause is set to REMOTE_REL
|
||||
in any means. So we don't have to set the release reason here.
|
||||
*/
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_TERMINATING);
|
||||
} /* if (!(sngss7_test_ckt_flag(sngss7_info, FLAG_GLARE))) */
|
||||
}
|
||||
break;
|
||||
/**************************************************************************/
|
||||
default: /* should not have gotten an IAM while in this state */
|
||||
SS7_ERROR_CHAN(ftdmchan, "Got IAM on channel in invalid state(%s)...reset!\n", ftdm_channel_state2str (ftdmchan->state));
|
||||
|
||||
/* reset the cic */
|
||||
sngss7_set_ckt_flag(sngss7_info, FLAG_RESET_TX);
|
||||
|
||||
/* move the state of the channel to RESTART to force a reset */
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_RESTART);
|
||||
/* throw the TX reset flag */
|
||||
if (!sngss7_tx_reset_status_pending(sngss7_info)) {
|
||||
sngss7_tx_reset_restart(sngss7_info);
|
||||
sngss7_set_ckt_flag (sngss7_info, FLAG_REMOTE_REL);
|
||||
|
||||
/* go to RESTART */
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_RESTART);
|
||||
}
|
||||
break;
|
||||
/**************************************************************************/
|
||||
} /* switch (ftdmchan->state) */
|
||||
|
@ -344,6 +377,8 @@ ftdm_status_t handle_con_sta(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
sngss7_chan_data_t *sngss7_info ;
|
||||
ftdm_channel_t *ftdmchan;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* get the ftdmchan and ss7_chan_data from the circuit */
|
||||
if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
|
||||
|
@ -389,11 +424,14 @@ ftdm_status_t handle_con_sta(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
SS7_ERROR_CHAN(ftdmchan, "RX ACM in invalid state :%s...resetting CIC\n",
|
||||
ftdm_channel_state2str (ftdmchan->state));
|
||||
|
||||
/* reset the cic */
|
||||
sngss7_set_ckt_flag(sngss7_info, FLAG_RESET_TX);
|
||||
/* throw the TX reset flag */
|
||||
if (!sngss7_tx_reset_status_pending(sngss7_info)) {
|
||||
sngss7_tx_reset_restart(sngss7_info);
|
||||
sngss7_set_ckt_flag (sngss7_info, FLAG_REMOTE_REL);
|
||||
|
||||
/* go to RESTART */
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_RESTART);
|
||||
/* go to RESTART */
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_RESTART);
|
||||
}
|
||||
break;
|
||||
/**********************************************************************/
|
||||
} /* switch (ftdmchan->state) */
|
||||
|
@ -422,10 +460,26 @@ ftdm_status_t handle_con_sta(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
/**************************************************************************/
|
||||
case (INFORMATION):
|
||||
SS7_INFO_CHAN(ftdmchan,"[CIC:%d]Rx INF\n", sngss7_info->circuit->cic);
|
||||
|
||||
SS7_DEBUG_CHAN (ftdmchan, "Cancelling T.39 timer %s\n", " ");
|
||||
/* check if t39 is active */
|
||||
if (sngss7_info->t39.hb_timer_id) {
|
||||
ftdm_sched_cancel_timer (sngss7_info->t39.sched, sngss7_info->t39.hb_timer_id);
|
||||
SS7_DEBUG_CHAN (ftdmchan, "T.39 timer has been cancelled upon receiving INF message %s\n", " ");
|
||||
}
|
||||
|
||||
sngss7_set_ckt_flag(sngss7_info, FLAG_INF_RX_DN);
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_IDLE);
|
||||
|
||||
break;
|
||||
/**************************************************************************/
|
||||
case (INFORMATREQ):
|
||||
SS7_INFO_CHAN(ftdmchan,"[CIC:%d]Rx INR\n", sngss7_info->circuit->cic);
|
||||
|
||||
ft_to_sngss7_inf(ftdmchan, siCnStEvnt);
|
||||
|
||||
sngss7_set_ckt_flag(sngss7_info, FLAG_INR_RX);
|
||||
|
||||
break;
|
||||
/**************************************************************************/
|
||||
case (SUBSADDR):
|
||||
|
@ -599,6 +653,8 @@ ftdm_status_t handle_con_cfm(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
sngss7_chan_data_t *sngss7_info ;
|
||||
ftdm_channel_t *ftdmchan;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* get the ftdmchan and ss7_chan_data from the circuit */
|
||||
if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
|
||||
|
@ -651,10 +707,13 @@ ftdm_status_t handle_con_cfm(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
SS7_INFO_CHAN(ftdmchan,"[CIC:%d]Rx ANM/CON\n", sngss7_info->circuit->cic);
|
||||
|
||||
/* throw the TX reset flag */
|
||||
sngss7_set_ckt_flag(sngss7_info, FLAG_GRP_RESET_TX);
|
||||
if (!sngss7_tx_reset_status_pending(sngss7_info)) {
|
||||
sngss7_tx_reset_restart(sngss7_info);
|
||||
sngss7_set_ckt_flag (sngss7_info, FLAG_REMOTE_REL);
|
||||
|
||||
/* go to RESTART */
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_RESTART);
|
||||
/* go to RESTART */
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_RESTART);
|
||||
}
|
||||
|
||||
break;
|
||||
/**************************************************************************/
|
||||
|
@ -674,6 +733,8 @@ ftdm_status_t handle_rel_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
sngss7_chan_data_t *sngss7_info ;
|
||||
ftdm_channel_t *ftdmchan;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* get the ftdmchan and ss7_chan_data from the circuit */
|
||||
if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
|
||||
|
@ -750,6 +811,10 @@ ftdm_status_t handle_rel_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
/* send out the release complete */
|
||||
ft_to_sngss7_rlc (ftdmchan);
|
||||
} else {
|
||||
SS7_DEBUG_CHAN(ftdmchan, "Collision of REL messages - resetting state.\n", " ");
|
||||
ft_to_sngss7_rlc (ftdmchan);
|
||||
goto rel_ind_reset;
|
||||
}
|
||||
break;
|
||||
/**************************************************************************/
|
||||
|
@ -772,11 +837,15 @@ ftdm_status_t handle_rel_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
/**************************************************************************/
|
||||
default:
|
||||
|
||||
/* throw the reset flag */
|
||||
sngss7_set_ckt_flag(sngss7_info, FLAG_RESET_RX);
|
||||
rel_ind_reset:
|
||||
/* throw the TX reset flag */
|
||||
if (!sngss7_tx_reset_status_pending(sngss7_info)) {
|
||||
sngss7_set_ckt_flag (sngss7_info, FLAG_REMOTE_REL);
|
||||
sngss7_tx_reset_restart(sngss7_info);
|
||||
|
||||
/* set the state to RESTART */
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_RESTART);
|
||||
/* go to RESTART */
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_RESTART);
|
||||
}
|
||||
break;
|
||||
/**************************************************************************/
|
||||
} /* switch (ftdmchan->state) */
|
||||
|
@ -796,6 +865,8 @@ ftdm_status_t handle_rel_cfm(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
sngss7_chan_data_t *sngss7_info ;
|
||||
ftdm_channel_t *ftdmchan;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* get the ftdmchan and ss7_chan_data from the circuit */
|
||||
if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
|
||||
|
@ -847,6 +918,8 @@ ftdm_status_t handle_dat_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
sngss7_chan_data_t *sngss7_info ;
|
||||
ftdm_channel_t *ftdmchan;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* get the ftdmchan and ss7_chan_data from the circuit */
|
||||
if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
|
||||
|
@ -874,6 +947,8 @@ ftdm_status_t handle_fac_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
sngss7_chan_data_t *sngss7_info ;
|
||||
ftdm_channel_t *ftdmchan;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* get the ftdmchan and ss7_chan_data from the circuit */
|
||||
if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
|
||||
|
@ -901,6 +976,8 @@ ftdm_status_t handle_fac_cfm(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
sngss7_chan_data_t *sngss7_info ;
|
||||
ftdm_channel_t *ftdmchan;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* get the ftdmchan and ss7_chan_data from the circuit */
|
||||
if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
|
||||
|
@ -928,6 +1005,8 @@ ftdm_status_t handle_umsg_ind(uint32_t suInstId, uint32_t spInstId, uint32_t cir
|
|||
|
||||
sngss7_chan_data_t *sngss7_info ;
|
||||
ftdm_channel_t *ftdmchan;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* get the ftdmchan and ss7_chan_data from the circuit */
|
||||
if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
|
||||
|
@ -955,6 +1034,8 @@ ftdm_status_t handle_susp_ind(uint32_t suInstId, uint32_t spInstId, uint32_t cir
|
|||
|
||||
sngss7_chan_data_t *sngss7_info ;
|
||||
ftdm_channel_t *ftdmchan;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* get the ftdmchan and ss7_chan_data from the circuit */
|
||||
if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
|
||||
|
@ -982,6 +1063,8 @@ ftdm_status_t handle_resm_ind(uint32_t suInstId, uint32_t spInstId, uint32_t cir
|
|||
|
||||
sngss7_chan_data_t *sngss7_info ;
|
||||
ftdm_channel_t *ftdmchan;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* get the ftdmchan and ss7_chan_data from the circuit */
|
||||
if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
|
||||
|
@ -1006,6 +1089,8 @@ ftdm_status_t handle_resm_ind(uint32_t suInstId, uint32_t spInstId, uint32_t cir
|
|||
ftdm_status_t handle_sta_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, uint8_t globalFlg, uint8_t evntType, SiStaEvnt *siStaEvnt)
|
||||
{
|
||||
SS7_FUNC_TRACE_ENTER(__FUNCTION__);
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is active on our side otherwise move to the next circuit */
|
||||
if (!sngss7_test_flag(&g_ftdm_sngss7_data.cfg.isupCkt[circuit], SNGSS7_ACTIVE)) {
|
||||
|
@ -1098,11 +1183,12 @@ ftdm_status_t handle_sta_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
break;
|
||||
/**************************************************************************/
|
||||
case SIT_STA_CGBRSP: /* mntc. oriented CGB response */
|
||||
/*handle_cgb_req(suInstId, spInstId, circuit, globalFlg, evntType, siStaEvnt);*/
|
||||
SS7_INFO(" Rx CGBA \n");
|
||||
break;
|
||||
/**************************************************************************/
|
||||
case SIT_STA_CGURSP: /* mntc. oriented CGU response */
|
||||
/*SS7_WARN(" %s indication not currently supported\n", DECODE_LCC_EVENT(evntType));*/
|
||||
SS7_INFO(" Rx CGUA \n");
|
||||
break;
|
||||
/**************************************************************************/
|
||||
case SIT_STA_GRSREQ: /* circuit group reset request */
|
||||
|
@ -1206,6 +1292,8 @@ ftdm_status_t handle_reattempt(uint32_t suInstId, uint32_t spInstId, uint32_t ci
|
|||
|
||||
sngss7_chan_data_t *sngss7_info = NULL;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[circuit].type != SNG_CKT_VOICE) {
|
||||
|
@ -1235,6 +1323,7 @@ ftdm_status_t handle_reattempt(uint32_t suInstId, uint32_t spInstId, uint32_t ci
|
|||
/* the glare flag is already up so it was caught ... do nothing */
|
||||
SS7_DEBUG_CHAN(ftdmchan, "Glare flag is already up...nothing to do!%s\n", " ");
|
||||
} else {
|
||||
int bHangup = 0;
|
||||
SS7_DEBUG_CHAN(ftdmchan, "Glare flag is not up yet...indicating glare from reattempt!%s\n", " ");
|
||||
/* glare, throw the flag */
|
||||
sngss7_set_ckt_flag(sngss7_info, FLAG_GLARE);
|
||||
|
@ -1242,14 +1331,45 @@ ftdm_status_t handle_reattempt(uint32_t suInstId, uint32_t spInstId, uint32_t ci
|
|||
/* clear any existing glare data from the channel */
|
||||
memset(&sngss7_info->glare, 0x0, sizeof(sngss7_glare_data_t));
|
||||
|
||||
if (g_ftdm_sngss7_data.cfg.glareResolution == SNGSS7_GLARE_DOWN) {
|
||||
/* If I'm in DOWN mode, I will always hangup my call. */
|
||||
bHangup = 1;
|
||||
}
|
||||
else if (g_ftdm_sngss7_data.cfg.glareResolution == SNGSS7_GLARE_PC) {
|
||||
/* I'm in PointCode mode.
|
||||
Case 1: My point code is higher than the other side.
|
||||
If the CIC number is even, I'm trying to control.
|
||||
If the CIC number is odd, I'll hangup my call and back off.
|
||||
Case 2: My point code is lower than the other side.
|
||||
If the CIC number is odd, I'm trying to control.
|
||||
If the CIC number is even, I'll hangup my call and back off.
|
||||
*/
|
||||
if( g_ftdm_sngss7_data.cfg.isupIntf[sngss7_info->circuit->infId].spc > g_ftdm_sngss7_data.cfg.isupIntf[sngss7_info->circuit->infId].dpc )
|
||||
{
|
||||
if ((sngss7_info->circuit->cic % 2) == 1 ) {
|
||||
bHangup = 1;
|
||||
}
|
||||
} else {
|
||||
if( (sngss7_info->circuit->cic % 2) == 0 ) {
|
||||
bHangup = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
/* If I'm in CONTROL mode, I will not hangup my call. */
|
||||
bHangup = 0;
|
||||
}
|
||||
|
||||
if (bHangup) {
|
||||
/* setup the hangup cause */
|
||||
ftdmchan->caller_data.hangup_cause = 34; /* Circuit Congrestion */
|
||||
|
||||
/* this is a remote hangup request */
|
||||
sngss7_set_ckt_flag(sngss7_info, FLAG_REMOTE_REL);
|
||||
|
||||
/* move the state of the channel to Terminating to end the call */
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_TERMINATING);
|
||||
/* move the state of the channel to Terminating to end the call
|
||||
in TERMINATING state, the release cause is set to REMOTE_REL
|
||||
in any means. So we don't have to set the release reason here.
|
||||
*/
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_TERMINATING);
|
||||
}
|
||||
}
|
||||
|
||||
/* unlock the channel again before we exit */
|
||||
|
@ -1269,6 +1389,8 @@ ftdm_status_t handle_pause(uint32_t suInstId, uint32_t spInstId, uint32_t circui
|
|||
int infId;
|
||||
int i;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* extract the affected infId from the circuit structure */
|
||||
infId = g_ftdm_sngss7_data.cfg.isupCkt[circuit].infId;
|
||||
|
||||
|
@ -1333,6 +1455,8 @@ ftdm_status_t handle_resume(uint32_t suInstId, uint32_t spInstId, uint32_t circu
|
|||
ftdm_channel_t *ftdmchan = NULL;
|
||||
int infId;
|
||||
int i;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* extract the affect infId from the circuit structure */
|
||||
infId = g_ftdm_sngss7_data.cfg.isupCkt[circuit].infId;
|
||||
|
@ -1397,6 +1521,8 @@ ftdm_status_t handle_cot_start(uint32_t suInstId, uint32_t spInstId, uint32_t ci
|
|||
|
||||
sngss7_chan_data_t *sngss7_info = NULL;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[circuit].type != SNG_CKT_VOICE) {
|
||||
|
@ -1452,6 +1578,8 @@ ftdm_status_t handle_cot_stop(uint32_t suInstId, uint32_t spInstId, uint32_t cir
|
|||
|
||||
sngss7_chan_data_t *sngss7_info = NULL;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[circuit].type != SNG_CKT_VOICE) {
|
||||
|
@ -1497,6 +1625,8 @@ ftdm_status_t handle_cot(uint32_t suInstId, uint32_t spInstId, uint32_t circuit,
|
|||
|
||||
sngss7_chan_data_t *sngss7_info = NULL;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[circuit].type != SNG_CKT_VOICE) {
|
||||
|
@ -1565,6 +1695,8 @@ ftdm_status_t handle_blo_req(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
sngss7_chan_data_t *sngss7_info = NULL;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[circuit].type != SNG_CKT_VOICE) {
|
||||
|
@ -1597,6 +1729,7 @@ ftdm_status_t handle_blo_req(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
/* throw the ckt block flag */
|
||||
sngss7_set_ckt_blk_flag(sngss7_info, FLAG_CKT_MN_BLOCK_RX);
|
||||
sngss7_clear_ckt_blk_flag(sngss7_info, FLAG_CKT_MN_BLOCK_RX_DN);
|
||||
|
||||
/* set the channel to suspended state */
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_SUSPENDED);
|
||||
|
@ -1615,6 +1748,8 @@ ftdm_status_t handle_blo_rsp(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
sngss7_chan_data_t *sngss7_info = NULL;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[circuit].type != SNG_CKT_VOICE) {
|
||||
|
@ -1656,6 +1791,8 @@ ftdm_status_t handle_ubl_req(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
sngss7_chan_data_t *sngss7_info = NULL;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[circuit].type != SNG_CKT_VOICE) {
|
||||
|
@ -1744,6 +1881,8 @@ ftdm_status_t handle_rsc_req(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
sngss7_chan_data_t *sngss7_info = NULL;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[circuit].type != SNG_CKT_VOICE) {
|
||||
|
@ -1784,6 +1923,7 @@ ftdm_status_t handle_rsc_req(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
default:
|
||||
|
||||
/* set the state of the channel to restart...the rest is done by the chan monitor */
|
||||
sngss7_set_ckt_flag(sngss7_info, FLAG_REMOTE_REL);
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_RESTART);
|
||||
break;
|
||||
/**************************************************************************/
|
||||
|
@ -1803,6 +1943,8 @@ ftdm_status_t handle_local_rsc_req(uint32_t suInstId, uint32_t spInstId, uint32_
|
|||
|
||||
sngss7_chan_data_t *sngss7_info = NULL;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[circuit].type != SNG_CKT_VOICE) {
|
||||
|
@ -1861,6 +2003,8 @@ ftdm_status_t handle_rsc_rsp(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
sngss7_chan_data_t *sngss7_info = NULL;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[circuit].type != SNG_CKT_VOICE) {
|
||||
|
@ -1917,7 +2061,7 @@ ftdm_status_t handle_rsc_rsp(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
sngss7_set_ckt_flag(sngss7_info, FLAG_RESET_TX_RSP);
|
||||
|
||||
/* go to DOWN */
|
||||
/*ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_DOWN);*/
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_RESTART);
|
||||
|
||||
break;
|
||||
/**********************************************************************/
|
||||
|
@ -1951,6 +2095,8 @@ ftdm_status_t handle_grs_req(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
ftdm_channel_t *ftdmchan = NULL;
|
||||
sngss7_span_data_t *sngss7_span = NULL;
|
||||
int range = 0;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[circuit].type != SNG_CKT_VOICE) {
|
||||
|
@ -2008,6 +2154,8 @@ ftdm_status_t handle_grs_rsp(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
ftdm_channel_t *ftdmchan = NULL;
|
||||
sngss7_span_data_t *sngss7_span = NULL;
|
||||
int range = 0;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[circuit].type != SNG_CKT_VOICE) {
|
||||
|
@ -2072,6 +2220,8 @@ ftdm_status_t handle_local_blk(uint32_t suInstId, uint32_t spInstId, uint32_t ci
|
|||
|
||||
sngss7_chan_data_t *sngss7_info = NULL;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[circuit].type != SNG_CKT_VOICE) {
|
||||
|
@ -2122,6 +2272,8 @@ ftdm_status_t handle_local_ubl(uint32_t suInstId, uint32_t spInstId, uint32_t ci
|
|||
|
||||
sngss7_chan_data_t *sngss7_info = NULL;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[circuit].type != SNG_CKT_VOICE) {
|
||||
|
@ -2177,6 +2329,7 @@ ftdm_status_t handle_ucic(uint32_t suInstId, uint32_t spInstId, uint32_t circuit
|
|||
sngss7_span_data_t *sngss7_span = NULL;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[circuit].type != SNG_CKT_VOICE) {
|
||||
|
@ -2215,6 +2368,8 @@ ftdm_status_t handle_ucic(uint32_t suInstId, uint32_t spInstId, uint32_t circuit
|
|||
cinfo->ucic.range = cinfo->tx_grs.range;
|
||||
ftdm_set_flag(sngss7_span, SNGSS7_UCIC_PENDING);
|
||||
|
||||
SS7_WARN("Set span SNGSS7_UCIC_PENDING for ISUP circuit = %d!\n", circuit);
|
||||
|
||||
ftdm_channel_unlock(fchan);
|
||||
|
||||
goto done;
|
||||
|
@ -2227,6 +2382,7 @@ ftdm_status_t handle_ucic(uint32_t suInstId, uint32_t spInstId, uint32_t circuit
|
|||
ftdm_mutex_lock(ftdmchan->mutex);
|
||||
|
||||
/* throw the ckt block flag */
|
||||
SS7_DEBUG("Set FLAG_CKT_UCIC_BLOCK for ISUP circuit = %d!\n", circuit);
|
||||
sngss7_set_ckt_blk_flag(sngss7_info, FLAG_CKT_UCIC_BLOCK);
|
||||
|
||||
/* set the channel to suspended state */
|
||||
|
@ -2256,7 +2412,10 @@ ftdm_status_t handle_cgb_req(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
int blockType = 0;
|
||||
int byte = 0;
|
||||
int bit = 0;
|
||||
int x;
|
||||
int x;
|
||||
int loop_range=0;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
memset(&status[0], '\0', sizeof(status));
|
||||
|
||||
|
@ -2321,61 +2480,56 @@ ftdm_status_t handle_cgb_req(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
}
|
||||
|
||||
/* loop over the cics starting from circuit until range+1 */
|
||||
for (x = circuit; x < (circuit + range + 1); x++) {
|
||||
/* confirm this is a voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[x].type != SNG_CKT_VOICE) continue;
|
||||
|
||||
/* grab the circuit in question */
|
||||
if (extract_chan_data(x, &sngss7_info, &ftdmchan)) {
|
||||
SS7_ERROR("Failed to extract channel data for circuit = %d!\n", x);
|
||||
break;
|
||||
loop_range = circuit + range + 1;
|
||||
x = circuit;
|
||||
while( x < loop_range ) {
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[x].type != SNG_CKT_VOICE) {
|
||||
loop_range++;
|
||||
}
|
||||
|
||||
/* lock the channel */
|
||||
ftdm_mutex_lock(ftdmchan->mutex);
|
||||
else {
|
||||
if (extract_chan_data(x, &sngss7_info, &ftdmchan)) {
|
||||
SS7_ERROR("Failed to extract channel data for circuit = %d!\n", x);
|
||||
} else {
|
||||
ftdm_mutex_lock(ftdmchan->mutex);
|
||||
if (status[byte] & (1 << bit)) {
|
||||
switch (blockType) {
|
||||
/**********************************************************************/
|
||||
case 0: /* maintenance oriented */
|
||||
sngss7_set_ckt_blk_flag(sngss7_info, FLAG_GRP_MN_BLOCK_RX);
|
||||
break;
|
||||
/**********************************************************************/
|
||||
case 1: /* hardware failure oriented */
|
||||
sngss7_set_ckt_blk_flag(sngss7_info, FLAG_GRP_HW_BLOCK_RX);
|
||||
break;
|
||||
/**********************************************************************/
|
||||
case 2: /* reserved for national use */
|
||||
break;
|
||||
/**********************************************************************/
|
||||
default:
|
||||
break;
|
||||
/**********************************************************************/
|
||||
}
|
||||
}
|
||||
|
||||
#if 0
|
||||
SS7_ERROR("KONRAD -> circuit=%d, byte=%d, bit=%d, status[byte]=%d, math=%d\n",
|
||||
x,
|
||||
byte,
|
||||
bit,
|
||||
status[byte],
|
||||
(status[byte] & (1 << bit)));
|
||||
#endif
|
||||
if (status[byte] & (1 << bit)) {
|
||||
switch (blockType) {
|
||||
/**********************************************************************/
|
||||
case 0: /* maintenance oriented */
|
||||
sngss7_set_ckt_blk_flag(sngss7_info, FLAG_GRP_MN_BLOCK_RX);
|
||||
break;
|
||||
/**********************************************************************/
|
||||
case 1: /* hardware failure oriented */
|
||||
sngss7_set_ckt_blk_flag(sngss7_info, FLAG_GRP_HW_BLOCK_RX);
|
||||
break;
|
||||
/**********************************************************************/
|
||||
case 2: /* reserved for national use */
|
||||
break;
|
||||
/**********************************************************************/
|
||||
default:
|
||||
break;
|
||||
/**********************************************************************/
|
||||
} /* switch (blockType) */
|
||||
/* bring the sig status down */
|
||||
sngss7_set_sig_status(sngss7_info, FTDM_SIG_STATE_DOWN);
|
||||
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_SUSPENDED);
|
||||
|
||||
/* unlock the channel again before we exit */
|
||||
ftdm_mutex_unlock(ftdmchan->mutex);
|
||||
|
||||
/* update the bit and byte counter*/
|
||||
bit ++;
|
||||
if (bit == 8) {
|
||||
byte++;
|
||||
bit = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
x++;
|
||||
}
|
||||
|
||||
/* bring the sig status down */
|
||||
sngss7_set_sig_status(sngss7_info, FTDM_SIG_STATE_DOWN);
|
||||
|
||||
/* unlock the channel again before we exit */
|
||||
ftdm_mutex_unlock(ftdmchan->mutex);
|
||||
|
||||
/* update the bit and byte counter*/
|
||||
bit ++;
|
||||
if (bit == 8) {
|
||||
byte++;
|
||||
bit = 0;
|
||||
}
|
||||
|
||||
} /* for (x = circuit; x < (circuit + range + 1); x++) */
|
||||
|
||||
/* get the ftdmchan and ss7_chan_data from the circuit */
|
||||
if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
|
||||
|
@ -2402,8 +2556,11 @@ ftdm_status_t handle_cgu_req(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
int blockType = 0;
|
||||
int byte = 0;
|
||||
int bit = 0;
|
||||
int x;
|
||||
int x;
|
||||
int loop_range=0;
|
||||
ftdm_sigmsg_t sigev;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
memset(&sigev, 0, sizeof (sigev));
|
||||
memset(&status[0], '\0', sizeof(status));
|
||||
|
@ -2470,57 +2627,62 @@ ftdm_status_t handle_cgu_req(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
}
|
||||
|
||||
/* loop over the cics starting from circuit until range+1 */
|
||||
for (x = circuit; x < (circuit + range + 1); x++) {
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[x].type != SNG_CKT_VOICE) continue;
|
||||
/* grab the circuit in question */
|
||||
if (extract_chan_data(x, &sngss7_info, &ftdmchan)) {
|
||||
SS7_ERROR("Failed to extract channel data for circuit = %d!\n", x);
|
||||
break;
|
||||
loop_range = circuit + range + 1;
|
||||
x = circuit;
|
||||
while( x < loop_range ) {
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[x].type != SNG_CKT_VOICE) {
|
||||
loop_range++;
|
||||
} else {
|
||||
if (extract_chan_data(x, &sngss7_info, &ftdmchan)) {
|
||||
SS7_ERROR("Failed to extract channel data for circuit = %d!\n", x);
|
||||
}
|
||||
else {
|
||||
ftdm_mutex_lock(ftdmchan->mutex);
|
||||
|
||||
if (status[byte] & (1 << bit)) {
|
||||
switch (blockType) {
|
||||
/**********************************************************************/
|
||||
case 0: /* maintenance oriented */
|
||||
sngss7_clear_ckt_blk_flag(sngss7_info, FLAG_GRP_MN_BLOCK_RX);
|
||||
sngss7_clear_ckt_blk_flag(sngss7_info, FLAG_CKT_MN_BLOCK_RX);
|
||||
sngss7_clear_ckt_blk_flag(sngss7_info, FLAG_CKT_MN_BLOCK_RX_DN);
|
||||
break;
|
||||
/**********************************************************************/
|
||||
case 1: /* hardware failure oriented */
|
||||
sngss7_clear_ckt_blk_flag(sngss7_info, FLAG_GRP_HW_BLOCK_RX);
|
||||
break;
|
||||
/**********************************************************************/
|
||||
case 2: /* reserved for national use */
|
||||
break;
|
||||
/**********************************************************************/
|
||||
default:
|
||||
break;
|
||||
/**********************************************************************/
|
||||
} /* switch (blockType) */
|
||||
} /* if (status[byte] & (1 << bit)) */
|
||||
|
||||
sigev.chan_id = ftdmchan->chan_id;
|
||||
sigev.span_id = ftdmchan->span_id;
|
||||
sigev.channel = ftdmchan;
|
||||
|
||||
/* bring the sig status down */
|
||||
if (sngss7_channel_status_clear(sngss7_info)) {
|
||||
sngss7_set_sig_status(sngss7_info, FTDM_SIG_STATE_UP);
|
||||
}
|
||||
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_SUSPENDED);
|
||||
ftdm_mutex_unlock(ftdmchan->mutex);
|
||||
|
||||
/* update the bit and byte counter*/
|
||||
bit ++;
|
||||
if (bit == 8) {
|
||||
byte++;
|
||||
bit = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* lock the channel */
|
||||
ftdm_mutex_lock(ftdmchan->mutex);
|
||||
|
||||
if (status[byte] & (1 << bit)) {
|
||||
switch (blockType) {
|
||||
/**********************************************************************/
|
||||
case 0: /* maintenance oriented */
|
||||
sngss7_clear_ckt_blk_flag(sngss7_info, FLAG_GRP_MN_BLOCK_RX);
|
||||
sngss7_clear_ckt_blk_flag(sngss7_info, FLAG_CKT_MN_BLOCK_RX);
|
||||
sngss7_clear_ckt_blk_flag(sngss7_info, FLAG_CKT_MN_BLOCK_RX_DN);
|
||||
break;
|
||||
/**********************************************************************/
|
||||
case 1: /* hardware failure oriented */
|
||||
sngss7_clear_ckt_blk_flag(sngss7_info, FLAG_GRP_HW_BLOCK_RX);
|
||||
break;
|
||||
/**********************************************************************/
|
||||
case 2: /* reserved for national use */
|
||||
break;
|
||||
/**********************************************************************/
|
||||
default:
|
||||
break;
|
||||
/**********************************************************************/
|
||||
} /* switch (blockType) */
|
||||
} /* if (status[byte] & (1 << bit)) */
|
||||
|
||||
sigev.chan_id = ftdmchan->chan_id;
|
||||
sigev.span_id = ftdmchan->span_id;
|
||||
sigev.channel = ftdmchan;
|
||||
|
||||
/* bring the sig status down */
|
||||
sngss7_set_sig_status(sngss7_info, FTDM_SIG_STATE_UP);
|
||||
|
||||
/* unlock the channel again before we exit */
|
||||
ftdm_mutex_unlock(ftdmchan->mutex);
|
||||
|
||||
/* update the bit and byte counter*/
|
||||
bit ++;
|
||||
if (bit == 8) {
|
||||
byte++;
|
||||
bit = 0;
|
||||
}
|
||||
|
||||
} /* for (x = circuit; x < (circuit + range + 1); x++) */
|
||||
x++;
|
||||
}
|
||||
|
||||
/* get the ftdmchan and ss7_chan_data from the circuit */
|
||||
if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
|
||||
|
@ -2541,6 +2703,8 @@ ftdm_status_t handle_olm_msg(uint32_t suInstId, uint32_t spInstId, uint32_t circ
|
|||
|
||||
sngss7_chan_data_t *sngss7_info = NULL;
|
||||
ftdm_channel_t *ftdmchan = NULL;
|
||||
|
||||
ftdm_running_return(FTDM_FAIL);
|
||||
|
||||
/* confirm that the circuit is voice channel */
|
||||
if (g_ftdm_sngss7_data.cfg.isupCkt[circuit].type != SNG_CKT_VOICE) {
|
||||
|
|
|
@ -81,6 +81,7 @@ void sngss7_con_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, SiCo
|
|||
|
||||
/* initalize the sngss7_event */
|
||||
sngss7_event = ftdm_malloc(sizeof(*sngss7_event));
|
||||
|
||||
if (sngss7_event == NULL) {
|
||||
SS7_ERROR("Failed to allocate memory for sngss7_event!\n");
|
||||
SS7_FUNC_TRACE_EXIT(__FUNCTION__);
|
||||
|
|
|
@ -114,6 +114,7 @@ void handle_sng_mtp2_alarm(Pst *pst, SdMngmt *sta)
|
|||
{
|
||||
char buf[50];
|
||||
int x = 1;
|
||||
int log_level = FTDM_LOG_LEVEL_DEBUG;
|
||||
|
||||
memset(buf, '\0', sizeof(buf));
|
||||
|
||||
|
@ -158,11 +159,22 @@ void handle_sng_mtp2_alarm(Pst *pst, SdMngmt *sta)
|
|||
break;
|
||||
case (LCM_CAUSE_UNKNOWN):
|
||||
default:
|
||||
ftdm_log(FTDM_LOG_DEBUG,"[MTP2]%s cause:%s event:%s\n",
|
||||
buf,
|
||||
DECODE_LCM_CAUSE(sta->t.usta.alarm.cause),
|
||||
DECODE_LSD_EVENT(sta->t.usta.alarm.event));
|
||||
break;
|
||||
{
|
||||
if ((LSD_EVENT_ALIGN_LOST == sta->t.usta.alarm.event) ||
|
||||
(LSD_EVENT_PROT_ST_DN == sta->t.usta.alarm.event)) {
|
||||
log_level = FTDM_LOG_LEVEL_WARNING;
|
||||
} else if ((LSD_EVENT_LINK_ALIGNED == sta->t.usta.alarm.event) ||
|
||||
(LSD_EVENT_PROT_ST_UP == sta->t.usta.alarm.event)){
|
||||
log_level = FTDM_LOG_LEVEL_INFO;
|
||||
} else {
|
||||
log_level = FTDM_LOG_LEVEL_WARNING;
|
||||
}
|
||||
ftdm_log(FTDM_PRE, log_level,"[MTP2]%s cause:%s event:%s\n",
|
||||
buf,
|
||||
DECODE_LCM_CAUSE(sta->t.usta.alarm.cause),
|
||||
DECODE_LSD_EVENT(sta->t.usta.alarm.event));
|
||||
break;
|
||||
}
|
||||
/******************************************************************/
|
||||
} /* switch (sta->t.usta.alarm.cause) */
|
||||
break;
|
||||
|
@ -184,7 +196,7 @@ void handle_sng_mtp2_alarm(Pst *pst, SdMngmt *sta)
|
|||
sprintf(buf, "[%s]", g_ftdm_sngss7_data.cfg.mtp2Link[x].name);
|
||||
}
|
||||
|
||||
ftdm_log(FTDM_LOG_ERROR,"[MTP2]%s %s : %s\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[MTP2]%s %s : %s\n",
|
||||
buf,
|
||||
DECODE_LSD_EVENT(sta->t.usta.alarm.event),
|
||||
DECODE_LSD_CAUSE(sta->t.usta.alarm.cause));
|
||||
|
@ -207,7 +219,7 @@ void handle_sng_mtp2_alarm(Pst *pst, SdMngmt *sta)
|
|||
sprintf(buf, "[%s]", g_ftdm_sngss7_data.cfg.mtp2Link[x].name);
|
||||
}
|
||||
|
||||
ftdm_log(FTDM_LOG_DEBUG,"[MTP2]%s %s : %s\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[MTP2]%s %s : %s\n",
|
||||
buf,
|
||||
DECODE_LSD_EVENT(sta->t.usta.alarm.event),
|
||||
DECODE_DISC_REASON(sta->t.usta.evntParm[1]));
|
||||
|
@ -231,7 +243,7 @@ void handle_sng_mtp2_alarm(Pst *pst, SdMngmt *sta)
|
|||
sprintf(buf, "[%s]", g_ftdm_sngss7_data.cfg.mtp2Link[x].name);
|
||||
}
|
||||
|
||||
ftdm_log(FTDM_LOG_ERROR,"[MTP2]%s %s : RTB Queue Len(%d)|Oldest BSN(%d)|Tx Queue Len(%d)|Outstanding Frames(%d)\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[MTP2]%s %s : RTB Queue Len(%d)|Oldest BSN(%d)|Tx Queue Len(%d)|Outstanding Frames(%d)\n",
|
||||
buf,
|
||||
DECODE_LSD_EVENT(sta->t.usta.alarm.event),
|
||||
sta->t.usta.evntParm[1],
|
||||
|
@ -257,7 +269,7 @@ void handle_sng_mtp2_alarm(Pst *pst, SdMngmt *sta)
|
|||
sprintf(buf, "[%s]", g_ftdm_sngss7_data.cfg.mtp2Link[x].name);
|
||||
}
|
||||
|
||||
ftdm_log(FTDM_LOG_ERROR,"[MTP2]%s %s : RTB Queue Len(%d)\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[MTP2]%s %s : RTB Queue Len(%d)\n",
|
||||
buf,
|
||||
DECODE_LSD_EVENT(sta->t.usta.alarm.event),
|
||||
sta->t.usta.evntParm[1]);
|
||||
|
@ -280,7 +292,7 @@ void handle_sng_mtp2_alarm(Pst *pst, SdMngmt *sta)
|
|||
sprintf(buf, "[%s]", g_ftdm_sngss7_data.cfg.mtp2Link[x].name);
|
||||
}
|
||||
|
||||
ftdm_log(FTDM_LOG_ERROR,"[MTP2]%s %s : %d\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[MTP2]%s %s : %d\n",
|
||||
buf,
|
||||
DECODE_LSD_EVENT(sta->t.usta.alarm.event),
|
||||
DECODE_DISC_REASON(sta->t.usta.evntParm[1]));
|
||||
|
@ -288,7 +300,7 @@ void handle_sng_mtp2_alarm(Pst *pst, SdMngmt *sta)
|
|||
/**********************************************************************/
|
||||
case (LCM_EVENT_UI_INV_EVT):
|
||||
case (LCM_EVENT_LI_INV_EVT):
|
||||
ftdm_log(FTDM_LOG_ERROR,"[MTP2] %s(%d) : %s(%d) : Primitive (%d)\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[MTP2] %s(%d) : %s(%d) : Primitive (%d)\n",
|
||||
DECODE_LSD_EVENT(sta->t.usta.alarm.event),
|
||||
sta->t.usta.alarm.event,
|
||||
DECODE_LCM_CAUSE(sta->t.usta.alarm.cause),
|
||||
|
@ -302,14 +314,14 @@ void handle_sng_mtp2_alarm(Pst *pst, SdMngmt *sta)
|
|||
/******************************************************************/
|
||||
case (LCM_CAUSE_UNKNOWN):
|
||||
case (LCM_CAUSE_SWVER_NAVAIL):
|
||||
ftdm_log(FTDM_LOG_ERROR,"[MTP2] %s : %s : Event (%d)\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[MTP2] %s : %s : Event (%d)\n",
|
||||
DECODE_LSD_EVENT(sta->t.usta.alarm.event),
|
||||
DECODE_LCM_CAUSE(sta->t.usta.alarm.cause),
|
||||
sta->t.usta.evntParm[0]);
|
||||
break;
|
||||
/******************************************************************/
|
||||
case (LCM_CAUSE_DECODE_ERR):
|
||||
ftdm_log(FTDM_LOG_ERROR,"[MTP2] %s : %s : Primitive (%d)|Version (%d)\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[MTP2] %s : %s : Primitive (%d)|Version (%d)\n",
|
||||
DECODE_LSD_EVENT(sta->t.usta.alarm.event),
|
||||
DECODE_LCM_CAUSE(sta->t.usta.alarm.cause),
|
||||
sta->t.usta.evntParm[0],
|
||||
|
@ -317,7 +329,7 @@ void handle_sng_mtp2_alarm(Pst *pst, SdMngmt *sta)
|
|||
break;
|
||||
/******************************************************************/
|
||||
default:
|
||||
ftdm_log(FTDM_LOG_ERROR,"[MTP2] %s(%d) : %s(%d)\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[MTP2] %s(%d) : %s(%d)\n",
|
||||
DECODE_LSD_EVENT(sta->t.usta.alarm.event),
|
||||
sta->t.usta.alarm.event,
|
||||
DECODE_LSD_CAUSE(sta->t.usta.alarm.cause),
|
||||
|
@ -328,7 +340,7 @@ void handle_sng_mtp2_alarm(Pst *pst, SdMngmt *sta)
|
|||
break;
|
||||
/**********************************************************************/
|
||||
default:
|
||||
ftdm_log(FTDM_LOG_ERROR,"[MTP2] %s(%d) : %s(%d)\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[MTP2] %s(%d) : %s(%d)\n",
|
||||
DECODE_LSD_EVENT(sta->t.usta.alarm.event),
|
||||
sta->t.usta.alarm.event,
|
||||
DECODE_LSD_CAUSE(sta->t.usta.alarm.cause),
|
||||
|
@ -381,7 +393,7 @@ void handle_sng_mtp3_alarm(Pst *pst, SnMngmt *sta)
|
|||
/**********************************************************************/
|
||||
case (LSN_EVENT_INV_OPC_OTHER_END):
|
||||
|
||||
ftdm_log(FTDM_LOG_ERROR,"[MTP3]%s %s : %s : OPC(0x%X%X%X%X)\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[MTP3]%s %s : %s : OPC(0x%X%X%X%X)\n",
|
||||
buf,
|
||||
DECODE_LSN_EVENT(sta->t.usta.alarm.event),
|
||||
DECODE_LSN_CAUSE(sta->t.usta.alarm.cause),
|
||||
|
@ -392,7 +404,7 @@ void handle_sng_mtp3_alarm(Pst *pst, SnMngmt *sta)
|
|||
break;
|
||||
/**********************************************************************/
|
||||
case (LSN_EVENT_INV_SLC_OTHER_END):
|
||||
ftdm_log(FTDM_LOG_ERROR,"[MTP3]%s %s : %s : SLC(%d)\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[MTP3]%s %s : %s : SLC(%d)\n",
|
||||
buf,
|
||||
DECODE_LSN_EVENT(sta->t.usta.alarm.event),
|
||||
DECODE_LSN_CAUSE(sta->t.usta.alarm.cause),
|
||||
|
@ -400,7 +412,7 @@ void handle_sng_mtp3_alarm(Pst *pst, SnMngmt *sta)
|
|||
break;
|
||||
/**********************************************************************/
|
||||
default:
|
||||
ftdm_log(FTDM_LOG_DEBUG,"[MTP3]%s %s(%d) : %s(%d)\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[MTP3]%s %s(%d) : %s(%d)\n",
|
||||
buf,
|
||||
DECODE_LSN_EVENT(sta->t.usta.alarm.event),
|
||||
sta->t.usta.alarm.event,
|
||||
|
@ -412,7 +424,7 @@ void handle_sng_mtp3_alarm(Pst *pst, SnMngmt *sta)
|
|||
break;
|
||||
/**************************************************************************/
|
||||
case (STNSAP):
|
||||
ftdm_log(FTDM_LOG_ERROR,"[MTP3][SAPID:%d] %s : %s\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[MTP3][SAPID:%d] %s : %s\n",
|
||||
sta->hdr.elmId.elmntInst1,
|
||||
DECODE_LSN_EVENT(sta->t.usta.alarm.event),
|
||||
DECODE_LSN_CAUSE(sta->t.usta.alarm.cause));
|
||||
|
@ -463,7 +475,7 @@ void handle_sng_mtp3_alarm(Pst *pst, SnMngmt *sta)
|
|||
break;
|
||||
/**********************************************************************/
|
||||
default:
|
||||
ftdm_log(FTDM_LOG_ERROR,"[MTP3][DPC:0x%X%X%X%X] %s : %s\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[MTP3][DPC:0x%X%X%X%X] %s : %s\n",
|
||||
sta->t.usta.evntParm[0],
|
||||
sta->t.usta.evntParm[1],
|
||||
sta->t.usta.evntParm[2],
|
||||
|
@ -733,7 +745,7 @@ void handle_sng_isup_alarm(Pst *pst, SiMngmt *sta)
|
|||
} /* switch (sta->t.usta.dgn.dgnVal[x].t.type) */
|
||||
} /* for (x = 0; x < 5; x++) */
|
||||
|
||||
ftdm_log(FTDM_LOG_ERROR,"%s %s : %s\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"%s %s : %s\n",
|
||||
msg,
|
||||
DECODE_LSI_EVENT(sta->t.usta.alarm.event),
|
||||
DECODE_LSI_CAUSE(sta->t.usta.alarm.cause));
|
||||
|
@ -759,7 +771,7 @@ void handle_sng_relay_alarm(Pst *pst, RyMngmt *sta)
|
|||
switch (sta->hdr.elmId.elmnt) {
|
||||
/**************************************************************************/
|
||||
case (LRY_USTA_ERR): /* ERROR */
|
||||
ftdm_log(FTDM_LOG_ERROR,"[RELAY] Error: tx procId %d: err procId %d: channel %d: seq %s: reason %s\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[RELAY] Error: tx procId %d: err procId %d: channel %d: seq %s: reason %s\n",
|
||||
sta->t.usta.s.ryErrUsta.sendPid,
|
||||
sta->t.usta.s.ryErrUsta.errPid,
|
||||
sta->t.usta.s.ryErrUsta.id,
|
||||
|
@ -783,7 +795,7 @@ void handle_sng_relay_alarm(Pst *pst, RyMngmt *sta)
|
|||
break;
|
||||
/**************************************************************************/
|
||||
case (LRY_USTA_CNG): /* Congestion */
|
||||
ftdm_log(FTDM_LOG_ERROR,"[RELAY] Congestion: tx procId %d: rem procId %d: channel %d: %s\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[RELAY] Congestion: tx procId %d: rem procId %d: channel %d: %s\n",
|
||||
sta->t.usta.s.ryCongUsta.sendPid,
|
||||
sta->t.usta.s.ryCongUsta.remPid,
|
||||
sta->t.usta.s.ryCongUsta.id,
|
||||
|
@ -791,7 +803,7 @@ void handle_sng_relay_alarm(Pst *pst, RyMngmt *sta)
|
|||
break;
|
||||
/**************************************************************************/
|
||||
case (LRY_USTA_UP): /* channel up */
|
||||
ftdm_log(FTDM_LOG_ERROR,"[RELAY] Channel UP: tx procId %d: channel %d\n",
|
||||
ftdm_log(FTDM_LOG_INFO,"[RELAY] Channel UP: tx procId %d: channel %d\n",
|
||||
sta->t.usta.s.ryUpUsta.sendPid,
|
||||
sta->t.usta.s.ryUpUsta.id);
|
||||
|
||||
|
@ -801,7 +813,7 @@ void handle_sng_relay_alarm(Pst *pst, RyMngmt *sta)
|
|||
break;
|
||||
/**************************************************************************/
|
||||
case (LRY_USTA_DN): /* channel down */
|
||||
ftdm_log(FTDM_LOG_ERROR,"[RELAY] Channel DOWN: tx procId %d: channel %d\n",
|
||||
ftdm_log(FTDM_LOG_WARNING,"[RELAY] Channel DOWN: tx procId %d: channel %d\n",
|
||||
sta->t.usta.s.ryUpUsta.sendPid,
|
||||
sta->t.usta.s.ryUpUsta.id);
|
||||
|
||||
|
@ -810,6 +822,11 @@ void handle_sng_relay_alarm(Pst *pst, RyMngmt *sta)
|
|||
|
||||
break;
|
||||
/**************************************************************************/
|
||||
case (LRY_USTA_TCP_CONN_FAILED):
|
||||
ftdm_log(FTDM_LOG_WARNING,"[RELAY] TCP connection failed \n" );
|
||||
|
||||
break;
|
||||
/**************************************************************************/
|
||||
default:
|
||||
ftdm_log(FTDM_LOG_ERROR,"Unknown Relay Alram\n");
|
||||
break;
|
||||
|
@ -819,6 +836,311 @@ void handle_sng_relay_alarm(Pst *pst, RyMngmt *sta)
|
|||
return;
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
void handle_sng_m2ua_alarm(Pst *pst, MwMgmt *sta)
|
||||
{
|
||||
/* To print the general information */
|
||||
ftdm_log(FTDM_LOG_INFO, "Recieved a status indication from M2UA layer \n\n");
|
||||
ftdm_log(FTDM_LOG_INFO," Category = %d , event = %d , cause = %d\n",
|
||||
sta->t.usta.alarm.category, sta->t.usta.alarm.event, sta->t.usta.alarm.cause);
|
||||
|
||||
|
||||
/* To print the affected element value */
|
||||
switch(sta->hdr.elmId.elmnt)
|
||||
{
|
||||
case STMWDLSAP:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," STMWDLSAP: with lnkNmb (%d) \n\n",
|
||||
sta->t.usta.s.lnkNmb);
|
||||
break;
|
||||
}
|
||||
case STMWSCTSAP:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," STMWSCTSAP: suId (%d) \n\n",
|
||||
sta->t.usta.s.suId);
|
||||
break;
|
||||
}
|
||||
case STMWPEER:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," STMWPEER: peerId (%d) \n\n",
|
||||
sta->t.usta.s.peerId);
|
||||
break;
|
||||
}
|
||||
case STMWCLUSTER:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," STMWCLUSTER: clusterId (%d) \n\n",
|
||||
sta->t.usta.s.peerId);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_ERROR, "[MW_USTA]: Invalid element \n\n");
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* To print the event specific information */
|
||||
switch(sta->t.usta.alarm.event)
|
||||
{
|
||||
case LMW_EVENT_TERM_OK:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," M2UA : LMW_EVENT_TERM_OK: Association Terminated with PeerId[%d] \n",sta->t.usta.s.peerId);
|
||||
break;
|
||||
}
|
||||
case LMW_EVENT_ENDPOPEN_OK:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," M2UA : LMW_EVENT_ENDPOPEN_OK: \n");
|
||||
break;
|
||||
}
|
||||
case LMW_EVENT_ESTABLISH_OK:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," M2UA : LMW_EVENT_ESTABLISH_OK Event raised on peerId[%d]\n",sta->t.usta.s.peerId);
|
||||
break;
|
||||
}
|
||||
case LMW_EVENT_ESTABLISH_FAIL:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," M2UA : LMW_EVENT_ESTABLISH_FAIL Event raised on peerId[%d]\n",sta->t.usta.s.peerId);
|
||||
break;
|
||||
}
|
||||
case LMW_EVENT_ASPM:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," M2UA : LMW_EVENT_ASPM Event raised with peerId (%d), aspId (%d),"
|
||||
" msgType (%d)\n\n",sta->t.usta.s.peerId,
|
||||
sta->t.usta.t.aspm.msgType);
|
||||
break;
|
||||
}
|
||||
case LMW_EVENT_CLUSTER:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," M2UA : LMW_EVENT_CLUSTER Event raised on clusterId (%d), state (%d)\n\n",
|
||||
sta->t.usta.s.clusterId, sta->t.usta.t.cluster.state);
|
||||
|
||||
break;
|
||||
}
|
||||
case LMW_EVENT_NOTIFY:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," M2UA : LMW_EVENT_NOTIFY: peerId (%d), aspId (%d), ntfy status type (%d),"
|
||||
" ntfy status id (%d)\n\n", sta->t.usta.s.peerId,
|
||||
sta->t.usta.t.ntfy.aspId, sta->t.usta.t.ntfy.stType,
|
||||
sta->t.usta.t.ntfy.stId);
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
case LMW_EVENT_M2UA_PROTO_ERROR:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_ERROR, " M2UA : LMW_EVENT_M2UA_PROTO_ERROR with errorCode (%d)\n\n",
|
||||
sta->t.usta.t.error.errCode);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
} /* handle_sng_m2ua_alarm */
|
||||
|
||||
/******************************************************************************/
|
||||
void handle_sng_nif_alarm(Pst *pst, NwMgmt *sta)
|
||||
{
|
||||
/* To print the general information */
|
||||
ftdm_log(FTDM_LOG_INFO," Recieved a status indication from NIF layer\n");
|
||||
ftdm_log(FTDM_LOG_INFO," Category = %d , event = %d , cause = %d\n", sta->t.usta.alarm.category,
|
||||
sta->t.usta.alarm.event, sta->t.usta.alarm.cause);
|
||||
|
||||
switch(sta->hdr.elmId.elmnt)
|
||||
{
|
||||
case STNWDLSAP:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," Recieved STNWDLSAP status indication for suId (%d) \n", sta->t.usta.suId);
|
||||
switch(sta->t.usta.alarm.event)
|
||||
{
|
||||
case LCM_EVENT_LI_INV_EVT:
|
||||
{
|
||||
switch(sta->t.usta.alarm.cause)
|
||||
{
|
||||
case LCM_CAUSE_INV_SAP:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_ERROR, " LCM_CAUSE_INV_SAP Alarm \n");
|
||||
break;
|
||||
}
|
||||
case LCM_CAUSE_INV_STATE:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_ERROR, " LCM_CAUSE_INV_STATE Alarm \n");
|
||||
break;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case LCM_EVENT_BND_OK:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," NIF: LCM_EVENT_BND_OK Alarm \n");
|
||||
break;
|
||||
}
|
||||
case LCM_EVENT_BND_FAIL:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," NIF: LCM_EVENT_BND_FAIL Alarm \n");
|
||||
break;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
} /* handle_sng_nif_alarm */
|
||||
|
||||
/******************************************************************************/
|
||||
void handle_sng_tucl_alarm(Pst *pst, HiMngmt *sta)
|
||||
{
|
||||
/* To print the general information */
|
||||
ftdm_log(FTDM_LOG_INFO, "Recieved a status indication from TUCL layer \n\n");
|
||||
ftdm_log(FTDM_LOG_INFO, " Category = %d , event = %d , cause = %d\n",
|
||||
sta->t.usta.alarm.category,
|
||||
sta->t.usta.alarm.event, sta->t.usta.alarm.cause);
|
||||
|
||||
switch(sta->t.usta.alarm.event)
|
||||
{
|
||||
case LCM_EVENT_INV_EVT:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," [HI_USTA]: LCM_EVENT_INV_EVT with type (%d)\n\n",
|
||||
sta->t.usta.info.type);
|
||||
break;
|
||||
}
|
||||
case LHI_EVENT_BNDREQ:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," [HI_USTA]: LHI_EVENT_BNDREQ with type (%d) spId (%d)\n\n",
|
||||
sta->t.usta.info.type, sta->t.usta.info.spId);
|
||||
break;
|
||||
}
|
||||
case LHI_EVENT_SERVOPENREQ:
|
||||
case LHI_EVENT_DATREQ:
|
||||
case LHI_EVENT_UDATREQ:
|
||||
case LHI_EVENT_CONREQ:
|
||||
case LHI_EVENT_DISCREQ:
|
||||
#if(defined(HI_TLS) && defined(HI_TCP_TLS))
|
||||
case LHI_EVENT_TLS_ESTREQ:
|
||||
#endif
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO," [HI_USTA]: partype (%d) type(%d)\n\n",
|
||||
sta->t.usta.info.inf.parType, sta->t.usta.info.type);
|
||||
break;
|
||||
}
|
||||
case LCM_EVENT_DMEM_ALLOC_FAIL:
|
||||
case LCM_EVENT_SMEM_ALLOC_FAIL:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_ERROR," [HI_USTA]: MEM_ALLOC_FAIL with region(%d) pool (%d) type(%d)\n\n",
|
||||
sta->t.usta.info.inf.mem.region, sta->t.usta.info.inf.mem.pool,
|
||||
sta->t.usta.info.type);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
} /* handle_sng_tucl_alarm */
|
||||
|
||||
/******************************************************************************/
|
||||
void handle_sng_sctp_alarm(Pst *pst, SbMgmt *sta)
|
||||
{
|
||||
ftdm_log(FTDM_LOG_INFO, "Recieved a status indication from SCTP layer \n\n");
|
||||
ftdm_log(FTDM_LOG_INFO," Category = %d , event = %d , cause = %d "
|
||||
" [SB_USTA]: sapId (%d) and swtch (%d)\n",
|
||||
sta->t.usta.alarm.category,
|
||||
sta->t.usta.alarm.event, sta->t.usta.alarm.cause,
|
||||
sta->t.usta.sapId, sta->t.usta.swtch);
|
||||
|
||||
switch(sta->t.usta.alarm.category)
|
||||
{
|
||||
case LCM_CATEGORY_INTERFACE:
|
||||
{
|
||||
switch(sta->t.usta.alarm.cause)
|
||||
{
|
||||
case LCM_CAUSE_INV_SPID:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_ERROR, "SCTP : LCM_CAUSE_INV_SPID Alarm \n");
|
||||
break;
|
||||
}
|
||||
case LCM_CAUSE_SWVER_NAVAIL:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_ERROR, "SCTP : LCM_CAUSE_SWVER_NAVAIL Alarm\n");
|
||||
break;
|
||||
}
|
||||
case LCM_CAUSE_INV_PAR_VAL:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_ERROR, "SCTP : LCM_CAUSE_INV_PAR_VAL Alarm\n");
|
||||
break;
|
||||
}
|
||||
case LCM_CAUSE_INV_SUID:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_ERROR, "SCTP : LCM_CAUSE_INV_SUID Alarm\n");
|
||||
break;
|
||||
}
|
||||
case LCM_CAUSE_INV_SAP:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_ERROR, "SCTP : LCM_CAUSE_INV_SAP Alarm\n");
|
||||
break;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
case LCM_CATEGORY_RESOURCE:
|
||||
{
|
||||
switch(sta->t.usta.alarm.cause)
|
||||
{
|
||||
case LCM_CAUSE_MEM_ALLOC_FAIL:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_ERROR, "SCTP : LCM_CAUSE_MEM_ALLOC_FAIL Alarm \n");
|
||||
break;
|
||||
}
|
||||
case LSB_CAUSE_NUM_ADDR_EXCEED:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_ERROR, "SCTP : LSB_CAUSE_NUM_ADDR_EXCEED Alarm\n");
|
||||
break;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case LCM_CATEGORY_PROTOCOL:
|
||||
{
|
||||
switch(sta->t.usta.alarm.cause)
|
||||
{
|
||||
case LSB_CAUSE_PATH_FAILURE:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_ERROR, "SCTP : LSB_CAUSE_PATH_FAILURE Alarm \n");
|
||||
break;
|
||||
}
|
||||
case LSB_CAUSE_PATH_ACTIVE:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_ERROR, "SCTP : LSB_CAUSE_PATH_ACTIVE Alarm \n");
|
||||
break;
|
||||
}
|
||||
case LSB_CAUSE_UNRSLVD_ADDR:
|
||||
{
|
||||
ftdm_log(FTDM_LOG_ERROR, "SCTP : LSB_CAUSE_UNRSLVD_ADDR Alarm \n");
|
||||
break;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
} /* handle_sng_sctp_alarm */
|
||||
/******************************************************************************/
|
||||
|
||||
|
||||
/******************************************************************************/
|
||||
/* For Emacs:
|
||||
* Local Variables:
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,136 @@
|
|||
/*
|
||||
* Copyright (c) 2012, Kapil Gupta <kgupta@sangoma.com>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
*
|
||||
* * Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
*
|
||||
* * Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
*
|
||||
* * Neither the name of the original author; nor the names of any contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
|
||||
* OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
|
||||
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
|
||||
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
||||
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
*
|
||||
* Contributors:
|
||||
*
|
||||
*/
|
||||
/******************************************************************************/
|
||||
#ifndef __FTMOD_SNG_SS7_M2UA_H__
|
||||
#define __FTMOD_SNG_SS7_M2UA_H__
|
||||
/******************************************************************************/
|
||||
#include "private/ftdm_core.h"
|
||||
|
||||
#define MAX_NAME_LEN 25
|
||||
|
||||
typedef struct sng_nif_cfg{
|
||||
char name[MAX_NAME_LEN];
|
||||
uint32_t flags;
|
||||
uint32_t id;
|
||||
uint32_t m2uaLnkNmb;
|
||||
uint32_t mtp2LnkNmb;
|
||||
}sng_nif_cfg_t;
|
||||
|
||||
typedef enum{
|
||||
SNG_M2UA_NODE_TYPE_SGP = 1, /* type SG */
|
||||
SNG_M2UA_NODE_TYPE_ASP = 2, /* type ASP */
|
||||
}sng_m2ua_node_types_e;
|
||||
|
||||
typedef struct sng_m2ua_cfg{
|
||||
char name[MAX_NAME_LEN];
|
||||
uint32_t flags;
|
||||
uint32_t id; /* ID */
|
||||
uint32_t iid; /* ID */
|
||||
uint8_t nodeType; /*Node Type SG/ASP */
|
||||
uint8_t end_point_opened; /* flag to check is end-point already opened */
|
||||
uint16_t clusterId; /* idx to m2ua_cluster profile */
|
||||
}sng_m2ua_cfg_t;
|
||||
|
||||
typedef struct sng_m2ua_peer_cfg{
|
||||
char name[MAX_NAME_LEN];
|
||||
uint32_t flags;
|
||||
uint32_t id; /* ID */
|
||||
uint8_t aspIdFlag; /* Flag used to indicate whether include the ASP ID in the ASP UP message */
|
||||
uint16_t selfAspId; /* Self ASP ID. ASP identifier for this ASP node if the aspIdFlag is TRUE. */
|
||||
uint32_t numDestAddr; /* Number of destination address defined */
|
||||
uint16_t sctpId; /* idx to sctp profile */
|
||||
uint16_t port;
|
||||
uint32_t destAddrList[SCT_MAX_NET_ADDRS+1]; /* Destination adddress list */
|
||||
uint16_t locOutStrms; /*Number of outgoing streams supported by this association*/
|
||||
int init_sctp_assoc; /* flag to tell if we need to initiate SCTP association */
|
||||
}sng_m2ua_peer_cfg_t;
|
||||
|
||||
typedef enum{
|
||||
SNG_M2UA_LOAD_SHARE_ALGO_RR = 0x1, /* Round Robin Mode*/
|
||||
SNG_M2UA_LOAD_SHARE_ALGO_LS = 0x2, /* Link Specified */
|
||||
SNG_M2UA_LOAD_SHARE_ALGO_CS = 0x3, /* Customer Specified */
|
||||
}sng_m2ua_load_share_algo_types_e;
|
||||
|
||||
|
||||
/* Possible values of Traffic mode */
|
||||
typedef enum{
|
||||
SNG_M2UA_TRF_MODE_OVERRIDE = 0x1, /* Override Mode */
|
||||
SNG_M2UA_TRF_MODE_LOADSHARE = 0x2, /* Loadshare Mode */
|
||||
SNG_M2UA_TRF_MODE_BROADCAST = 0x3, /* Broadcast Mode */
|
||||
SNG_M2UA_TRF_MODE_ANY = 0x0, /* ANY Mode */
|
||||
}sng_m2ua_traffic_mode_types_e;
|
||||
|
||||
typedef struct sng_m2ua_cluster_cfg{
|
||||
char name[MAX_NAME_LEN];
|
||||
uint32_t flags;
|
||||
uint32_t id; /* ID */
|
||||
uint32_t sct_sap_id; /* Internal - sct_sap_id */
|
||||
uint8_t trfMode; /* Traffic mode. This parameter defines the mode in which this m2ua cluster is supposed to work */
|
||||
uint8_t loadShareAlgo; /* This parameter defines the M2UA load share algorithm which is used to distribute the traffic */
|
||||
uint16_t numOfPeers; /* idx to m2ua_peer profile */
|
||||
uint16_t peerIdLst[MW_MAX_NUM_OF_PEER]; /* idx to m2ua_peer profile */
|
||||
}sng_m2ua_cluster_cfg_t;
|
||||
|
||||
typedef struct sng_m2ua_gbl_cfg{
|
||||
sng_nif_cfg_t nif[MW_MAX_NUM_OF_INTF+1];
|
||||
sng_m2ua_cfg_t m2ua[MW_MAX_NUM_OF_INTF+1];
|
||||
sng_m2ua_peer_cfg_t m2ua_peer[MW_MAX_NUM_OF_PEER+1];
|
||||
sng_m2ua_cluster_cfg_t m2ua_clus[MW_MAX_NUM_OF_CLUSTER+1];
|
||||
}sng_m2ua_gbl_cfg_t;
|
||||
|
||||
/* m2ua xml parsing APIs */
|
||||
int ftmod_ss7_parse_nif_interfaces(ftdm_conf_node_t *nif_interfaces);
|
||||
int ftmod_ss7_parse_m2ua_interfaces(ftdm_conf_node_t *m2ua_interfaces);
|
||||
int ftmod_ss7_parse_m2ua_peer_interfaces(ftdm_conf_node_t *m2ua_peer_interfaces);
|
||||
int ftmod_ss7_parse_m2ua_clust_interfaces(ftdm_conf_node_t *m2ua_clust_interfaces);
|
||||
int ftmod_ss7_parse_sctp_links(ftdm_conf_node_t *node);
|
||||
uint32_t iptoul(const char *ip);
|
||||
|
||||
int ftmod_ss7_m2ua_start(void);
|
||||
void ftmod_ss7_m2ua_free(void);
|
||||
|
||||
ftdm_status_t ftmod_ss7_m2ua_cfg(void);
|
||||
ftdm_status_t ftmod_ss7_m2ua_init(void);
|
||||
|
||||
int ftmod_sctp_ssta_req(int elemt, int id, SbMgmt* cfm);
|
||||
int ftmod_m2ua_ssta_req(int elemt, int id, MwMgmt* cfm);
|
||||
int ftmod_nif_ssta_req(int elemt, int id, NwMgmt* cfm);
|
||||
void ftmod_ss7_enable_m2ua_sg_logging(void);
|
||||
void ftmod_ss7_disable_m2ua_sg_logging(void);
|
||||
|
||||
|
||||
#endif /*__FTMOD_SNG_SS7_M2UA_H__*/
|
|
@ -0,0 +1,690 @@
|
|||
/*
|
||||
* Copyright (c) 2012, Kapil Gupta <kgupta@sangoma.com>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
*
|
||||
* * Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
*
|
||||
* * Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
*
|
||||
* * Neither the name of the original author; nor the names of any contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
|
||||
* OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
|
||||
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
|
||||
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
||||
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
*
|
||||
* Contributors:
|
||||
*
|
||||
*
|
||||
*/
|
||||
|
||||
/* INCLUDE ********************************************************************/
|
||||
#include "ftmod_sangoma_ss7_main.h"
|
||||
/******************************************************************************/
|
||||
|
||||
/* DEFINES ********************************************************************/
|
||||
/******************************************************************************/
|
||||
|
||||
static int ftmod_ss7_parse_nif_interface(ftdm_conf_node_t *nif_interface);
|
||||
static int ftmod_ss7_parse_m2ua_interface(ftdm_conf_node_t *m2ua_interface);
|
||||
static int ftmod_ss7_parse_m2ua_peer_interface(ftdm_conf_node_t *m2ua_peer_interface);
|
||||
static int ftmod_ss7_parse_m2ua_clust_interface(ftdm_conf_node_t *m2ua_clust_interface);
|
||||
static int ftmod_ss7_fill_in_nif_interface(sng_nif_cfg_t *nif_iface);
|
||||
static int ftmod_ss7_fill_in_m2ua_interface(sng_m2ua_cfg_t *m2ua_iface);
|
||||
static int ftmod_ss7_fill_in_m2ua_peer_interface(sng_m2ua_peer_cfg_t *m2ua_peer_face);
|
||||
static int ftmod_ss7_fill_in_m2ua_clust_interface(sng_m2ua_cluster_cfg_t *m2ua_cluster_face);
|
||||
|
||||
static int ftmod_ss7_parse_sctp_link(ftdm_conf_node_t *node);
|
||||
|
||||
/******************************************************************************/
|
||||
int ftmod_ss7_parse_nif_interfaces(ftdm_conf_node_t *nif_interfaces)
|
||||
{
|
||||
ftdm_conf_node_t *nif_interface = NULL;
|
||||
|
||||
/* confirm that we are looking at sng_nif_interfaces */
|
||||
if (strcasecmp(nif_interfaces->name, "sng_nif_interfaces")) {
|
||||
SS7_ERROR("We're looking at \"%s\"...but we're supposed to be looking at \"sng_nif_interfaces\"!\n",nif_interfaces->name);
|
||||
return FTDM_FAIL;
|
||||
} else {
|
||||
SS7_DEBUG("Parsing \"nif_interfaces\"...\n");
|
||||
}
|
||||
|
||||
/* extract the isup_interfaces */
|
||||
nif_interface = nif_interfaces->child;
|
||||
|
||||
while (nif_interface != NULL) {
|
||||
/* parse the found mtp_route */
|
||||
if (ftmod_ss7_parse_nif_interface(nif_interface)) {
|
||||
SS7_ERROR("Failed to parse \"nif_interface\"\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
/* go to the next nif_interface */
|
||||
nif_interface = nif_interface->next;
|
||||
}
|
||||
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
static int ftmod_ss7_parse_nif_interface(ftdm_conf_node_t *nif_interface)
|
||||
{
|
||||
sng_nif_cfg_t sng_nif;
|
||||
ftdm_conf_parameter_t *parm = nif_interface->parameters;
|
||||
int num_parms = nif_interface->n_parameters;
|
||||
int i;
|
||||
|
||||
/* initalize the nif intf and isap structure */
|
||||
memset(&sng_nif, 0x0, sizeof(sng_nif));
|
||||
|
||||
if(!nif_interface){
|
||||
SS7_ERROR("ftmod_ss7_parse_nif_interface: Null XML Node pointer \n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
/* confirm that we are looking at an nif_interface */
|
||||
if (strcasecmp(nif_interface->name, "sng_nif_interface")) {
|
||||
SS7_ERROR("We're looking at \"%s\"...but we're supposed to be looking at \"nif_interface\"!\n",nif_interface->name);
|
||||
return FTDM_FAIL;
|
||||
} else {
|
||||
SS7_DEBUG("Parsing \"nif_interface\"...\n");
|
||||
}
|
||||
|
||||
|
||||
for (i = 0; i < num_parms; i++) {
|
||||
/**************************************************************************/
|
||||
|
||||
/* try to match the parameter to what we expect */
|
||||
if (!strcasecmp(parm->var, "name")) {
|
||||
/**********************************************************************/
|
||||
strcpy((char *)sng_nif.name, parm->val);
|
||||
SS7_DEBUG("Found an nif_interface named = %s\n", sng_nif.name);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "id")) {
|
||||
/**********************************************************************/
|
||||
sng_nif.id = atoi(parm->val);
|
||||
SS7_DEBUG("Found an nif id = %d\n", sng_nif.id);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "m2ua-interface-id")) {
|
||||
/**********************************************************************/
|
||||
sng_nif.m2uaLnkNmb = atoi(parm->val);
|
||||
SS7_DEBUG("Found an nif m2ua-interface-id = %d\n", sng_nif.m2uaLnkNmb);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "mtp2-interface-id")) {
|
||||
/**********************************************************************/
|
||||
sng_nif.mtp2LnkNmb=atoi(parm->val);
|
||||
|
||||
SS7_DEBUG("Found an nif mtp2-interface-id = %d\n", sng_nif.mtp2LnkNmb);
|
||||
/**********************************************************************/
|
||||
} else {
|
||||
/**********************************************************************/
|
||||
SS7_ERROR("Found an invalid parameter %s!\n", parm->var);
|
||||
return FTDM_FAIL;
|
||||
/**********************************************************************/
|
||||
}
|
||||
|
||||
/* move to the next parameter */
|
||||
parm = parm + 1;
|
||||
/**************************************************************************/
|
||||
} /* for (i = 0; i < num_parms; i++) */
|
||||
|
||||
/* fill in the nif interface */
|
||||
ftmod_ss7_fill_in_nif_interface(&sng_nif);
|
||||
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
/******************************************************************************/
|
||||
static int ftmod_ss7_fill_in_nif_interface(sng_nif_cfg_t *nif_iface)
|
||||
{
|
||||
int i = nif_iface->id;
|
||||
|
||||
strncpy((char *)g_ftdm_sngss7_data.cfg.g_m2ua_cfg.nif[i].name, (char *)nif_iface->name, MAX_NAME_LEN-1);
|
||||
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.nif[i].id = nif_iface->id;
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.nif[i].m2uaLnkNmb = nif_iface->m2uaLnkNmb;
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.nif[i].mtp2LnkNmb = nif_iface->mtp2LnkNmb;
|
||||
|
||||
sngss7_set_flag(&g_ftdm_sngss7_data.cfg, SNGSS7_NIF_PRESENT);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
int ftmod_ss7_parse_m2ua_interfaces(ftdm_conf_node_t *m2ua_interfaces)
|
||||
{
|
||||
ftdm_conf_node_t *m2ua_interface = NULL;
|
||||
|
||||
/* confirm that we are looking at sng_m2ua_interfaces */
|
||||
if (strcasecmp(m2ua_interfaces->name, "sng_m2ua_interfaces")) {
|
||||
SS7_ERROR("We're looking at \"%s\"...but we're supposed to be looking at \"m2ua_nif_interfaces\"!\n",m2ua_interfaces->name);
|
||||
return FTDM_FAIL;
|
||||
} else {
|
||||
SS7_DEBUG("Parsing \"m2ua_interfaces\"...\n");
|
||||
}
|
||||
|
||||
/* extract the isup_interfaces */
|
||||
m2ua_interface = m2ua_interfaces->child;
|
||||
|
||||
while (m2ua_interface != NULL) {
|
||||
/* parse the found mtp_route */
|
||||
if (ftmod_ss7_parse_m2ua_interface(m2ua_interface)) {
|
||||
SS7_ERROR("Failed to parse \"m2ua_interface\"\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
/* go to the next m2ua_interface */
|
||||
m2ua_interface = m2ua_interface->next;
|
||||
}
|
||||
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
static int ftmod_ss7_parse_m2ua_interface(ftdm_conf_node_t *m2ua_interface)
|
||||
{
|
||||
sng_m2ua_cfg_t sng_m2ua;
|
||||
ftdm_conf_parameter_t *parm = m2ua_interface->parameters;
|
||||
int num_parms = m2ua_interface->n_parameters;
|
||||
int i;
|
||||
|
||||
/* initalize the m2ua intf */
|
||||
memset(&sng_m2ua, 0x0, sizeof(sng_m2ua));
|
||||
|
||||
if(!m2ua_interface){
|
||||
SS7_ERROR("ftmod_ss7_parse_m2ua_interface: Null XML Node pointer \n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
/* confirm that we are looking at an nif_interface */
|
||||
if (strcasecmp(m2ua_interface->name, "sng_m2ua_interface")) {
|
||||
SS7_ERROR("We're looking at \"%s\"...but we're supposed to be looking at \"m2ua_interface\"!\n",m2ua_interface->name);
|
||||
return FTDM_FAIL;
|
||||
} else {
|
||||
SS7_DEBUG("Parsing \"m2ua_interface\"...\n");
|
||||
}
|
||||
|
||||
|
||||
for (i = 0; i < num_parms; i++) {
|
||||
/**************************************************************************/
|
||||
|
||||
/* try to match the parameter to what we expect */
|
||||
if (!strcasecmp(parm->var, "name")) {
|
||||
/**********************************************************************/
|
||||
strcpy((char *)sng_m2ua.name, parm->val);
|
||||
SS7_DEBUG("Found an m2ua_interface named = %s\n", sng_m2ua.name);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "id")) {
|
||||
/**********************************************************************/
|
||||
sng_m2ua.id = atoi(parm->val);
|
||||
SS7_DEBUG("Found an m2ua id = %d\n", sng_m2ua.id);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "m2ua-cluster-interface-id")) {
|
||||
/**********************************************************************/
|
||||
sng_m2ua.clusterId=atoi(parm->val);
|
||||
|
||||
SS7_DEBUG("Found an m2ua cluster_id = %d\n", sng_m2ua.clusterId);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "interface-identifier")) {
|
||||
/**********************************************************************/
|
||||
sng_m2ua.iid=atoi(parm->val);
|
||||
|
||||
SS7_DEBUG("Found an m2ua interface-identifier = %d\n", sng_m2ua.iid);
|
||||
/**********************************************************************/
|
||||
} else {
|
||||
/**********************************************************************/
|
||||
SS7_ERROR("Found an invalid parameter %s!\n", parm->var);
|
||||
return FTDM_FAIL;
|
||||
/**********************************************************************/
|
||||
}
|
||||
|
||||
/* move to the next parameter */
|
||||
parm = parm + 1;
|
||||
/**************************************************************************/
|
||||
} /* for (i = 0; i < num_parms; i++) */
|
||||
|
||||
sng_m2ua.nodeType = SNG_M2UA_NODE_TYPE_SGP;
|
||||
|
||||
/* fill in the nif interface */
|
||||
ftmod_ss7_fill_in_m2ua_interface(&sng_m2ua);
|
||||
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
/******************************************************************************/
|
||||
static int ftmod_ss7_fill_in_m2ua_interface(sng_m2ua_cfg_t *m2ua_iface)
|
||||
{
|
||||
int i = m2ua_iface->id;
|
||||
|
||||
strncpy((char *)g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua[i].name, (char *)m2ua_iface->name, MAX_NAME_LEN-1);
|
||||
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua[i].id = m2ua_iface->id;
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua[i].nodeType = m2ua_iface->nodeType;
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua[i].clusterId = m2ua_iface->clusterId;
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua[i].iid = m2ua_iface->iid;
|
||||
sngss7_set_flag(&g_ftdm_sngss7_data.cfg, SNGSS7_M2UA_PRESENT);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
int ftmod_ss7_parse_m2ua_peer_interfaces(ftdm_conf_node_t *m2ua_peer_interfaces)
|
||||
{
|
||||
ftdm_conf_node_t *m2ua_peer_interface = NULL;
|
||||
|
||||
/* confirm that we are looking at m2ua_peer_interfaces */
|
||||
if (strcasecmp(m2ua_peer_interfaces->name, "sng_m2ua_peer_interfaces")) {
|
||||
SS7_ERROR("We're looking at \"%s\"...but we're supposed to be looking at \"m2ua_peer_interfaces\"!\n",m2ua_peer_interfaces->name);
|
||||
return FTDM_FAIL;
|
||||
} else {
|
||||
SS7_DEBUG("Parsing \"m2ua_peer_interfaces\"...\n");
|
||||
}
|
||||
|
||||
/* extract the m2ua_peer_interfaces */
|
||||
m2ua_peer_interface = m2ua_peer_interfaces->child;
|
||||
|
||||
while (m2ua_peer_interface != NULL) {
|
||||
/* parse the found mtp_route */
|
||||
if (ftmod_ss7_parse_m2ua_peer_interface(m2ua_peer_interface)) {
|
||||
SS7_ERROR("Failed to parse \"m2ua_peer_interface\"\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
/* go to the next m2ua_peer_interface */
|
||||
m2ua_peer_interface = m2ua_peer_interface->next;
|
||||
}
|
||||
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
static int ftmod_ss7_parse_m2ua_peer_interface(ftdm_conf_node_t *m2ua_peer_interface)
|
||||
{
|
||||
sng_m2ua_peer_cfg_t sng_m2ua_peer;
|
||||
ftdm_conf_parameter_t *parm = m2ua_peer_interface->parameters;
|
||||
int num_parms = m2ua_peer_interface->n_parameters;
|
||||
int i;
|
||||
|
||||
/* initalize the m2ua intf */
|
||||
memset(&sng_m2ua_peer, 0x0, sizeof(sng_m2ua_peer));
|
||||
|
||||
if(!m2ua_peer_interface){
|
||||
SS7_ERROR("ftmod_ss7_parse_m2ua_peer_interface: Null XML Node pointer \n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
/* confirm that we are looking at an m2ua_peer_interface */
|
||||
if (strcasecmp(m2ua_peer_interface->name, "sng_m2ua_peer_interface")) {
|
||||
SS7_ERROR("We're looking at \"%s\"...but we're supposed to be looking at \"m2ua_peer_interface\"!\n",m2ua_peer_interface->name);
|
||||
return FTDM_FAIL;
|
||||
} else {
|
||||
SS7_DEBUG("Parsing \"m2ua_peer_interface\"...\n");
|
||||
}
|
||||
|
||||
for (i = 0; i < num_parms; i++) {
|
||||
/**************************************************************************/
|
||||
|
||||
/* try to match the parameter to what we expect */
|
||||
if (!strcasecmp(parm->var, "name")) {
|
||||
/**********************************************************************/
|
||||
strcpy((char *)sng_m2ua_peer.name, parm->val);
|
||||
SS7_DEBUG("Found an sng_m2ua_peer named = %s\n", sng_m2ua_peer.name);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "id")) {
|
||||
/**********************************************************************/
|
||||
sng_m2ua_peer.id = atoi(parm->val);
|
||||
SS7_DEBUG("Found an sng_m2ua_peer id = %d\n", sng_m2ua_peer.id);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "include-asp-identifier")) {
|
||||
/**********************************************************************/
|
||||
if(!strcasecmp(parm->val, "TRUE")){
|
||||
sng_m2ua_peer.aspIdFlag = 0x01;
|
||||
} else if(!strcasecmp(parm->val, "FALSE")){
|
||||
sng_m2ua_peer.aspIdFlag = 0x00;
|
||||
} else {
|
||||
SS7_ERROR("Found an invalid aspIdFlag Parameter Value[%s]\n", parm->val);
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
SS7_DEBUG("Found an sng_m2ua_peer aspIdFlag = %d\n", sng_m2ua_peer.aspIdFlag);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "asp-identifier")) {
|
||||
/**********************************************************************/
|
||||
sng_m2ua_peer.selfAspId=atoi(parm->val);
|
||||
|
||||
SS7_DEBUG("Found an sng_m2ua_peer self_asp_id = %d\n", sng_m2ua_peer.selfAspId);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "sctp-interface-id")) {
|
||||
/**********************************************************************/
|
||||
sng_m2ua_peer.sctpId = atoi(parm->val);
|
||||
|
||||
SS7_DEBUG("Found an sng_m2ua_peer sctp_id = %d\n", sng_m2ua_peer.sctpId);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "destination-port")) {
|
||||
/**********************************************************************/
|
||||
sng_m2ua_peer.port = atoi(parm->val);
|
||||
|
||||
SS7_DEBUG("Found an sng_m2ua_peer port = %d\n", sng_m2ua_peer.port);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "address")) {
|
||||
/**********************************************************************/
|
||||
if (sng_m2ua_peer.numDestAddr < SCT_MAX_NET_ADDRS) {
|
||||
sng_m2ua_peer.destAddrList[sng_m2ua_peer.numDestAddr] = iptoul (parm->val);
|
||||
sng_m2ua_peer.numDestAddr++;
|
||||
SS7_DEBUG("sng_m2ua_peer - Parsing with dest IP Address = %s \n", parm->val);
|
||||
} else {
|
||||
SS7_ERROR("sng_m2ua_peer - too many dest address configured. dropping %s \n", parm->val);
|
||||
}
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "number-of-outgoing-streams")) {
|
||||
/**********************************************************************/
|
||||
sng_m2ua_peer.locOutStrms=atoi(parm->val);
|
||||
|
||||
SS7_DEBUG("Found an sng_m2ua_peer number-of-outgoing-streams = %d\n", sng_m2ua_peer.locOutStrms);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "init-sctp-association")) {
|
||||
/**********************************************************************/
|
||||
if(!strcasecmp(parm->val, "TRUE")){
|
||||
sng_m2ua_peer.init_sctp_assoc = 0x01;
|
||||
} else if(!strcasecmp(parm->val, "FALSE")){
|
||||
sng_m2ua_peer.init_sctp_assoc = 0x00;
|
||||
} else {
|
||||
SS7_ERROR("Found an invalid init_sctp_assoc Parameter Value[%s]\n", parm->val);
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
SS7_DEBUG("Found an sng_m2ua_peer init_sctp_assoc = %d\n", sng_m2ua_peer.init_sctp_assoc);
|
||||
/**********************************************************************/
|
||||
} else {
|
||||
/**********************************************************************/
|
||||
SS7_ERROR("Found an invalid parameter %s!\n", parm->var);
|
||||
return FTDM_FAIL;
|
||||
/**********************************************************************/
|
||||
}
|
||||
|
||||
/* move to the next parameter */
|
||||
parm = parm + 1;
|
||||
/**************************************************************************/
|
||||
} /* for (i = 0; i < num_parms; i++) */
|
||||
|
||||
/* fill in the sng_m2ua_peer interface */
|
||||
ftmod_ss7_fill_in_m2ua_peer_interface(&sng_m2ua_peer);
|
||||
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
/******************************************************************************/
|
||||
static int ftmod_ss7_fill_in_m2ua_peer_interface(sng_m2ua_peer_cfg_t *m2ua_peer_iface)
|
||||
{
|
||||
int k = 0x00;
|
||||
int i = m2ua_peer_iface->id;
|
||||
|
||||
strncpy((char *)g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua_peer[i].name, (char *)m2ua_peer_iface->name, MAX_NAME_LEN-1);
|
||||
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua_peer[i].id = m2ua_peer_iface->id;
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua_peer[i].aspIdFlag = m2ua_peer_iface->aspIdFlag;
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua_peer[i].selfAspId = m2ua_peer_iface->selfAspId;
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua_peer[i].locOutStrms = m2ua_peer_iface->locOutStrms;
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua_peer[i].numDestAddr = m2ua_peer_iface->numDestAddr;
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua_peer[i].sctpId = m2ua_peer_iface->sctpId;
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua_peer[i].port = m2ua_peer_iface->port;
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua_peer[i].init_sctp_assoc = m2ua_peer_iface->init_sctp_assoc;
|
||||
for (k=0; k<m2ua_peer_iface->numDestAddr; k++) {
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua_peer[i].destAddrList[k] = m2ua_peer_iface->destAddrList[k];
|
||||
}
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
int ftmod_ss7_parse_m2ua_clust_interfaces(ftdm_conf_node_t *m2ua_cluster_interfaces)
|
||||
{
|
||||
ftdm_conf_node_t *m2ua_cluster_interface = NULL;
|
||||
|
||||
/* confirm that we are looking at m2ua_cluster_interfaces */
|
||||
if (strcasecmp(m2ua_cluster_interfaces->name, "sng_m2ua_cluster_interfaces")) {
|
||||
SS7_ERROR("We're looking at \"%s\"...but we're supposed to be looking at \"m2ua_cluster_interfaces\"!\n",m2ua_cluster_interfaces->name);
|
||||
return FTDM_FAIL;
|
||||
} else {
|
||||
SS7_DEBUG("Parsing \"m2ua_cluster_interfaces\"...\n");
|
||||
}
|
||||
|
||||
/* extract the m2ua_cluster_interfaces */
|
||||
m2ua_cluster_interface = m2ua_cluster_interfaces->child;
|
||||
|
||||
while (m2ua_cluster_interface != NULL) {
|
||||
/* parse the found m2ua_cluster_interface */
|
||||
if (ftmod_ss7_parse_m2ua_clust_interface(m2ua_cluster_interface)) {
|
||||
SS7_ERROR("Failed to parse \"m2ua_cluster_interface\"\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
/* go to the next m2ua_cluster_interface */
|
||||
m2ua_cluster_interface = m2ua_cluster_interface->next;
|
||||
}
|
||||
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
static int ftmod_ss7_parse_m2ua_clust_interface(ftdm_conf_node_t *m2ua_cluster_interface)
|
||||
{
|
||||
sng_m2ua_cluster_cfg_t sng_m2ua_cluster;
|
||||
ftdm_conf_parameter_t *parm = m2ua_cluster_interface->parameters;
|
||||
int num_parms = m2ua_cluster_interface->n_parameters;
|
||||
int i;
|
||||
|
||||
/* initalize the m2ua_cluster_interface */
|
||||
memset(&sng_m2ua_cluster, 0x0, sizeof(sng_m2ua_cluster));
|
||||
|
||||
if (!m2ua_cluster_interface){
|
||||
SS7_ERROR("ftmod_ss7_parse_m2ua_clust_interface - NULL XML Node pointer \n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
/* confirm that we are looking at an m2ua_cluster_interface */
|
||||
if (strcasecmp(m2ua_cluster_interface->name, "sng_m2ua_cluster_interface")) {
|
||||
SS7_ERROR("We're looking at \"%s\"...but we're supposed to be looking at \"m2ua_cluster_interface\"!\n",m2ua_cluster_interface->name);
|
||||
return FTDM_FAIL;
|
||||
} else {
|
||||
SS7_DEBUG("Parsing \"m2ua_cluster_interface\"...\n");
|
||||
}
|
||||
|
||||
|
||||
for (i = 0; i < num_parms; i++) {
|
||||
/**************************************************************************/
|
||||
|
||||
/* try to match the parameter to what we expect */
|
||||
if (!strcasecmp(parm->var, "name")) {
|
||||
/**********************************************************************/
|
||||
strcpy((char *)sng_m2ua_cluster.name, parm->val);
|
||||
SS7_DEBUG("Found an sng_m2ua_cluster named = %s\n", sng_m2ua_cluster.name);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "id")) {
|
||||
/**********************************************************************/
|
||||
sng_m2ua_cluster.id = atoi(parm->val);
|
||||
SS7_DEBUG("Found an sng_m2ua_cluster id = %d\n", sng_m2ua_cluster.id);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "traffic-mode")) {
|
||||
/**********************************************************************/
|
||||
if(!strcasecmp(parm->val, "loadshare")){
|
||||
sng_m2ua_cluster.trfMode = SNG_M2UA_TRF_MODE_LOADSHARE;
|
||||
} else if(!strcasecmp(parm->val, "override")){
|
||||
sng_m2ua_cluster.trfMode = SNG_M2UA_TRF_MODE_OVERRIDE;
|
||||
} else if(!strcasecmp(parm->val, "broadcast")){
|
||||
sng_m2ua_cluster.trfMode = SNG_M2UA_TRF_MODE_BROADCAST;
|
||||
} else {
|
||||
SS7_ERROR("Found an invalid trfMode Parameter Value[%s]..adding default one[ANY]\n", parm->val);
|
||||
sng_m2ua_cluster.trfMode = SNG_M2UA_TRF_MODE_ANY;
|
||||
}
|
||||
SS7_DEBUG("Found an sng_m2ua_cluster.trfMode = %d\n", sng_m2ua_cluster.trfMode);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "load-share-algorithm")) {
|
||||
/**********************************************************************/
|
||||
if(!strcasecmp(parm->val, "roundrobin")){
|
||||
sng_m2ua_cluster.loadShareAlgo = SNG_M2UA_LOAD_SHARE_ALGO_RR;
|
||||
} else if(!strcasecmp(parm->val, "linkspecified")){
|
||||
sng_m2ua_cluster.loadShareAlgo = SNG_M2UA_LOAD_SHARE_ALGO_LS;
|
||||
} else if(!strcasecmp(parm->val, "customerspecified")){
|
||||
sng_m2ua_cluster.loadShareAlgo = SNG_M2UA_LOAD_SHARE_ALGO_CS;
|
||||
} else {
|
||||
SS7_ERROR("Found an invalid loadShareAlgo Parameter Value[%s]\n", parm->val);
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
SS7_DEBUG("Found an sng_m2ua_cluster.loadShareAlgo = %d\n", sng_m2ua_cluster.loadShareAlgo);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "m2ua-peer-interface-id")) {
|
||||
/**********************************************************************/
|
||||
if(sng_m2ua_cluster.numOfPeers < MW_MAX_NUM_OF_PEER) {
|
||||
sng_m2ua_cluster.peerIdLst[sng_m2ua_cluster.numOfPeers] = atoi(parm->val);
|
||||
SS7_DEBUG("Found an sng_m2ua_cluster peerId[%d], Total numOfPeers[%d] \n",
|
||||
sng_m2ua_cluster.peerIdLst[sng_m2ua_cluster.numOfPeers],
|
||||
sng_m2ua_cluster.numOfPeers+1);
|
||||
sng_m2ua_cluster.numOfPeers++;
|
||||
}else{
|
||||
SS7_ERROR("Peer List excedding max[%d] limit \n", MW_MAX_NUM_OF_PEER);
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
/**********************************************************************/
|
||||
} else {
|
||||
/**********************************************************************/
|
||||
SS7_ERROR("Found an invalid parameter %s!\n", parm->var);
|
||||
return FTDM_FAIL;
|
||||
/**********************************************************************/
|
||||
}
|
||||
|
||||
/* move to the next parameter */
|
||||
parm = parm + 1;
|
||||
/**************************************************************************/
|
||||
} /* for (i = 0; i < num_parms; i++) */
|
||||
|
||||
/* fill in the sng_m2ua_peer interface */
|
||||
ftmod_ss7_fill_in_m2ua_clust_interface(&sng_m2ua_cluster);
|
||||
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
/******************************************************************************/
|
||||
static int ftmod_ss7_fill_in_m2ua_clust_interface(sng_m2ua_cluster_cfg_t *m2ua_cluster_iface)
|
||||
{
|
||||
int k = 0x00;
|
||||
int i = m2ua_cluster_iface->id;
|
||||
|
||||
strncpy((char *)g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua_clus[i].name, (char *)m2ua_cluster_iface->name, MAX_NAME_LEN-1);
|
||||
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua_clus[i].id = m2ua_cluster_iface->id;
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua_clus[i].trfMode = m2ua_cluster_iface->trfMode;
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua_clus[i].loadShareAlgo = m2ua_cluster_iface->loadShareAlgo;
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua_clus[i].numOfPeers = m2ua_cluster_iface->numOfPeers;
|
||||
for(k=0;k<m2ua_cluster_iface->numOfPeers;k++){
|
||||
g_ftdm_sngss7_data.cfg.g_m2ua_cfg.m2ua_clus[i].peerIdLst[k] = m2ua_cluster_iface->peerIdLst[k];
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
int ftmod_ss7_parse_sctp_links(ftdm_conf_node_t *node)
|
||||
{
|
||||
ftdm_conf_node_t *node_sctp_link = NULL;
|
||||
|
||||
if (!node)
|
||||
return FTDM_FAIL;
|
||||
|
||||
if (strcasecmp(node->name, "sng_sctp_interfaces")) {
|
||||
SS7_ERROR("SCTP - We're looking at <%s>...but we're supposed to be looking at <sng_sctp_interfaces>!\n", node->name);
|
||||
return FTDM_FAIL;
|
||||
} else {
|
||||
SS7_DEBUG("SCTP - Parsing <sng_sctp_interface> configurations\n");
|
||||
}
|
||||
|
||||
for (node_sctp_link = node->child; node_sctp_link != NULL; node_sctp_link = node_sctp_link->next) {
|
||||
if (ftmod_ss7_parse_sctp_link(node_sctp_link) != FTDM_SUCCESS) {
|
||||
SS7_ERROR("SCTP - Failed to parse <node_sctp_link>. \n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
}
|
||||
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
static int ftmod_ss7_parse_sctp_link(ftdm_conf_node_t *node)
|
||||
{
|
||||
ftdm_conf_parameter_t *param = NULL;
|
||||
int num_params = 0;
|
||||
int i=0;
|
||||
|
||||
if (!node){
|
||||
SS7_ERROR("SCTP - NULL XML Node pointer \n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
param = node->parameters;
|
||||
num_params = node->n_parameters;
|
||||
|
||||
sng_sctp_link_t t_link;
|
||||
memset (&t_link, 0, sizeof(sng_sctp_link_t));
|
||||
|
||||
if (strcasecmp(node->name, "sng_sctp_interface")) {
|
||||
SS7_ERROR("SCTP - We're looking at <%s>...but we're supposed to be looking at <sng_sctp_interface>!\n", node->name);
|
||||
return FTDM_FAIL;
|
||||
} else {
|
||||
SS7_DEBUG("SCTP - Parsing <sng_sctp_interface> configurations\n");
|
||||
}
|
||||
|
||||
for (i=0; i<num_params; i++, param++) {
|
||||
if (!strcasecmp(param->var, "name")) {
|
||||
int n_strlen = strlen(param->val);
|
||||
strncpy((char*)t_link.name, param->val, (n_strlen>MAX_NAME_LEN)?MAX_NAME_LEN:n_strlen);
|
||||
SS7_DEBUG("SCTP - Parsing <sng_sctp_interface> with name = %s\n", param->val);
|
||||
}
|
||||
else if (!strcasecmp(param->var, "id")) {
|
||||
t_link.id = atoi(param->val);
|
||||
SS7_DEBUG("SCTP - Parsing <sng_sctp_interface> with id = %s\n", param->val);
|
||||
}
|
||||
else if (!strcasecmp(param->var, "address")) {
|
||||
if (t_link.numSrcAddr < SCT_MAX_NET_ADDRS) {
|
||||
t_link.srcAddrList[t_link.numSrcAddr+1] = iptoul (param->val);
|
||||
t_link.numSrcAddr++;
|
||||
SS7_DEBUG("SCTP - Parsing <sng_sctp_interface> with source IP Address = %s\n", param->val);
|
||||
} else {
|
||||
SS7_ERROR("SCTP - too many source address configured. dropping %s \n", param->val);
|
||||
}
|
||||
} else if (!strcasecmp(param->var, "source-port")) {
|
||||
t_link.port = atoi(param->val);
|
||||
SS7_DEBUG("SCTP - Parsing <sng_sctp_interface> with port = %s\n", param->val);
|
||||
}
|
||||
else {
|
||||
SS7_ERROR("SCTP - Found an unknown parameter <%s>. Skipping it.\n", param->var);
|
||||
}
|
||||
}
|
||||
|
||||
g_ftdm_sngss7_data.cfg.sctpCfg.linkCfg[t_link.id].id = t_link.id;
|
||||
g_ftdm_sngss7_data.cfg.sctpCfg.linkCfg[t_link.id].port = t_link.port;
|
||||
strncpy((char*)g_ftdm_sngss7_data.cfg.sctpCfg.linkCfg[t_link.id].name, t_link.name, strlen(t_link.name) );
|
||||
g_ftdm_sngss7_data.cfg.sctpCfg.linkCfg[t_link.id].numSrcAddr = t_link.numSrcAddr;
|
||||
for (i=1; i<=t_link.numSrcAddr; i++) {
|
||||
g_ftdm_sngss7_data.cfg.sctpCfg.linkCfg[t_link.id].srcAddrList[i] = t_link.srcAddrList[i];
|
||||
}
|
||||
|
||||
sngss7_set_flag(&g_ftdm_sngss7_data.cfg, SNGSS7_SCTP_PRESENT);
|
||||
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
/******************************************************************************/
|
File diff suppressed because it is too large
Load Diff
|
@ -29,6 +29,12 @@
|
|||
* 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:
|
||||
*
|
||||
* James Zhang <jzhang@sangoma.com>
|
||||
*
|
||||
*/
|
||||
/******************************************************************************/
|
||||
#ifndef __FTMOD_SNG_SS7_H__
|
||||
|
@ -46,17 +52,20 @@
|
|||
#include "private/ftdm_core.h"
|
||||
|
||||
#include "sng_ss7/sng_ss7.h"
|
||||
#include "ftmod_sangoma_ss7_m2ua.h"
|
||||
|
||||
/******************************************************************************/
|
||||
|
||||
/* DEFINES ********************************************************************/
|
||||
#define MAX_NAME_LEN 25
|
||||
#define MAX_PATH 4096
|
||||
|
||||
#define MAX_CIC_LENGTH 5
|
||||
#define MAX_CIC_MAP_LENGTH 1000
|
||||
#define MAX_SCTP_LINK 100
|
||||
|
||||
#define SNGSS7_EVENT_QUEUE_SIZE 100
|
||||
#define SNGSS7_PEER_CHANS_QUEUE_SIZE 100
|
||||
#define SNGSS7_CHAN_EVENT_QUEUE_SIZE 100
|
||||
|
||||
#define MAX_SIZEOF_SUBADDR_IE 24 /* as per Q931 4.5.9 */
|
||||
|
||||
|
@ -64,6 +73,14 @@
|
|||
(switchtype == LSI_SW_ANS92) || \
|
||||
(switchtype == LSI_SW_ANS95)
|
||||
|
||||
#define sngss7_flush_queue(queue) \
|
||||
do { \
|
||||
void *__queue_data = NULL; \
|
||||
while ((__queue_data = ftdm_queue_dequeue(queue))) { \
|
||||
ftdm_safe_free(__queue_data); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
typedef struct ftdm2trillium {
|
||||
uint8_t ftdm_val;
|
||||
uint8_t trillium_val;
|
||||
|
@ -82,8 +99,12 @@ typedef enum {
|
|||
SNGSS7_STA_IND_EVENT,
|
||||
SNGSS7_SUSP_IND_EVENT,
|
||||
SNGSS7_RESM_IND_EVENT,
|
||||
SNGSS7_SSP_STA_CFM_EVENT
|
||||
SNGSS7_SSP_STA_CFM_EVENT,
|
||||
SNGSS7_INVALID_EVENT,
|
||||
} sng_event_type_t;
|
||||
#define SNG_EVENT_TYPE_STRINGS "CON_IND", "CON_CFM", "CON_STA", "REL_IND", "REL_CFM", "DAT_IND", "FAC_IND", \
|
||||
"FAC_CFM", "UMSG_IND", "STA_IND", "SUSP_IND", "RESM_IND", "SSP_STA_CFM", "INVALID"
|
||||
FTDM_STR2ENUM_P(ftdm_str2sngss7_event, ftdm_sngss7_event2str, sng_event_type_t)
|
||||
|
||||
typedef enum {
|
||||
SNG_BIT_A = (1 << 0),
|
||||
|
@ -117,6 +138,12 @@ typedef enum {
|
|||
SNG_CALLING = 2
|
||||
} sng_addr_type_t;
|
||||
|
||||
typedef enum {
|
||||
SNG_GEN_CFG_STATUS_INIT = 0,
|
||||
SNG_GEN_CFG_STATUS_PENDING = 1,
|
||||
SNG_GEN_CFG_STATUS_DONE = 2
|
||||
} nsg_gen_cfg_type_t;
|
||||
|
||||
typedef struct sng_mtp2_error_type {
|
||||
int init;
|
||||
char sng_type[MAX_NAME_LEN];
|
||||
|
@ -176,6 +203,21 @@ typedef struct sng_mtp2_link {
|
|||
uint32_t t7;
|
||||
} sng_mtp2_link_t;
|
||||
|
||||
/* defining glare handling methods:
|
||||
SNGSS7_GLARE_PC:
|
||||
higher PointCode controls even number CIC
|
||||
lower PointCode controls odd number CIC
|
||||
SNGSS7_GLARE_DOWN:
|
||||
always give control to the other side
|
||||
SNGSS7_GLARE_CONTROL:
|
||||
always trying to control
|
||||
*/
|
||||
typedef enum {
|
||||
SNGSS7_GLARE_PC = 0,
|
||||
SNGSS7_GLARE_DOWN,
|
||||
SNGSS7_GLARE_CONTROL
|
||||
} sng_glare_resolution;
|
||||
|
||||
typedef struct sng_mtp3_link {
|
||||
char name[MAX_NAME_LEN];
|
||||
uint32_t flags;
|
||||
|
@ -328,6 +370,7 @@ typedef struct sng_isup_ckt {
|
|||
uint32_t clg_nadi;
|
||||
uint32_t cld_nadi;
|
||||
uint8_t rdnis_nadi;
|
||||
uint32_t loc_nadi;
|
||||
|
||||
/* Generic Number defaults */
|
||||
uint8_t gn_nmbqual; /* Number Qualifier */
|
||||
|
@ -339,8 +382,11 @@ typedef struct sng_isup_ckt {
|
|||
/* END - Generic Number defaults */
|
||||
|
||||
uint32_t min_digits;
|
||||
uint8_t itx_auto_reply;
|
||||
uint32_t transparent_iam_max_size;
|
||||
uint8_t transparent_iam;
|
||||
uint8_t cpg_on_progress_media;
|
||||
uint8_t cpg_on_progress;
|
||||
uint8_t itx_auto_reply;
|
||||
void *obj;
|
||||
uint16_t t3;
|
||||
uint32_t t10;
|
||||
|
@ -351,6 +397,7 @@ typedef struct sng_isup_ckt {
|
|||
uint16_t t16;
|
||||
uint16_t t17;
|
||||
uint32_t t35;
|
||||
uint32_t t39;
|
||||
uint16_t tval;
|
||||
} sng_isup_ckt_t;
|
||||
|
||||
|
@ -404,11 +451,34 @@ typedef struct sng_relay {
|
|||
uint32_t procId;
|
||||
} sng_relay_t;
|
||||
|
||||
/**********************************************
|
||||
sctp structures and data definitions
|
||||
**********************************************/
|
||||
|
||||
typedef struct sng_sctp_gen_cfg {
|
||||
} sng_sctp_gen_cfg_t;
|
||||
|
||||
typedef struct sng_sctp_link {
|
||||
char name[MAX_NAME_LEN];
|
||||
uint32_t flags;
|
||||
uint32_t id;
|
||||
uint32_t port;
|
||||
uint32_t numSrcAddr;
|
||||
uint32_t srcAddrList[SCT_MAX_NET_ADDRS+1];
|
||||
} sng_sctp_link_t;
|
||||
|
||||
typedef struct sng_sctp_cfg {
|
||||
sng_sctp_gen_cfg_t genCfg;
|
||||
sng_sctp_link_t linkCfg[MAX_SCTP_LINK+1];
|
||||
} sng_sctp_cfg_t;
|
||||
|
||||
|
||||
|
||||
typedef struct sng_ss7_cfg {
|
||||
uint32_t spc;
|
||||
uint32_t procId;
|
||||
char license[MAX_PATH];
|
||||
char signature[MAX_PATH];
|
||||
char license[MAX_SNGSS7_PATH];
|
||||
char signature[MAX_SNGSS7_PATH];
|
||||
uint32_t transparent_iam_max_size;
|
||||
uint32_t flags;
|
||||
sng_relay_t relay[MAX_RELAY_CHANNELS+1];
|
||||
|
@ -421,6 +491,10 @@ typedef struct sng_ss7_cfg {
|
|||
sng_isup_ckt_t isupCkt[10000]; /* KONRAD - only need 2000 ( and 0-1000 aren't used) since other servers are registerd else where */
|
||||
sng_nsap_t nsap[MAX_NSAPS+1];
|
||||
sng_isap_t isap[MAX_ISAPS+1];
|
||||
sng_glare_resolution glareResolution;
|
||||
uint32_t force_inr;
|
||||
sng_m2ua_gbl_cfg_t g_m2ua_cfg;
|
||||
sng_sctp_cfg_t sctpCfg;
|
||||
} sng_ss7_cfg_t;
|
||||
|
||||
typedef struct ftdm_sngss7_data {
|
||||
|
@ -433,6 +507,14 @@ typedef struct ftdm_sngss7_data {
|
|||
fio_signal_cb_t sig_cb;
|
||||
} ftdm_sngss7_data_t;
|
||||
|
||||
typedef enum{
|
||||
SNG_SS7_OPR_MODE_NONE,
|
||||
SNG_SS7_OPR_MODE_M2UA_SG,
|
||||
SNG_SS7_OPR_MODE_ISUP,
|
||||
}ftdm_sngss7_operating_modes_e;
|
||||
|
||||
typedef ftdm_sngss7_operating_modes_e ftdm_sngss7_opr_mode;
|
||||
|
||||
typedef struct sngss7_timer_data {
|
||||
ftdm_timer_id_t hb_timer_id;
|
||||
int beat;
|
||||
|
@ -472,10 +554,14 @@ typedef struct sngss7_chan_data {
|
|||
sngss7_glare_data_t glare;
|
||||
sngss7_timer_data_t t35;
|
||||
sngss7_timer_data_t t10;
|
||||
sngss7_timer_data_t t39;
|
||||
sngss7_group_data_t rx_grs;
|
||||
sngss7_group_data_t rx_gra;
|
||||
sngss7_group_data_t tx_grs;
|
||||
sngss7_group_data_t ucic;
|
||||
ftdm_queue_t *event_queue;
|
||||
struct sngss7_chan_data *peer_data;
|
||||
uint8_t peer_event_transfer_cnt;
|
||||
} sngss7_chan_data_t;
|
||||
|
||||
#define SNGSS7_RX_GRS_PENDING (1 << 0)
|
||||
|
@ -533,6 +619,18 @@ typedef enum {
|
|||
FLAG_INFID_RESUME = (1 << 14),
|
||||
FLAG_INFID_PAUSED = (1 << 15),
|
||||
FLAG_SENT_ACM = (1 << 16),
|
||||
FLAG_SENT_CPG = (1 << 17),
|
||||
FLAG_SUS_RECVD = (1 << 18),
|
||||
FLAG_T6_CANCELED = (1 << 19),
|
||||
FLAG_INR_TX = (1 << 20),
|
||||
FLAG_INR_SENT = (1 << 21),
|
||||
FLAG_INR_RX = (1 << 22),
|
||||
FLAG_INR_RX_DN = (1 << 23),
|
||||
FLAG_INF_TX = (1 << 24),
|
||||
FLAG_INF_SENT = (1 << 25),
|
||||
FLAG_INF_RX = (1 << 26),
|
||||
FLAG_INF_RX_DN = (1 << 27),
|
||||
FLAG_FULL_NUMBER = (1 << 28),
|
||||
FLAG_RELAY_DOWN = (1 << 30),
|
||||
FLAG_CKT_RECONFIG = (1 << 31)
|
||||
} sng_ckt_flag_t;
|
||||
|
@ -541,20 +639,28 @@ typedef enum {
|
|||
"RX_RSC", \
|
||||
"TX_RSC", \
|
||||
"TX_RSC_REQ_SENT", \
|
||||
"TX_RSC_RSP_RECIEVED", \
|
||||
"TX_RSC_RSP_RECEIVED", \
|
||||
"RX_GRS", \
|
||||
"RX_GRS_DONE", \
|
||||
"RX_GRS_CMPLT", \
|
||||
"GRS_BASE", \
|
||||
"TX_GRS", \
|
||||
"TX_GRS_REQ_SENT", \
|
||||
"TX_GRS_RSP_RECIEVED", \
|
||||
"TX_GRS_RSP_RECEIVED", \
|
||||
"REMOTE_REL", \
|
||||
"LOCAL_REL", \
|
||||
"GLARE", \
|
||||
"INF_RESUME", \
|
||||
"INF_PAUSED", \
|
||||
"TX_ACM_SENT" \
|
||||
"TX_INR" \
|
||||
"INR_SENT" \
|
||||
"RX_INR" \
|
||||
"RX_INR_DN" \
|
||||
"TX_INF" \
|
||||
"INF SENT" \
|
||||
"RX_INF" \
|
||||
"RX_INF_DN" \
|
||||
"RELAY_DOWN", \
|
||||
"CKT_RECONFIG"
|
||||
FTDM_STR2ENUM_P(ftmod_ss7_ckt_state2flag, ftmod_ss7_ckt_flag2str, sng_ckt_flag_t)
|
||||
|
@ -588,7 +694,7 @@ typedef enum {
|
|||
FLAG_GRP_HW_UNBLK_TX = (1 << 24),
|
||||
FLAG_GRP_HW_UNBLK_TX_DN = (1 << 25),
|
||||
FLAG_GRP_MN_UNBLK_TX = (1 << 26),
|
||||
FLAG_GRP_MN_UNBLK_TX_DN = (1 << 27)
|
||||
FLAG_GRP_MN_UNBLK_TX_DN = (1 << 27),
|
||||
} sng_ckt_block_flag_t;
|
||||
|
||||
#define BLK_FLAGS_STRING \
|
||||
|
@ -652,11 +758,27 @@ typedef enum {
|
|||
|
||||
SNGSS7_CC_PRESENT = (1 << 12),
|
||||
SNGSS7_CC_STARTED = (1 << 13),
|
||||
|
||||
SNGSS7_TUCL_PRESENT = (1 << 14),
|
||||
SNGSS7_TUCL_STARTED = (1 << 15),
|
||||
|
||||
SNGSS7_SCTP_PRESENT = (1 << 16),
|
||||
SNGSS7_SCTP_STARTED = (1 << 17),
|
||||
|
||||
SNGSS7_M2UA_PRESENT = (1 << 18),
|
||||
SNGSS7_M2UA_STARTED = (1 << 19),
|
||||
SNGSS7_M2UA_EP_OPENED = (1 << 20),
|
||||
SNGSS7_M2UA_INIT_ASSOC_DONE = (1 << 21),
|
||||
|
||||
SNGSS7_NIF_PRESENT = (1 << 22),
|
||||
SNGSS7_NIF_STARTED = (1 << 23),
|
||||
|
||||
} sng_task_flag_t;
|
||||
/******************************************************************************/
|
||||
|
||||
/* GLOBALS ********************************************************************/
|
||||
extern ftdm_sngss7_data_t g_ftdm_sngss7_data;
|
||||
extern ftdm_sngss7_opr_mode g_ftdm_operating_mode;
|
||||
extern sng_ssf_type_t sng_ssf_type_map[];
|
||||
extern sng_switch_type_t sng_switch_type_map[];
|
||||
extern sng_link_type_t sng_link_type_map[];
|
||||
|
@ -679,6 +801,10 @@ void handle_sng_mtp3_alarm(Pst *pst, SnMngmt *sta);
|
|||
void handle_sng_isup_alarm(Pst *pst, SiMngmt *sta);
|
||||
void handle_sng_cc_alarm(Pst *pst, CcMngmt *sta);
|
||||
void handle_sng_relay_alarm(Pst *pst, RyMngmt *sta);
|
||||
void handle_sng_m2ua_alarm(Pst *pst, MwMgmt *sta);
|
||||
void handle_sng_nif_alarm(Pst *pst, NwMgmt *sta);
|
||||
void handle_sng_tucl_alarm(Pst *pst, HiMngmt *sta);
|
||||
void handle_sng_sctp_alarm(Pst *pst, SbMgmt *sta);
|
||||
|
||||
/* in ftmod_sangoma_ss7_relay.c */
|
||||
ftdm_status_t handle_relay_connect(RyMngmt *sta);
|
||||
|
@ -731,7 +857,9 @@ int ftmod_ss7_enable_grp_mtp3Link(uint32_t procId);
|
|||
|
||||
int ftmod_ss7_disable_grp_mtp2Link(uint32_t procId);
|
||||
|
||||
int ftmod_ss7_block_isup_ckt(uint32_t cktId);
|
||||
#define ftmod_ss7_block_isup_ckt(x) __ftmod_ss7_block_isup_ckt(x,FTDM_TRUE)
|
||||
#define ftmod_ss7_block_isup_ckt_nowait(x) __ftmod_ss7_block_isup_ckt(x,FTDM_FALSE)
|
||||
int __ftmod_ss7_block_isup_ckt(uint32_t cktId, ftdm_bool_t wait);
|
||||
int ftmod_ss7_unblock_isup_ckt(uint32_t cktId);
|
||||
|
||||
|
||||
|
@ -767,6 +895,9 @@ void ft_to_sngss7_cgb(ftdm_channel_t * ftdmchan);
|
|||
void ft_to_sngss7_cgu(ftdm_channel_t * ftdmchan);
|
||||
void ft_to_sngss7_itx (ftdm_channel_t * ftdmchan);
|
||||
void ft_to_sngss7_txa (ftdm_channel_t * ftdmchan);
|
||||
void ft_to_sngss7_inr(ftdm_channel_t * ftdmchan);
|
||||
void ft_to_sngss7_inf(ftdm_channel_t *ftdmchan, SiCnStEvnt *inr);
|
||||
|
||||
|
||||
|
||||
/* in ftmod_sangoma_ss7_in.c */
|
||||
|
@ -835,15 +966,27 @@ ftdm_status_t copy_cdPtyNum_from_sngss7(ftdm_channel_t *ftdmchan, SiCdPtyNum *cd
|
|||
ftdm_status_t copy_cdPtyNum_to_sngss7(ftdm_channel_t *ftdmchan, SiCdPtyNum *cdPtyNum);
|
||||
ftdm_status_t copy_redirgNum_to_sngss7(ftdm_channel_t *ftdmchan, SiRedirNum *redirgNum);
|
||||
ftdm_status_t copy_redirgNum_from_sngss7(ftdm_channel_t *ftdmchan, SiRedirNum *redirgNum);
|
||||
ftdm_status_t copy_redirgInfo_from_sngss7(ftdm_channel_t *ftdmchan, SiRedirInfo *redirInfo);
|
||||
ftdm_status_t copy_redirgInfo_to_sngss7(ftdm_channel_t *ftdmchan, SiRedirInfo *redirInfo);
|
||||
ftdm_status_t copy_ocn_to_sngss7(ftdm_channel_t *ftdmchan, SiOrigCdNum *origCdNum);
|
||||
ftdm_status_t copy_ocn_from_sngss7(ftdm_channel_t *ftdmchan, SiOrigCdNum *origCdNum);
|
||||
|
||||
ftdm_status_t copy_access_transport_from_sngss7(ftdm_channel_t *ftdmchan, SiAccTrnspt *accTrnspt);
|
||||
ftdm_status_t copy_access_transport_to_sngss7(ftdm_channel_t *ftdmchan, SiAccTrnspt *accTrnspt);
|
||||
ftdm_status_t copy_locPtyNum_to_sngss7(ftdm_channel_t *ftdmchan, SiCgPtyNum *locPtyNum);
|
||||
ftdm_status_t copy_locPtyNum_from_sngss7(ftdm_channel_t *ftdmchan, SiCgPtyNum *locPtyNum);
|
||||
ftdm_status_t copy_genNmb_to_sngss7(ftdm_channel_t *ftdmchan, SiGenNum *genNmb);
|
||||
ftdm_status_t copy_genNmb_from_sngss7(ftdm_channel_t *ftdmchan, SiGenNum *genNmb);
|
||||
ftdm_status_t copy_cgPtyCat_to_sngss7(ftdm_channel_t *ftdmchan, SiCgPtyCat *cgPtyCat);
|
||||
ftdm_status_t copy_cgPtyCat_from_sngss7(ftdm_channel_t *ftdmchan, SiCgPtyCat *cgPtyCat);
|
||||
ftdm_status_t copy_accTrnspt_to_sngss7(ftdm_channel_t *ftdmchan, SiAccTrnspt *accTrnspt);
|
||||
ftdm_status_t copy_natConInd_to_sngss7(ftdm_channel_t *ftdmchan, SiNatConInd *natConInd);
|
||||
ftdm_status_t copy_fwdCallInd_hex_from_sngss7(ftdm_channel_t *ftdmchan, SiFwdCallInd *fwdCallInd);
|
||||
ftdm_status_t copy_fwdCallInd_to_sngss7(ftdm_channel_t *ftdmchan, SiFwdCallInd *fwdCallInd);
|
||||
ftdm_status_t copy_txMedReq_to_sngss7(ftdm_channel_t *ftdmchan, SiTxMedReq *txMedReq);
|
||||
ftdm_status_t copy_usrServInfoA_to_sngss7(ftdm_channel_t *ftdmchan, SiUsrServInfo *usrServInfoA);
|
||||
ftdm_status_t copy_NatureOfConnection_from_sngss7(ftdm_channel_t *ftdmchan, SiNatConInd *natConInd );
|
||||
ftdm_status_t copy_NatureOfConnection_to_sngss7(ftdm_channel_t *ftdmchan, SiNatConInd *natConInd);
|
||||
|
||||
ftdm_status_t copy_tknStr_from_sngss7(TknStr str, char *ftdm, TknU8 oddEven);
|
||||
ftdm_status_t append_tknStr_from_sngss7(TknStr str, char *ftdm, TknU8 oddEven);
|
||||
|
@ -889,6 +1032,8 @@ ftdm_status_t sngss7_add_raw_data(sngss7_chan_data_t *sngss7_info, uint8_t* data
|
|||
/* in ftmod_sangoma_ss7_timers.c */
|
||||
void handle_isup_t35(void *userdata);
|
||||
void handle_isup_t10(void *userdata);
|
||||
void handle_isup_t39(void *userdata);
|
||||
|
||||
|
||||
/******************************************************************************/
|
||||
|
||||
|
@ -910,9 +1055,9 @@ if (ftdmchan->state == new_state) { \
|
|||
#define SS7_INFO_CHAN(fchan, msg, args...) ftdm_log_chan(fchan, FTDM_LOG_INFO, msg , ##args)
|
||||
#define SS7_WARN_CHAN(fchan, msg, args...) ftdm_log_chan(fchan, FTDM_LOG_WARNING, msg , ##args)
|
||||
#define SS7_ERROR_CHAN(fchan, msg, args...) ftdm_log_chan(fchan, FTDM_LOG_ERROR, msg , ##args)
|
||||
#define SS7_CTRIT_CHAN(fchan, msg, args...) ftdm_log_chan(fchan, FTDM_LOG_CRIT, msg , ##args)
|
||||
#define SS7_CRIT_CHAN(fchan, msg, args...) ftdm_log_chan(fchan, FTDM_LOG_CRIT, msg , ##args)
|
||||
|
||||
#ifdef KONRAD_DEVEL
|
||||
#ifdef SS7_CODE_DEVEL
|
||||
#define SS7_DEVEL_DEBUG(a,...) ftdm_log(FTDM_LOG_DEBUG,a,##__VA_ARGS__ );
|
||||
#else
|
||||
#define SS7_DEVEL_DEBUG(a,...)
|
||||
|
@ -1039,6 +1184,40 @@ if (ftdmchan->state == new_state) { \
|
|||
#define sngss7_clear_options(obj, option) ((obj)->options &= ~(option))
|
||||
#define sngss7_set_options(obj, option) ((obj)->options |= (option))
|
||||
|
||||
#define sngss7_tx_block_status_clear(obj) (!sngss7_test_ckt_blk_flag(obj, (FLAG_CKT_MN_BLOCK_TX | \
|
||||
FLAG_CKT_MN_BLOCK_TX_DN | \
|
||||
FLAG_GRP_MN_BLOCK_TX | \
|
||||
FLAG_GRP_MN_BLOCK_TX_DN | \
|
||||
FLAG_GRP_HW_BLOCK_TX | \
|
||||
FLAG_GRP_HW_BLOCK_TX_DN | \
|
||||
FLAG_GRP_HW_UNBLK_TX | \
|
||||
FLAG_CKT_MN_UNBLK_TX )))
|
||||
|
||||
#define sngss7_block_status_clear(obj) (obj->blk_flags == 0)
|
||||
|
||||
#define sngss7_reset_status_clear(obj) (!sngss7_test_ckt_flag(obj, (FLAG_RESET_TX | \
|
||||
FLAG_RESET_RX | \
|
||||
FLAG_GRP_RESET_TX | \
|
||||
FLAG_GRP_RESET_RX )))
|
||||
|
||||
#define sngss7_tx_reset_sent(obj) ((sngss7_test_ckt_flag(obj, (FLAG_RESET_TX)) && \
|
||||
sngss7_test_ckt_flag(obj, (FLAG_RESET_SENT))) || \
|
||||
(sngss7_test_ckt_flag(obj, (FLAG_GRP_RESET_TX)) && \
|
||||
sngss7_test_ckt_flag(obj, (FLAG_GRP_RESET_SENT))))
|
||||
|
||||
#define sngss7_tx_reset_status_pending(obj) (sngss7_test_ckt_flag(obj, (FLAG_RESET_TX)) || sngss7_test_ckt_flag(obj, (FLAG_GRP_RESET_TX)))
|
||||
|
||||
#define sngss7_channel_status_clear(obj) ((sngss7_block_status_clear(obj)) && \
|
||||
(sngss7_reset_status_clear(obj)) && \
|
||||
(!sngss7_test_ckt_flag((obj),FLAG_INFID_PAUSED)))
|
||||
|
||||
#define sngss7_tx_reset_restart(obj) do { clear_tx_grs_flags((obj)); \
|
||||
clear_tx_grs_data((obj)); \
|
||||
clear_tx_rsc_flags((obj)); \
|
||||
sngss7_set_ckt_flag((obj), (FLAG_RESET_TX)); \
|
||||
} while (0);
|
||||
|
||||
|
||||
|
||||
#ifdef SMG_RELAY_DBG
|
||||
#define SS7_RELAY_DBG(a,...) printf(a"\n", ##__VA_ARGS__)
|
||||
|
|
|
@ -44,8 +44,11 @@
|
|||
/* FUNCTIONS ******************************************************************/
|
||||
void ft_to_sngss7_iam (ftdm_channel_t * ftdmchan)
|
||||
{
|
||||
const char *var = NULL;
|
||||
SiConEvnt iam;
|
||||
ftdm_bool_t native_going_up = FTDM_FALSE;
|
||||
sngss7_chan_data_t *sngss7_info = ftdmchan->call_data;;
|
||||
sngss7_event_data_t *event_clone = NULL;
|
||||
|
||||
SS7_FUNC_TRACE_ENTER (__FUNCTION__);
|
||||
|
||||
|
@ -55,9 +58,113 @@ void ft_to_sngss7_iam (ftdm_channel_t * ftdmchan)
|
|||
|
||||
memset (&iam, 0x0, sizeof (iam));
|
||||
|
||||
if (sngss7_info->circuit->transparent_iam &&
|
||||
if (ftdm_test_flag(ftdmchan, FTDM_CHANNEL_NATIVE_SIGBRIDGE)) {
|
||||
ftdm_span_t *peer_span = NULL;
|
||||
ftdm_channel_t *peer_chan = NULL;
|
||||
sngss7_chan_data_t *peer_info = NULL;
|
||||
|
||||
var = ftdm_usrmsg_get_var(ftdmchan->usrmsg, "sigbridge_peer");
|
||||
ftdm_get_channel_from_string(var, &peer_span, &peer_chan);
|
||||
if (!peer_chan) {
|
||||
SS7_ERROR_CHAN(ftdmchan, "Failed to find sigbridge peer from string '%s'\n", var);
|
||||
} else {
|
||||
if (peer_span->signal_type != FTDM_SIGTYPE_SS7) {
|
||||
SS7_ERROR_CHAN(ftdmchan, "Peer channel '%s' has different signaling type %d'\n",
|
||||
var, peer_span->signal_type);
|
||||
} else {
|
||||
peer_info = peer_chan->call_data;
|
||||
SS7_INFO_CHAN(ftdmchan,"[CIC:%d]Starting native bridge with peer CIC %d\n",
|
||||
sngss7_info->circuit->cic, peer_info->circuit->cic);
|
||||
|
||||
/* retrieve only first message from the others guys queue (must be IAM) */
|
||||
event_clone = ftdm_queue_dequeue(peer_info->event_queue);
|
||||
|
||||
/* make each one of us aware of the native bridge */
|
||||
peer_info->peer_data = sngss7_info;
|
||||
sngss7_info->peer_data = peer_info;
|
||||
|
||||
/* Go to up until release comes, note that state processing is done different and much simpler when there is a peer,
|
||||
We can't go to UP state right away yet though, so do not set the state to UP here, wait until the end of this function
|
||||
because moving from one state to another causes the ftdmchan->usrmsg structure to be wiped
|
||||
and we still need those variables for further IAM processing */
|
||||
native_going_up = FTDM_TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (ftdm_test_flag(ftdmchan, FTDM_CHANNEL_NATIVE_SIGBRIDGE)) {
|
||||
if (!event_clone) {
|
||||
SS7_ERROR_CHAN(ftdmchan, "No IAM event clone in peer queue!%s\n", "");
|
||||
} else if (event_clone->event_id != SNGSS7_CON_IND_EVENT) {
|
||||
/* first message in the queue should ALWAYS be an IAM */
|
||||
SS7_ERROR_CHAN(ftdmchan, "Invalid initial peer message type '%d'\n", event_clone->event_id);
|
||||
} else {
|
||||
ftdm_caller_data_t *caller_data = &ftdmchan->caller_data;
|
||||
|
||||
SS7_INFO_CHAN(ftdmchan,"[CIC:%d]Tx IAM (Bridged, dialing %s)\n", sngss7_info->circuit->cic, caller_data->dnis.digits);
|
||||
|
||||
/* copy original incoming IAM */
|
||||
memcpy(&iam, &event_clone->event.siConEvnt, sizeof(iam));
|
||||
|
||||
/* Change DNIS to whatever was specified, do not change NADI or anything else! */
|
||||
copy_tknStr_to_sngss7(caller_data->dnis.digits, &iam.cdPtyNum.addrSig, &iam.cdPtyNum.oddEven);
|
||||
|
||||
/* SPIROU certification hack
|
||||
If the IAM already contain RDINF, just increment the count and set the RDNIS digits
|
||||
otherwise, honor RDNIS and RDINF stuff coming from the user */
|
||||
if (iam.redirInfo.eh.pres == PRSNT_NODEF) {
|
||||
const char *val = NULL;
|
||||
if (iam.redirInfo.redirCnt.pres) {
|
||||
iam.redirInfo.redirCnt.val++;
|
||||
SS7_DEBUG_CHAN(ftdmchan,"[CIC:%d]Tx IAM (Bridged), redirect count incremented = %d\n", sngss7_info->circuit->cic, iam.redirInfo.redirCnt.val);
|
||||
}
|
||||
val = ftdm_usrmsg_get_var(ftdmchan->usrmsg, "ss7_rdnis_digits");
|
||||
if (!ftdm_strlen_zero(val)) {
|
||||
SS7_DEBUG_CHAN(ftdmchan,"[CIC:%d]Tx IAM (Bridged), found user supplied RDNIS digits = %s\n", sngss7_info->circuit->cic, val);
|
||||
copy_tknStr_to_sngss7((char*)val, &iam.redirgNum.addrSig, &iam.redirgNum.oddEven);
|
||||
} else {
|
||||
SS7_DEBUG_CHAN(ftdmchan,"[CIC:%d]Tx IAM (Bridged), not found user supplied RDNIS digits\n", sngss7_info->circuit->cic);
|
||||
}
|
||||
} else {
|
||||
SS7_DEBUG_CHAN(ftdmchan,"[CIC:%d]Tx IAM (Bridged), redirect info not present, attempting to copy user supplied values\n", sngss7_info->circuit->cic);
|
||||
/* Redirecting Number */
|
||||
copy_redirgNum_to_sngss7(ftdmchan, &iam.redirgNum);
|
||||
|
||||
/* Redirecting Information */
|
||||
copy_redirgInfo_to_sngss7(ftdmchan, &iam.redirInfo);
|
||||
}
|
||||
|
||||
if (iam.origCdNum.eh.pres != PRSNT_NODEF) {
|
||||
/* Original Called Number */
|
||||
copy_ocn_to_sngss7(ftdmchan, &iam.origCdNum);
|
||||
}
|
||||
copy_access_transport_to_sngss7(ftdmchan, &iam.accTrnspt);
|
||||
}
|
||||
} else if (sngss7_info->circuit->transparent_iam &&
|
||||
sngss7_retrieve_iam(ftdmchan, &iam) == FTDM_SUCCESS) {
|
||||
SS7_INFO_CHAN(ftdmchan,"[CIC:%d]Tx IAM (Transparent)\n", sngss7_info->circuit->cic);
|
||||
|
||||
/* Called Number information */
|
||||
copy_cdPtyNum_to_sngss7(ftdmchan, &iam.cdPtyNum);
|
||||
|
||||
/* Redirecting Number */
|
||||
copy_redirgNum_to_sngss7(ftdmchan, &iam.redirgNum);
|
||||
|
||||
/* Redirecting Information */
|
||||
copy_redirgInfo_to_sngss7(ftdmchan, &iam.redirInfo);
|
||||
|
||||
/* Location Number information */
|
||||
copy_locPtyNum_to_sngss7(ftdmchan, &iam.cgPtyNum1);
|
||||
|
||||
/* Forward Call Indicators */
|
||||
copy_fwdCallInd_to_sngss7(ftdmchan, &iam.fwdCallInd);
|
||||
|
||||
/* Original Called Number */
|
||||
copy_ocn_to_sngss7(ftdmchan, &iam.origCdNum);
|
||||
|
||||
copy_access_transport_to_sngss7(ftdmchan, &iam.accTrnspt);
|
||||
|
||||
copy_NatureOfConnection_to_sngss7(ftdmchan, &iam.natConInd);
|
||||
} else {
|
||||
/* Nature of Connection Indicators */
|
||||
copy_natConInd_to_sngss7(ftdmchan, &iam.natConInd);
|
||||
|
@ -79,6 +186,9 @@ void ft_to_sngss7_iam (ftdm_channel_t * ftdmchan)
|
|||
/* Calling Number information */
|
||||
copy_cgPtyNum_to_sngss7(ftdmchan, &iam.cgPtyNum);
|
||||
|
||||
/* Location Number information */
|
||||
copy_locPtyNum_to_sngss7(ftdmchan, &iam.cgPtyNum1);
|
||||
|
||||
/* Generic Number information */
|
||||
copy_genNmb_to_sngss7(ftdmchan, &iam.genNmb);
|
||||
|
||||
|
@ -88,15 +198,30 @@ void ft_to_sngss7_iam (ftdm_channel_t * ftdmchan)
|
|||
/* Redirecting Number */
|
||||
copy_redirgNum_to_sngss7(ftdmchan, &iam.redirgNum);
|
||||
|
||||
/* Access Transport */
|
||||
copy_accTrnspt_to_sngss7(ftdmchan, &iam.accTrnspt);
|
||||
/* Redirecting Information */
|
||||
copy_redirgInfo_to_sngss7(ftdmchan, &iam.redirInfo);
|
||||
|
||||
SS7_INFO_CHAN(ftdmchan,"[CIC:%d]Tx IAM clg = \"%s\" (NADI=%d), cld = \"%s\" (NADI=%d)\n",
|
||||
/* Original Called Number */
|
||||
copy_ocn_to_sngss7(ftdmchan, &iam.origCdNum);
|
||||
|
||||
/* Access Transport - old implementation, taking from channel variable of ss7_clg_subaddr */
|
||||
copy_accTrnspt_to_sngss7(ftdmchan, &iam.accTrnspt);
|
||||
|
||||
/* Access Transport - taking from channel variable of ss7_access_transport_urlenc.
|
||||
This will overwirte the IE value set be above old implementation.
|
||||
*/
|
||||
copy_access_transport_to_sngss7(ftdmchan, &iam.accTrnspt);
|
||||
|
||||
copy_NatureOfConnection_to_sngss7(ftdmchan, &iam.natConInd);
|
||||
|
||||
SS7_INFO_CHAN(ftdmchan,"[CIC:%d]Tx IAM clg = \"%s\" (NADI=%d), cld = \"%s\" (NADI=%d), loc = %s (NADI=%d)\n",
|
||||
sngss7_info->circuit->cic,
|
||||
ftdmchan->caller_data.cid_num.digits,
|
||||
iam.cgPtyNum.natAddrInd.val,
|
||||
ftdmchan->caller_data.dnis.digits,
|
||||
iam.cdPtyNum.natAddrInd.val);
|
||||
iam.cdPtyNum.natAddrInd.val,
|
||||
ftdmchan->caller_data.loc.digits,
|
||||
iam.cgPtyNum1.natAddrInd.val);
|
||||
}
|
||||
|
||||
sng_cc_con_request (sngss7_info->spId,
|
||||
|
@ -106,16 +231,124 @@ void ft_to_sngss7_iam (ftdm_channel_t * ftdmchan)
|
|||
&iam,
|
||||
0);
|
||||
|
||||
if (native_going_up) {
|
||||
/*
|
||||
Note that this function (ft_to_sngss7_iam) is run within the main SS7 processing loop in
|
||||
response to the DIALING state handler, we can set the state to UP here and that will
|
||||
implicitly complete the DIALING state, but we *MUST* also advance the state handler
|
||||
right away for a native bridge, otherwise, the processing state function (ftdm_sangoma_ss7_process_state_change)
|
||||
will complete the state without having executed the handler for FTDM_CHANNEL_STATE_UP, and we won't notify
|
||||
the user sending FTDM_SIGEVENT_UP which can cause the application to misbehave (ie, no audio) */
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_UP);
|
||||
ftdm_channel_advance_states(ftdmchan);
|
||||
}
|
||||
|
||||
ftdm_safe_free(event_clone);
|
||||
|
||||
SS7_FUNC_TRACE_EXIT (__FUNCTION__);
|
||||
return;
|
||||
}
|
||||
|
||||
void ft_to_sngss7_inf(ftdm_channel_t *ftdmchan, SiCnStEvnt *inr)
|
||||
{
|
||||
SiCnStEvnt evnt;
|
||||
sngss7_chan_data_t *sngss7_info = ftdmchan->call_data;
|
||||
|
||||
memset (&evnt, 0x0, sizeof (evnt));
|
||||
|
||||
evnt.infoInd.eh.pres = PRSNT_NODEF;
|
||||
evnt.infoInd.cgPtyAddrRespInd.pres = PRSNT_NODEF;
|
||||
evnt.infoInd.cgPtyCatRespInd.pres = PRSNT_NODEF;
|
||||
|
||||
evnt.infoInd.chrgInfoRespInd.pres = PRSNT_NODEF;
|
||||
evnt.infoInd.chrgInfoRespInd.val = 0;
|
||||
evnt.infoInd.solInfoInd.pres = PRSNT_NODEF;
|
||||
evnt.infoInd.solInfoInd.val = 0;
|
||||
evnt.infoInd.holdProvInd.pres = PRSNT_NODEF;
|
||||
evnt.infoInd.holdProvInd.val = 0;
|
||||
evnt.infoInd.spare.pres = PRSNT_NODEF;
|
||||
evnt.infoInd.spare.val = 0;
|
||||
|
||||
if (inr->infoReqInd.eh.pres == PRSNT_NODEF) {
|
||||
if ((inr->infoReqInd.holdingInd.pres == PRSNT_NODEF) && (inr->infoReqInd.holdingInd.val == HOLD_REQ)) {
|
||||
SS7_DEBUG_CHAN(ftdmchan,"[CIC:%d]Received INR requesting holding information. Holding is not supported in INF.\n", sngss7_info->circuit->cic);
|
||||
}
|
||||
if ((inr->infoReqInd.chrgInfoReqInd.pres == PRSNT_NODEF) && (inr->infoReqInd.chrgInfoReqInd.val == CHRGINFO_REQ)) {
|
||||
SS7_DEBUG_CHAN(ftdmchan,"[CIC:%d]Received INR requesting charging information. Charging is not supported in INF.\n", sngss7_info->circuit->cic);
|
||||
}
|
||||
if ((inr->infoReqInd.malCaIdReqInd.pres == PRSNT_NODEF) && (inr->infoReqInd.malCaIdReqInd.val == CHRGINFO_REQ)) {
|
||||
SS7_DEBUG_CHAN(ftdmchan,"[CIC:%d]Received INR requesting malicious call id. Malicious call id is not supported in INF.\n", sngss7_info->circuit->cic);
|
||||
}
|
||||
|
||||
if ((inr->infoReqInd.cgPtyAdReqInd.pres == PRSNT_NODEF) && (inr->infoReqInd.cgPtyAdReqInd.val == CGPRTYADDREQ_REQ)) {
|
||||
evnt.infoInd.cgPtyAddrRespInd.val=CGPRTYADDRESP_INCL;
|
||||
copy_cgPtyNum_to_sngss7 (ftdmchan, &evnt.cgPtyNum);
|
||||
} else {
|
||||
evnt.infoInd.cgPtyAddrRespInd.val=CGPRTYADDRESP_NOTINCL;
|
||||
}
|
||||
|
||||
if ((inr->infoReqInd.cgPtyCatReqInd.pres == PRSNT_NODEF) && (inr->infoReqInd.cgPtyCatReqInd.val == CGPRTYCATREQ_REQ)) {
|
||||
evnt.infoInd.cgPtyCatRespInd.val = CGPRTYCATRESP_INCL;
|
||||
copy_cgPtyCat_to_sngss7 (ftdmchan, &evnt.cgPtyCat);
|
||||
} else {
|
||||
evnt.infoInd.cgPtyCatRespInd.val = CGPRTYCATRESP_NOTINCL;
|
||||
}
|
||||
}
|
||||
else {
|
||||
SS7_DEBUG_CHAN(ftdmchan,"[CIC:%d]Received INR with no information request. Sending back default INF.\n", sngss7_info->circuit->cic);
|
||||
}
|
||||
|
||||
sng_cc_inf(1,
|
||||
sngss7_info->suInstId,
|
||||
sngss7_info->spInstId,
|
||||
sngss7_info->circuit->id,
|
||||
&evnt,
|
||||
INFORMATION);
|
||||
|
||||
SS7_INFO_CHAN(ftdmchan,"[CIC:%d]Tx INF\n", sngss7_info->circuit->cic);
|
||||
|
||||
}
|
||||
|
||||
void ft_to_sngss7_inr(ftdm_channel_t *ftdmchan)
|
||||
{
|
||||
SiCnStEvnt evnt;
|
||||
sngss7_chan_data_t *sngss7_info = ftdmchan->call_data;
|
||||
|
||||
memset (&evnt, 0x0, sizeof (evnt));
|
||||
|
||||
evnt.infoReqInd.eh.pres = PRSNT_NODEF;
|
||||
evnt.infoReqInd.cgPtyAdReqInd.pres = PRSNT_NODEF;
|
||||
evnt.infoReqInd.cgPtyAdReqInd.val=CGPRTYADDREQ_REQ;
|
||||
|
||||
evnt.infoReqInd.holdingInd.pres = PRSNT_NODEF;
|
||||
evnt.infoReqInd.holdingInd.val = HOLD_REQ;
|
||||
|
||||
evnt.infoReqInd.cgPtyCatReqInd.pres = PRSNT_NODEF;
|
||||
evnt.infoReqInd.cgPtyCatReqInd.val = CGPRTYCATREQ_REQ;
|
||||
|
||||
evnt.infoReqInd.chrgInfoReqInd.pres = PRSNT_NODEF;
|
||||
evnt.infoReqInd.chrgInfoReqInd.val = CHRGINFO_REQ;
|
||||
|
||||
evnt.infoReqInd.malCaIdReqInd.pres = PRSNT_NODEF;
|
||||
evnt.infoReqInd.malCaIdReqInd.val = MLBG_INFOREQ;
|
||||
|
||||
sng_cc_inr(1,
|
||||
sngss7_info->suInstId,
|
||||
sngss7_info->spInstId,
|
||||
sngss7_info->circuit->id,
|
||||
&evnt,
|
||||
INFORMATREQ);
|
||||
|
||||
SS7_INFO_CHAN(ftdmchan,"[CIC:%d]Tx INR\n", sngss7_info->circuit->cic);
|
||||
}
|
||||
|
||||
void ft_to_sngss7_acm (ftdm_channel_t * ftdmchan)
|
||||
{
|
||||
SS7_FUNC_TRACE_ENTER (__FUNCTION__);
|
||||
|
||||
sngss7_chan_data_t *sngss7_info = ftdmchan->call_data;
|
||||
SiCnStEvnt acm;
|
||||
const char *backwardInd = NULL;
|
||||
|
||||
memset (&acm, 0x0, sizeof (acm));
|
||||
|
||||
|
@ -133,8 +366,16 @@ void ft_to_sngss7_acm (ftdm_channel_t * ftdmchan)
|
|||
acm.bckCallInd.intInd.val = INTIND_NOINTW;
|
||||
acm.bckCallInd.end2EndInfoInd.pres = PRSNT_NODEF;
|
||||
acm.bckCallInd.end2EndInfoInd.val = E2EINF_NOINFO;
|
||||
|
||||
acm.bckCallInd.isdnUsrPrtInd.pres = PRSNT_NODEF;
|
||||
acm.bckCallInd.isdnUsrPrtInd.val = ISUP_USED;
|
||||
acm.bckCallInd.isdnUsrPrtInd.val = ISUP_NOTUSED;
|
||||
backwardInd = ftdm_usrmsg_get_var(ftdmchan->usrmsg, "acm_bi_iup");
|
||||
if (!ftdm_strlen_zero(backwardInd)) {
|
||||
ftdm_log_chan(ftdmchan, FTDM_LOG_DEBUG, "Found user supplied backward indicator ISDN user part indicator ACM, value \"%s\"\n", backwardInd);
|
||||
if (atoi(backwardInd) != 0 ) {
|
||||
acm.bckCallInd.isdnUsrPrtInd.val = ISUP_USED;
|
||||
}
|
||||
}
|
||||
acm.bckCallInd.holdInd.pres = PRSNT_NODEF;
|
||||
acm.bckCallInd.holdInd.val = HOLD_NOTREQD;
|
||||
acm.bckCallInd.isdnAccInd.pres = PRSNT_NODEF;
|
||||
|
@ -241,6 +482,7 @@ void ft_to_sngss7_anm (ftdm_channel_t * ftdmchan)
|
|||
/******************************************************************************/
|
||||
void ft_to_sngss7_rel (ftdm_channel_t * ftdmchan)
|
||||
{
|
||||
const char *loc_ind = NULL;
|
||||
SS7_FUNC_TRACE_ENTER (__FUNCTION__);
|
||||
|
||||
sngss7_chan_data_t *sngss7_info = ftdmchan->call_data;
|
||||
|
@ -250,7 +492,15 @@ void ft_to_sngss7_rel (ftdm_channel_t * ftdmchan)
|
|||
|
||||
rel.causeDgn.eh.pres = PRSNT_NODEF;
|
||||
rel.causeDgn.location.pres = PRSNT_NODEF;
|
||||
rel.causeDgn.location.val = 0x01;
|
||||
|
||||
loc_ind = ftdm_usrmsg_get_var(ftdmchan->usrmsg, "ss7_rel_loc");
|
||||
if (!ftdm_strlen_zero(loc_ind)) {
|
||||
ftdm_log_chan(ftdmchan, FTDM_LOG_DEBUG, "Found user supplied location indicator in REL, value \"%s\"\n", loc_ind);
|
||||
rel.causeDgn.location.val = atoi(loc_ind);
|
||||
} else {
|
||||
rel.causeDgn.location.val = 0x01;
|
||||
ftdm_log_chan(ftdmchan, FTDM_LOG_DEBUG, "No user supplied location indicator in REL, using 0x01\"%s\"\n", "");
|
||||
}
|
||||
rel.causeDgn.cdeStand.pres = PRSNT_NODEF;
|
||||
rel.causeDgn.cdeStand.val = 0x00;
|
||||
rel.causeDgn.recommend.pres = NOTPRSNT;
|
||||
|
@ -260,10 +510,10 @@ void ft_to_sngss7_rel (ftdm_channel_t * ftdmchan)
|
|||
|
||||
/* send the REL request to LibSngSS7 */
|
||||
sng_cc_rel_request (1,
|
||||
sngss7_info->suInstId,
|
||||
sngss7_info->spInstId,
|
||||
sngss7_info->circuit->id,
|
||||
&rel);
|
||||
sngss7_info->suInstId,
|
||||
sngss7_info->spInstId,
|
||||
sngss7_info->circuit->id,
|
||||
&rel);
|
||||
|
||||
SS7_INFO_CHAN(ftdmchan,"[CIC:%d]Tx REL cause=%d \n",
|
||||
sngss7_info->circuit->cic,
|
||||
|
@ -518,8 +768,6 @@ void ft_to_sngss7_grs (ftdm_channel_t *fchan)
|
|||
cinfo->circuit->cic,
|
||||
(cinfo->circuit->cic + cinfo->tx_grs.range));
|
||||
|
||||
memset(&cinfo->tx_grs, 0, sizeof(cinfo->tx_grs));
|
||||
|
||||
sngss7_set_ckt_flag(cinfo, FLAG_GRP_RESET_SENT);
|
||||
|
||||
SS7_FUNC_TRACE_EXIT (__FUNCTION__);
|
||||
|
|
|
@ -42,8 +42,6 @@
|
|||
/******************************************************************************/
|
||||
|
||||
/* PROTOTYPES *****************************************************************/
|
||||
ftdm_status_t handle_relay_connect(RyMngmt *sta);
|
||||
ftdm_status_t handle_relay_disconnect(RyMngmt *sta);
|
||||
|
||||
/*static ftdm_status_t enable_all_ckts_for_relay(void);*/
|
||||
static ftdm_status_t reconfig_all_ckts_for_relay(void);
|
||||
|
@ -66,11 +64,9 @@ ftdm_status_t handle_relay_connect(RyMngmt *sta)
|
|||
|
||||
SS7_INFO("Relay Channel %d connection UP\n", sng_relay->id);
|
||||
if (sng_relay->type == LRY_CT_TCP_CLIENT) {
|
||||
if (!sngss7_test_flag(sng_relay, SNGSS7_RELAY_INIT)) {
|
||||
if (reconfig_all_ckts_for_relay()) {
|
||||
SS7_ERROR("Failed to reconfigure ISUP Ckts!\n");
|
||||
/* we're done....this is very bad! */
|
||||
}
|
||||
if (reconfig_all_ckts_for_relay()) {
|
||||
SS7_ERROR("Failed to reconfigure ISUP Ckts!\n");
|
||||
/* we're done....this is very bad! */
|
||||
}
|
||||
return FTDM_SUCCESS;
|
||||
} else if (sng_relay->type == LRY_CT_TCP_SERVER) {
|
||||
|
@ -84,23 +80,24 @@ ftdm_status_t handle_relay_connect(RyMngmt *sta)
|
|||
/******************************************************************************/
|
||||
ftdm_status_t handle_relay_disconnect_on_error(RyMngmt *sta)
|
||||
{
|
||||
SS7_DEBUG("SS7 relay disconnect on error\n");
|
||||
|
||||
/* check which procId is in error, if it is 1, disable the ckts */
|
||||
if (sta->t.usta.s.ryErrUsta.errPid == 1 ) {
|
||||
/* we've lost the server, bring down the mtp2 links */
|
||||
disble_all_mtp2_sigs_for_relay();
|
||||
|
||||
/* we've lost the server, bring the sig status down on all ckts */
|
||||
disable_all_ckts_for_relay();
|
||||
|
||||
/* we've lost the server, bring down the mtp2 links */
|
||||
disble_all_mtp2_sigs_for_relay();
|
||||
}
|
||||
|
||||
/* check if the channel is a server, means we just lost a MGW */
|
||||
if (g_ftdm_sngss7_data.cfg.relay[sta->t.usta.s.ryErrUsta.errPid].type == LRY_CT_TCP_SERVER) {
|
||||
/* we've lost the client, bring down all mtp3 links for this procId */
|
||||
disable_all_sigs_for_relay(sta->t.usta.s.ryErrUsta.errPid);
|
||||
|
||||
/* we've lost the client, bring down all the ckts for this procId */
|
||||
block_all_ckts_for_relay(sta->t.usta.s.ryErrUsta.errPid);
|
||||
|
||||
/* we've lost the client, bring down all mtp3 links for this procId */
|
||||
disable_all_sigs_for_relay(sta->t.usta.s.ryErrUsta.errPid);
|
||||
}
|
||||
|
||||
return FTDM_SUCCESS;
|
||||
|
@ -110,6 +107,8 @@ ftdm_status_t handle_relay_disconnect_on_error(RyMngmt *sta)
|
|||
ftdm_status_t handle_relay_disconnect_on_down(RyMngmt *sta)
|
||||
{
|
||||
|
||||
SS7_DEBUG("SS7 relay disconnect on down\n");
|
||||
|
||||
/* check if the channel is a server, means we just lost a MGW */
|
||||
if (g_ftdm_sngss7_data.cfg.relay[sta->t.usta.s.ryUpUsta.id].type == LRY_CT_TCP_SERVER) {
|
||||
block_all_ckts_for_relay(sta->t.usta.s.ryUpUsta.id);
|
||||
|
@ -248,7 +247,7 @@ ftdm_status_t block_all_ckts_for_relay(uint32_t procId)
|
|||
if (g_ftdm_sngss7_data.cfg.isupCkt[x].type == SNG_CKT_VOICE) {
|
||||
|
||||
/* send a block request via stack manager */
|
||||
ret = ftmod_ss7_block_isup_ckt(g_ftdm_sngss7_data.cfg.isupCkt[x].id);
|
||||
ret = ftmod_ss7_block_isup_ckt_nowait(g_ftdm_sngss7_data.cfg.isupCkt[x].id);
|
||||
if (ret) {
|
||||
SS7_INFO("Successfully BLOcked CIC:%d(ckt:%d) due to Relay failure\n",
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].cic,
|
||||
|
@ -331,6 +330,7 @@ static ftdm_status_t unblock_all_ckts_for_relay(uint32_t procId)
|
|||
}
|
||||
#endif
|
||||
|
||||
|
||||
/******************************************************************************/
|
||||
/* For Emacs:
|
||||
* Local Variables:
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -49,7 +49,7 @@
|
|||
/******************************************************************************/
|
||||
|
||||
/* PROTOTYPES *****************************************************************/
|
||||
void handle_isup_t35(void *userdata);
|
||||
|
||||
/******************************************************************************/
|
||||
|
||||
/* FUNCTIONS ******************************************************************/
|
||||
|
@ -76,10 +76,13 @@ void handle_isup_t35(void *userdata)
|
|||
/* end the call */
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_CANCEL);
|
||||
|
||||
/* kill t10 if active */
|
||||
/* kill t10 t39 if active */
|
||||
if (sngss7_info->t10.hb_timer_id) {
|
||||
ftdm_sched_cancel_timer (sngss7_info->t10.sched, sngss7_info->t10.hb_timer_id);
|
||||
}
|
||||
if (sngss7_info->t39.hb_timer_id) {
|
||||
ftdm_sched_cancel_timer (sngss7_info->t39.sched, sngss7_info->t39.hb_timer_id);
|
||||
}
|
||||
|
||||
/*unlock*/
|
||||
ftdm_channel_unlock(ftdmchan);
|
||||
|
@ -108,7 +111,43 @@ void handle_isup_t10(void *userdata)
|
|||
|
||||
SS7_FUNC_TRACE_EXIT(__FUNCTION__);
|
||||
}
|
||||
|
||||
|
||||
void handle_isup_t39(void *userdata)
|
||||
{
|
||||
SS7_FUNC_TRACE_ENTER(__FUNCTION__);
|
||||
|
||||
sngss7_timer_data_t *timer = userdata;
|
||||
sngss7_chan_data_t *sngss7_info = timer->sngss7_info;
|
||||
ftdm_channel_t *ftdmchan = sngss7_info->ftdmchan;
|
||||
|
||||
/* now that we have the right channel...put a lock on it so no-one else can use it */
|
||||
ftdm_channel_lock(ftdmchan);
|
||||
|
||||
/* Q.764 2.2.5 Address incomplete (T35 expiry action is hangup with cause 28 according to Table A.1/Q.764) */
|
||||
SS7_ERROR("[Call-Control] Timer 39 expired on CIC = %d\n", sngss7_info->circuit->cic);
|
||||
|
||||
/* set the flag to indicate this hangup is started from the local side */
|
||||
sngss7_set_ckt_flag(sngss7_info, FLAG_LOCAL_REL);
|
||||
|
||||
/* hang up on timer expiry */
|
||||
ftdmchan->caller_data.hangup_cause = FTDM_CAUSE_INVALID_NUMBER_FORMAT;
|
||||
|
||||
/* end the call */
|
||||
ftdm_set_state(ftdmchan, FTDM_CHANNEL_STATE_CANCEL);
|
||||
|
||||
/* kill t10 t35 if active */
|
||||
if (sngss7_info->t10.hb_timer_id) {
|
||||
ftdm_sched_cancel_timer (sngss7_info->t10.sched, sngss7_info->t10.hb_timer_id);
|
||||
}
|
||||
if (sngss7_info->t35.hb_timer_id) {
|
||||
ftdm_sched_cancel_timer (sngss7_info->t35.sched, sngss7_info->t35.hb_timer_id);
|
||||
}
|
||||
|
||||
/*unlock*/
|
||||
ftdm_channel_unlock(ftdmchan);
|
||||
|
||||
SS7_FUNC_TRACE_EXIT(__FUNCTION__);
|
||||
}
|
||||
/******************************************************************************/
|
||||
/* For Emacs:
|
||||
* Local Variables:
|
||||
|
|
|
@ -29,6 +29,12 @@
|
|||
* 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:
|
||||
*
|
||||
* James Zhang <jzhang@sangoma.com>
|
||||
*
|
||||
*/
|
||||
|
||||
/* INCLUDE ********************************************************************/
|
||||
|
@ -124,9 +130,13 @@ typedef struct sng_ccSpan
|
|||
uint32_t clg_nadi;
|
||||
uint32_t cld_nadi;
|
||||
uint32_t rdnis_nadi;
|
||||
uint32_t loc_nadi;
|
||||
uint32_t min_digits;
|
||||
uint8_t itx_auto_reply;
|
||||
uint32_t transparent_iam_max_size;
|
||||
uint8_t transparent_iam;
|
||||
uint8_t cpg_on_progress_media;
|
||||
uint8_t cpg_on_progress;
|
||||
uint8_t itx_auto_reply;
|
||||
uint32_t t3;
|
||||
uint32_t t10;
|
||||
uint32_t t12;
|
||||
|
@ -136,6 +146,7 @@ typedef struct sng_ccSpan
|
|||
uint32_t t16;
|
||||
uint32_t t17;
|
||||
uint32_t t35;
|
||||
uint32_t t39;
|
||||
uint32_t tval;
|
||||
} sng_ccSpan_t;
|
||||
|
||||
|
@ -187,18 +198,20 @@ static int ftmod_ss7_fill_in_self_route(int spc, int linkType, int switchType, i
|
|||
static int ftmod_ss7_fill_in_circuits(sng_span_t *sngSpan);
|
||||
|
||||
static int ftmod_ss7_next_timeslot(char *ch_map, sng_timeslot_t *timeslot);
|
||||
static void ftmod_ss7_set_glare_resolution (const char *method);
|
||||
|
||||
/******************************************************************************/
|
||||
|
||||
/* FUNCTIONS ******************************************************************/
|
||||
|
||||
int ftmod_ss7_parse_xml(ftdm_conf_parameter_t *ftdm_parameters, ftdm_span_t *span)
|
||||
{
|
||||
sng_route_t self_route;
|
||||
sng_span_t sngSpan;
|
||||
int i = 0;
|
||||
const char *var = NULL;
|
||||
const char *val = NULL;
|
||||
ftdm_conf_node_t *ptr = NULL;
|
||||
sng_route_t self_route;
|
||||
sng_span_t sngSpan;
|
||||
|
||||
/* clean out the isup ckt */
|
||||
memset(&sngSpan, 0x0, sizeof(sngSpan));
|
||||
|
@ -206,11 +219,31 @@ int ftmod_ss7_parse_xml(ftdm_conf_parameter_t *ftdm_parameters, ftdm_span_t *spa
|
|||
/* clean out the self route */
|
||||
memset(&self_route, 0x0, sizeof(self_route));
|
||||
|
||||
var = ftdm_parameters[i].var;
|
||||
val = ftdm_parameters[i].val;
|
||||
|
||||
g_ftdm_operating_mode = SNG_SS7_OPR_MODE_ISUP;
|
||||
|
||||
/* confirm that the first parameter is the "operating-mode" */
|
||||
if(!strcasecmp(var, "operating-mode")){
|
||||
if(!strcasecmp(val, "ISUP")) {
|
||||
g_ftdm_operating_mode = SNG_SS7_OPR_MODE_ISUP;
|
||||
}
|
||||
else if(!strcasecmp(val, "M2UA_SG")) {
|
||||
g_ftdm_operating_mode = SNG_SS7_OPR_MODE_M2UA_SG;
|
||||
} else {
|
||||
SS7_DEBUG("Operating mode not specified, defaulting to ISUP\n");
|
||||
}
|
||||
i++;
|
||||
}
|
||||
|
||||
|
||||
|
||||
var = ftdm_parameters[i].var;
|
||||
val = ftdm_parameters[i].val;
|
||||
ptr = (ftdm_conf_node_t *)ftdm_parameters[i].ptr;
|
||||
|
||||
/* confirm that the first parameter is the "confnode" */
|
||||
/* confirm that the 2nd parameter is the "confnode" */
|
||||
if (!strcasecmp(var, "confnode")) {
|
||||
/* parse the confnode and fill in the global libsng_ss7 config structure */
|
||||
if (ftmod_ss7_parse_sng_isup(ptr)) {
|
||||
|
@ -225,28 +258,20 @@ int ftmod_ss7_parse_xml(ftdm_conf_parameter_t *ftdm_parameters, ftdm_span_t *spa
|
|||
}
|
||||
|
||||
i++;
|
||||
while (ftdm_parameters[i].var != NULL) {
|
||||
/**************************************************************************/
|
||||
|
||||
while (ftdm_parameters[i].var != NULL) {
|
||||
var = ftdm_parameters[i].var;
|
||||
val = ftdm_parameters[i].val;
|
||||
|
||||
if (!strcasecmp(var, "dialplan")) {
|
||||
/**********************************************************************/
|
||||
/* don't care for now */
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(var, "context")) {
|
||||
/**********************************************************************/
|
||||
/* don't care for now */
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(var, "ccSpanId")) {
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(var, "span-id") || !strcasecmp(var, "ccSpanId")) {
|
||||
sngSpan.ccSpanId = atoi(val);
|
||||
SS7_DEBUG("Found an ccSpanId = %d\n",sngSpan.ccSpanId);
|
||||
/**********************************************************************/
|
||||
} else {
|
||||
SS7_ERROR("Unknown parameter found =\"%s\"...ignoring it!\n", var);
|
||||
/**********************************************************************/
|
||||
}
|
||||
|
||||
i++;
|
||||
|
@ -255,10 +280,12 @@ int ftmod_ss7_parse_xml(ftdm_conf_parameter_t *ftdm_parameters, ftdm_span_t *spa
|
|||
/* fill the pointer to span into isupCkt */
|
||||
sngSpan.span = span;
|
||||
|
||||
/* setup the circuits structure */
|
||||
if(ftmod_ss7_fill_in_circuits(&sngSpan)) {
|
||||
SS7_ERROR("Failed to fill in circuits structure!\n");
|
||||
goto ftmod_ss7_parse_xml_error;
|
||||
if(SNG_SS7_OPR_MODE_ISUP == g_ftdm_operating_mode){
|
||||
/* setup the circuits structure */
|
||||
if(ftmod_ss7_fill_in_circuits(&sngSpan)) {
|
||||
SS7_ERROR("Failed to fill in circuits structure!\n");
|
||||
goto ftmod_ss7_parse_xml_error;
|
||||
}
|
||||
}
|
||||
|
||||
return FTDM_SUCCESS;
|
||||
|
@ -280,6 +307,11 @@ static int ftmod_ss7_parse_sng_isup(ftdm_conf_node_t *sng_isup)
|
|||
ftdm_conf_node_t *isup_interfaces = NULL;
|
||||
ftdm_conf_node_t *cc_spans = NULL;
|
||||
ftdm_conf_node_t *tmp_node = NULL;
|
||||
ftdm_conf_node_t *nif_ifaces = NULL;
|
||||
ftdm_conf_node_t *m2ua_ifaces = NULL;
|
||||
ftdm_conf_node_t *m2ua_peer_ifaces = NULL;
|
||||
ftdm_conf_node_t *m2ua_clust_ifaces = NULL;
|
||||
ftdm_conf_node_t *sctp_ifaces = NULL;
|
||||
|
||||
/* confirm that we are looking at sng_isup */
|
||||
if (strcasecmp(sng_isup->name, "sng_isup")) {
|
||||
|
@ -385,12 +417,62 @@ static int ftmod_ss7_parse_sng_isup(ftdm_conf_node_t *sng_isup)
|
|||
return FTDM_FAIL;
|
||||
}
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(tmp_node->name, "sng_nif_interfaces")) {
|
||||
/**********************************************************************/
|
||||
if (nif_ifaces == NULL) {
|
||||
nif_ifaces = tmp_node;
|
||||
SS7_DEBUG("Found a \"sng_nif_interfaces\" section!\n");
|
||||
} else {
|
||||
SS7_ERROR("Found a second \"sng_nif_interfaces\" section\n!");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(tmp_node->name, "sng_m2ua_interfaces")) {
|
||||
/**********************************************************************/
|
||||
if (m2ua_ifaces == NULL) {
|
||||
m2ua_ifaces = tmp_node;
|
||||
SS7_DEBUG("Found a \"sng_m2ua_interfaces\" section!\n");
|
||||
} else {
|
||||
SS7_ERROR("Found a second \"sng_m2ua_interfaces\" section\n!");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(tmp_node->name, "sng_m2ua_peer_interfaces")) {
|
||||
/**********************************************************************/
|
||||
if (m2ua_peer_ifaces == NULL) {
|
||||
m2ua_peer_ifaces = tmp_node;
|
||||
SS7_DEBUG("Found a \"sng_m2ua_peer_interfaces\" section!\n");
|
||||
} else {
|
||||
SS7_ERROR("Found a second \"sng_m2ua_peer_interfaces\" section\n!");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(tmp_node->name, "sng_m2ua_cluster_interfaces")) {
|
||||
/**********************************************************************/
|
||||
if (m2ua_clust_ifaces == NULL) {
|
||||
m2ua_clust_ifaces = tmp_node;
|
||||
SS7_DEBUG("Found a \"sng_m2ua_cluster_interfaces\" section!\n");
|
||||
} else {
|
||||
SS7_ERROR("Found a second \"sng_m2ua_peer_interfaces\" section\n!");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(tmp_node->name, "sng_sctp_interfaces")) {
|
||||
/**********************************************************************/
|
||||
if (sctp_ifaces == NULL) {
|
||||
sctp_ifaces = tmp_node;
|
||||
SS7_DEBUG("Found a <sng_sctp_interfaces> section!\n");
|
||||
} else {
|
||||
SS7_ERROR("Found a second <sng_sctp_interfaces> section!\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
/**********************************************************************/
|
||||
} else {
|
||||
/**********************************************************************/
|
||||
SS7_ERROR("\tFound an unknown section \"%s\"!\n", tmp_node->name);
|
||||
return FTDM_FAIL;
|
||||
/**********************************************************************/
|
||||
}
|
||||
}
|
||||
|
||||
/* go to the next sibling */
|
||||
tmp_node = tmp_node->next;
|
||||
|
@ -417,34 +499,92 @@ static int ftmod_ss7_parse_sng_isup(ftdm_conf_node_t *sng_isup)
|
|||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
if (ftmod_ss7_parse_mtp3_links(mtp3_links)) {
|
||||
SS7_ERROR("Failed to parse \"mtp3_links\"!\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
if (ftmod_ss7_parse_mtp_linksets(mtp_linksets)) {
|
||||
SS7_ERROR("Failed to parse \"mtp_linksets\"!\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
switch(g_ftdm_operating_mode)
|
||||
{
|
||||
case SNG_SS7_OPR_MODE_ISUP:
|
||||
{
|
||||
if (mtp3_links && ftmod_ss7_parse_mtp3_links(mtp3_links)) {
|
||||
SS7_ERROR("Failed to parse \"mtp3_links\"!\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
if (ftmod_ss7_parse_mtp_routes(mtp_routes)) {
|
||||
SS7_ERROR("Failed to parse \"mtp_routes\"!\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
if (ftmod_ss7_parse_mtp_linksets(mtp_linksets)) {
|
||||
SS7_ERROR("Failed to parse \"mtp_linksets\"!\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
if (ftmod_ss7_parse_isup_interfaces(isup_interfaces)) {
|
||||
SS7_ERROR("Failed to parse \"isup_interfaces\"!\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
if (ftmod_ss7_parse_mtp_routes(mtp_routes)) {
|
||||
SS7_ERROR("Failed to parse \"mtp_routes\"!\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
if (isup_interfaces && ftmod_ss7_parse_isup_interfaces(isup_interfaces)) {
|
||||
SS7_ERROR("Failed to parse \"isup_interfaces\"!\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
if (cc_spans && ftmod_ss7_parse_cc_spans(cc_spans)) {
|
||||
SS7_ERROR("Failed to parse \"cc_spans\"!\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case SNG_SS7_OPR_MODE_M2UA_SG:
|
||||
{
|
||||
if (ftmod_ss7_parse_sctp_links(sctp_ifaces) != FTDM_SUCCESS) {
|
||||
SS7_ERROR("Failed to parse <sctp_links>!\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
if (nif_ifaces && ftmod_ss7_parse_nif_interfaces(nif_ifaces)) {
|
||||
SS7_ERROR("Failed to parse \"nif_ifaces\"!\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
if (m2ua_ifaces && ftmod_ss7_parse_m2ua_interfaces(m2ua_ifaces)) {
|
||||
SS7_ERROR("Failed to parse \"m2ua_ifaces\"!\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
if (m2ua_peer_ifaces && ftmod_ss7_parse_m2ua_peer_interfaces(m2ua_peer_ifaces)) {
|
||||
SS7_ERROR("Failed to parse \"m2ua_peer_ifaces\"!\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
if (m2ua_clust_ifaces && ftmod_ss7_parse_m2ua_clust_interfaces(m2ua_clust_ifaces)) {
|
||||
SS7_ERROR("Failed to parse \"m2ua_clust_ifaces\"!\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
SS7_ERROR("Invalid operating mode[%d]\n",g_ftdm_operating_mode);
|
||||
break;
|
||||
|
||||
if (ftmod_ss7_parse_cc_spans(cc_spans)) {
|
||||
SS7_ERROR("Failed to parse \"cc_spans\"!\n");
|
||||
return FTDM_FAIL;
|
||||
}
|
||||
|
||||
return FTDM_SUCCESS;
|
||||
}
|
||||
|
||||
static void ftmod_ss7_set_glare_resolution (const char *method)
|
||||
{
|
||||
sng_glare_resolution iMethod=SNGSS7_GLARE_PC;
|
||||
if (!method || (strlen (method) <=0) ) {
|
||||
SS7_ERROR( "Wrong glare resolution parameter, using default. \n" );
|
||||
} else {
|
||||
if (!strcasecmp( method, "PointCode")) {
|
||||
iMethod = SNGSS7_GLARE_PC;
|
||||
} else if (!strcasecmp( method, "Down")) {
|
||||
iMethod = SNGSS7_GLARE_DOWN;
|
||||
} else if (!strcasecmp( method, "Control")) {
|
||||
iMethod = SNGSS7_GLARE_CONTROL;
|
||||
} else {
|
||||
SS7_ERROR( "Wrong glare resolution parameter, using default. \n" );
|
||||
iMethod = SNGSS7_GLARE_PC;
|
||||
}
|
||||
}
|
||||
g_ftdm_sngss7_data.cfg.glareResolution = iMethod;
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
static int ftmod_ss7_parse_sng_gen(ftdm_conf_node_t *sng_gen)
|
||||
{
|
||||
|
@ -452,31 +592,41 @@ static int ftmod_ss7_parse_sng_gen(ftdm_conf_node_t *sng_gen)
|
|||
int num_parms = sng_gen->n_parameters;
|
||||
int i = 0;
|
||||
|
||||
/* Set the transparent_iam_max_size to default value */
|
||||
g_ftdm_sngss7_data.cfg.transparent_iam_max_size=800;
|
||||
g_ftdm_sngss7_data.cfg.force_inr = 0;
|
||||
|
||||
/* extract all the information from the parameters */
|
||||
for (i = 0; i < num_parms; i++) {
|
||||
/**************************************************************************/
|
||||
|
||||
if (!strcasecmp(parm->var, "procId")) {
|
||||
/**********************************************************************/
|
||||
g_ftdm_sngss7_data.cfg.procId = atoi(parm->val);
|
||||
SS7_DEBUG("Found a procId = %d\n", g_ftdm_sngss7_data.cfg.procId);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "license")) {
|
||||
/**********************************************************************/
|
||||
strcpy(g_ftdm_sngss7_data.cfg.license, parm->val);
|
||||
strcpy(g_ftdm_sngss7_data.cfg.signature, parm->val);
|
||||
strcat(g_ftdm_sngss7_data.cfg.signature, ".sig");
|
||||
}
|
||||
else if (!strcasecmp(parm->var, "license")) {
|
||||
ftdm_set_string(g_ftdm_sngss7_data.cfg.license, parm->val);
|
||||
snprintf(g_ftdm_sngss7_data.cfg.signature, sizeof(g_ftdm_sngss7_data.cfg.signature), "%s.sig", parm->val);
|
||||
SS7_DEBUG("Found license file = %s\n", g_ftdm_sngss7_data.cfg.license);
|
||||
SS7_DEBUG("Found signature file = %s\n", g_ftdm_sngss7_data.cfg.signature);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "transparent_iam_max_size")) {
|
||||
}
|
||||
else if (!strcasecmp(parm->var, "transparent_iam_max_size")) {
|
||||
g_ftdm_sngss7_data.cfg.transparent_iam_max_size = atoi(parm->val);
|
||||
SS7_DEBUG("Found a transparent_iam max size = %d\n", g_ftdm_sngss7_data.cfg.transparent_iam_max_size);
|
||||
} else {
|
||||
/**********************************************************************/
|
||||
}
|
||||
else if (!strcasecmp(parm->var, "glare-reso")) {
|
||||
ftmod_ss7_set_glare_resolution (parm->val);
|
||||
SS7_DEBUG("Found glare resolution configuration = %d %s\n", g_ftdm_sngss7_data.cfg.glareResolution, parm->val );
|
||||
}
|
||||
else if (!strcasecmp(parm->var, "force-inr")) {
|
||||
if (ftdm_true(parm->val)) {
|
||||
g_ftdm_sngss7_data.cfg.force_inr = 1;
|
||||
} else {
|
||||
g_ftdm_sngss7_data.cfg.force_inr = 0;
|
||||
}
|
||||
SS7_DEBUG("Found INR force configuration = %s\n", parm->val );
|
||||
}
|
||||
else {
|
||||
SS7_ERROR("Found an invalid parameter \"%s\"!\n", parm->val);
|
||||
return FTDM_FAIL;
|
||||
/**********************************************************************/
|
||||
}
|
||||
|
||||
/* move to the next parmeter */
|
||||
|
@ -1845,12 +1995,14 @@ static int ftmod_ss7_parse_cc_span(ftdm_conf_node_t *cc_span)
|
|||
int flag_clg_nadi = 0;
|
||||
int flag_cld_nadi = 0;
|
||||
int flag_rdnis_nadi = 0;
|
||||
int flag_loc_nadi = 0;
|
||||
int i;
|
||||
int ret;
|
||||
|
||||
/* initalize the ccSpan structure */
|
||||
memset(&sng_ccSpan, 0x0, sizeof(sng_ccSpan));
|
||||
|
||||
|
||||
/* confirm that we are looking at an mtp_link */
|
||||
if (strcasecmp(cc_span->name, "cc_span")) {
|
||||
SS7_ERROR("We're looking at \"%s\"...but we're supposed to be looking at \"cc_span\"!\n",cc_span->name);
|
||||
|
@ -1859,6 +2011,14 @@ static int ftmod_ss7_parse_cc_span(ftdm_conf_node_t *cc_span)
|
|||
SS7_DEBUG("Parsing \"cc_span\"...\n");
|
||||
}
|
||||
|
||||
/* Backward compatible.
|
||||
* If cpg_on_progress_media is not in the config file
|
||||
* default the cpg on progress_media to TRUE */
|
||||
sng_ccSpan.cpg_on_progress_media=FTDM_TRUE;
|
||||
/* If transparent_iam_max_size is not set in cc spans
|
||||
* use the global value */
|
||||
sng_ccSpan.transparent_iam_max_size=g_ftdm_sngss7_data.cfg.transparent_iam_max_size;
|
||||
|
||||
|
||||
for (i = 0; i < num_parms; i++) {
|
||||
/**************************************************************************/
|
||||
|
@ -1904,6 +2064,15 @@ static int ftmod_ss7_parse_cc_span(ftdm_conf_node_t *cc_span)
|
|||
sng_ccSpan.transparent_iam = ftdm_true(parm->val);
|
||||
SS7_DEBUG("Found transparent_iam %d\n", sng_ccSpan.transparent_iam);
|
||||
#endif
|
||||
} else if (!strcasecmp(parm->var, "transparent_iam_max_size")) {
|
||||
sng_ccSpan.transparent_iam_max_size = atoi(parm->val);
|
||||
SS7_DEBUG("Found transparent_iam_max_size %d\n", sng_ccSpan.transparent_iam_max_size);
|
||||
} else if (!strcasecmp(parm->var, "cpg_on_progress_media")) {
|
||||
sng_ccSpan.cpg_on_progress_media = ftdm_true(parm->val);
|
||||
SS7_DEBUG("Found cpg_on_progress_media %d\n", sng_ccSpan.cpg_on_progress_media);
|
||||
} else if (!strcasecmp(parm->var, "cpg_on_progress")) {
|
||||
sng_ccSpan.cpg_on_progress = ftdm_true(parm->val);
|
||||
SS7_DEBUG("Found cpg_on_progress %d\n", sng_ccSpan.cpg_on_progress);
|
||||
} else if (!strcasecmp(parm->var, "cicbase")) {
|
||||
/**********************************************************************/
|
||||
sng_ccSpan.cicbase = atoi(parm->val);
|
||||
|
@ -1946,6 +2115,12 @@ static int ftmod_ss7_parse_cc_span(ftdm_conf_node_t *cc_span)
|
|||
SS7_DEBUG("Invalid parm->value for obci_bita option\n");
|
||||
}
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "loc_nadi")) {
|
||||
/* add location reference number */
|
||||
flag_loc_nadi = 1;
|
||||
sng_ccSpan.loc_nadi = atoi(parm->val);
|
||||
SS7_DEBUG("Found default LOC_NADI parm->value = %d\n", sng_ccSpan.loc_nadi);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "lpa_on_cot")) {
|
||||
/**********************************************************************/
|
||||
if (*parm->val == '1') {
|
||||
|
@ -2002,6 +2177,11 @@ static int ftmod_ss7_parse_cc_span(ftdm_conf_node_t *cc_span)
|
|||
sng_ccSpan.t35 = atoi(parm->val);
|
||||
SS7_DEBUG("Found isup t35 = %d\n",sng_ccSpan.t35);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "isup.t39")) {
|
||||
/**********************************************************************/
|
||||
sng_ccSpan.t39 = atoi(parm->val);
|
||||
SS7_DEBUG("Found isup t39 = %d\n",sng_ccSpan.t39);
|
||||
/**********************************************************************/
|
||||
} else if (!strcasecmp(parm->var, "isup.tval")) {
|
||||
/**********************************************************************/
|
||||
sng_ccSpan.tval = atoi(parm->val);
|
||||
|
@ -2035,6 +2215,11 @@ static int ftmod_ss7_parse_cc_span(ftdm_conf_node_t *cc_span)
|
|||
sng_ccSpan.rdnis_nadi = 0x03;
|
||||
}
|
||||
|
||||
if (!flag_loc_nadi) {
|
||||
/* default the nadi value to national */
|
||||
sng_ccSpan.loc_nadi = 0x03;
|
||||
}
|
||||
|
||||
/* pull up the SSF and Switchtype from the isup interface */
|
||||
sng_ccSpan.ssf = g_ftdm_sngss7_data.cfg.isupIntf[sng_ccSpan.isupInf].ssf;
|
||||
sng_ccSpan.switchType = g_ftdm_sngss7_data.cfg.isupIntf[sng_ccSpan.isupInf].switchType;
|
||||
|
@ -2723,7 +2908,7 @@ static int ftmod_ss7_fill_in_isap(sng_isap_t *sng_isap)
|
|||
if (sng_isap->t1 != 0) {
|
||||
g_ftdm_sngss7_data.cfg.isap[i].t1 = sng_isap->t1;
|
||||
} else {
|
||||
g_ftdm_sngss7_data.cfg.isap[i].t1 = 200;
|
||||
g_ftdm_sngss7_data.cfg.isap[i].t1 = 150;
|
||||
}
|
||||
if (sng_isap->t2 != 0) {
|
||||
g_ftdm_sngss7_data.cfg.isap[i].t2 = sng_isap->t2;
|
||||
|
@ -2738,17 +2923,17 @@ static int ftmod_ss7_fill_in_isap(sng_isap_t *sng_isap)
|
|||
if (sng_isap->t6 != 0) {
|
||||
g_ftdm_sngss7_data.cfg.isap[i].t6 = sng_isap->t6;
|
||||
} else {
|
||||
g_ftdm_sngss7_data.cfg.isap[i].t6 = 200;
|
||||
g_ftdm_sngss7_data.cfg.isap[i].t6 = 600;
|
||||
}
|
||||
if (sng_isap->t7 != 0) {
|
||||
g_ftdm_sngss7_data.cfg.isap[i].t7 = sng_isap->t7;
|
||||
} else {
|
||||
g_ftdm_sngss7_data.cfg.isap[i].t7 = 250;
|
||||
g_ftdm_sngss7_data.cfg.isap[i].t7 = 200;
|
||||
}
|
||||
if (sng_isap->t8 != 0) {
|
||||
g_ftdm_sngss7_data.cfg.isap[i].t8 = sng_isap->t8;
|
||||
} else {
|
||||
g_ftdm_sngss7_data.cfg.isap[i].t8 = 120;
|
||||
g_ftdm_sngss7_data.cfg.isap[i].t8 = 100;
|
||||
}
|
||||
if (sng_isap->t9 != 0) {
|
||||
g_ftdm_sngss7_data.cfg.isap[i].t9 = sng_isap->t9;
|
||||
|
@ -2863,7 +3048,7 @@ static int ftmod_ss7_fill_in_ccSpan(sng_ccSpan_t *ccSpan)
|
|||
(g_ftdm_sngss7_data.cfg.isupCkt[x].chan == count)) {
|
||||
|
||||
/* we are processing a circuit that already exists */
|
||||
SS7_DEBUG("Found an existing circuit %d, ccSpanId=%d, chan%d\n",
|
||||
SS7_DEVEL_DEBUG("Found an existing circuit %d, ccSpanId=%d, chan%d\n",
|
||||
x,
|
||||
ccSpan->id,
|
||||
count);
|
||||
|
@ -2872,7 +3057,7 @@ static int ftmod_ss7_fill_in_ccSpan(sng_ccSpan_t *ccSpan)
|
|||
flag = 1;
|
||||
|
||||
/* not supporting reconfig at this time */
|
||||
SS7_DEBUG("Not supporting ckt reconfig at this time!\n");
|
||||
SS7_DEVEL_DEBUG("Not supporting ckt reconfig at this time!\n");
|
||||
goto move_along;
|
||||
} else {
|
||||
/* this is not the droid you are looking for */
|
||||
|
@ -2885,6 +3070,9 @@ static int ftmod_ss7_fill_in_ccSpan(sng_ccSpan_t *ccSpan)
|
|||
/* prepare the global info sturcture */
|
||||
ss7_info = ftdm_calloc(1, sizeof(sngss7_chan_data_t));
|
||||
ss7_info->ftdmchan = NULL;
|
||||
if (ftdm_queue_create(&ss7_info->event_queue, SNGSS7_CHAN_EVENT_QUEUE_SIZE) != FTDM_SUCCESS) {
|
||||
SS7_CRITICAL("Failed to create ss7 cic event queue\n");
|
||||
}
|
||||
ss7_info->circuit = &g_ftdm_sngss7_data.cfg.isupCkt[x];
|
||||
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].obj = ss7_info;
|
||||
|
@ -2919,12 +3107,16 @@ static int ftmod_ss7_fill_in_ccSpan(sng_ccSpan_t *ccSpan)
|
|||
g_ftdm_sngss7_data.cfg.isupCkt[x].ssf = ccSpan->ssf;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].cld_nadi = ccSpan->cld_nadi;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].clg_nadi = ccSpan->clg_nadi;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].rdnis_nadi = ccSpan->rdnis_nadi;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].rdnis_nadi = ccSpan->rdnis_nadi;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].loc_nadi = ccSpan->loc_nadi;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].options = ccSpan->options;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].switchType = ccSpan->switchType;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].min_digits = ccSpan->min_digits;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].itx_auto_reply = ccSpan->itx_auto_reply;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].transparent_iam = ccSpan->transparent_iam;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].switchType = ccSpan->switchType;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].min_digits = ccSpan->min_digits;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].itx_auto_reply = ccSpan->itx_auto_reply;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].transparent_iam = ccSpan->transparent_iam;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].transparent_iam_max_size = ccSpan->transparent_iam_max_size;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].cpg_on_progress_media = ccSpan->cpg_on_progress_media;
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].cpg_on_progress = ccSpan->cpg_on_progress;
|
||||
|
||||
if (ccSpan->t3 == 0) {
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].t3 = 1200;
|
||||
|
@ -2972,6 +3164,12 @@ static int ftmod_ss7_fill_in_ccSpan(sng_ccSpan_t *ccSpan)
|
|||
} else {
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].t35 = ccSpan->t35;
|
||||
}
|
||||
if (ccSpan->t39 == 0) {
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].t39 = 120;
|
||||
} else {
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].t39 = ccSpan->t39;
|
||||
}
|
||||
|
||||
if (ccSpan->tval == 0) {
|
||||
g_ftdm_sngss7_data.cfg.isupCkt[x].tval = 10;
|
||||
} else {
|
||||
|
@ -3076,6 +3274,13 @@ static int ftmod_ss7_fill_in_circuits(sng_span_t *sngSpan)
|
|||
ss7_info->t10.callback = handle_isup_t10;
|
||||
ss7_info->t10.sngss7_info = ss7_info;
|
||||
|
||||
/* prepare the timer structures */
|
||||
ss7_info->t39.sched = ((sngss7_span_data_t *)(ftdmspan->signal_data))->sched;
|
||||
ss7_info->t39.counter = 1;
|
||||
ss7_info->t39.beat = (isupCkt->t39) * 100; /* beat is in ms, t39 is in 100ms */
|
||||
ss7_info->t39.callback = handle_isup_t39;
|
||||
ss7_info->t39.sngss7_info = ss7_info;
|
||||
|
||||
|
||||
/**************************************************************************/
|
||||
} /* for (i == 1; i < ftdmspan->chan_count; i++) */
|
||||
|
|
|
@ -764,6 +764,28 @@ static FIO_COMMAND_FUNCTION(wanpipe_command)
|
|||
ftdm_log_chan_msg(ftdmchan, FTDM_LOG_DEBUG, "Disabled DTMF events\n");
|
||||
#else
|
||||
return FTDM_NOTIMPL;
|
||||
#endif
|
||||
}
|
||||
break;
|
||||
case FTDM_COMMAND_ENABLE_DTMF_REMOVAL:
|
||||
{
|
||||
#ifdef WP_API_FEATURE_LIBSNG_HWEC
|
||||
int return_code = 0;
|
||||
err = sangoma_hwec_set_hwdtmf_removal(ftdmchan->sockfd, ftdmchan->physical_chan_id, &return_code, 1, 0);
|
||||
if (return_code) {
|
||||
ftdm_log_chan_msg(ftdmchan, FTDM_LOG_ERROR, "Wanpipe failed to Disable HW-DTMF removal\n");
|
||||
}
|
||||
#endif
|
||||
}
|
||||
break;
|
||||
case FTDM_COMMAND_DISABLE_DTMF_REMOVAL:
|
||||
{
|
||||
#ifdef WP_API_FEATURE_LIBSNG_HWEC
|
||||
int return_code = 0;
|
||||
err = sangoma_hwec_set_hwdtmf_removal(ftdmchan->sockfd, ftdmchan->physical_chan_id, &return_code, 0, 0);
|
||||
if (return_code) {
|
||||
ftdm_log_chan_msg(ftdmchan, FTDM_LOG_ERROR, "Wanpipe failed to Disable HW-DTMF removal\n");
|
||||
}
|
||||
#endif
|
||||
}
|
||||
break;
|
||||
|
|
|
@ -40,7 +40,6 @@
|
|||
#ifndef FREETDM_H
|
||||
#define FREETDM_H
|
||||
|
||||
|
||||
#include "ftdm_declare.h"
|
||||
#include "ftdm_call_utils.h"
|
||||
|
||||
|
@ -359,6 +358,7 @@ typedef struct ftdm_caller_data {
|
|||
ftdm_number_t ani; /*!< ANI (Automatic Number Identification) */
|
||||
ftdm_number_t dnis; /*!< DNIS (Dialed Number Identification Service) */
|
||||
ftdm_number_t rdnis; /*!< RDNIS (Redirected Dialed Number Identification Service) */
|
||||
ftdm_number_t loc; /*!< LOC (Location Reference Code) */
|
||||
char aniII[FTDM_DIGITS_LIMIT]; /*! ANI II */
|
||||
uint8_t screen; /*!< Screening */
|
||||
uint8_t pres; /*!< Presentation*/
|
||||
|
@ -733,6 +733,10 @@ typedef enum {
|
|||
/*!< Enable/disable IO stats in the channel */
|
||||
FTDM_COMMAND_SWITCH_IOSTATS = 60,
|
||||
|
||||
/*!< Enable/disable DTMF removal */
|
||||
FTDM_COMMAND_ENABLE_DTMF_REMOVAL = 61,
|
||||
FTDM_COMMAND_DISABLE_DTMF_REMOVAL = 62,
|
||||
|
||||
FTDM_COMMAND_COUNT,
|
||||
} ftdm_command_t;
|
||||
|
||||
|
@ -1366,7 +1370,7 @@ FT_DECLARE(uint32_t) ftdm_group_get_id(const ftdm_group_t *group);
|
|||
* Only use ftdm_channel_close if there is no call (incoming or outgoing) in the channel
|
||||
*
|
||||
* \param span_id The span id the channel belongs to
|
||||
* \param chan_id Channel id of the channel you want to open
|
||||
* \param chan_id Logical channel id of the channel you want to open
|
||||
* \param ftdmchan Pointer to store the channel once is open
|
||||
*
|
||||
* \retval FTDM_SUCCESS success (the channel was found and is available)
|
||||
|
@ -1374,6 +1378,23 @@ FT_DECLARE(uint32_t) ftdm_group_get_id(const ftdm_group_t *group);
|
|||
*/
|
||||
FT_DECLARE(ftdm_status_t) ftdm_channel_open(uint32_t span_id, uint32_t chan_id, ftdm_channel_t **ftdmchan);
|
||||
|
||||
/*!
|
||||
* \brief Open a channel specifying the span id and physical chan id (required before placing a call on the channel)
|
||||
*
|
||||
* \warning Try using ftdm_call_place instead if you plan to place a call after opening the channel
|
||||
*
|
||||
* \note You must call ftdm_channel_close() or ftdm_channel_call_hangup() to release the channel afterwards
|
||||
* Only use ftdm_channel_close if there is no call (incoming or outgoing) in the channel
|
||||
*
|
||||
* \param span_id The span id the channel belongs to
|
||||
* \param chan_id Physical channel id of the channel you want to open
|
||||
* \param ftdmchan Pointer to store the channel once is open
|
||||
*
|
||||
* \retval FTDM_SUCCESS success (the channel was found and is available)
|
||||
* \retval FTDM_FAIL failure (channel was not found or not available)
|
||||
*/
|
||||
FT_DECLARE(ftdm_status_t) ftdm_channel_open_ph(uint32_t span_id, uint32_t chan_id, ftdm_channel_t **ftdmchan);
|
||||
|
||||
/*!
|
||||
* \brief Hunts and opens a channel specifying the span id only
|
||||
*
|
||||
|
@ -1611,6 +1632,17 @@ FT_DECLARE(ftdm_status_t) ftdm_configure_span(ftdm_span_t *span, const char *typ
|
|||
*/
|
||||
FT_DECLARE(ftdm_status_t) ftdm_configure_span_signaling(ftdm_span_t *span, const char *type, fio_signal_cb_t sig_cb, ftdm_conf_parameter_t *parameters);
|
||||
|
||||
/*!
|
||||
* \brief Register callback to listen for incoming events
|
||||
* \note This function should only be used when there is no signalling module
|
||||
* \param span The span to register to
|
||||
* \param sig_cb The callback that the signaling stack will use to notify about events
|
||||
*
|
||||
* \retval FTDM_SUCCESS success
|
||||
* \retval FTDM_FAIL failure
|
||||
*/
|
||||
FT_DECLARE(ftdm_status_t) ftdm_span_register_signal_cb(ftdm_span_t *span, fio_signal_cb_t sig_cb);
|
||||
|
||||
/*!
|
||||
* \brief Start the span signaling (must call ftdm_configure_span_signaling first)
|
||||
*
|
||||
|
@ -1626,7 +1658,6 @@ FT_DECLARE(ftdm_status_t) ftdm_configure_span_signaling(ftdm_span_t *span, const
|
|||
*/
|
||||
FT_DECLARE(ftdm_status_t) ftdm_span_start(ftdm_span_t *span);
|
||||
|
||||
|
||||
/*!
|
||||
* \brief Stop the span signaling (must call ftdm_span_start first)
|
||||
* \note certain signalings (boost signaling) does not support granular span start/stop
|
||||
|
@ -1745,15 +1776,25 @@ FT_DECLARE(ftdm_trunk_type_t) ftdm_span_get_trunk_type(const ftdm_span_t *span);
|
|||
FT_DECLARE(const char *) ftdm_span_get_trunk_type_str(const ftdm_span_t *span);
|
||||
|
||||
/*!
|
||||
* \brief Return the channel identified by the provided id
|
||||
* \brief Return the channel identified by the provided logical id
|
||||
*
|
||||
* \param span The span where the channel belongs
|
||||
* \param chanid The channel id within the span
|
||||
* \param chanid The logical channel id within the span
|
||||
*
|
||||
* \return The channel pointer if found, NULL otherwise
|
||||
*/
|
||||
FT_DECLARE(ftdm_channel_t *) ftdm_span_get_channel(const ftdm_span_t *span, uint32_t chanid);
|
||||
|
||||
/*!
|
||||
* \brief Return the channel identified by the provided physical id
|
||||
*
|
||||
* \param span The span where the channel belongs
|
||||
* \param chanid The physical channel id within the span
|
||||
*
|
||||
* \return The channel pointer if found, NULL otherwise
|
||||
*/
|
||||
FT_DECLARE(ftdm_channel_t *) ftdm_span_get_channel_ph(const ftdm_span_t *span, uint32_t chanid);
|
||||
|
||||
/*! \brief Return the channel count number for the given span */
|
||||
FT_DECLARE(uint32_t) ftdm_span_get_chan_count(const ftdm_span_t *span);
|
||||
|
||||
|
|
|
@ -130,6 +130,9 @@
|
|||
extern "C" {
|
||||
#endif
|
||||
|
||||
#define SPAN_PENDING_CHANS_QUEUE_SIZE 1000
|
||||
#define SPAN_PENDING_SIGNALS_QUEUE_SIZE 1000
|
||||
|
||||
#define GOTO_STATUS(label,st) status = st; goto label ;
|
||||
|
||||
#define ftdm_copy_string(x,y,z) strncpy(x, y, z - 1)
|
||||
|
@ -477,6 +480,7 @@ struct ftdm_channel {
|
|||
int32_t txdrops;
|
||||
int32_t rxdrops;
|
||||
ftdm_usrmsg_t *usrmsg;
|
||||
ftdm_time_t last_state_change_time;
|
||||
};
|
||||
|
||||
struct ftdm_span {
|
||||
|
@ -693,6 +697,9 @@ FT_DECLARE(ftdm_status_t) ftdm_sigmsg_remove_var(ftdm_sigmsg_t *sigmsg, const ch
|
|||
*/
|
||||
FT_DECLARE(ftdm_status_t) ftdm_sigmsg_set_raw_data(ftdm_sigmsg_t *sigmsg, void *data, ftdm_size_t datalen);
|
||||
|
||||
/*! \brief Retrieve a span and channel data structure from a string in the format 'span_id:chan_id'*/
|
||||
FT_DECLARE(ftdm_status_t) ftdm_get_channel_from_string(const char *string_id, ftdm_span_t **out_span, ftdm_channel_t **out_channel);
|
||||
|
||||
/*!
|
||||
\brief Assert condition
|
||||
*/
|
||||
|
|
|
@ -162,6 +162,7 @@ typedef enum {
|
|||
FTDM_SIGTYPE_ANALOG,
|
||||
FTDM_SIGTYPE_SANGOMABOOST,
|
||||
FTDM_SIGTYPE_M3UA,
|
||||
FTDM_SIGTYPE_M2UA,
|
||||
FTDM_SIGTYPE_R2,
|
||||
FTDM_SIGTYPE_SS7,
|
||||
FTDM_SIGTYPE_GSM
|
||||
|
@ -198,6 +199,8 @@ typedef enum {
|
|||
FTDM_SPAN_NON_STOPPABLE = (1 << 13),
|
||||
/* If this flag is set, then this span supports TRANSFER state */
|
||||
FTDM_SPAN_USE_TRANSFER = (1 << 14),
|
||||
/* This is the last flag, no more flags bigger than this */
|
||||
FTDM_SPAN_MAX_FLAG = (1 << 15),
|
||||
} ftdm_span_flag_t;
|
||||
|
||||
/*! \brief Channel supported features */
|
||||
|
@ -266,6 +269,12 @@ typedef enum {
|
|||
#define FTDM_CHANNEL_BLOCKING (1ULL << 35)
|
||||
/*!< Media is digital */
|
||||
#define FTDM_CHANNEL_DIGITAL_MEDIA (1ULL << 36)
|
||||
/*!< Native signaling bridge is enabled */
|
||||
#define FTDM_CHANNEL_NATIVE_SIGBRIDGE (1ULL << 37)
|
||||
|
||||
/*!< This no more flags after this flag */
|
||||
#define FTDM_CHANNEL_MAX_FLAG (1ULL << 38)
|
||||
/*!<When adding a new flag, need to update ftdm_io.c:channel_flag_strs */
|
||||
|
||||
#include "ftdm_state.h"
|
||||
|
||||
|
|
|
@ -18,7 +18,7 @@ a separate process, and your application communicates with it through pipes or
|
|||
sockets.
|
||||
|
||||
This implementation of G.722.1 is adapted from the reference source code
|
||||
provided by Polycom. Polycom has given its concent for this library to be
|
||||
provided by Polycom. Polycom has given its consent for this library to be
|
||||
distributed as source code, either on its own or as part of a larger package
|
||||
which they have licenced under their royalty free licencing scheme.
|
||||
|
||||
|
|
|
@ -0,0 +1,6 @@
|
|||
%{
|
||||
#include "scgi.h"
|
||||
#include "scgi_oop.h"
|
||||
%}
|
||||
|
||||
%include "scgi_oop.h"
|
|
@ -0,0 +1,51 @@
|
|||
PWD=$(shell pwd)
|
||||
INCS=-I$(PWD)/src/include
|
||||
DEBUG=-g -ggdb
|
||||
BASE_FLAGS=$(INCS) $(DEBUG) -fPIC
|
||||
PICKY=-O2
|
||||
CFLAGS=$(BASE_FLAGS) $(PICKY)
|
||||
CXXFLAGS=$(BASE_FLAGS)
|
||||
MYLIB=libscgi.a
|
||||
LIBS=
|
||||
LDFLAGS=-L.
|
||||
OBJS=src/scgi.o
|
||||
SRC=src/scgi.c src/scgi_oop.cpp
|
||||
HEADERS=src/include/scgi.h src/include/scgi_oop.h
|
||||
SOLINK=-shared -Xlinker -x
|
||||
|
||||
# comment the next line to disable c++ (no swig mods for you then)
|
||||
OBJS += src/scgi_oop.o
|
||||
|
||||
all: $(MYLIB) testclient testserver
|
||||
|
||||
$(MYLIB): $(OBJS) $(HEADERS) $(SRC)
|
||||
ar rcs $(MYLIB) $(OBJS)
|
||||
ranlib $(MYLIB)
|
||||
|
||||
%.o: %.c $(HEADERS)
|
||||
$(CC) $(CC_CFLAGS) $(CFLAGS) -c $< -o $@
|
||||
|
||||
%.o: %.cpp $(HEADERS)
|
||||
$(CXX) $(CXX_CFLAGS) $(CXXFLAGS) -c $< -o $@
|
||||
|
||||
testclient: $(MYLIB) testclient.c
|
||||
$(CC) $(CC_CFLAGS) $(CFLAGS) testclient.c -o testclient -lscgi $(LDFLAGS) $(LIBS)
|
||||
|
||||
testserver: $(MYLIB) testserver.c
|
||||
$(CC) $(CC_CFLAGS) $(CFLAGS) testserver.c -o testserver -lscgi $(LDFLAGS) $(LIBS)
|
||||
|
||||
clean:
|
||||
rm -f *.o src/*.o libscgi.a *~ src/*~ src/include/*~ testclient testserver
|
||||
$(MAKE) -C perl clean
|
||||
|
||||
reswig: swigclean
|
||||
$(MAKE) -C perl reswig
|
||||
|
||||
swigclean: clean
|
||||
$(MAKE) -C perl swigclean
|
||||
|
||||
perlmod: $(MYLIB)
|
||||
$(MAKE) MYLIB="../$(MYLIB)" SOLINK="$(SOLINK)" CFLAGS="$(CFLAGS)" CXXFLAGS="$(CXXFLAGS)" CXX_CFLAGS="$(CXX_CFLAGS)" -C perl
|
||||
|
||||
perlmod-install: perlmod
|
||||
$(MAKE) -C perl install
|
|
@ -0,0 +1,105 @@
|
|||
# This file was automatically generated by SWIG (http://www.swig.org).
|
||||
# Version 1.3.35
|
||||
#
|
||||
# Don't modify this file, modify the SWIG interface instead.
|
||||
|
||||
package FSSCGI;
|
||||
require Exporter;
|
||||
require DynaLoader;
|
||||
@ISA = qw(Exporter DynaLoader);
|
||||
package FSSCGIc;
|
||||
bootstrap FSSCGI;
|
||||
package FSSCGI;
|
||||
@EXPORT = qw( );
|
||||
|
||||
# ---------- BASE METHODS -------------
|
||||
|
||||
package FSSCGI;
|
||||
|
||||
sub TIEHASH {
|
||||
my ($classname,$obj) = @_;
|
||||
return bless $obj, $classname;
|
||||
}
|
||||
|
||||
sub CLEAR { }
|
||||
|
||||
sub FIRSTKEY { }
|
||||
|
||||
sub NEXTKEY { }
|
||||
|
||||
sub FETCH {
|
||||
my ($self,$field) = @_;
|
||||
my $member_func = "swig_${field}_get";
|
||||
$self->$member_func();
|
||||
}
|
||||
|
||||
sub STORE {
|
||||
my ($self,$field,$newval) = @_;
|
||||
my $member_func = "swig_${field}_set";
|
||||
$self->$member_func($newval);
|
||||
}
|
||||
|
||||
sub this {
|
||||
my $ptr = shift;
|
||||
return tied(%$ptr);
|
||||
}
|
||||
|
||||
|
||||
# ------- FUNCTION WRAPPERS --------
|
||||
|
||||
package FSSCGI;
|
||||
|
||||
|
||||
############# Class : FSSCGI::SCGIhandle ##############
|
||||
|
||||
package FSSCGI::SCGIhandle;
|
||||
use vars qw(@ISA %OWNER %ITERATORS %BLESSEDMEMBERS);
|
||||
@ISA = qw( FSSCGI );
|
||||
%OWNER = ();
|
||||
%ITERATORS = ();
|
||||
sub new {
|
||||
my $pkg = shift;
|
||||
my $self = FSSCGIc::new_SCGIhandle(@_);
|
||||
bless $self, $pkg if defined($self);
|
||||
}
|
||||
|
||||
sub DESTROY {
|
||||
return unless $_[0]->isa('HASH');
|
||||
my $self = tied(%{$_[0]});
|
||||
return unless defined $self;
|
||||
delete $ITERATORS{$self};
|
||||
if (exists $OWNER{$self}) {
|
||||
FSSCGIc::delete_SCGIhandle($self);
|
||||
delete $OWNER{$self};
|
||||
}
|
||||
}
|
||||
|
||||
*connected = *FSSCGIc::SCGIhandle_connected;
|
||||
*socketDescriptor = *FSSCGIc::SCGIhandle_socketDescriptor;
|
||||
*disconnect = *FSSCGIc::SCGIhandle_disconnect;
|
||||
*addParam = *FSSCGIc::SCGIhandle_addParam;
|
||||
*addBody = *FSSCGIc::SCGIhandle_addBody;
|
||||
*getBody = *FSSCGIc::SCGIhandle_getBody;
|
||||
*getParam = *FSSCGIc::SCGIhandle_getParam;
|
||||
*sendRequest = *FSSCGIc::SCGIhandle_sendRequest;
|
||||
*respond = *FSSCGIc::SCGIhandle_respond;
|
||||
*bind = *FSSCGIc::SCGIhandle_bind;
|
||||
*accept = *FSSCGIc::SCGIhandle_accept;
|
||||
sub DISOWN {
|
||||
my $self = shift;
|
||||
my $ptr = tied(%$self);
|
||||
delete $OWNER{$ptr};
|
||||
}
|
||||
|
||||
sub ACQUIRE {
|
||||
my $self = shift;
|
||||
my $ptr = tied(%$self);
|
||||
$OWNER{$ptr} = 1;
|
||||
}
|
||||
|
||||
|
||||
# ------- VARIABLE STUBS --------
|
||||
|
||||
package FSSCGI;
|
||||
|
||||
1;
|
|
@ -0,0 +1,38 @@
|
|||
PERL=$(shell which perl)
|
||||
PERL_SITEDIR=$(shell perl -MConfig -e 'print $$Config{sitelibexp}')
|
||||
PERL_LIBDIR=-L$(shell perl -MConfig -e 'print $$Config{archlib}')/CORE
|
||||
PERL_LIBS=$(shell perl -MConfig -e 'print $$Config{libs}')
|
||||
LOCAL_CFLAGS=-w -DMULTIPLICITY $(shell $(PERL) -MExtUtils::Embed -e ccopts) -DEMBED_PERL
|
||||
LOCAL_LDFLAGS=$(shell $(PERL) -MExtUtils::Embed -e ldopts) $(shell $(PERL) -MConfig -e 'print $$Config{libs}')
|
||||
GCC_WARNING_JUNK=-w
|
||||
PERL_INC=$(shell $(PERL) -MExtUtils::Embed -e perl_inc)
|
||||
all: FSSCGI.so
|
||||
|
||||
scgi_wrap.cpp:
|
||||
swig -module FSSCGI -shadow -perl5 -c++ -DMULTIPLICITY -I../src/include -o scgi_wrap.cpp ../FSSCGI.i
|
||||
|
||||
perlxsi.c:
|
||||
$(PERL) -MExtUtils::Embed -e xsinit -- -o perlxsi.c
|
||||
|
||||
perlxsi.o: perlxsi.c
|
||||
$(CC) $(CC_CFLAGS) $(CFLAGS) $(LOCAL_CFLAGS) -c perlxsi.c -o perlxsi.o
|
||||
|
||||
scgi_wrap.o: scgi_wrap.cpp
|
||||
$(CXX) $(CXX_CFLAGS) $(CXXFLAGS) $(GCC_WARNING_JUNK) $(PERL_INC) -c scgi_wrap.cpp -o scgi_wrap.o
|
||||
|
||||
FSSCGI.so: scgi_wrap.o perlxsi.o
|
||||
$(CXX) $(SOLINK) scgi_wrap.o perlxsi.o $(MYLIB) $(LOCAL_LDFLAGS) -o FSSCGI.so -L. $(LIBS)
|
||||
|
||||
clean:
|
||||
rm -f *.o *.so *~
|
||||
|
||||
swigclean:
|
||||
rm -f scgi_wrap.* FSSCGI.so FSSCGI.pm perlxsi.*
|
||||
|
||||
reswig: swigclean scgi_wrap.cpp perlxsi.c
|
||||
|
||||
install: FSSCGI.so
|
||||
install -m 755 FSSCGI.so $(PERL_SITEDIR)
|
||||
install -m 755 FSSCGI.pm $(PERL_SITEDIR)
|
||||
install -d -m 755 FSSCGI $(PERL_SITEDIR)/FSSCGI
|
||||
install -m 755 FSSCGI/* $(PERL_SITEDIR)/FSSCGI
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,16 @@
|
|||
#include <EXTERN.h>
|
||||
#include <perl.h>
|
||||
|
||||
EXTERN_C void xs_init (pTHX);
|
||||
|
||||
EXTERN_C void boot_DynaLoader (pTHX_ CV* cv);
|
||||
|
||||
EXTERN_C void
|
||||
xs_init(pTHX)
|
||||
{
|
||||
char *file = __FILE__;
|
||||
dXSUB_SYS;
|
||||
|
||||
/* DynaLoader is a special case */
|
||||
newXS("DynaLoader::boot_DynaLoader", boot_DynaLoader, file);
|
||||
}
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,19 @@
|
|||
use FSSCGI;
|
||||
|
||||
|
||||
my $handle = new FSSCGI::SCGIhandle();
|
||||
|
||||
$handle->addParam( "REQUEST_METHOD", "POST");
|
||||
$handle->addParam( "REQUEST_URI", "/deepthought");
|
||||
$handle->addParam( "TESTING", "TRUE");
|
||||
$handle->addParam( "TESTING", "TRUE");
|
||||
$handle->addBody("What is the answer to life?");
|
||||
|
||||
|
||||
|
||||
if ((my $response = $handle->sendRequest("127.0.0.1", 7777, 10000))) {
|
||||
print "RESP[$response]\n";
|
||||
} else {
|
||||
print "ERROR!\n";
|
||||
}
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
use FSSCGI;
|
||||
|
||||
|
||||
my $handle = new FSSCGI::SCGIhandle();
|
||||
|
||||
if ($handle->bind("127.0.0.1", 7777)) {
|
||||
|
||||
while($handle->accept()) {
|
||||
print "REQ: " . $handle->getBody(). "\n\n";
|
||||
$handle->respond("W00t!!!!!!\n");
|
||||
}
|
||||
|
||||
print "DONE\n";
|
||||
|
||||
} else {
|
||||
print "FAIL\n";
|
||||
}
|
|
@ -0,0 +1,101 @@
|
|||
SCGI: A Simple Common Gateway Interface alternative
|
||||
Neil Schemenauer <nas@python.ca>
|
||||
2008-06-23
|
||||
|
||||
1. Introduction
|
||||
|
||||
The SCGI protocol is a replacement for the Common Gateway Interface
|
||||
(CGI) protocol. It is a standard for applications to interface with
|
||||
HTTP servers. It is similar to FastCGI but is designed to be easier
|
||||
to implement.
|
||||
|
||||
In this document, a string of 8-bit bytes may be written in two
|
||||
different forms: as a series of hexadecimal numbers between angle
|
||||
brackets, or as a sequence of ASCII characters between double quotes.
|
||||
For example, <68 65 6c 6c 6f 20 77 6f 72 6c 64 21> is a string of
|
||||
length 12; it is the same as the string "hello world!". Note that
|
||||
these notations are part of this document, not part of the protocol.
|
||||
|
||||
|
||||
2. Protocol
|
||||
|
||||
The client connects to a SCGI server over a reliable stream protocol
|
||||
allowing transmission of 8-bit bytes. The client begins by sending a
|
||||
request. See section 3 for the format of the request. When the SCGI
|
||||
server sees the end of the request it sends back a response and closes
|
||||
the connection. The format of the response is not specified by this
|
||||
protocol.
|
||||
|
||||
|
||||
3. Request Format
|
||||
|
||||
A request consists of a number of headers and a body. The format of
|
||||
the headers is:
|
||||
|
||||
headers ::= header*
|
||||
header ::= name NUL value NUL
|
||||
name ::= notnull+
|
||||
value ::= notnull*
|
||||
notnull ::= <01> | <02> | <03> | ... | <ff>
|
||||
NUL = <00>
|
||||
|
||||
Duplicate names are not allowed in the headers. The first header
|
||||
must have the name "CONTENT_LENGTH" and a value that is a nonempty
|
||||
sequence of ASCII digits giving the of the body length in decimal.
|
||||
The "CONTENT_LENGTH" header must always be present, even if its
|
||||
value is "0". There must also always be a header with the name
|
||||
"SCGI" and a value of "1". In order to facilitate the transition
|
||||
from CGI, standard CGI environment variables should be provided as
|
||||
SCGI headers.
|
||||
|
||||
The headers are sent encoded as a netstring. Netstring encoding is
|
||||
explained in section 4. The body is sent following the headers and
|
||||
its length is specified by the "CONTENT_LENGTH" header.
|
||||
|
||||
|
||||
4. Netstrings
|
||||
|
||||
Any string of 8-bit bytes may be encoded as [len]":"[string]",". Here
|
||||
[string] is the string and [len] is a nonempty sequence of ASCII
|
||||
digits giving the length of [string] in decimal. The ASCII digits are
|
||||
<30> for 0, <31> for 1, and so on up through <39> for 9. Extra zeros
|
||||
at the front of [len] are prohibited: [len] begins with <30> exactly
|
||||
when [string] is empty.
|
||||
|
||||
For example, the string "hello world!" is encoded as <31 32 3a 68 65
|
||||
6c 6c 6f 20 77 6f 72 6c 64 21 2c>, i.e., "12:hello world!,". The empty
|
||||
string is encoded as "0:,".
|
||||
|
||||
[len]":"[string]"," is called a netstring. [string] is called the
|
||||
interpretation of the netstring.
|
||||
|
||||
|
||||
5. Example
|
||||
|
||||
The web server (a SCGI client) opens a connection and sends the
|
||||
concatenation of the following strings:
|
||||
|
||||
"70:"
|
||||
"CONTENT_LENGTH" <00> "27" <00>
|
||||
"SCGI" <00> "1" <00>
|
||||
"REQUEST_METHOD" <00> "POST" <00>
|
||||
"REQUEST_URI" <00> "/deepthought" <00>
|
||||
","
|
||||
"What is the answer to life?"
|
||||
|
||||
The SCGI server sends the following response:
|
||||
|
||||
"Status: 200 OK" <0d 0a>
|
||||
"Content-Type: text/plain" <0d 0a>
|
||||
"" <0d 0a>
|
||||
"42"
|
||||
|
||||
The SCGI server closes the connection.
|
||||
|
||||
|
||||
6. Copyright
|
||||
|
||||
This document has been placed in the public domain.
|
||||
|
||||
|
||||
/* vim: set ai tw=74 et sw=4 sts=4: */
|
|
@ -0,0 +1,220 @@
|
|||
/*
|
||||
* Copyright (c) 2012-2013, Anthony Minessale II
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
*
|
||||
* * Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
*
|
||||
* * Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
*
|
||||
* * Neither the name of the original author; nor the names of any contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
|
||||
* OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
|
||||
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
|
||||
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
||||
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#ifndef _SCGI_H_
|
||||
#define _SCGI_H_
|
||||
|
||||
#include <stdarg.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif /* defined(__cplusplus) */
|
||||
#if EMACS_BUG
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef _MSC_VER
|
||||
#define FD_SETSIZE 8192
|
||||
#define SCGI_USE_SELECT
|
||||
#else
|
||||
#define SCGI_USE_POLL
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
#ifdef SCGI_USE_POLL
|
||||
#include <poll.h>
|
||||
#endif
|
||||
|
||||
#ifdef WIN32
|
||||
#include <winsock2.h>
|
||||
#include <windows.h>
|
||||
typedef SOCKET scgi_socket_t;
|
||||
typedef unsigned __int64 uint64_t;
|
||||
typedef unsigned __int32 uint32_t;
|
||||
typedef unsigned __int16 uint16_t;
|
||||
typedef unsigned __int8 uint8_t;
|
||||
typedef __int64 int64_t;
|
||||
typedef __int32 int32_t;
|
||||
typedef __int16 int16_t;
|
||||
typedef __int8 int8_t;
|
||||
typedef intptr_t scgi_ssize_t;
|
||||
typedef int scgi_filehandle_t;
|
||||
#define SCGI_SOCK_INVALID INVALID_SOCKET
|
||||
#define strerror_r(num, buf, size) strerror_s(buf, size, num)
|
||||
#if defined(SCGI_DECLARE_STATIC)
|
||||
#define SCGI_DECLARE(type) type __stdcall
|
||||
#define SCGI_DECLARE_NONSTD(type) type __cdecl
|
||||
#define SCGI_DECLARE_DATA
|
||||
#elif defined(SCGI_EXPORTS)
|
||||
#define SCGI_DECLARE(type) __declspec(dllexport) type __stdcall
|
||||
#define SCGI_DECLARE_NONSTD(type) __declspec(dllexport) type __cdecl
|
||||
#define SCGI_DECLARE_DATA __declspec(dllexport)
|
||||
#else
|
||||
#define SCGI_DECLARE(type) __declspec(dllimport) type __stdcall
|
||||
#define SCGI_DECLARE_NONSTD(type) __declspec(dllimport) type __cdecl
|
||||
#define SCGI_DECLARE_DATA __declspec(dllimport)
|
||||
#endif
|
||||
#else
|
||||
#define SCGI_DECLARE(type) type
|
||||
#define SCGI_DECLARE_NONSTD(type) type
|
||||
#define SCGI_DECLARE_DATA
|
||||
#include <stdint.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <stdarg.h>
|
||||
#include <sys/socket.h>
|
||||
#include <netinet/in.h>
|
||||
#include <netdb.h>
|
||||
#define SCGI_SOCK_INVALID -1
|
||||
typedef int scgi_socket_t;
|
||||
typedef ssize_t scgi_ssize_t;
|
||||
typedef int scgi_filehandle_t;
|
||||
#endif
|
||||
|
||||
|
||||
#include <time.h>
|
||||
#ifndef WIN32
|
||||
#include <sys/time.h>
|
||||
#endif
|
||||
|
||||
#include <stdarg.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#ifndef WIN32
|
||||
#include <sys/types.h>
|
||||
#include <sys/select.h>
|
||||
#include <netinet/tcp.h>
|
||||
#include <sys/signal.h>
|
||||
#include <unistd.h>
|
||||
#include <ctype.h>
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_STRINGS_H
|
||||
#include <strings.h>
|
||||
#endif
|
||||
#include <assert.h>
|
||||
|
||||
#if (_MSC_VER >= 1400) // VC8+
|
||||
#define scgi_assert(expr) assert(expr);__analysis_assume( expr )
|
||||
#endif
|
||||
|
||||
#ifndef scgi_assert
|
||||
#define scgi_assert(_x) assert(_x)
|
||||
#endif
|
||||
|
||||
#define scgi_safe_free(_x) if (_x) free(_x); _x = NULL
|
||||
#define scgi_strlen_zero(s) (!s || *(s) == '\0')
|
||||
#define scgi_strlen_zero_buf(s) (*(s) == '\0')
|
||||
#define end_of(_s) *(*_s == '\0' ? _s : _s + strlen(_s) - 1)
|
||||
#define end_of_p(_s) (*_s == '\0' ? _s : _s + strlen(_s) - 1)
|
||||
|
||||
typedef enum {
|
||||
SCGI_POLL_READ = (1 << 0),
|
||||
SCGI_POLL_WRITE = (1 << 1),
|
||||
SCGI_POLL_ERROR = (1 << 2)
|
||||
} scgi_poll_t;
|
||||
|
||||
|
||||
typedef struct scgi_param_s {
|
||||
char *name;
|
||||
char *value;
|
||||
struct scgi_param_s *next;
|
||||
} scgi_param_t;
|
||||
|
||||
typedef struct scgi_handle_s {
|
||||
scgi_param_t *params;
|
||||
char *body;
|
||||
struct sockaddr_in sockaddr;
|
||||
struct hostent hostent;
|
||||
char hostbuf[256];
|
||||
scgi_socket_t sock;
|
||||
char err[256];
|
||||
int errnum;
|
||||
int connected;
|
||||
struct sockaddr_in addr;
|
||||
int destroyed;
|
||||
} scgi_handle_t;
|
||||
|
||||
|
||||
typedef int16_t scgi_port_t;
|
||||
typedef size_t scgi_size_t;
|
||||
|
||||
typedef enum {
|
||||
SCGI_SUCCESS,
|
||||
SCGI_FAIL,
|
||||
SCGI_BREAK,
|
||||
SCGI_DISCONNECTED,
|
||||
SCGI_GENERR
|
||||
} scgi_status_t;
|
||||
|
||||
typedef void (*scgi_listen_callback_t)(scgi_socket_t server_sock, scgi_socket_t *client_sock, struct sockaddr_in *addr);
|
||||
|
||||
SCGI_DECLARE(scgi_status_t) scgi_connect(scgi_handle_t *handle, const char *host, scgi_port_t port, uint32_t timeout);
|
||||
SCGI_DECLARE(scgi_status_t) scgi_disconnect(scgi_handle_t *handle);
|
||||
SCGI_DECLARE(scgi_status_t) scgi_parse(scgi_socket_t sock, scgi_handle_t *handle);
|
||||
SCGI_DECLARE(int) scgi_wait_sock(scgi_socket_t sock, uint32_t ms, scgi_poll_t flags);
|
||||
SCGI_DECLARE(ssize_t) scgi_recv(scgi_handle_t *handle, unsigned char *buf, size_t buflen);
|
||||
SCGI_DECLARE(scgi_status_t) scgi_send_request(scgi_handle_t *handle);
|
||||
SCGI_DECLARE(scgi_status_t) scgi_add_param(scgi_handle_t *handle, const char *name, const char *value);
|
||||
SCGI_DECLARE(scgi_status_t) scgi_add_body(scgi_handle_t *handle, const char *value);
|
||||
SCGI_DECLARE(size_t) scgi_build_message(scgi_handle_t *handle, char **buffer);
|
||||
SCGI_DECLARE(scgi_status_t) scgi_destroy_params(scgi_handle_t *handle);
|
||||
SCGI_DECLARE(scgi_status_t) scgi_listen(const char *host, scgi_port_t port, scgi_listen_callback_t callback);
|
||||
SCGI_DECLARE(const char *) scgi_get_body(scgi_handle_t *handle);
|
||||
SCGI_DECLARE(const char *) scgi_get_param(scgi_handle_t *handle, const char *name);
|
||||
SCGI_DECLARE(scgi_status_t) scgi_bind(const char *host, scgi_port_t port, scgi_socket_t *socketp);
|
||||
SCGI_DECLARE(scgi_status_t) scgi_accept(scgi_socket_t server_sock, scgi_socket_t *client_sock_p, struct sockaddr_in *echoClntAddr);
|
||||
|
||||
#ifndef WIN32
|
||||
#define closesocket(x) close(x)
|
||||
#endif
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif /* defined(__cplusplus) */
|
||||
|
||||
|
||||
#endif /* defined(_SCGI_H_) */
|
||||
|
||||
/* For Emacs:
|
||||
* Local Variables:
|
||||
* mode:c
|
||||
* indent-tabs-mode:t
|
||||
* tab-width:4
|
||||
* c-basic-offset:4
|
||||
* End:
|
||||
* For VIM:
|
||||
* vim:set softtabstop=4 shiftwidth=4 tabstop=4:
|
||||
*/
|
|
@ -0,0 +1,78 @@
|
|||
/*
|
||||
* Copyright (c) 2007-2012, Anthony Minessale II
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
*
|
||||
* * Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
*
|
||||
* * Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
*
|
||||
* * Neither the name of the original author; nor the names of any contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
|
||||
* OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
|
||||
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
|
||||
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
||||
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#ifndef _SCGI_OOP_H_
|
||||
#define _SCGI_OOP_H_
|
||||
#include <scgi.h>
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#define this_check(x) do { if (!this) { scgi_log(SCGI_LOG_ERROR, "object is not initalized\n"); return x;}} while(0)
|
||||
#define this_check_void() do { if (!this) { scgi_log(SCGI_LOG_ERROR, "object is not initalized\n"); return;}} while(0)
|
||||
|
||||
|
||||
|
||||
class SCGIhandle {
|
||||
private:
|
||||
scgi_socket_t server_sock;
|
||||
scgi_handle_t handle;
|
||||
unsigned char buf[65536];
|
||||
char *data_buf;
|
||||
int buflen;
|
||||
int bufsize;
|
||||
public:
|
||||
SCGIhandle();
|
||||
virtual ~SCGIhandle();
|
||||
int connected();
|
||||
int socketDescriptor();
|
||||
int disconnect(void);
|
||||
int addParam(const char *name, const char *value);
|
||||
int addBody(const char *value);
|
||||
char *getBody();
|
||||
char *getParam(const char *name);
|
||||
char *sendRequest(const char *host, int port, int timeout);
|
||||
int respond(char *msg);
|
||||
int bind(const char *host, int port);
|
||||
int accept(void);
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -0,0 +1,739 @@
|
|||
/*
|
||||
* Copyright (c) 2012-2013, Anthony Minessale II
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
*
|
||||
* * Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
*
|
||||
* * Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
*
|
||||
* * Neither the name of the original author; nor the names of any contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
||||
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
|
||||
* OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
|
||||
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
|
||||
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
||||
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
||||
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include <scgi.h>
|
||||
|
||||
#ifndef WIN32
|
||||
#include <fcntl.h>
|
||||
#include <errno.h>
|
||||
#else
|
||||
#pragma warning (disable:6386)
|
||||
/* These warnings need to be ignored warning in sdk header */
|
||||
#include <Ws2tcpip.h>
|
||||
#include <windows.h>
|
||||
#ifndef errno
|
||||
#define errno WSAGetLastError()
|
||||
#endif
|
||||
#ifndef EINTR
|
||||
#define EINTR WSAEINTR
|
||||
#endif
|
||||
#pragma warning (default:6386)
|
||||
#endif
|
||||
|
||||
static scgi_status_t scgi_push_param(scgi_handle_t *handle, const char *name, const char *value);
|
||||
|
||||
static int sock_setup(scgi_handle_t *handle)
|
||||
{
|
||||
|
||||
if (handle->sock == SCGI_SOCK_INVALID) {
|
||||
return SCGI_FAIL;
|
||||
}
|
||||
|
||||
#ifdef WIN32
|
||||
{
|
||||
BOOL bOptVal = TRUE;
|
||||
int bOptLen = sizeof(BOOL);
|
||||
setsockopt(handle->sock, IPPROTO_TCP, TCP_NODELAY, (const char *)&bOptVal, bOptLen);
|
||||
}
|
||||
#else
|
||||
{
|
||||
int x = 1;
|
||||
setsockopt(handle->sock, IPPROTO_TCP, TCP_NODELAY, &x, sizeof(x));
|
||||
}
|
||||
#endif
|
||||
|
||||
return SCGI_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
SCGI_DECLARE(size_t) scgi_build_message(scgi_handle_t *handle, char **bufferp)
|
||||
{
|
||||
scgi_param_t *pp;
|
||||
size_t len = 0, plen = 0, ctlen = 0;
|
||||
char *s, *bp;
|
||||
char *buffer = NULL;
|
||||
char tmp[128] = "";
|
||||
|
||||
scgi_push_param(handle, "SCGI", "1");
|
||||
|
||||
if (handle->body) {
|
||||
ctlen = strlen(handle->body);
|
||||
}
|
||||
|
||||
snprintf(tmp, sizeof(tmp), "%d", (int)ctlen);
|
||||
|
||||
scgi_push_param(handle, "CONTENT_LENGTH", tmp);
|
||||
|
||||
|
||||
for(pp = handle->params; pp; pp = pp->next) {
|
||||
plen += (strlen(pp->name) + strlen(pp->value) + 2);
|
||||
}
|
||||
|
||||
snprintf(tmp, sizeof(tmp), "%d", (int) (plen + ctlen));
|
||||
|
||||
len = plen + ctlen + strlen(tmp) + 2;
|
||||
|
||||
buffer = malloc(len);
|
||||
memset(buffer, 0, len);
|
||||
|
||||
snprintf(buffer, len, "%d:", (int)plen);
|
||||
bp = buffer + strlen(buffer);
|
||||
|
||||
for(pp = handle->params; pp; pp = pp->next) {
|
||||
|
||||
for (s = pp->name; s && *s; s++) {
|
||||
*bp++ = *s;
|
||||
}
|
||||
|
||||
*bp++ = '\0';
|
||||
|
||||
for (s = pp->value; s && *s; s++) {
|
||||
*bp++ = *s;
|
||||
}
|
||||
|
||||
*bp++ = '\0';
|
||||
}
|
||||
|
||||
*bp++ = ',';
|
||||
|
||||
if (handle->body) {
|
||||
for (s = handle->body; s && *s; s++) {
|
||||
*bp++ = *s;
|
||||
}
|
||||
}
|
||||
|
||||
*bufferp = buffer;
|
||||
|
||||
return len;
|
||||
}
|
||||
|
||||
SCGI_DECLARE(scgi_status_t) scgi_destroy_params(scgi_handle_t *handle)
|
||||
{
|
||||
scgi_param_t *param, *pp;
|
||||
|
||||
pp = handle->params;
|
||||
|
||||
while(pp) {
|
||||
param = pp;
|
||||
pp = pp->next;
|
||||
|
||||
free(param->name);
|
||||
free(param->value);
|
||||
free(param);
|
||||
}
|
||||
|
||||
handle->params = NULL;
|
||||
|
||||
return SCGI_SUCCESS;
|
||||
}
|
||||
|
||||
SCGI_DECLARE(scgi_status_t) scgi_add_body(scgi_handle_t *handle, const char *value)
|
||||
{
|
||||
handle->body = strdup(value);
|
||||
|
||||
return SCGI_SUCCESS;
|
||||
}
|
||||
|
||||
SCGI_DECLARE(const char *) scgi_get_body(scgi_handle_t *handle)
|
||||
{
|
||||
return handle->body;
|
||||
}
|
||||
|
||||
SCGI_DECLARE(scgi_status_t) scgi_add_param(scgi_handle_t *handle, const char *name, const char *value)
|
||||
{
|
||||
scgi_param_t *param, *pp;
|
||||
|
||||
for(pp = handle->params; pp && pp->next; pp = pp->next) {
|
||||
if (!strcasecmp(pp->name, name)) {
|
||||
return SCGI_FAIL;
|
||||
}
|
||||
}
|
||||
|
||||
param = malloc(sizeof(*param));
|
||||
memset(param, 0, sizeof(*param));
|
||||
|
||||
param->name = strdup(name);
|
||||
param->value = strdup(value);
|
||||
|
||||
if (!pp) {
|
||||
handle->params = param;
|
||||
} else {
|
||||
pp->next = param;
|
||||
}
|
||||
|
||||
return SCGI_SUCCESS;
|
||||
}
|
||||
|
||||
SCGI_DECLARE(const char *) scgi_get_param(scgi_handle_t *handle, const char *name)
|
||||
{
|
||||
scgi_param_t *pp;
|
||||
|
||||
for(pp = handle->params; pp; pp = pp->next) {
|
||||
if (!strcasecmp(pp->name, name)) {
|
||||
return pp->value;
|
||||
}
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static scgi_status_t scgi_push_param(scgi_handle_t *handle, const char *name, const char *value)
|
||||
{
|
||||
scgi_param_t *param;
|
||||
|
||||
param = malloc(sizeof(*param));
|
||||
memset(param, 0, sizeof(*param));
|
||||
|
||||
param->name = strdup(name);
|
||||
param->value = strdup(value);
|
||||
|
||||
param->next = handle->params;
|
||||
handle->params = param;
|
||||
|
||||
return SCGI_SUCCESS;
|
||||
}
|
||||
|
||||
SCGI_DECLARE(scgi_status_t) scgi_send_request(scgi_handle_t *handle)
|
||||
{
|
||||
scgi_status_t status = SCGI_SUCCESS;
|
||||
char *buffer = NULL;
|
||||
size_t bytes = 0;
|
||||
ssize_t sent = 0;
|
||||
|
||||
if (handle->connected != 1) {
|
||||
return SCGI_FAIL;
|
||||
}
|
||||
|
||||
bytes = scgi_build_message(handle, &buffer);
|
||||
sent = send(handle->sock, buffer, bytes, 0);
|
||||
|
||||
if (sent <= 0) {
|
||||
handle->connected = -1;
|
||||
}
|
||||
|
||||
scgi_safe_free(buffer);
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
|
||||
SCGI_DECLARE(ssize_t) scgi_recv(scgi_handle_t *handle, unsigned char *buf, size_t buflen)
|
||||
{
|
||||
ssize_t recvd;
|
||||
|
||||
if (handle->connected != 1) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
recvd = recv(handle->sock, buf, buflen, 0);
|
||||
|
||||
if (recvd == 0) {
|
||||
handle->connected = -1;
|
||||
}
|
||||
|
||||
|
||||
return recvd;
|
||||
}
|
||||
|
||||
SCGI_DECLARE(scgi_status_t) scgi_connect(scgi_handle_t *handle, const char *host, scgi_port_t port, uint32_t timeout)
|
||||
{
|
||||
int rval = 0;
|
||||
|
||||
struct addrinfo hints = { 0 }, *result;
|
||||
#ifndef WIN32
|
||||
int fd_flags = 0;
|
||||
#else
|
||||
WORD wVersionRequested = MAKEWORD(2, 0);
|
||||
WSADATA wsaData;
|
||||
int err = WSAStartup(wVersionRequested, &wsaData);
|
||||
if (err != 0) {
|
||||
snprintf(handle->err, sizeof(handle->err), "WSAStartup Error");
|
||||
return SCGI_FAIL;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
handle->sock = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP);
|
||||
|
||||
if (handle->sock == SCGI_SOCK_INVALID) {
|
||||
snprintf(handle->err, sizeof(handle->err), "Socket Error");
|
||||
return SCGI_FAIL;
|
||||
}
|
||||
|
||||
|
||||
hints.ai_family = AF_INET;
|
||||
hints.ai_socktype = SOCK_STREAM;
|
||||
|
||||
if (getaddrinfo(host, NULL, &hints, &result)) {
|
||||
strncpy(handle->err, "Cannot resolve host", sizeof(handle->err));
|
||||
goto fail;
|
||||
}
|
||||
|
||||
memcpy(&handle->sockaddr, result->ai_addr, sizeof(handle->sockaddr));
|
||||
handle->sockaddr.sin_family = AF_INET;
|
||||
handle->sockaddr.sin_port = htons(port);
|
||||
freeaddrinfo(result);
|
||||
|
||||
if (timeout) {
|
||||
#ifdef WIN32
|
||||
u_long arg = 1;
|
||||
if (ioctlsocket(handle->sock, FIONBIO, &arg) == SOCKET_ERROR) {
|
||||
snprintf(handle->err, sizeof(handle->err), "Socket Connection Error");
|
||||
goto fail;
|
||||
}
|
||||
#else
|
||||
fd_flags = fcntl(handle->sock, F_GETFL, 0);
|
||||
if (fcntl(handle->sock, F_SETFL, fd_flags | O_NONBLOCK)) {
|
||||
snprintf(handle->err, sizeof(handle->err), "Socket Connection Error");
|
||||
goto fail;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
rval = connect(handle->sock, (struct sockaddr*)&handle->sockaddr, sizeof(handle->sockaddr));
|
||||
|
||||
if (timeout) {
|
||||
int r;
|
||||
|
||||
|
||||
r = scgi_wait_sock(handle->sock, timeout, SCGI_POLL_WRITE);
|
||||
|
||||
if (r <= 0) {
|
||||
snprintf(handle->err, sizeof(handle->err), "Connection timed out");
|
||||
goto fail;
|
||||
}
|
||||
|
||||
if (!(r & SCGI_POLL_WRITE)) {
|
||||
snprintf(handle->err, sizeof(handle->err), "Connection timed out");
|
||||
goto fail;
|
||||
}
|
||||
|
||||
#ifdef WIN32
|
||||
{
|
||||
u_long arg = 0;
|
||||
if (ioctlsocket(handle->sock, FIONBIO, &arg) == SOCKET_ERROR) {
|
||||
snprintf(handle->err, sizeof(handle->err), "Socket Connection Error");
|
||||
goto fail;
|
||||
}
|
||||
}
|
||||
#else
|
||||
fcntl(handle->sock, F_SETFL, fd_flags);
|
||||
#endif
|
||||
rval = 0;
|
||||
}
|
||||
|
||||
result = NULL;
|
||||
|
||||
if (rval) {
|
||||
snprintf(handle->err, sizeof(handle->err), "Socket Connection Error");
|
||||
goto fail;
|
||||
}
|
||||
|
||||
sock_setup(handle);
|
||||
|
||||
handle->connected = 1;
|
||||
|
||||
|
||||
return SCGI_SUCCESS;
|
||||
|
||||
fail:
|
||||
|
||||
handle->connected = 0;
|
||||
scgi_disconnect(handle);
|
||||
|
||||
return SCGI_FAIL;
|
||||
}
|
||||
|
||||
|
||||
|
||||
SCGI_DECLARE(scgi_status_t) scgi_disconnect(scgi_handle_t *handle)
|
||||
{
|
||||
scgi_status_t status = SCGI_FAIL;
|
||||
|
||||
if (handle->destroyed) {
|
||||
return SCGI_FAIL;
|
||||
}
|
||||
|
||||
if (handle->sock != SCGI_SOCK_INVALID) {
|
||||
closesocket(handle->sock);
|
||||
handle->sock = SCGI_SOCK_INVALID;
|
||||
status = SCGI_SUCCESS;
|
||||
}
|
||||
|
||||
handle->destroyed = 1;
|
||||
handle->connected = 0;
|
||||
|
||||
scgi_destroy_params(handle);
|
||||
scgi_safe_free(handle->body);
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
|
||||
/* USE WSAPoll on vista or higher */
|
||||
#ifdef SCGI_USE_WSAPOLL
|
||||
SCGI_DECLARE(int) scgi_wait_sock(scgi_socket_t sock, uint32_t ms, scgi_poll_t flags)
|
||||
{
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef SCGI_USE_SELECT
|
||||
#ifdef WIN32
|
||||
#pragma warning( push )
|
||||
#pragma warning( disable : 6262 ) /* warning C6262: Function uses '98348' bytes of stack: exceeds /analyze:stacksize'16384'. Consider moving some data to heap */
|
||||
#endif
|
||||
SCGI_DECLARE(int) scgi_wait_sock(scgi_socket_t sock, uint32_t ms, scgi_poll_t flags)
|
||||
{
|
||||
int s = 0, r = 0;
|
||||
fd_set rfds;
|
||||
fd_set wfds;
|
||||
fd_set efds;
|
||||
struct timeval tv;
|
||||
|
||||
FD_ZERO(&rfds);
|
||||
FD_ZERO(&wfds);
|
||||
FD_ZERO(&efds);
|
||||
|
||||
#ifndef WIN32
|
||||
/* Wouldn't you rather know?? */
|
||||
assert(sock <= FD_SETSIZE);
|
||||
#endif
|
||||
|
||||
if ((flags & SCGI_POLL_READ)) {
|
||||
|
||||
#ifdef WIN32
|
||||
#pragma warning( push )
|
||||
#pragma warning( disable : 4127 )
|
||||
FD_SET(sock, &rfds);
|
||||
#pragma warning( pop )
|
||||
#else
|
||||
FD_SET(sock, &rfds);
|
||||
#endif
|
||||
}
|
||||
|
||||
if ((flags & SCGI_POLL_WRITE)) {
|
||||
|
||||
#ifdef WIN32
|
||||
#pragma warning( push )
|
||||
#pragma warning( disable : 4127 )
|
||||
FD_SET(sock, &wfds);
|
||||
#pragma warning( pop )
|
||||
#else
|
||||
FD_SET(sock, &wfds);
|
||||
#endif
|
||||
}
|
||||
|
||||
if ((flags & SCGI_POLL_ERROR)) {
|
||||
|
||||
#ifdef WIN32
|
||||
#pragma warning( push )
|
||||
#pragma warning( disable : 4127 )
|
||||
FD_SET(sock, &efds);
|
||||
#pragma warning( pop )
|
||||
#else
|
||||
FD_SET(sock, &efds);
|
||||
#endif
|
||||
}
|
||||
|
||||
tv.tv_sec = ms / 1000;
|
||||
tv.tv_usec = (ms % 1000) * ms;
|
||||
|
||||
s = select(sock + 1, (flags & SCGI_POLL_READ) ? &rfds : NULL, (flags & SCGI_POLL_WRITE) ? &wfds : NULL, (flags & SCGI_POLL_ERROR) ? &efds : NULL, &tv);
|
||||
|
||||
if (s < 0) {
|
||||
r = s;
|
||||
} else if (s > 0) {
|
||||
if ((flags & SCGI_POLL_READ) && FD_ISSET(sock, &rfds)) {
|
||||
r |= SCGI_POLL_READ;
|
||||
}
|
||||
|
||||
if ((flags & SCGI_POLL_WRITE) && FD_ISSET(sock, &wfds)) {
|
||||
r |= SCGI_POLL_WRITE;
|
||||
}
|
||||
|
||||
if ((flags & SCGI_POLL_ERROR) && FD_ISSET(sock, &efds)) {
|
||||
r |= SCGI_POLL_ERROR;
|
||||
}
|
||||
}
|
||||
|
||||
return r;
|
||||
|
||||
}
|
||||
#ifdef WIN32
|
||||
#pragma warning( pop )
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifdef SCGI_USE_POLL
|
||||
SCGI_DECLARE(int) scgi_wait_sock(scgi_socket_t sock, uint32_t ms, scgi_poll_t flags)
|
||||
{
|
||||
struct pollfd pfds[2] = { { 0 } };
|
||||
int s = 0, r = 0;
|
||||
|
||||
pfds[0].fd = sock;
|
||||
|
||||
if ((flags & SCGI_POLL_READ)) {
|
||||
pfds[0].events |= POLLIN;
|
||||
}
|
||||
|
||||
if ((flags & SCGI_POLL_WRITE)) {
|
||||
pfds[0].events |= POLLOUT;
|
||||
}
|
||||
|
||||
if ((flags & SCGI_POLL_ERROR)) {
|
||||
pfds[0].events |= POLLERR;
|
||||
}
|
||||
|
||||
s = poll(pfds, 1, ms);
|
||||
|
||||
if (s < 0) {
|
||||
r = s;
|
||||
} else if (s > 0) {
|
||||
if ((pfds[0].revents & POLLIN)) {
|
||||
r |= SCGI_POLL_READ;
|
||||
}
|
||||
if ((pfds[0].revents & POLLOUT)) {
|
||||
r |= SCGI_POLL_WRITE;
|
||||
}
|
||||
if ((pfds[0].revents & POLLERR)) {
|
||||
r |= SCGI_POLL_ERROR;
|
||||
}
|
||||
}
|
||||
|
||||
return r;
|
||||
|
||||
}
|
||||
#endif
|
||||
|
||||
static int scgi_socket_reuseaddr(scgi_socket_t socket)
|
||||
{
|
||||
#ifdef WIN32
|
||||
BOOL reuse_addr = TRUE;
|
||||
return setsockopt(socket, SOL_SOCKET, SO_REUSEADDR, (char *)&reuse_addr, sizeof(reuse_addr));
|
||||
#else
|
||||
int reuse_addr = 1;
|
||||
return setsockopt(socket, SOL_SOCKET, SO_REUSEADDR, &reuse_addr, sizeof(reuse_addr));
|
||||
#endif
|
||||
}
|
||||
|
||||
SCGI_DECLARE(scgi_status_t) scgi_bind(const char *host, scgi_port_t port, scgi_socket_t *socketp)
|
||||
{
|
||||
scgi_socket_t server_sock = SCGI_SOCK_INVALID;
|
||||
struct sockaddr_in addr;
|
||||
scgi_status_t status = SCGI_SUCCESS;
|
||||
|
||||
if ((server_sock = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0) {
|
||||
return SCGI_FAIL;
|
||||
}
|
||||
|
||||
scgi_socket_reuseaddr(server_sock);
|
||||
|
||||
memset(&addr, 0, sizeof(addr));
|
||||
addr.sin_family = AF_INET;
|
||||
addr.sin_addr.s_addr = htonl(INADDR_ANY);
|
||||
addr.sin_port = htons(port);
|
||||
|
||||
if (bind(server_sock, (struct sockaddr *) &addr, sizeof(addr)) < 0) {
|
||||
status = SCGI_FAIL;
|
||||
goto end;
|
||||
}
|
||||
|
||||
if (listen(server_sock, 10000) < 0) {
|
||||
status = SCGI_FAIL;
|
||||
goto end;
|
||||
}
|
||||
|
||||
end:
|
||||
|
||||
if (status == SCGI_FAIL) {
|
||||
if (server_sock != SCGI_SOCK_INVALID) {
|
||||
closesocket(server_sock);
|
||||
server_sock = SCGI_SOCK_INVALID;
|
||||
}
|
||||
} else {
|
||||
*socketp = server_sock;
|
||||
}
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
SCGI_DECLARE(scgi_status_t) scgi_accept(scgi_socket_t server_sock, scgi_socket_t *client_sock_p, struct sockaddr_in *echoClntAddr)
|
||||
{
|
||||
scgi_status_t status = SCGI_SUCCESS;
|
||||
int client_sock;
|
||||
struct sockaddr_in local_echoClntAddr;
|
||||
#ifdef WIN32
|
||||
int clntLen;
|
||||
#else
|
||||
unsigned int clntLen;
|
||||
#endif
|
||||
|
||||
if (!echoClntAddr) {
|
||||
echoClntAddr = &local_echoClntAddr;
|
||||
}
|
||||
|
||||
clntLen = sizeof(*echoClntAddr);
|
||||
|
||||
if ((client_sock = accept(server_sock, (struct sockaddr *) echoClntAddr, &clntLen)) == SCGI_SOCK_INVALID) {
|
||||
printf("FRICK %s\n", strerror(errno));
|
||||
status = SCGI_FAIL;
|
||||
} else {
|
||||
*client_sock_p = client_sock;
|
||||
}
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
SCGI_DECLARE(scgi_status_t) scgi_listen(const char *host, scgi_port_t port, scgi_listen_callback_t callback)
|
||||
{
|
||||
|
||||
scgi_socket_t server_sock = SCGI_SOCK_INVALID, client_sock = SCGI_SOCK_INVALID;
|
||||
scgi_status_t status = SCGI_FAIL;
|
||||
struct sockaddr_in echoClntAddr;
|
||||
|
||||
if ((status = scgi_bind(host, port, &server_sock)) == SCGI_SUCCESS) {
|
||||
|
||||
while(scgi_accept(server_sock, &client_sock, &echoClntAddr) == SCGI_SUCCESS) {
|
||||
callback(server_sock, &client_sock, &echoClntAddr);
|
||||
|
||||
if (client_sock != SCGI_SOCK_INVALID) {
|
||||
closesocket(client_sock);
|
||||
client_sock = SCGI_SOCK_INVALID;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return status;
|
||||
|
||||
}
|
||||
|
||||
#define next_str(_e, _s) _s = _e; while(*_s) _s++; _s++
|
||||
|
||||
SCGI_DECLARE(scgi_status_t) scgi_parse(scgi_socket_t sock, scgi_handle_t *handle)
|
||||
{
|
||||
char sbuf[128] = "";
|
||||
char *p = sbuf, *e, *end;
|
||||
ssize_t r = 0;
|
||||
scgi_status_t status = SCGI_FAIL;
|
||||
ssize_t bytes = 0;
|
||||
char *headers = NULL;
|
||||
int loops = 0;
|
||||
ssize_t clen = 0;
|
||||
char *body = NULL;
|
||||
char comma = 0;
|
||||
|
||||
memset(handle, 0, sizeof(*handle));
|
||||
|
||||
handle->sock = sock;
|
||||
|
||||
handle->connected = 1;
|
||||
sock_setup(handle);
|
||||
|
||||
for(;;) {
|
||||
|
||||
if ((r = recv(sock, p, 1, 0)) < 1) {
|
||||
break;
|
||||
}
|
||||
|
||||
if (*p == ':') {
|
||||
*p = '\0';
|
||||
break;
|
||||
}
|
||||
p++;
|
||||
}
|
||||
|
||||
if (r <= 0) goto end;
|
||||
|
||||
bytes = atoi(sbuf);
|
||||
|
||||
if (bytes <= 0) goto end;
|
||||
|
||||
headers = malloc(bytes);
|
||||
r = recv(sock, headers, bytes, 0);
|
||||
if (r <= 0) goto end;
|
||||
|
||||
r = recv(sock, &comma, 1, 0);
|
||||
if (r <= 0 || comma != ',') goto end;
|
||||
|
||||
|
||||
p = headers;
|
||||
end = p + bytes;
|
||||
e = NULL;
|
||||
|
||||
while(p < end) {
|
||||
next_str(p, e);
|
||||
|
||||
if (!e) break;
|
||||
|
||||
if (!loops++) {
|
||||
if (!strcasecmp(p, "CONTENT_LENGTH") && e) {
|
||||
clen = atoi(e);
|
||||
if (clen) {
|
||||
body = malloc(clen+1);
|
||||
r = recv(sock, body, clen, 0);
|
||||
*(body + clen) = '\0';
|
||||
if (r <= 0) goto end;
|
||||
scgi_add_body(handle, body);
|
||||
scgi_safe_free(body);
|
||||
}
|
||||
|
||||
status = SCGI_SUCCESS;
|
||||
|
||||
} else {
|
||||
goto end;
|
||||
}
|
||||
}
|
||||
|
||||
scgi_add_param(handle, p, e);
|
||||
next_str(e, p);
|
||||
}
|
||||
|
||||
end:
|
||||
|
||||
scgi_safe_free(headers);
|
||||
|
||||
return status;
|
||||
}
|
||||
|
||||
|
||||
/* For Emacs:
|
||||
* Local Variables:
|
||||
* mode:c
|
||||
* indent-tabs-mode:t
|
||||
* tab-width:4
|
||||
* c-basic-offset:4
|
||||
* End:
|
||||
* For VIM:
|
||||
* vim:set softtabstop=4 shiftwidth=4 tabstop=4:
|
||||
*/
|
|
@ -0,0 +1,127 @@
|
|||
#include <scgi.h>
|
||||
#include <scgi_oop.h>
|
||||
|
||||
#define connection_construct_common() memset(&handle, 0, sizeof(handle))
|
||||
|
||||
|
||||
|
||||
SCGIhandle::SCGIhandle(void)
|
||||
{
|
||||
connection_construct_common();
|
||||
}
|
||||
|
||||
SCGIhandle::~SCGIhandle()
|
||||
{
|
||||
|
||||
scgi_disconnect(&handle);
|
||||
scgi_safe_free(data_buf);
|
||||
buflen = 0;
|
||||
bufsize = 0;
|
||||
|
||||
}
|
||||
|
||||
int SCGIhandle::socketDescriptor()
|
||||
{
|
||||
if (handle.connected) {
|
||||
return (int) handle.sock;
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
int SCGIhandle::disconnect()
|
||||
{
|
||||
return scgi_disconnect(&handle);
|
||||
}
|
||||
|
||||
int SCGIhandle::connected()
|
||||
{
|
||||
return handle.connected;
|
||||
}
|
||||
|
||||
int SCGIhandle::addParam(const char *name, const char *value)
|
||||
{
|
||||
return (int) scgi_add_param(&handle, name, value);
|
||||
}
|
||||
|
||||
int SCGIhandle::addBody(const char *value)
|
||||
{
|
||||
return (int) scgi_add_body(&handle, value);
|
||||
}
|
||||
|
||||
char *SCGIhandle::getBody()
|
||||
{
|
||||
return handle.body;
|
||||
}
|
||||
|
||||
char *SCGIhandle::getParam(const char *name)
|
||||
{
|
||||
return (char *) scgi_get_param(&handle, name);
|
||||
}
|
||||
|
||||
char *SCGIhandle::sendRequest(const char *host, int port, int timeout)
|
||||
{
|
||||
ssize_t len;
|
||||
|
||||
if (!host) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (timeout < 1000) {
|
||||
timeout = 1000;
|
||||
}
|
||||
|
||||
if (scgi_connect(&handle, host, port, timeout) == SCGI_SUCCESS) {
|
||||
if (scgi_send_request(&handle) == SCGI_SUCCESS) {
|
||||
while((len = scgi_recv(&handle, buf, sizeof(buf))) > 0) {
|
||||
if (buflen + len > bufsize) {
|
||||
bufsize = buflen + len + 1024;
|
||||
void *tmp = realloc(data_buf, bufsize);
|
||||
assert(tmp);
|
||||
data_buf = (char *)tmp;
|
||||
|
||||
*(data_buf+buflen) = '\0';
|
||||
}
|
||||
snprintf(data_buf+buflen, bufsize-buflen, "%s", buf);
|
||||
buflen += len;
|
||||
}
|
||||
|
||||
return data_buf;
|
||||
}
|
||||
}
|
||||
|
||||
return (char *) "";
|
||||
}
|
||||
|
||||
int SCGIhandle::bind(const char *host, int port)
|
||||
{
|
||||
return (scgi_bind(host, port, &server_sock) == SCGI_SUCCESS) ? 1 : 0;
|
||||
}
|
||||
|
||||
|
||||
int SCGIhandle::accept(void)
|
||||
{
|
||||
scgi_socket_t client_sock;
|
||||
|
||||
if (scgi_accept(server_sock, &client_sock, NULL) == SCGI_SUCCESS) {
|
||||
if (scgi_parse(client_sock, &handle) == SCGI_SUCCESS) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
closesocket(client_sock);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
int SCGIhandle::respond(char *msg)
|
||||
{
|
||||
int b = write(handle.sock, msg, strlen(msg));
|
||||
scgi_disconnect(&handle);
|
||||
scgi_safe_free(data_buf);
|
||||
buflen = 0;
|
||||
bufsize = 0;
|
||||
return b;
|
||||
}
|
|
@ -0,0 +1,40 @@
|
|||
#include <scgi.h>
|
||||
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
char buf[16336] = "";
|
||||
ssize_t len;
|
||||
scgi_handle_t handle = { 0 };
|
||||
char *ip;
|
||||
int port = 0;
|
||||
|
||||
if (argc < 2) {
|
||||
fprintf(stderr, "usage: testclient <ip> <port>\n");
|
||||
exit(-1);
|
||||
}
|
||||
|
||||
ip = argv[1];
|
||||
port = atoi(argv[2]);
|
||||
|
||||
|
||||
|
||||
scgi_add_param(&handle, "REQUEST_METHOD", "POST");
|
||||
scgi_add_param(&handle, "REQUEST_URI", "/deepthought");
|
||||
scgi_add_param(&handle, "TESTING", "TRUE");
|
||||
scgi_add_param(&handle, "TESTING", "TRUE");
|
||||
scgi_add_body(&handle, "What is the answer to life?");
|
||||
|
||||
|
||||
scgi_connect(&handle, ip, port, 10000);
|
||||
|
||||
scgi_send_request(&handle);
|
||||
|
||||
|
||||
while((len = scgi_recv(&handle, buf, sizeof(buf))) > 0) {
|
||||
printf("READ [%s]\n", buf);
|
||||
}
|
||||
|
||||
scgi_disconnect(&handle);
|
||||
|
||||
}
|
|
@ -0,0 +1,43 @@
|
|||
#include <scgi.h>
|
||||
|
||||
static void callback(scgi_socket_t server_sock, scgi_socket_t *client_sock, struct sockaddr_in *addr)
|
||||
{
|
||||
scgi_handle_t handle = { 0 };
|
||||
|
||||
if (scgi_parse(*client_sock, &handle) == SCGI_SUCCESS) {
|
||||
scgi_param_t *pp;
|
||||
|
||||
*client_sock = SCGI_SOCK_INVALID;
|
||||
|
||||
for(pp = handle.params; pp; pp = pp->next) {
|
||||
printf("HEADER: [%s] VALUE: [%s]\n", pp->name, pp->value);
|
||||
}
|
||||
|
||||
if (handle.body) {
|
||||
printf("\n\nBODY:\n%s\n\n", handle.body);
|
||||
}
|
||||
|
||||
scgi_disconnect(&handle);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
char *ip;
|
||||
int port = 0;
|
||||
|
||||
if (argc < 2) {
|
||||
fprintf(stderr, "usage: testserver <ip> <port>\n");
|
||||
exit(-1);
|
||||
}
|
||||
|
||||
ip = argv[1];
|
||||
port = atoi(argv[2]);
|
||||
|
||||
|
||||
scgi_listen(ip, port, callback);
|
||||
|
||||
|
||||
|
||||
}
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue