Christmas Presence

git-svn-id: http://svn.freeswitch.org/svn/freeswitch/trunk@3083 d0543943-73ff-0310-b7d9-9358b9ac24b2
This commit is contained in:
Anthony Minessale 2006-10-18 22:57:35 +00:00
parent 61e118db18
commit 70bfba5b63
19 changed files with 2163 additions and 179 deletions

View File

@ -53,7 +53,7 @@ DIST_COMMON = README $(am__configure_deps) $(library_include_HEADERS) \
ChangeLog INSTALL NEWS build/config/compile \ ChangeLog INSTALL NEWS build/config/compile \
build/config/config.guess build/config/config.sub \ build/config/config.guess build/config/config.sub \
build/config/depcomp build/config/install-sh \ build/config/depcomp build/config/install-sh \
build/config/ltmain.sh build/config/missing mkinstalldirs build/config/ltmain.sh build/config/missing
subdir = . subdir = .
ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
am__aclocal_m4_deps = $(top_srcdir)/configure.in am__aclocal_m4_deps = $(top_srcdir)/configure.in

View File

@ -56,6 +56,12 @@ else
fi fi
fi fi
if [ ! -f $root/.nothanks ] && [ $uncompressed/.complete -ot $uncompressed ] ; then
echo remove stale .complete
rm $uncompressed/.complete
cd $uncompressed && $MAKE clean distclean
fi
if [ -f $uncompressed/.complete ] ; then if [ -f $uncompressed/.complete ] ; then
echo $uncompressed already installed echo $uncompressed already installed
exit 0 exit 0

View File

@ -17,7 +17,7 @@ AM_CFLAGS += $(shell $(APU_CONFIG) --includes)
AM_LDFLAGS += $(shell $(APU_CONFIG) --link-ld --libs ) AM_LDFLAGS += $(shell $(APU_CONFIG) --link-ld --libs )
lib_LTLIBRARIES = libdingaling.la lib_LTLIBRARIES = libdingaling.la
libdingaling_la_SOURCES = src/libdingaling.c libdingaling_la_SOURCES = src/libdingaling.c src/sha1.c
libdingaling_la_CFLAGS = $(AM_CFLAGS) libdingaling_la_CFLAGS = $(AM_CFLAGS)
libdingaling_la_LDFLAGS = libdingaling_la_LDFLAGS =

View File

@ -39,9 +39,9 @@ build_triplet = @build@
host_triplet = @host@ host_triplet = @host@
DIST_COMMON = README $(am__configure_deps) $(library_include_HEADERS) \ DIST_COMMON = README $(am__configure_deps) $(library_include_HEADERS) \
$(srcdir)/Makefile.am $(srcdir)/Makefile.in \ $(srcdir)/Makefile.am $(srcdir)/Makefile.in \
$(top_srcdir)/configure AUTHORS COPYING ChangeLog INSTALL NEWS \ $(top_srcdir)/configure $(top_srcdir)/src/config.h.in AUTHORS \
compile config.guess config.sub depcomp install-sh ltmain.sh \ COPYING ChangeLog INSTALL NEWS compile config.guess config.sub \
missing mkinstalldirs depcomp install-sh ltmain.sh missing mkinstalldirs
subdir = . subdir = .
ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
am__aclocal_m4_deps = $(top_srcdir)/configure.in am__aclocal_m4_deps = $(top_srcdir)/configure.in
@ -50,6 +50,7 @@ am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \
am__CONFIG_DISTCLEAN_FILES = config.status config.cache config.log \ am__CONFIG_DISTCLEAN_FILES = config.status config.cache config.log \
configure.lineno configure.status.lineno configure.lineno configure.status.lineno
mkinstalldirs = $(SHELL) $(top_srcdir)/mkinstalldirs mkinstalldirs = $(SHELL) $(top_srcdir)/mkinstalldirs
CONFIG_HEADER = $(top_builddir)/src/config.h
CONFIG_CLEAN_FILES = CONFIG_CLEAN_FILES =
am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`;
am__vpath_adj = case $$p in \ am__vpath_adj = case $$p in \
@ -62,9 +63,10 @@ am__installdirs = "$(DESTDIR)$(libdir)" \
libLTLIBRARIES_INSTALL = $(INSTALL) libLTLIBRARIES_INSTALL = $(INSTALL)
LTLIBRARIES = $(lib_LTLIBRARIES) LTLIBRARIES = $(lib_LTLIBRARIES)
libdingaling_la_LIBADD = libdingaling_la_LIBADD =
am_libdingaling_la_OBJECTS = libdingaling_la-libdingaling.lo am_libdingaling_la_OBJECTS = libdingaling_la-libdingaling.lo \
libdingaling_la-sha1.lo
libdingaling_la_OBJECTS = $(am_libdingaling_la_OBJECTS) libdingaling_la_OBJECTS = $(am_libdingaling_la_OBJECTS)
DEFAULT_INCLUDES = -I. -I$(srcdir) DEFAULT_INCLUDES = -I. -I$(srcdir) -I$(top_builddir)/src
depcomp = $(SHELL) $(top_srcdir)/depcomp depcomp = $(SHELL) $(top_srcdir)/depcomp
am__depfiles_maybe = depfiles am__depfiles_maybe = depfiles
COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \ COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \
@ -210,7 +212,7 @@ AM_LDFLAGS = -liksemel -L$(PREFIX)/lib $(shell $(APR_CONFIG) --link-ld \
APR_CONFIG = $(prefix)/bin/apr-1-config APR_CONFIG = $(prefix)/bin/apr-1-config
APU_CONFIG = $(prefix)/bin/apu-1-config APU_CONFIG = $(prefix)/bin/apu-1-config
lib_LTLIBRARIES = libdingaling.la lib_LTLIBRARIES = libdingaling.la
libdingaling_la_SOURCES = src/libdingaling.c libdingaling_la_SOURCES = src/libdingaling.c src/sha1.c
libdingaling_la_CFLAGS = $(AM_CFLAGS) libdingaling_la_CFLAGS = $(AM_CFLAGS)
libdingaling_la_LDFLAGS = libdingaling_la_LDFLAGS =
library_includedir = $(prefix)/include library_includedir = $(prefix)/include
@ -252,6 +254,23 @@ $(top_srcdir)/configure: $(am__configure_deps)
cd $(srcdir) && $(AUTOCONF) cd $(srcdir) && $(AUTOCONF)
$(ACLOCAL_M4): $(am__aclocal_m4_deps) $(ACLOCAL_M4): $(am__aclocal_m4_deps)
cd $(srcdir) && $(ACLOCAL) $(ACLOCAL_AMFLAGS) cd $(srcdir) && $(ACLOCAL) $(ACLOCAL_AMFLAGS)
src/config.h: src/stamp-h1
@if test ! -f $@; then \
rm -f src/stamp-h1; \
$(MAKE) src/stamp-h1; \
else :; fi
src/stamp-h1: $(top_srcdir)/src/config.h.in $(top_builddir)/config.status
@rm -f src/stamp-h1
cd $(top_builddir) && $(SHELL) ./config.status src/config.h
$(top_srcdir)/src/config.h.in: $(am__configure_deps)
cd $(top_srcdir) && $(AUTOHEADER)
rm -f src/stamp-h1
touch $@
distclean-hdr:
-rm -f src/config.h src/stamp-h1
install-libLTLIBRARIES: $(lib_LTLIBRARIES) install-libLTLIBRARIES: $(lib_LTLIBRARIES)
@$(NORMAL_INSTALL) @$(NORMAL_INSTALL)
test -z "$(libdir)" || $(mkdir_p) "$(DESTDIR)$(libdir)" test -z "$(libdir)" || $(mkdir_p) "$(DESTDIR)$(libdir)"
@ -289,6 +308,7 @@ distclean-compile:
-rm -f *.tab.c -rm -f *.tab.c
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libdingaling_la-libdingaling.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libdingaling_la-libdingaling.Plo@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/libdingaling_la-sha1.Plo@am__quote@
.c.o: .c.o:
@am__fastdepCC_TRUE@ if $(COMPILE) -MT $@ -MD -MP -MF "$(DEPDIR)/$*.Tpo" -c -o $@ $<; \ @am__fastdepCC_TRUE@ if $(COMPILE) -MT $@ -MD -MP -MF "$(DEPDIR)/$*.Tpo" -c -o $@ $<; \
@ -318,6 +338,13 @@ libdingaling_la-libdingaling.lo: src/libdingaling.c
@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
@am__fastdepCC_FALSE@ $(LIBTOOL) --tag=CC --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libdingaling_la_CFLAGS) $(CFLAGS) -c -o libdingaling_la-libdingaling.lo `test -f 'src/libdingaling.c' || echo '$(srcdir)/'`src/libdingaling.c @am__fastdepCC_FALSE@ $(LIBTOOL) --tag=CC --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libdingaling_la_CFLAGS) $(CFLAGS) -c -o libdingaling_la-libdingaling.lo `test -f 'src/libdingaling.c' || echo '$(srcdir)/'`src/libdingaling.c
libdingaling_la-sha1.lo: src/sha1.c
@am__fastdepCC_TRUE@ if $(LIBTOOL) --tag=CC --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libdingaling_la_CFLAGS) $(CFLAGS) -MT libdingaling_la-sha1.lo -MD -MP -MF "$(DEPDIR)/libdingaling_la-sha1.Tpo" -c -o libdingaling_la-sha1.lo `test -f 'src/sha1.c' || echo '$(srcdir)/'`src/sha1.c; \
@am__fastdepCC_TRUE@ then mv -f "$(DEPDIR)/libdingaling_la-sha1.Tpo" "$(DEPDIR)/libdingaling_la-sha1.Plo"; else rm -f "$(DEPDIR)/libdingaling_la-sha1.Tpo"; exit 1; fi
@AMDEP_TRUE@@am__fastdepCC_FALSE@ source='src/sha1.c' object='libdingaling_la-sha1.lo' libtool=yes @AMDEPBACKSLASH@
@AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
@am__fastdepCC_FALSE@ $(LIBTOOL) --tag=CC --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(libdingaling_la_CFLAGS) $(CFLAGS) -c -o libdingaling_la-sha1.lo `test -f 'src/sha1.c' || echo '$(srcdir)/'`src/sha1.c
mostlyclean-libtool: mostlyclean-libtool:
-rm -f *.lo -rm -f *.lo
@ -661,7 +688,7 @@ distclean: distclean-recursive
-rm -rf ./$(DEPDIR) -rm -rf ./$(DEPDIR)
-rm -f Makefile -rm -f Makefile
distclean-am: clean-am distclean-compile distclean-generic \ distclean-am: clean-am distclean-compile distclean-generic \
distclean-libtool distclean-tags distclean-hdr distclean-libtool distclean-tags
dvi: dvi-recursive dvi: dvi-recursive
@ -713,11 +740,11 @@ uninstall-info: uninstall-info-recursive
clean-libtool clean-recursive ctags ctags-recursive dist \ clean-libtool clean-recursive ctags ctags-recursive dist \
dist-all dist-bzip2 dist-gzip dist-shar dist-tarZ dist-zip \ dist-all dist-bzip2 dist-gzip dist-shar dist-tarZ dist-zip \
distcheck distclean distclean-compile distclean-generic \ distcheck distclean distclean-compile distclean-generic \
distclean-libtool distclean-recursive distclean-tags \ distclean-hdr distclean-libtool distclean-recursive \
distcleancheck distdir distuninstallcheck dvi dvi-am html \ distclean-tags distcleancheck distdir distuninstallcheck dvi \
html-am info info-am install install-am install-data \ dvi-am html html-am info info-am install install-am \
install-data-am install-exec install-exec-am install-info \ install-data install-data-am install-exec install-exec-am \
install-info-am install-libLTLIBRARIES \ install-info install-info-am install-libLTLIBRARIES \
install-library_includeHEADERS install-man install-strip \ install-library_includeHEADERS install-man install-strip \
installcheck installcheck-am installdirs installdirs-am \ installcheck installcheck-am installdirs installdirs-am \
maintainer-clean maintainer-clean-generic \ maintainer-clean maintainer-clean-generic \

View File

@ -1947,6 +1947,8 @@ am__tar='${AMTAR} chof - "$$tardir"'; am__untar='${AMTAR} xf -'
ac_config_headers="$ac_config_headers src/config.h"
#AC_CONFIG_HEADER([]) #AC_CONFIG_HEADER([])
# Checks for programs. # Checks for programs.
@ -3689,7 +3691,7 @@ ia64-*-hpux*)
;; ;;
*-*-irix6*) *-*-irix6*)
# Find out which ABI we are using. # Find out which ABI we are using.
echo '#line 3692 "configure"' > conftest.$ac_ext echo '#line 3694 "configure"' > conftest.$ac_ext
if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5 if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5
(eval $ac_compile) 2>&5 (eval $ac_compile) 2>&5
ac_status=$? ac_status=$?
@ -5268,7 +5270,7 @@ fi
# Provide some information about the compiler. # Provide some information about the compiler.
echo "$as_me:5271:" \ echo "$as_me:5273:" \
"checking for Fortran 77 compiler version" >&5 "checking for Fortran 77 compiler version" >&5
ac_compiler=`set X $ac_compile; echo $2` ac_compiler=`set X $ac_compile; echo $2`
{ (eval echo "$as_me:$LINENO: \"$ac_compiler --version </dev/null >&5\"") >&5 { (eval echo "$as_me:$LINENO: \"$ac_compiler --version </dev/null >&5\"") >&5
@ -6366,11 +6368,11 @@ else
-e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \
-e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \
-e 's:$: $lt_compiler_flag:'` -e 's:$: $lt_compiler_flag:'`
(eval echo "\"\$as_me:6369: $lt_compile\"" >&5) (eval echo "\"\$as_me:6371: $lt_compile\"" >&5)
(eval "$lt_compile" 2>conftest.err) (eval "$lt_compile" 2>conftest.err)
ac_status=$? ac_status=$?
cat conftest.err >&5 cat conftest.err >&5
echo "$as_me:6373: \$? = $ac_status" >&5 echo "$as_me:6375: \$? = $ac_status" >&5
if (exit $ac_status) && test -s "$ac_outfile"; then if (exit $ac_status) && test -s "$ac_outfile"; then
# The compiler can only warn and ignore the option if not recognized # The compiler can only warn and ignore the option if not recognized
# So say no if there are warnings other than the usual output. # So say no if there are warnings other than the usual output.
@ -6628,11 +6630,11 @@ else
-e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \
-e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \
-e 's:$: $lt_compiler_flag:'` -e 's:$: $lt_compiler_flag:'`
(eval echo "\"\$as_me:6631: $lt_compile\"" >&5) (eval echo "\"\$as_me:6633: $lt_compile\"" >&5)
(eval "$lt_compile" 2>conftest.err) (eval "$lt_compile" 2>conftest.err)
ac_status=$? ac_status=$?
cat conftest.err >&5 cat conftest.err >&5
echo "$as_me:6635: \$? = $ac_status" >&5 echo "$as_me:6637: \$? = $ac_status" >&5
if (exit $ac_status) && test -s "$ac_outfile"; then if (exit $ac_status) && test -s "$ac_outfile"; then
# The compiler can only warn and ignore the option if not recognized # The compiler can only warn and ignore the option if not recognized
# So say no if there are warnings other than the usual output. # So say no if there are warnings other than the usual output.
@ -6690,11 +6692,11 @@ else
-e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \
-e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \
-e 's:$: $lt_compiler_flag:'` -e 's:$: $lt_compiler_flag:'`
(eval echo "\"\$as_me:6693: $lt_compile\"" >&5) (eval echo "\"\$as_me:6695: $lt_compile\"" >&5)
(eval "$lt_compile" 2>out/conftest.err) (eval "$lt_compile" 2>out/conftest.err)
ac_status=$? ac_status=$?
cat out/conftest.err >&5 cat out/conftest.err >&5
echo "$as_me:6697: \$? = $ac_status" >&5 echo "$as_me:6699: \$? = $ac_status" >&5
if (exit $ac_status) && test -s out/conftest2.$ac_objext if (exit $ac_status) && test -s out/conftest2.$ac_objext
then then
# The compiler can only warn and ignore the option if not recognized # The compiler can only warn and ignore the option if not recognized
@ -8938,7 +8940,7 @@ else
lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2
lt_status=$lt_dlunknown lt_status=$lt_dlunknown
cat > conftest.$ac_ext <<EOF cat > conftest.$ac_ext <<EOF
#line 8941 "configure" #line 8943 "configure"
#include "confdefs.h" #include "confdefs.h"
#if HAVE_DLFCN_H #if HAVE_DLFCN_H
@ -9036,7 +9038,7 @@ else
lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2
lt_status=$lt_dlunknown lt_status=$lt_dlunknown
cat > conftest.$ac_ext <<EOF cat > conftest.$ac_ext <<EOF
#line 9039 "configure" #line 9041 "configure"
#include "confdefs.h" #include "confdefs.h"
#if HAVE_DLFCN_H #if HAVE_DLFCN_H
@ -11291,11 +11293,11 @@ else
-e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \
-e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \
-e 's:$: $lt_compiler_flag:'` -e 's:$: $lt_compiler_flag:'`
(eval echo "\"\$as_me:11294: $lt_compile\"" >&5) (eval echo "\"\$as_me:11296: $lt_compile\"" >&5)
(eval "$lt_compile" 2>conftest.err) (eval "$lt_compile" 2>conftest.err)
ac_status=$? ac_status=$?
cat conftest.err >&5 cat conftest.err >&5
echo "$as_me:11298: \$? = $ac_status" >&5 echo "$as_me:11300: \$? = $ac_status" >&5
if (exit $ac_status) && test -s "$ac_outfile"; then if (exit $ac_status) && test -s "$ac_outfile"; then
# The compiler can only warn and ignore the option if not recognized # The compiler can only warn and ignore the option if not recognized
# So say no if there are warnings other than the usual output. # So say no if there are warnings other than the usual output.
@ -11353,11 +11355,11 @@ else
-e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \
-e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \
-e 's:$: $lt_compiler_flag:'` -e 's:$: $lt_compiler_flag:'`
(eval echo "\"\$as_me:11356: $lt_compile\"" >&5) (eval echo "\"\$as_me:11358: $lt_compile\"" >&5)
(eval "$lt_compile" 2>out/conftest.err) (eval "$lt_compile" 2>out/conftest.err)
ac_status=$? ac_status=$?
cat out/conftest.err >&5 cat out/conftest.err >&5
echo "$as_me:11360: \$? = $ac_status" >&5 echo "$as_me:11362: \$? = $ac_status" >&5
if (exit $ac_status) && test -s out/conftest2.$ac_objext if (exit $ac_status) && test -s out/conftest2.$ac_objext
then then
# The compiler can only warn and ignore the option if not recognized # The compiler can only warn and ignore the option if not recognized
@ -12730,7 +12732,7 @@ else
lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2
lt_status=$lt_dlunknown lt_status=$lt_dlunknown
cat > conftest.$ac_ext <<EOF cat > conftest.$ac_ext <<EOF
#line 12733 "configure" #line 12735 "configure"
#include "confdefs.h" #include "confdefs.h"
#if HAVE_DLFCN_H #if HAVE_DLFCN_H
@ -12828,7 +12830,7 @@ else
lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2
lt_status=$lt_dlunknown lt_status=$lt_dlunknown
cat > conftest.$ac_ext <<EOF cat > conftest.$ac_ext <<EOF
#line 12831 "configure" #line 12833 "configure"
#include "confdefs.h" #include "confdefs.h"
#if HAVE_DLFCN_H #if HAVE_DLFCN_H
@ -13713,11 +13715,11 @@ else
-e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \
-e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \
-e 's:$: $lt_compiler_flag:'` -e 's:$: $lt_compiler_flag:'`
(eval echo "\"\$as_me:13716: $lt_compile\"" >&5) (eval echo "\"\$as_me:13718: $lt_compile\"" >&5)
(eval "$lt_compile" 2>conftest.err) (eval "$lt_compile" 2>conftest.err)
ac_status=$? ac_status=$?
cat conftest.err >&5 cat conftest.err >&5
echo "$as_me:13720: \$? = $ac_status" >&5 echo "$as_me:13722: \$? = $ac_status" >&5
if (exit $ac_status) && test -s "$ac_outfile"; then if (exit $ac_status) && test -s "$ac_outfile"; then
# The compiler can only warn and ignore the option if not recognized # The compiler can only warn and ignore the option if not recognized
# So say no if there are warnings other than the usual output. # So say no if there are warnings other than the usual output.
@ -13775,11 +13777,11 @@ else
-e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \
-e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \
-e 's:$: $lt_compiler_flag:'` -e 's:$: $lt_compiler_flag:'`
(eval echo "\"\$as_me:13778: $lt_compile\"" >&5) (eval echo "\"\$as_me:13780: $lt_compile\"" >&5)
(eval "$lt_compile" 2>out/conftest.err) (eval "$lt_compile" 2>out/conftest.err)
ac_status=$? ac_status=$?
cat out/conftest.err >&5 cat out/conftest.err >&5
echo "$as_me:13782: \$? = $ac_status" >&5 echo "$as_me:13784: \$? = $ac_status" >&5
if (exit $ac_status) && test -s out/conftest2.$ac_objext if (exit $ac_status) && test -s out/conftest2.$ac_objext
then then
# The compiler can only warn and ignore the option if not recognized # The compiler can only warn and ignore the option if not recognized
@ -15905,11 +15907,11 @@ else
-e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \
-e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \
-e 's:$: $lt_compiler_flag:'` -e 's:$: $lt_compiler_flag:'`
(eval echo "\"\$as_me:15908: $lt_compile\"" >&5) (eval echo "\"\$as_me:15910: $lt_compile\"" >&5)
(eval "$lt_compile" 2>conftest.err) (eval "$lt_compile" 2>conftest.err)
ac_status=$? ac_status=$?
cat conftest.err >&5 cat conftest.err >&5
echo "$as_me:15912: \$? = $ac_status" >&5 echo "$as_me:15914: \$? = $ac_status" >&5
if (exit $ac_status) && test -s "$ac_outfile"; then if (exit $ac_status) && test -s "$ac_outfile"; then
# The compiler can only warn and ignore the option if not recognized # The compiler can only warn and ignore the option if not recognized
# So say no if there are warnings other than the usual output. # So say no if there are warnings other than the usual output.
@ -16167,11 +16169,11 @@ else
-e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \
-e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \
-e 's:$: $lt_compiler_flag:'` -e 's:$: $lt_compiler_flag:'`
(eval echo "\"\$as_me:16170: $lt_compile\"" >&5) (eval echo "\"\$as_me:16172: $lt_compile\"" >&5)
(eval "$lt_compile" 2>conftest.err) (eval "$lt_compile" 2>conftest.err)
ac_status=$? ac_status=$?
cat conftest.err >&5 cat conftest.err >&5
echo "$as_me:16174: \$? = $ac_status" >&5 echo "$as_me:16176: \$? = $ac_status" >&5
if (exit $ac_status) && test -s "$ac_outfile"; then if (exit $ac_status) && test -s "$ac_outfile"; then
# The compiler can only warn and ignore the option if not recognized # The compiler can only warn and ignore the option if not recognized
# So say no if there are warnings other than the usual output. # So say no if there are warnings other than the usual output.
@ -16229,11 +16231,11 @@ else
-e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \
-e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \
-e 's:$: $lt_compiler_flag:'` -e 's:$: $lt_compiler_flag:'`
(eval echo "\"\$as_me:16232: $lt_compile\"" >&5) (eval echo "\"\$as_me:16234: $lt_compile\"" >&5)
(eval "$lt_compile" 2>out/conftest.err) (eval "$lt_compile" 2>out/conftest.err)
ac_status=$? ac_status=$?
cat out/conftest.err >&5 cat out/conftest.err >&5
echo "$as_me:16236: \$? = $ac_status" >&5 echo "$as_me:16238: \$? = $ac_status" >&5
if (exit $ac_status) && test -s out/conftest2.$ac_objext if (exit $ac_status) && test -s out/conftest2.$ac_objext
then then
# The compiler can only warn and ignore the option if not recognized # The compiler can only warn and ignore the option if not recognized
@ -18477,7 +18479,7 @@ else
lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2
lt_status=$lt_dlunknown lt_status=$lt_dlunknown
cat > conftest.$ac_ext <<EOF cat > conftest.$ac_ext <<EOF
#line 18480 "configure" #line 18482 "configure"
#include "confdefs.h" #include "confdefs.h"
#if HAVE_DLFCN_H #if HAVE_DLFCN_H
@ -18575,7 +18577,7 @@ else
lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2
lt_status=$lt_dlunknown lt_status=$lt_dlunknown
cat > conftest.$ac_ext <<EOF cat > conftest.$ac_ext <<EOF
#line 18578 "configure" #line 18580 "configure"
#include "confdefs.h" #include "confdefs.h"
#if HAVE_DLFCN_H #if HAVE_DLFCN_H
@ -21107,6 +21109,251 @@ done
#AC_CHECK_FUNCS([gethostname gettimeofday localtime_r memmove memset socket strcasecmp strchr strdup strncasecmp strstr]) #AC_CHECK_FUNCS([gethostname gettimeofday localtime_r memmove memset socket strcasecmp strchr strdup strncasecmp strstr])
echo "$as_me:$LINENO: checking whether byte ordering is bigendian" >&5
echo $ECHO_N "checking whether byte ordering is bigendian... $ECHO_C" >&6
if test "${ac_cv_c_bigendian+set}" = set; then
echo $ECHO_N "(cached) $ECHO_C" >&6
else
# See if sys/param.h defines the BYTE_ORDER macro.
cat >conftest.$ac_ext <<_ACEOF
/* confdefs.h. */
_ACEOF
cat confdefs.h >>conftest.$ac_ext
cat >>conftest.$ac_ext <<_ACEOF
/* end confdefs.h. */
#include <sys/types.h>
#include <sys/param.h>
int
main ()
{
#if !BYTE_ORDER || !BIG_ENDIAN || !LITTLE_ENDIAN
bogus endian macros
#endif
;
return 0;
}
_ACEOF
rm -f conftest.$ac_objext
if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5
(eval $ac_compile) 2>conftest.er1
ac_status=$?
grep -v '^ *+' conftest.er1 >conftest.err
rm -f conftest.er1
cat conftest.err >&5
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); } &&
{ ac_try='test -z "$ac_c_werror_flag"
|| test ! -s conftest.err'
{ (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
(eval $ac_try) 2>&5
ac_status=$?
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); }; } &&
{ ac_try='test -s conftest.$ac_objext'
{ (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
(eval $ac_try) 2>&5
ac_status=$?
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); }; }; then
# It does; now see whether it defined to BIG_ENDIAN or not.
cat >conftest.$ac_ext <<_ACEOF
/* confdefs.h. */
_ACEOF
cat confdefs.h >>conftest.$ac_ext
cat >>conftest.$ac_ext <<_ACEOF
/* end confdefs.h. */
#include <sys/types.h>
#include <sys/param.h>
int
main ()
{
#if BYTE_ORDER != BIG_ENDIAN
not big endian
#endif
;
return 0;
}
_ACEOF
rm -f conftest.$ac_objext
if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5
(eval $ac_compile) 2>conftest.er1
ac_status=$?
grep -v '^ *+' conftest.er1 >conftest.err
rm -f conftest.er1
cat conftest.err >&5
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); } &&
{ ac_try='test -z "$ac_c_werror_flag"
|| test ! -s conftest.err'
{ (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
(eval $ac_try) 2>&5
ac_status=$?
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); }; } &&
{ ac_try='test -s conftest.$ac_objext'
{ (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
(eval $ac_try) 2>&5
ac_status=$?
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); }; }; then
ac_cv_c_bigendian=yes
else
echo "$as_me: failed program was:" >&5
sed 's/^/| /' conftest.$ac_ext >&5
ac_cv_c_bigendian=no
fi
rm -f conftest.err conftest.$ac_objext conftest.$ac_ext
else
echo "$as_me: failed program was:" >&5
sed 's/^/| /' conftest.$ac_ext >&5
# It does not; compile a test program.
if test "$cross_compiling" = yes; then
# try to guess the endianness by grepping values into an object file
ac_cv_c_bigendian=unknown
cat >conftest.$ac_ext <<_ACEOF
/* confdefs.h. */
_ACEOF
cat confdefs.h >>conftest.$ac_ext
cat >>conftest.$ac_ext <<_ACEOF
/* end confdefs.h. */
short ascii_mm[] = { 0x4249, 0x4765, 0x6E44, 0x6961, 0x6E53, 0x7953, 0 };
short ascii_ii[] = { 0x694C, 0x5454, 0x656C, 0x6E45, 0x6944, 0x6E61, 0 };
void _ascii () { char *s = (char *) ascii_mm; s = (char *) ascii_ii; }
short ebcdic_ii[] = { 0x89D3, 0xE3E3, 0x8593, 0x95C5, 0x89C4, 0x9581, 0 };
short ebcdic_mm[] = { 0xC2C9, 0xC785, 0x95C4, 0x8981, 0x95E2, 0xA8E2, 0 };
void _ebcdic () { char *s = (char *) ebcdic_mm; s = (char *) ebcdic_ii; }
int
main ()
{
_ascii (); _ebcdic ();
;
return 0;
}
_ACEOF
rm -f conftest.$ac_objext
if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5
(eval $ac_compile) 2>conftest.er1
ac_status=$?
grep -v '^ *+' conftest.er1 >conftest.err
rm -f conftest.er1
cat conftest.err >&5
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); } &&
{ ac_try='test -z "$ac_c_werror_flag"
|| test ! -s conftest.err'
{ (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
(eval $ac_try) 2>&5
ac_status=$?
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); }; } &&
{ ac_try='test -s conftest.$ac_objext'
{ (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
(eval $ac_try) 2>&5
ac_status=$?
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); }; }; then
if grep BIGenDianSyS conftest.$ac_objext >/dev/null ; then
ac_cv_c_bigendian=yes
fi
if grep LiTTleEnDian conftest.$ac_objext >/dev/null ; then
if test "$ac_cv_c_bigendian" = unknown; then
ac_cv_c_bigendian=no
else
# finding both strings is unlikely to happen, but who knows?
ac_cv_c_bigendian=unknown
fi
fi
else
echo "$as_me: failed program was:" >&5
sed 's/^/| /' conftest.$ac_ext >&5
fi
rm -f conftest.err conftest.$ac_objext conftest.$ac_ext
else
cat >conftest.$ac_ext <<_ACEOF
/* confdefs.h. */
_ACEOF
cat confdefs.h >>conftest.$ac_ext
cat >>conftest.$ac_ext <<_ACEOF
/* end confdefs.h. */
int
main ()
{
/* Are we little or big endian? From Harbison&Steele. */
union
{
long l;
char c[sizeof (long)];
} u;
u.l = 1;
exit (u.c[sizeof (long) - 1] == 1);
}
_ACEOF
rm -f conftest$ac_exeext
if { (eval echo "$as_me:$LINENO: \"$ac_link\"") >&5
(eval $ac_link) 2>&5
ac_status=$?
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); } && { ac_try='./conftest$ac_exeext'
{ (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
(eval $ac_try) 2>&5
ac_status=$?
echo "$as_me:$LINENO: \$? = $ac_status" >&5
(exit $ac_status); }; }; then
ac_cv_c_bigendian=no
else
echo "$as_me: program exited with status $ac_status" >&5
echo "$as_me: failed program was:" >&5
sed 's/^/| /' conftest.$ac_ext >&5
( exit $ac_status )
ac_cv_c_bigendian=yes
fi
rm -f core *.core gmon.out bb.out conftest$ac_exeext conftest.$ac_objext conftest.$ac_ext
fi
fi
rm -f conftest.err conftest.$ac_objext conftest.$ac_ext
fi
echo "$as_me:$LINENO: result: $ac_cv_c_bigendian" >&5
echo "${ECHO_T}$ac_cv_c_bigendian" >&6
case $ac_cv_c_bigendian in
yes)
cat >>confdefs.h <<\_ACEOF
#define __BYTE_ORDER __BIG_ENDIAN
_ACEOF
;;
no)
cat >>confdefs.h <<\_ACEOF
#define __BYTE_ORDER __LITTLE_ENDIAN
_ACEOF
;;
*)
{ { echo "$as_me:$LINENO: error: unknown endianness
presetting ac_cv_c_bigendian=no (or yes) will help" >&5
echo "$as_me: error: unknown endianness
presetting ac_cv_c_bigendian=no (or yes) will help" >&2;}
{ (exit 1); exit 1; }; } ;;
esac
cat >>confdefs.h <<\_ACEOF
#define __LITTLE_ENDIAN 1234
_ACEOF
cat >>confdefs.h <<\_ACEOF
#define __BIG_ENDIAN 4321
_ACEOF
ac_config_files="$ac_config_files Makefile" ac_config_files="$ac_config_files Makefile"
@ -21184,38 +21431,7 @@ s/^[^=]*=[ ]*$//;
}' }'
fi fi
# Transform confdefs.h into DEFS. DEFS=-DHAVE_CONFIG_H
# Protect against shell expansion while executing Makefile rules.
# Protect against Makefile macro expansion.
#
# If the first sed substitution is executed (which looks for macros that
# take arguments), then we branch to the quote section. Otherwise,
# look for a macro that doesn't take arguments.
cat >confdef2opt.sed <<\_ACEOF
t clear
: clear
s,^[ ]*#[ ]*define[ ][ ]*\([^ (][^ (]*([^)]*)\)[ ]*\(.*\),-D\1=\2,g
t quote
s,^[ ]*#[ ]*define[ ][ ]*\([^ ][^ ]*\)[ ]*\(.*\),-D\1=\2,g
t quote
d
: quote
s,[ `~#$^&*(){}\\|;'"<>?],\\&,g
s,\[,\\&,g
s,\],\\&,g
s,\$,$$,g
p
_ACEOF
# We use echo to avoid assuming a particular line-breaking character.
# The extra dot is to prevent the shell from consuming trailing
# line-breaks from the sub-command output. A line-break within
# single-quotes doesn't work because, if this script is created in a
# platform that uses two characters for line-breaks (e.g., DOS), tr
# would break.
ac_LF_and_DOT=`echo; echo .`
DEFS=`sed -n -f confdef2opt.sed confdefs.h | tr "$ac_LF_and_DOT" ' .'`
rm -f confdef2opt.sed
ac_libobjs= ac_libobjs=
ac_ltlibobjs= ac_ltlibobjs=
@ -21570,10 +21786,15 @@ Usage: $0 [OPTIONS] [FILE]...
--recheck update $as_me by reconfiguring in the same conditions --recheck update $as_me by reconfiguring in the same conditions
--file=FILE[:TEMPLATE] --file=FILE[:TEMPLATE]
instantiate the configuration file FILE instantiate the configuration file FILE
--header=FILE[:TEMPLATE]
instantiate the configuration header FILE
Configuration files: Configuration files:
$config_files $config_files
Configuration headers:
$config_headers
Configuration commands: Configuration commands:
$config_commands $config_commands
@ -21694,6 +21915,7 @@ do
# Handling of arguments. # Handling of arguments.
"Makefile" ) CONFIG_FILES="$CONFIG_FILES Makefile" ;; "Makefile" ) CONFIG_FILES="$CONFIG_FILES Makefile" ;;
"depfiles" ) CONFIG_COMMANDS="$CONFIG_COMMANDS depfiles" ;; "depfiles" ) CONFIG_COMMANDS="$CONFIG_COMMANDS depfiles" ;;
"src/config.h" ) CONFIG_HEADERS="$CONFIG_HEADERS src/config.h" ;;
*) { { echo "$as_me:$LINENO: error: invalid argument: $ac_config_target" >&5 *) { { echo "$as_me:$LINENO: error: invalid argument: $ac_config_target" >&5
echo "$as_me: error: invalid argument: $ac_config_target" >&2;} echo "$as_me: error: invalid argument: $ac_config_target" >&2;}
{ (exit 1); exit 1; }; };; { (exit 1); exit 1; }; };;
@ -21706,6 +21928,7 @@ done
# bizarre bug on SunOS 4.1.3. # bizarre bug on SunOS 4.1.3.
if $ac_need_defaults; then if $ac_need_defaults; then
test "${CONFIG_FILES+set}" = set || CONFIG_FILES=$config_files test "${CONFIG_FILES+set}" = set || CONFIG_FILES=$config_files
test "${CONFIG_HEADERS+set}" = set || CONFIG_HEADERS=$config_headers
test "${CONFIG_COMMANDS+set}" = set || CONFIG_COMMANDS=$config_commands test "${CONFIG_COMMANDS+set}" = set || CONFIG_COMMANDS=$config_commands
fi fi
@ -22085,6 +22308,251 @@ done
_ACEOF _ACEOF
cat >>$CONFIG_STATUS <<\_ACEOF cat >>$CONFIG_STATUS <<\_ACEOF
#
# CONFIG_HEADER section.
#
# These sed commands are passed to sed as "A NAME B NAME C VALUE D", where
# NAME is the cpp macro being defined and VALUE is the value it is being given.
#
# ac_d sets the value in "#define NAME VALUE" lines.
ac_dA='s,^\([ ]*\)#\([ ]*define[ ][ ]*\)'
ac_dB='[ ].*$,\1#\2'
ac_dC=' '
ac_dD=',;t'
# ac_u turns "#undef NAME" without trailing blanks into "#define NAME VALUE".
ac_uA='s,^\([ ]*\)#\([ ]*\)undef\([ ][ ]*\)'
ac_uB='$,\1#\2define\3'
ac_uC=' '
ac_uD=',;t'
for ac_file in : $CONFIG_HEADERS; do test "x$ac_file" = x: && continue
# Support "outfile[:infile[:infile...]]", defaulting infile="outfile.in".
case $ac_file in
- | *:- | *:-:* ) # input from stdin
cat >$tmp/stdin
ac_file_in=`echo "$ac_file" | sed 's,[^:]*:,,'`
ac_file=`echo "$ac_file" | sed 's,:.*,,'` ;;
*:* ) ac_file_in=`echo "$ac_file" | sed 's,[^:]*:,,'`
ac_file=`echo "$ac_file" | sed 's,:.*,,'` ;;
* ) ac_file_in=$ac_file.in ;;
esac
test x"$ac_file" != x- && { echo "$as_me:$LINENO: creating $ac_file" >&5
echo "$as_me: creating $ac_file" >&6;}
# First look for the input files in the build tree, otherwise in the
# src tree.
ac_file_inputs=`IFS=:
for f in $ac_file_in; do
case $f in
-) echo $tmp/stdin ;;
[\\/$]*)
# Absolute (can't be DOS-style, as IFS=:)
test -f "$f" || { { echo "$as_me:$LINENO: error: cannot find input file: $f" >&5
echo "$as_me: error: cannot find input file: $f" >&2;}
{ (exit 1); exit 1; }; }
# Do quote $f, to prevent DOS paths from being IFS'd.
echo "$f";;
*) # Relative
if test -f "$f"; then
# Build tree
echo "$f"
elif test -f "$srcdir/$f"; then
# Source tree
echo "$srcdir/$f"
else
# /dev/null tree
{ { echo "$as_me:$LINENO: error: cannot find input file: $f" >&5
echo "$as_me: error: cannot find input file: $f" >&2;}
{ (exit 1); exit 1; }; }
fi;;
esac
done` || { (exit 1); exit 1; }
# Remove the trailing spaces.
sed 's/[ ]*$//' $ac_file_inputs >$tmp/in
_ACEOF
# Transform confdefs.h into two sed scripts, `conftest.defines' and
# `conftest.undefs', that substitutes the proper values into
# config.h.in to produce config.h. The first handles `#define'
# templates, and the second `#undef' templates.
# And first: Protect against being on the right side of a sed subst in
# config.status. Protect against being in an unquoted here document
# in config.status.
rm -f conftest.defines conftest.undefs
# Using a here document instead of a string reduces the quoting nightmare.
# Putting comments in sed scripts is not portable.
#
# `end' is used to avoid that the second main sed command (meant for
# 0-ary CPP macros) applies to n-ary macro definitions.
# See the Autoconf documentation for `clear'.
cat >confdef2sed.sed <<\_ACEOF
s/[\\&,]/\\&/g
s,[\\$`],\\&,g
t clear
: clear
s,^[ ]*#[ ]*define[ ][ ]*\([^ (][^ (]*\)\(([^)]*)\)[ ]*\(.*\)$,${ac_dA}\1${ac_dB}\1\2${ac_dC}\3${ac_dD},gp
t end
s,^[ ]*#[ ]*define[ ][ ]*\([^ ][^ ]*\)[ ]*\(.*\)$,${ac_dA}\1${ac_dB}\1${ac_dC}\2${ac_dD},gp
: end
_ACEOF
# If some macros were called several times there might be several times
# the same #defines, which is useless. Nevertheless, we may not want to
# sort them, since we want the *last* AC-DEFINE to be honored.
uniq confdefs.h | sed -n -f confdef2sed.sed >conftest.defines
sed 's/ac_d/ac_u/g' conftest.defines >conftest.undefs
rm -f confdef2sed.sed
# This sed command replaces #undef with comments. This is necessary, for
# example, in the case of _POSIX_SOURCE, which is predefined and required
# on some systems where configure will not decide to define it.
cat >>conftest.undefs <<\_ACEOF
s,^[ ]*#[ ]*undef[ ][ ]*[a-zA-Z_][a-zA-Z_0-9]*,/* & */,
_ACEOF
# Break up conftest.defines because some shells have a limit on the size
# of here documents, and old seds have small limits too (100 cmds).
echo ' # Handle all the #define templates only if necessary.' >>$CONFIG_STATUS
echo ' if grep "^[ ]*#[ ]*define" $tmp/in >/dev/null; then' >>$CONFIG_STATUS
echo ' # If there are no defines, we may have an empty if/fi' >>$CONFIG_STATUS
echo ' :' >>$CONFIG_STATUS
rm -f conftest.tail
while grep . conftest.defines >/dev/null
do
# Write a limited-size here document to $tmp/defines.sed.
echo ' cat >$tmp/defines.sed <<CEOF' >>$CONFIG_STATUS
# Speed up: don't consider the non `#define' lines.
echo '/^[ ]*#[ ]*define/!b' >>$CONFIG_STATUS
# Work around the forget-to-reset-the-flag bug.
echo 't clr' >>$CONFIG_STATUS
echo ': clr' >>$CONFIG_STATUS
sed ${ac_max_here_lines}q conftest.defines >>$CONFIG_STATUS
echo 'CEOF
sed -f $tmp/defines.sed $tmp/in >$tmp/out
rm -f $tmp/in
mv $tmp/out $tmp/in
' >>$CONFIG_STATUS
sed 1,${ac_max_here_lines}d conftest.defines >conftest.tail
rm -f conftest.defines
mv conftest.tail conftest.defines
done
rm -f conftest.defines
echo ' fi # grep' >>$CONFIG_STATUS
echo >>$CONFIG_STATUS
# Break up conftest.undefs because some shells have a limit on the size
# of here documents, and old seds have small limits too (100 cmds).
echo ' # Handle all the #undef templates' >>$CONFIG_STATUS
rm -f conftest.tail
while grep . conftest.undefs >/dev/null
do
# Write a limited-size here document to $tmp/undefs.sed.
echo ' cat >$tmp/undefs.sed <<CEOF' >>$CONFIG_STATUS
# Speed up: don't consider the non `#undef'
echo '/^[ ]*#[ ]*undef/!b' >>$CONFIG_STATUS
# Work around the forget-to-reset-the-flag bug.
echo 't clr' >>$CONFIG_STATUS
echo ': clr' >>$CONFIG_STATUS
sed ${ac_max_here_lines}q conftest.undefs >>$CONFIG_STATUS
echo 'CEOF
sed -f $tmp/undefs.sed $tmp/in >$tmp/out
rm -f $tmp/in
mv $tmp/out $tmp/in
' >>$CONFIG_STATUS
sed 1,${ac_max_here_lines}d conftest.undefs >conftest.tail
rm -f conftest.undefs
mv conftest.tail conftest.undefs
done
rm -f conftest.undefs
cat >>$CONFIG_STATUS <<\_ACEOF
# Let's still pretend it is `configure' which instantiates (i.e., don't
# use $as_me), people would be surprised to read:
# /* config.h. Generated by config.status. */
if test x"$ac_file" = x-; then
echo "/* Generated by configure. */" >$tmp/config.h
else
echo "/* $ac_file. Generated by configure. */" >$tmp/config.h
fi
cat $tmp/in >>$tmp/config.h
rm -f $tmp/in
if test x"$ac_file" != x-; then
if diff $ac_file $tmp/config.h >/dev/null 2>&1; then
{ echo "$as_me:$LINENO: $ac_file is unchanged" >&5
echo "$as_me: $ac_file is unchanged" >&6;}
else
ac_dir=`(dirname "$ac_file") 2>/dev/null ||
$as_expr X"$ac_file" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
X"$ac_file" : 'X\(//\)[^/]' \| \
X"$ac_file" : 'X\(//\)$' \| \
X"$ac_file" : 'X\(/\)' \| \
. : '\(.\)' 2>/dev/null ||
echo X"$ac_file" |
sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/; q; }
/^X\(\/\/\)[^/].*/{ s//\1/; q; }
/^X\(\/\/\)$/{ s//\1/; q; }
/^X\(\/\).*/{ s//\1/; q; }
s/.*/./; q'`
{ if $as_mkdir_p; then
mkdir -p "$ac_dir"
else
as_dir="$ac_dir"
as_dirs=
while test ! -d "$as_dir"; do
as_dirs="$as_dir $as_dirs"
as_dir=`(dirname "$as_dir") 2>/dev/null ||
$as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
X"$as_dir" : 'X\(//\)[^/]' \| \
X"$as_dir" : 'X\(//\)$' \| \
X"$as_dir" : 'X\(/\)' \| \
. : '\(.\)' 2>/dev/null ||
echo X"$as_dir" |
sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/; q; }
/^X\(\/\/\)[^/].*/{ s//\1/; q; }
/^X\(\/\/\)$/{ s//\1/; q; }
/^X\(\/\).*/{ s//\1/; q; }
s/.*/./; q'`
done
test ! -n "$as_dirs" || mkdir $as_dirs
fi || { { echo "$as_me:$LINENO: error: cannot create directory \"$ac_dir\"" >&5
echo "$as_me: error: cannot create directory \"$ac_dir\"" >&2;}
{ (exit 1); exit 1; }; }; }
rm -f $ac_file
mv $tmp/config.h $ac_file
fi
else
cat $tmp/config.h
rm -f $tmp/config.h
fi
# Compute $ac_file's index in $config_headers.
_am_stamp_count=1
for _am_header in $config_headers :; do
case $_am_header in
$ac_file | $ac_file:* )
break ;;
* )
_am_stamp_count=`expr $_am_stamp_count + 1` ;;
esac
done
echo "timestamp for $ac_file" >`(dirname $ac_file) 2>/dev/null ||
$as_expr X$ac_file : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \
X$ac_file : 'X\(//\)[^/]' \| \
X$ac_file : 'X\(//\)$' \| \
X$ac_file : 'X\(/\)' \| \
. : '\(.\)' 2>/dev/null ||
echo X$ac_file |
sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/; q; }
/^X\(\/\/\)[^/].*/{ s//\1/; q; }
/^X\(\/\/\)$/{ s//\1/; q; }
/^X\(\/\).*/{ s//\1/; q; }
s/.*/./; q'`/stamp-h$_am_stamp_count
done
_ACEOF
cat >>$CONFIG_STATUS <<\_ACEOF
# #
# CONFIG_COMMANDS section. # CONFIG_COMMANDS section.
# #

View File

@ -5,6 +5,7 @@
AC_INIT(FULL-PACKAGE-NAME, VERSION, BUG-REPORT-ADDRESS) AC_INIT(FULL-PACKAGE-NAME, VERSION, BUG-REPORT-ADDRESS)
AM_INIT_AUTOMAKE(libdingaling,0.1) AM_INIT_AUTOMAKE(libdingaling,0.1)
AC_CONFIG_SRCDIR([src]) AC_CONFIG_SRCDIR([src])
AC_CONFIG_HEADER([src/config.h])
#AC_CONFIG_HEADER([]) #AC_CONFIG_HEADER([])
# Checks for programs. # Checks for programs.
@ -32,6 +33,10 @@ AC_TYPE_SIGNAL
AC_FUNC_STRFTIME AC_FUNC_STRFTIME
#AC_CHECK_FUNCS([gethostname gettimeofday localtime_r memmove memset socket strcasecmp strchr strdup strncasecmp strstr]) #AC_CHECK_FUNCS([gethostname gettimeofday localtime_r memmove memset socket strcasecmp strchr strdup strncasecmp strstr])
AC_C_BIGENDIAN(AC_DEFINE([__BYTE_ORDER],__BIG_ENDIAN,[Big Endian]),AC_DEFINE([__BYTE_ORDER],__LITTLE_ENDIAN,[Little Endian]))
AC_DEFINE([__LITTLE_ENDIAN],1234,[for the places where it is not defined])
AC_DEFINE([__BIG_ENDIAN],4321,[for the places where it is not defined])
AC_CONFIG_FILES([Makefile]) AC_CONFIG_FILES([Makefile])
AC_OUTPUT AC_OUTPUT

View File

@ -60,6 +60,7 @@
#include "ldl_compat.h" #include "ldl_compat.h"
#include "libdingaling.h" #include "libdingaling.h"
#include "sha1.h"
#define microsleep(x) apr_sleep(x * 1000) #define microsleep(x) apr_sleep(x * 1000)
@ -89,6 +90,12 @@ struct ldl_buffer {
int hit; int hit;
}; };
typedef enum {
CS_NEW,
CS_START,
CS_CONNECTED
} ldl_handle_state_t;
struct ldl_handle { struct ldl_handle {
iksparser *parser; iksparser *parser;
iksid *acc; iksid *acc;
@ -116,6 +123,7 @@ struct ldl_handle {
apr_pool_t *pool; apr_pool_t *pool;
void *private_info; void *private_info;
FILE *log_stream; FILE *log_stream;
ldl_handle_state_t state;
}; };
struct ldl_session { struct ldl_session {
@ -125,6 +133,7 @@ struct ldl_session {
char *initiator; char *initiator;
char *them; char *them;
char *ip; char *ip;
char *login;
ldl_payload_t payloads[LDL_MAX_PAYLOADS]; ldl_payload_t payloads[LDL_MAX_PAYLOADS];
unsigned int payload_len; unsigned int payload_len;
ldl_candidate_t candidates[LDL_MAX_CANDIDATES]; ldl_candidate_t candidates[LDL_MAX_CANDIDATES];
@ -193,7 +202,7 @@ char *ldl_session_get_id(ldl_session_t *session)
void ldl_session_send_msg(ldl_session_t *session, char *subject, char *body) void ldl_session_send_msg(ldl_session_t *session, char *subject, char *body)
{ {
ldl_handle_send_msg(session->handle, session->them, subject, body); ldl_handle_send_msg(session->handle, session->login, session->them, subject, body);
} }
ldl_status ldl_session_destroy(ldl_session_t **session_p) ldl_status ldl_session_destroy(ldl_session_t **session_p)
@ -235,14 +244,21 @@ ldl_status ldl_session_create(ldl_session_t **session_p, ldl_handle_t *handle, c
*session_p = NULL; *session_p = NULL;
return LDL_STATUS_MEMERR; return LDL_STATUS_MEMERR;
} }
memset(session, 0, sizeof(ldl_session_t)); memset(session, 0, sizeof(ldl_session_t));
apr_pool_create(&session->pool, globals.memory_pool); apr_pool_create(&session->pool, globals.memory_pool);
session->id = apr_pstrdup(session->pool, id); session->id = apr_pstrdup(session->pool, id);
session->them = apr_pstrdup(session->pool, them); session->them = apr_pstrdup(session->pool, them);
if (me) {
session->initiator = apr_pstrdup(session->pool, me); //if (me) {
//session->initiator = apr_pstrdup(session->pool, them);
//}
if (ldl_test_flag(handle, LDL_FLAG_COMPONENT)) {
session->login = apr_pstrdup(session->pool, me);
} else {
session->login = apr_pstrdup(session->pool, handle->login);
} }
apr_hash_set(handle->sessions, session->id, APR_HASH_KEY_STRING, session); apr_hash_set(handle->sessions, session->id, APR_HASH_KEY_STRING, session);
apr_hash_set(handle->sessions, session->them, APR_HASH_KEY_STRING, session); apr_hash_set(handle->sessions, session->them, APR_HASH_KEY_STRING, session);
session->handle = handle; session->handle = handle;
@ -259,7 +275,7 @@ ldl_status ldl_session_create(ldl_session_t **session_p, ldl_handle_t *handle, c
return LDL_STATUS_SUCCESS; return LDL_STATUS_SUCCESS;
} }
static ldl_status parse_session_code(ldl_handle_t *handle, char *id, char *from, iks *xml, char *xtype) static ldl_status parse_session_code(ldl_handle_t *handle, char *id, char *from, char *to, iks *xml, char *xtype)
{ {
ldl_session_t *session = NULL; ldl_session_t *session = NULL;
ldl_signal_t signal = LDL_SIGNAL_NONE; ldl_signal_t signal = LDL_SIGNAL_NONE;
@ -267,7 +283,7 @@ static ldl_status parse_session_code(ldl_handle_t *handle, char *id, char *from,
char *msg = NULL; char *msg = NULL;
if (!(session = apr_hash_get(handle->sessions, id, APR_HASH_KEY_STRING))) { if (!(session = apr_hash_get(handle->sessions, id, APR_HASH_KEY_STRING))) {
ldl_session_create(&session, handle, id, from, initiator); ldl_session_create(&session, handle, id, from, to);
if (!session) { if (!session) {
return LDL_STATUS_MEMERR; return LDL_STATUS_MEMERR;
} }
@ -433,7 +449,7 @@ static ldl_status parse_session_code(ldl_handle_t *handle, char *id, char *from,
} }
if (handle->session_callback && signal) { if (handle->session_callback && signal) {
handle->session_callback(handle, session, signal, from, id, msg); handle->session_callback(handle, session, signal, to, from, id, msg);
} }
return LDL_STATUS_SUCCESS; return LDL_STATUS_SUCCESS;
@ -441,10 +457,208 @@ static ldl_status parse_session_code(ldl_handle_t *handle, char *id, char *from,
const char *marker = "TRUE"; const char *marker = "TRUE";
static int on_disco_info(void *user_data, ikspak *pak)
{
ldl_handle_t *handle = user_data;
if (pak->subtype == IKS_TYPE_RESULT) {
if (iks_find_with_attrib(pak->query, "feature", "var", "http://www.google.com/xmpp/protocol/voice/v1")) {
char *from = iks_find_attrib(pak->x, "from");
char id[1024];
char *resource;
struct ldl_buffer *buffer;
size_t x;
if (!apr_hash_get(handle->sub_hash, from, APR_HASH_KEY_STRING)) {
iks *msg;
apr_hash_set(handle->sub_hash, apr_pstrdup(handle->pool, from), APR_HASH_KEY_STRING, &marker);
msg = iks_make_s10n (IKS_TYPE_SUBSCRIBED, from, "Ding A Ling....");
apr_queue_push(handle->queue, msg);
}
apr_cpystrn(id, from, sizeof(id));
if ((resource = strchr(id, '/'))) {
*resource++ = '\0';
}
if (resource) {
for (x = 0; x < strlen(resource); x++) {
resource[x] = (char)tolower((int)resource[x]);
}
}
if (resource && strstr(resource, "talk") && (buffer = apr_hash_get(handle->probe_hash, id, APR_HASH_KEY_STRING))) {
apr_cpystrn(buffer->buf, from, buffer->len);
fflush(stderr);
buffer->hit = 1;
}
}
return IKS_FILTER_EAT;
}
if (pak->subtype == IKS_TYPE_GET) {
iks *iq, *query, *tag;
uint8_t send = 0;
if ((iq = iks_new("iq"))) {
do {
iks_insert_attrib(iq, "from", handle->login);
iks_insert_attrib(iq, "to", pak->from->full);
iks_insert_attrib(iq, "id", pak->id);
iks_insert_attrib(iq, "type", "result");
if (!(query = iks_insert (iq, "query"))) {
break;
}
iks_insert_attrib(query, "xmlns", "http://jabber.org/protocol/disco#info");
if (!(tag = iks_insert (query, "identity"))) {
break;
}
iks_insert_attrib(tag, "category", "client");
iks_insert_attrib(tag, "type", "voice");
iks_insert_attrib(tag, "name", "LibDingaLing");
if (!(tag = iks_insert (query, "feature"))) {
break;
}
iks_insert_attrib(tag, "var", "http://jabber.org/protocol/disco#info");
if (!(tag = iks_insert (query, "feature"))) {
break;
}
iks_insert_attrib(tag, "var", "http://www.google.com/xmpp/protocol/voice/v1");
iks_send(handle->parser, iq);
send = 1;
} while (0);
iks_delete(iq);
}
if (!send) {
globals.logger(DL_LOG_DEBUG, "Memory Error!\n");
}
}
return IKS_FILTER_EAT;
}
static int on_component_disco_info(void *user_data, ikspak *pak)
{
char *node = iks_find_attrib(pak->query, "node");
ldl_handle_t *handle = user_data;
if (pak->subtype == IKS_TYPE_RESULT) {
globals.logger(DL_LOG_DEBUG, "FixME!!! node=[%s]\n", node?node:"");
} else if (pak->subtype == IKS_TYPE_GET) {
// if (ldl_test_flag(handle, LDL_FLAG_COMPONENT)) {
if (node) {
} else {
iks *iq, *query, *tag;
uint8_t send = 0;
if ((iq = iks_new("iq"))) {
do {
iks_insert_attrib(iq, "from", handle->login);
iks_insert_attrib(iq, "to", pak->from->full);
iks_insert_attrib(iq, "id", pak->id);
iks_insert_attrib(iq, "type", "result");
if (!(query = iks_insert (iq, "query"))) {
break;
}
iks_insert_attrib(query, "xmlns", "http://jabber.org/protocol/disco#info");
if (!(tag = iks_insert (query, "identity"))) {
break;
}
iks_insert_attrib(tag, "category", "gateway");
iks_insert_attrib(tag, "type", "voice");
iks_insert_attrib(tag, "name", "LibDingaLing");
if (!(tag = iks_insert (query, "feature"))) {
break;
}
iks_insert_attrib(tag, "var", "http://jabber.org/protocol/disco");
if (!(tag = iks_insert (query, "feature"))) {
break;
}
iks_insert_attrib(tag, "var", "jabber:iq:register");
/*
if (!(tag = iks_insert (query, "feature"))) {
break;
}
iks_insert_attrib(tag, "var", "http://jabber.org/protocol/commands");
*/
if (!(tag = iks_insert (query, "feature"))) {
break;
}
iks_insert_attrib(tag, "var", "jabber:iq:gateway");
if (!(tag = iks_insert (query, "feature"))) {
break;
}
iks_insert_attrib(tag, "var", "jabber:iq:version");
if (!(tag = iks_insert (query, "feature"))) {
break;
}
iks_insert_attrib(tag, "var", "vcard-temp");
if (!(tag = iks_insert (query, "feature"))) {
break;
}
iks_insert_attrib(tag, "var", "jabber:iq:search");
iks_send(handle->parser, iq);
send = 1;
} while (0);
iks_delete(iq);
}
if (!send) {
globals.logger(DL_LOG_DEBUG, "Memory Error!\n");
}
}
}
return IKS_FILTER_EAT;
}
static int on_disco_items(void *user_data, ikspak *pak)
{
globals.logger(DL_LOG_DEBUG, "FixME!!!\n");
return IKS_FILTER_EAT;
}
static int on_disco_reg_in(void *user_data, ikspak *pak)
{
globals.logger(DL_LOG_DEBUG, "FixME!!!\n");
return IKS_FILTER_EAT;
}
static int on_disco_reg_out(void *user_data, ikspak *pak)
{
globals.logger(DL_LOG_DEBUG, "FixME!!!\n");
return IKS_FILTER_EAT;
}
static int on_presence(void *user_data, ikspak *pak) static int on_presence(void *user_data, ikspak *pak)
{ {
ldl_handle_t *handle = user_data; ldl_handle_t *handle = user_data;
char *from = iks_find_attrib(pak->x, "from"); char *from = iks_find_attrib(pak->x, "from");
char *to = iks_find_attrib(pak->x, "to");
char *type = iks_find_attrib(pak->x, "type"); char *type = iks_find_attrib(pak->x, "type");
char *show = iks_find_cdata(pak->x, "show"); char *show = iks_find_cdata(pak->x, "show");
char *status = iks_find_cdata(pak->x, "status"); char *status = iks_find_cdata(pak->x, "status");
@ -454,6 +668,7 @@ static int on_presence(void *user_data, ikspak *pak)
size_t x; size_t x;
ldl_signal_t signal; ldl_signal_t signal;
if (type && !strcasecmp(type, "unavailable")) { if (type && !strcasecmp(type, "unavailable")) {
signal = LDL_SIGNAL_PRESENCE_OUT; signal = LDL_SIGNAL_PRESENCE_OUT;
} else { } else {
@ -464,9 +679,7 @@ static int on_presence(void *user_data, ikspak *pak)
status = type; status = type;
} }
if (handle->session_callback) {
handle->session_callback(handle, NULL, signal, from, status ? status : "n/a", show ? show : "n/a");
}
if (!apr_hash_get(handle->sub_hash, from, APR_HASH_KEY_STRING)) { if (!apr_hash_get(handle->sub_hash, from, APR_HASH_KEY_STRING)) {
iks *msg; iks *msg;
@ -491,20 +704,104 @@ static int on_presence(void *user_data, ikspak *pak)
fflush(stderr); fflush(stderr);
buffer->hit = 1; buffer->hit = 1;
} }
if (!type || (type && strcasecmp(type, "probe"))) {
if (handle->session_callback) {
handle->session_callback(handle, NULL, signal, to, from, status ? status : "n/a", show ? show : "n/a");
}
}
return IKS_FILTER_EAT; return IKS_FILTER_EAT;
} }
static void do_presence(ldl_handle_t *handle, char *from, char *to, char *type, char *message)
{
iks *pres;
char buf[512];
iks *tag;
if (!strchr(from, '/')) {
snprintf(buf, sizeof(buf), "%s/talk", from);
from = buf;
}
if ((pres = iks_new("presence"))) {
iks_insert_attrib(pres, "xmlns", "jabber:client");
if (from) {
iks_insert_attrib(pres, "from", from);
}
if (to) {
iks_insert_attrib(pres, "to", to);
}
if (type) {
iks_insert_attrib(pres, "type", type);
}
if (message) {
if ((tag = iks_insert (pres, "status"))) {
iks_insert_cdata(tag, message ? message : "", 0);
if ((tag = iks_insert(pres, "c"))) {
iks_insert_attrib(tag, "node", "http://www.freeswitch.org/xmpp/client/caps");
iks_insert_attrib(tag, "ver", "1.0.0.1");
iks_insert_attrib(tag, "ext", "sidebar voice-v1");
iks_insert_attrib(tag, "client", "libdingaling2");
iks_insert_attrib(tag, "xmlns", "http://jabber.org/protocol/caps");
}
}
}
apr_queue_push(handle->queue, pres);
}
}
static void do_roster(ldl_handle_t *handle)
{
if (handle->session_callback) {
handle->session_callback(handle, NULL, LDL_SIGNAL_ROSTER, NULL, handle->login, NULL, NULL);
}
}
static int on_unsubscribe(void *user_data, ikspak *pak)
{
ldl_handle_t *handle = user_data;
char *from = iks_find_attrib(pak->x, "from");
char *to = iks_find_attrib(pak->x, "to");
if (handle->session_callback) {
handle->session_callback(handle, NULL, LDL_SIGNAL_SUBSCRIBE, to, from, NULL, NULL);
}
return IKS_FILTER_EAT;
}
static int on_subscribe(void *user_data, ikspak *pak) static int on_subscribe(void *user_data, ikspak *pak)
{ {
ldl_handle_t *handle = user_data; ldl_handle_t *handle = user_data;
char *from = iks_find_attrib(pak->x, "from"); char *from = iks_find_attrib(pak->x, "from");
char *to = iks_find_attrib(pak->x, "to");
iks *msg = iks_make_s10n (IKS_TYPE_SUBSCRIBED, from, "Ding A Ling...."); iks *msg = iks_make_s10n (IKS_TYPE_SUBSCRIBED, from, "Ding A Ling....");
if (to && ldl_test_flag(handle, LDL_FLAG_COMPONENT)) {
iks_insert_attrib(msg, "from", to);
}
apr_queue_push(handle->queue, msg); apr_queue_push(handle->queue, msg);
msg = iks_make_s10n (IKS_TYPE_SUBSCRIBE, from, "Ding A Ling...."); msg = iks_make_s10n (IKS_TYPE_SUBSCRIBE, from, "Ding A Ling....");
if (to && ldl_test_flag(handle, LDL_FLAG_COMPONENT)) {
iks_insert_attrib(msg, "from", to);
}
apr_queue_push(handle->queue, msg); apr_queue_push(handle->queue, msg);
if (handle->session_callback) {
handle->session_callback(handle, NULL, LDL_SIGNAL_SUBSCRIBE, to, from, NULL, NULL);
}
return IKS_FILTER_EAT; return IKS_FILTER_EAT;
} }
@ -526,7 +823,7 @@ static int on_commands(void *user_data, ikspak *pak)
{ {
ldl_handle_t *handle = user_data; ldl_handle_t *handle = user_data;
char *from = iks_find_attrib(pak->x, "from"); char *from = iks_find_attrib(pak->x, "from");
//char *to = iks_find_attrib(pak->x, "to"); char *to = iks_find_attrib(pak->x, "to");
char *iqid = iks_find_attrib(pak->x, "id"); char *iqid = iks_find_attrib(pak->x, "id");
char *type = iks_find_attrib(pak->x, "type"); char *type = iks_find_attrib(pak->x, "type");
uint8_t is_result = strcasecmp(type, "result") ? 0 : 1; uint8_t is_result = strcasecmp(type, "result") ? 0 : 1;
@ -540,9 +837,10 @@ static int on_commands(void *user_data, ikspak *pak)
if (!strcasecmp(iks_name(tag), "bind")) { if (!strcasecmp(iks_name(tag), "bind")) {
char *jid = iks_find_cdata(tag, "jid"); char *jid = iks_find_cdata(tag, "jid");
char *resource = strchr(jid, '/'); char *resource = strchr(jid, '/');
iks *iq, *x; //iks *iq, *x;
handle->acc->resource = apr_pstrdup(handle->pool, resource); handle->acc->resource = apr_pstrdup(handle->pool, resource);
handle->login = apr_pstrdup(handle->pool, jid); handle->login = apr_pstrdup(handle->pool, jid);
#if 0
if ((iq = iks_new("iq"))) { if ((iq = iks_new("iq"))) {
iks_insert_attrib(iq, "type", "get"); iks_insert_attrib(iq, "type", "get");
iks_insert_attrib(iq, "id", "roster"); iks_insert_attrib(iq, "id", "roster");
@ -555,6 +853,7 @@ static int on_commands(void *user_data, ikspak *pak)
iks_delete(iq); iks_delete(iq);
break; break;
} }
#endif
} }
tag = iks_next_tag(tag); tag = iks_next_tag(tag);
} }
@ -579,10 +878,11 @@ static int on_commands(void *user_data, ikspak *pak)
if (!strcasecmp(name, "session")) { if (!strcasecmp(name, "session")) {
char *id = iks_find_attrib(xml, "id"); char *id = iks_find_attrib(xml, "id");
//printf("SESSION type=%s name=%s id=%s\n", type, name, id); //printf("SESSION type=%s name=%s id=%s\n", type, name, id);
if (parse_session_code(handle, id, from, xml, strcasecmp(type, "error") ? NULL : type) == LDL_STATUS_SUCCESS) { if (parse_session_code(handle, id, from, to, xml, strcasecmp(type, "error") ? NULL : type) == LDL_STATUS_SUCCESS) {
iks *reply; iks *reply;
reply = iks_make_iq(IKS_TYPE_RESULT, NULL); reply = iks_make_iq(IKS_TYPE_RESULT, NULL);
iks_insert_attrib(reply, "to", from); iks_insert_attrib(reply, "to", from);
iks_insert_attrib(reply, "from", to);
iks_insert_attrib(reply, "id", iqid); iks_insert_attrib(reply, "id", iqid);
apr_queue_push(handle->queue, reply); apr_queue_push(handle->queue, reply);
} }
@ -644,7 +944,88 @@ static int b64encode(unsigned char *in, uint32_t ilen, unsigned char *out, uint3
return 0; return 0;
} }
static int on_stream(ldl_handle_t *handle, int type, iks * node) static void sha1_hash(char *out, char *in)
{
sha_context_t sha;
char *p;
int x;
unsigned char digest[20];
SHA1Init(&sha);
SHA1Update(&sha, (unsigned char *) in, strlen(in));
SHA1Final(digest, &sha);
p = out;
for (x = 0; x < 20; x++) {
p += sprintf(p, "%2.2x", digest[x]);
}
}
static int on_stream_component(ldl_handle_t *handle, int type, iks *node)
{
ikspak *pak = iks_packet(node);
switch (type) {
case IKS_NODE_START:
if (handle->state == CS_NEW) {
char secret[256];
char hash[256];
char handshake[512];
snprintf(secret, sizeof(secret), "%s%s", pak->id, handle->password);
sha1_hash(hash, secret);
snprintf(handshake, sizeof(handshake), "<handshake>%s</handshake>", hash);
iks_send_raw(handle->parser, handshake);
handle->state = CS_START;
if (iks_recv(handle->parser, 1) == 2) {
handle->state = CS_CONNECTED;
if (!ldl_test_flag(handle, LDL_FLAG_AUTHORIZED)) {
ldl_set_flag_locked(handle, LDL_FLAG_READY);
do_roster(handle);
if (handle->session_callback) {
handle->session_callback(handle, NULL, LDL_SIGNAL_LOGIN_SUCCESS, "user", "core", "Login Success", handle->login);
}
globals.logger(DL_LOG_DEBUG, "XMPP authenticated\n");
ldl_set_flag_locked(handle, LDL_FLAG_AUTHORIZED);
}
} else {
globals.logger(DL_LOG_ERR, "LOGIN ERROR!\n");
handle->state = CS_NEW;
}
break;
}
break;
case IKS_NODE_NORMAL:
break;
case IKS_NODE_ERROR:
globals.logger(DL_LOG_ERR, "NODE ERROR!\n");
return IKS_HOOK;
case IKS_NODE_STOP:
globals.logger(DL_LOG_ERR, "DISCONNECTED!\n");
return IKS_HOOK;
}
pak = iks_packet(node);
iks_filter_packet(handle->filter, pak);
if (handle->job_done == 1) {
return IKS_HOOK;
}
if (node) {
iks_delete(node);
}
return IKS_OK;
}
static int on_stream(ldl_handle_t *handle, int type, iks *node)
{ {
handle->counter = opt_timeout; handle->counter = opt_timeout;
@ -708,20 +1089,20 @@ static int on_stream(ldl_handle_t *handle, int type, iks * node)
} else if (strcmp("failure", iks_name(node)) == 0) { } else if (strcmp("failure", iks_name(node)) == 0) {
globals.logger(DL_LOG_DEBUG, "sasl authentication failed\n"); globals.logger(DL_LOG_DEBUG, "sasl authentication failed\n");
if (handle->session_callback) { if (handle->session_callback) {
handle->session_callback(handle, NULL, LDL_SIGNAL_LOGIN_FAILURE, "core", "Login Failure", handle->login); handle->session_callback(handle, NULL, LDL_SIGNAL_LOGIN_FAILURE, "user", "core", "Login Failure", handle->login);
} }
} else if (strcmp("success", iks_name(node)) == 0) { } else if (strcmp("success", iks_name(node)) == 0) {
globals.logger(DL_LOG_DEBUG, "XMPP server connected\n"); globals.logger(DL_LOG_DEBUG, "XMPP server connected\n");
iks_send_header(handle->parser, handle->acc->server); iks_send_header(handle->parser, handle->acc->server);
ldl_set_flag_locked(handle, LDL_FLAG_CONNECTED); ldl_set_flag_locked(handle, LDL_FLAG_CONNECTED);
if (handle->session_callback) { if (handle->session_callback) {
handle->session_callback(handle, NULL, LDL_SIGNAL_CONNECTED, "core", "Server Connected", handle->login); handle->session_callback(handle, NULL, LDL_SIGNAL_CONNECTED, "user", "core", "Server Connected", handle->login);
} }
} else { } else {
ikspak *pak; ikspak *pak;
if (!ldl_test_flag(handle, LDL_FLAG_AUTHORIZED)) { if (!ldl_test_flag(handle, LDL_FLAG_AUTHORIZED)) {
if (handle->session_callback) { if (handle->session_callback) {
handle->session_callback(handle, NULL, LDL_SIGNAL_LOGIN_SUCCESS, "core", "Login Success", handle->login); handle->session_callback(handle, NULL, LDL_SIGNAL_LOGIN_SUCCESS, "user", "core", "Login Success", handle->login);
} }
globals.logger(DL_LOG_DEBUG, "XMPP authenticated\n"); globals.logger(DL_LOG_DEBUG, "XMPP authenticated\n");
ldl_set_flag_locked(handle, LDL_FLAG_AUTHORIZED); ldl_set_flag_locked(handle, LDL_FLAG_AUTHORIZED);
@ -754,6 +1135,7 @@ static int on_stream(ldl_handle_t *handle, int type, iks * node)
static int on_msg(void *user_data, ikspak *pak) static int on_msg(void *user_data, ikspak *pak)
{ {
char *cmd = iks_find_cdata(pak->x, "body"); char *cmd = iks_find_cdata(pak->x, "body");
char *to = iks_find_attrib(pak->x, "to");
char *from = iks_find_attrib(pak->x, "from"); char *from = iks_find_attrib(pak->x, "from");
char *subject = iks_find_attrib(pak->x, "subject"); char *subject = iks_find_attrib(pak->x, "subject");
ldl_handle_t *handle = user_data; ldl_handle_t *handle = user_data;
@ -764,7 +1146,7 @@ static int on_msg(void *user_data, ikspak *pak)
} }
if (handle->session_callback) { if (handle->session_callback) {
handle->session_callback(handle, session, LDL_SIGNAL_MSG, from, subject ? subject : "N/A", cmd); handle->session_callback(handle, session, LDL_SIGNAL_MSG, to, from, subject ? subject : "N/A", cmd);
} }
return 0; return 0;
@ -789,18 +1171,13 @@ static void on_log(ldl_handle_t *handle, const char *data, size_t size, int is_i
fprintf(stderr, "[%s]\n", data); fprintf(stderr, "[%s]\n", data);
} }
static void j_setup_filter(ldl_handle_t *handle, char *login) static void j_setup_filter(ldl_handle_t *handle)
{ {
if (handle->filter) { if (handle->filter) {
iks_filter_delete(handle->filter); iks_filter_delete(handle->filter);
} }
handle->filter = iks_filter_new(); handle->filter = iks_filter_new();
/*
iks_filter_add_rule(handle->filter, on_msg, 0,
IKS_RULE_TYPE, IKS_PAK_MESSAGE,
IKS_RULE_SUBTYPE, IKS_TYPE_CHAT, IKS_RULE_FROM, login, IKS_RULE_DONE);
*/
iks_filter_add_rule(handle->filter, on_msg, handle, IKS_RULE_TYPE, IKS_PAK_MESSAGE, IKS_RULE_SUBTYPE, IKS_TYPE_CHAT, IKS_RULE_DONE); iks_filter_add_rule(handle->filter, on_msg, handle, IKS_RULE_TYPE, IKS_PAK_MESSAGE, IKS_RULE_SUBTYPE, IKS_TYPE_CHAT, IKS_RULE_DONE);
iks_filter_add_rule(handle->filter, on_result, handle, iks_filter_add_rule(handle->filter, on_result, handle,
@ -832,9 +1209,31 @@ static void j_setup_filter(ldl_handle_t *handle, char *login)
IKS_RULE_SUBTYPE, IKS_TYPE_SUBSCRIBE, IKS_RULE_SUBTYPE, IKS_TYPE_SUBSCRIBE,
IKS_RULE_DONE); IKS_RULE_DONE);
iks_filter_add_rule(handle->filter, on_unsubscribe, handle,
IKS_RULE_TYPE, IKS_PAK_S10N,
IKS_RULE_SUBTYPE, IKS_TYPE_UNSUBSCRIBE,
IKS_RULE_DONE);
iks_filter_add_rule(handle->filter, on_error, handle, iks_filter_add_rule(handle->filter, on_error, handle,
IKS_RULE_TYPE, IKS_PAK_IQ, IKS_RULE_TYPE, IKS_PAK_IQ,
IKS_RULE_SUBTYPE, IKS_TYPE_ERROR, IKS_RULE_ID, "auth", IKS_RULE_DONE); IKS_RULE_SUBTYPE, IKS_TYPE_ERROR, IKS_RULE_ID, "auth", IKS_RULE_DONE);
if (ldl_test_flag(handle, LDL_FLAG_COMPONENT)) {
iks_filter_add_rule(handle->filter, on_component_disco_info, handle,
IKS_RULE_NS, "http://jabber.org/protocol/disco#info", IKS_RULE_DONE);
iks_filter_add_rule(handle->filter, on_disco_items, handle,
IKS_RULE_NS, "http://jabber.org/protocol/disco#items", IKS_RULE_DONE);
iks_filter_add_rule(handle->filter, on_disco_reg_in, handle,
IKS_RULE_SUBTYPE, IKS_TYPE_GET, IKS_RULE_NS, "jabber:iq:register", IKS_RULE_DONE);
iks_filter_add_rule(handle->filter, on_disco_reg_out, handle,
IKS_RULE_SUBTYPE, IKS_TYPE_SET, IKS_RULE_NS, "jabber:iq:register", IKS_RULE_DONE);
} else {
iks_filter_add_rule(handle->filter, on_disco_info, handle,
IKS_RULE_NS, "http://jabber.org/protocol/disco#info", IKS_RULE_DONE);
}
} }
static void ldl_flush_queue(ldl_handle_t *handle) static void ldl_flush_queue(ldl_handle_t *handle)
@ -928,26 +1327,35 @@ static void xmpp_connect(ldl_handle_t *handle, char *jabber_id, char *pass)
{ {
while (ldl_test_flag(handle, LDL_FLAG_RUNNING)) { while (ldl_test_flag(handle, LDL_FLAG_RUNNING)) {
int e; int e;
char tmp[512], *sl;
handle->parser = iks_stream_new(ldl_test_flag(handle, LDL_FLAG_COMPONENT) ? IKS_NS_COMPONENT : IKS_NS_CLIENT,
handle,
(iksStreamHook *) (ldl_test_flag(handle, LDL_FLAG_COMPONENT) ? on_stream_component : on_stream));
handle->parser = iks_stream_new(IKS_NS_CLIENT, handle, (iksStreamHook *) on_stream);
if (globals.debug) { if (globals.debug) {
iks_set_log_hook(handle->parser, (iksLogHook *) on_log); iks_set_log_hook(handle->parser, (iksLogHook *) on_log);
} }
handle->acc = iks_id_new(iks_parser_stack(handle->parser), jabber_id);
if (NULL == handle->acc->resource) { strncpy(tmp, jabber_id, sizeof(tmp)-1);
sl = strchr(tmp, '/');
if (!sl && !ldl_test_flag(handle, LDL_FLAG_COMPONENT)) {
/* user gave no resource name, use the default */ /* user gave no resource name, use the default */
char tmp[512]; snprintf(tmp + strlen(tmp), sizeof(tmp) - strlen(tmp), "/%s", "talk");
sprintf(tmp, "%s@%s/%s", handle->acc->user, handle->acc->server, "dingaling"); } else if (sl && ldl_test_flag(handle, LDL_FLAG_COMPONENT)) {
handle->acc = iks_id_new(iks_parser_stack(handle->parser), tmp); *sl = '\0';
} }
handle->acc = iks_id_new(iks_parser_stack(handle->parser), tmp);
handle->password = pass; handle->password = pass;
j_setup_filter(handle, "fixme"); j_setup_filter(handle);
e = iks_connect_via(handle->parser, e = iks_connect_via(handle->parser,
handle->server ? handle->server : handle->acc->server, handle->server ? handle->server : handle->acc->server,
handle->port ? handle->port : IKS_JABBER_PORT, handle->port ? handle->port : IKS_JABBER_PORT,
//handle->server ? handle->server : handle->acc->server);
handle->acc->server); handle->acc->server);
switch (e) { switch (e) {
@ -1040,7 +1448,7 @@ static ldl_status new_session_iq(ldl_session_t *session, iks **iqp, iks **sessp,
snprintf(idbuf, sizeof(idbuf), "%u", myid); snprintf(idbuf, sizeof(idbuf), "%u", myid);
iq = iks_new("iq"); iq = iks_new("iq");
iks_insert_attrib(iq, "xmlns", "jabber:client"); iks_insert_attrib(iq, "xmlns", "jabber:client");
iks_insert_attrib(iq, "from", session->handle->login); iks_insert_attrib(iq, "from", session->login);
iks_insert_attrib(iq, "to", session->them); iks_insert_attrib(iq, "to", session->them);
iks_insert_attrib(iq, "type", "set"); iks_insert_attrib(iq, "type", "set");
iks_insert_attrib(iq, "id", idbuf); iks_insert_attrib(iq, "id", idbuf);
@ -1092,6 +1500,11 @@ char *ldl_session_get_caller(ldl_session_t *session)
return session->them; return session->them;
} }
char *ldl_session_get_callee(ldl_session_t *session)
{
return session->login;
}
void ldl_session_set_ip(ldl_session_t *session, char *ip) void ldl_session_set_ip(ldl_session_t *session, char *ip)
{ {
session->ip = apr_pstrdup(session->pool, ip); session->ip = apr_pstrdup(session->pool, ip);
@ -1123,7 +1536,7 @@ void ldl_session_accept_candidate(ldl_session_t *session, ldl_candidate_t *candi
iq = iks_new("iq"); iq = iks_new("iq");
iks_insert_attrib(iq, "type", "set"); iks_insert_attrib(iq, "type", "set");
iks_insert_attrib(iq, "id", idbuf); iks_insert_attrib(iq, "id", idbuf);
iks_insert_attrib(iq, "from", session->handle->login); iks_insert_attrib(iq, "from", session->login);
iks_insert_attrib(iq, "to", session->them); iks_insert_attrib(iq, "to", session->them);
sess = iks_insert (iq, "session"); sess = iks_insert (iq, "session");
iks_insert_attrib(sess, "xmlns", "http://www.google.com/session"); iks_insert_attrib(sess, "xmlns", "http://www.google.com/session");
@ -1142,7 +1555,12 @@ void *ldl_handle_get_private(ldl_handle_t *handle)
return handle->private_info; return handle->private_info;
} }
void ldl_handle_send_msg(ldl_handle_t *handle, char *to, char *subject, char *body) void ldl_handle_send_presence(ldl_handle_t *handle, char *from, char *to, char *type, char *message)
{
do_presence(handle, from, to, type, message);
}
void ldl_handle_send_msg(ldl_handle_t *handle, char *from, char *to, char *subject, char *body)
{ {
iks *msg; iks *msg;
@ -1153,6 +1571,12 @@ void ldl_handle_send_msg(ldl_handle_t *handle, char *to, char *subject, char *bo
msg = iks_make_msg(IKS_TYPE_NONE, to, body); msg = iks_make_msg(IKS_TYPE_NONE, to, body);
iks_insert_attrib(msg, "type", "chat"); iks_insert_attrib(msg, "type", "chat");
if (!from) {
from = handle->login;
}
iks_insert_attrib(msg, "from", from);
if (subject) { if (subject) {
iks_insert_attrib(msg, "subject", subject); iks_insert_attrib(msg, "subject", subject);
} }
@ -1235,7 +1659,7 @@ unsigned int ldl_session_candidates(ldl_session_t *session,
return id; return id;
} }
char *ldl_handle_probe(ldl_handle_t *handle, char *id, char *buf, unsigned int len) char *ldl_handle_probe(ldl_handle_t *handle, char *id, char *from, char *buf, unsigned int len)
{ {
iks *pres, *msg; iks *pres, *msg;
char *lid = NULL; char *lid = NULL;
@ -1251,11 +1675,13 @@ char *ldl_handle_probe(ldl_handle_t *handle, char *id, char *buf, unsigned int l
pres = iks_new("presence"); pres = iks_new("presence");
iks_insert_attrib(pres, "type", "probe"); iks_insert_attrib(pres, "type", "probe");
iks_insert_attrib(pres, "from", from);
iks_insert_attrib(pres, "to", id); iks_insert_attrib(pres, "to", id);
apr_hash_set(handle->probe_hash, id, APR_HASH_KEY_STRING, &buffer); apr_hash_set(handle->probe_hash, id, APR_HASH_KEY_STRING, &buffer);
msg = iks_make_s10n (IKS_TYPE_SUBSCRIBE, id, notice); msg = iks_make_s10n (IKS_TYPE_SUBSCRIBE, id, notice);
iks_insert_attrib(pres, "from", from);
apr_queue_push(handle->queue, msg); apr_queue_push(handle->queue, msg);
msg = iks_make_s10n (IKS_TYPE_SUBSCRIBED, id, notice); msg = iks_make_s10n (IKS_TYPE_SUBSCRIBED, id, notice);
apr_queue_push(handle->queue, msg); apr_queue_push(handle->queue, msg);
@ -1263,6 +1689,75 @@ char *ldl_handle_probe(ldl_handle_t *handle, char *id, char *buf, unsigned int l
//schedule_packet(handle, next_id(), pres, LDL_RETRY); //schedule_packet(handle, next_id(), pres, LDL_RETRY);
started = apr_time_now();
for(;;) {
elapsed = (unsigned int)((apr_time_now() - started) / 1000);
if (elapsed > 5000 && ! again) {
msg = iks_make_s10n (IKS_TYPE_SUBSCRIBE, id, notice);
iks_insert_attrib(pres, "from", from);
apr_queue_push(handle->queue, msg);
again++;
}
if (elapsed > 10000) {
break;
}
if (buffer.hit) {
lid = buffer.buf;
break;
}
ldl_yield(1000);
}
apr_hash_set(handle->probe_hash, id, APR_HASH_KEY_STRING, NULL);
return lid;
}
char *ldl_handle_disco(ldl_handle_t *handle, char *id, char *from, char *buf, unsigned int len)
{
iks *iq, *query, *msg;
char *lid = NULL;
struct ldl_buffer buffer;
apr_time_t started;
unsigned int elapsed;
char *notice = "Call Me!";
int again = 0;
unsigned int myid;
char idbuf[80];
myid = next_id();
snprintf(idbuf, sizeof(idbuf), "%u", myid);
buffer.buf = buf;
buffer.len = len;
buffer.hit = 0;
if ((iq = iks_new("iq"))) {
if ((query = iks_insert(iq, "query"))) {
iks_insert_attrib(iq, "type", "get");
iks_insert_attrib(iq, "to", id);
iks_insert_attrib(iq,"from", from);
iks_insert_attrib(iq, "id", idbuf);
iks_insert_attrib(query, "xmlns", "http://jabber.org/protocol/disco#info");
} else {
iks_delete(iq);
globals.logger(DL_LOG_DEBUG, "Memory ERROR!\n");
return NULL;
}
} else {
globals.logger(DL_LOG_DEBUG, "Memory ERROR!\n");
return NULL;
}
apr_hash_set(handle->probe_hash, id, APR_HASH_KEY_STRING, &buffer);
msg = iks_make_s10n (IKS_TYPE_SUBSCRIBE, id, notice);
apr_queue_push(handle->queue, msg);
msg = iks_make_s10n (IKS_TYPE_SUBSCRIBED, id, notice);
apr_queue_push(handle->queue, msg);
apr_queue_push(handle->queue, iq);
//schedule_packet(handle, next_id(), pres, LDL_RETRY);
started = apr_time_now(); started = apr_time_now();
for(;;) { for(;;) {
elapsed = (unsigned int)((apr_time_now() - started) / 1000); elapsed = (unsigned int)((apr_time_now() - started) / 1000);

View File

@ -50,6 +50,7 @@ extern "C" {
#define LDL_MAX_CANDIDATES 10 #define LDL_MAX_CANDIDATES 10
#define LDL_MAX_PAYLOADS 50 #define LDL_MAX_PAYLOADS 50
#define LDL_RETRY 3 #define LDL_RETRY 3
#define IKS_NS_COMPONENT "jabber:component:accept"
/*! \brief A structure to store a jingle candidate */ /*! \brief A structure to store a jingle candidate */
struct ldl_candidate { struct ldl_candidate {
@ -105,13 +106,14 @@ typedef enum {
LDL_FLAG_AUTHORIZED = (1 << 2), LDL_FLAG_AUTHORIZED = (1 << 2),
LDL_FLAG_READY = (1 << 3), LDL_FLAG_READY = (1 << 3),
LDL_FLAG_CONNECTED = (1 << 4), LDL_FLAG_CONNECTED = (1 << 4),
LDL_FLAG_QUEUE_RUNNING = (1 << 5), LDL_FLAG_QUEUE_RUNNING = (1 << 5)
} ldl_flag_t; } ldl_flag_t;
typedef enum { typedef enum {
LDL_FLAG_TLS = (1 << 10), LDL_FLAG_TLS = (1 << 10),
LDL_FLAG_SASL_PLAIN = (1 << 11), LDL_FLAG_SASL_PLAIN = (1 << 11),
LDL_FLAG_SASL_MD5 = (1 << 12) LDL_FLAG_SASL_MD5 = (1 << 12),
LDL_FLAG_COMPONENT = (1 << 13),
} ldl_user_flag_t; } ldl_user_flag_t;
typedef enum { typedef enum {
@ -121,6 +123,9 @@ typedef enum {
LDL_SIGNAL_MSG, LDL_SIGNAL_MSG,
LDL_SIGNAL_PRESENCE_IN, LDL_SIGNAL_PRESENCE_IN,
LDL_SIGNAL_PRESENCE_OUT, LDL_SIGNAL_PRESENCE_OUT,
LDL_SIGNAL_ROSTER,
LDL_SIGNAL_SUBSCRIBE,
LDL_SIGNAL_UNSUBSCRIBE,
LDL_SIGNAL_TERMINATE, LDL_SIGNAL_TERMINATE,
LDL_SIGNAL_ERROR, LDL_SIGNAL_ERROR,
LDL_SIGNAL_LOGIN_SUCCESS, LDL_SIGNAL_LOGIN_SUCCESS,
@ -156,7 +161,7 @@ typedef enum {
#define DL_LOG_EMERG DL_PRE, 0 #define DL_LOG_EMERG DL_PRE, 0
typedef ldl_status (*ldl_loop_callback_t)(ldl_handle_t *); typedef ldl_status (*ldl_loop_callback_t)(ldl_handle_t *);
typedef ldl_status (*ldl_session_callback_t)(ldl_handle_t *, ldl_session_t *, ldl_signal_t, char *, char *, char *); typedef ldl_status (*ldl_session_callback_t)(ldl_handle_t *, ldl_session_t *, ldl_signal_t, char *, char *, char *, char *);
typedef ldl_status (*ldl_response_callback_t)(ldl_handle_t *, char *); typedef ldl_status (*ldl_response_callback_t)(ldl_handle_t *, char *);
typedef void (*ldl_logger_t)(char *file, const char *func, int line, int level, char *fmt, ...); typedef void (*ldl_logger_t)(char *file, const char *func, int line, int level, char *fmt, ...);
@ -265,6 +270,13 @@ char *ldl_session_get_id(ldl_session_t *session);
*/ */
char *ldl_session_get_caller(ldl_session_t *session); char *ldl_session_get_caller(ldl_session_t *session);
/*!
\brief Get the callee name of a session
\param session the session to get the callee from
\return the callee name
*/
char *ldl_session_get_callee(ldl_session_t *session);
/*! /*!
\brief Set the ip of a session \brief Set the ip of a session
\param session the session to set the ip on \param session the session to set the ip on
@ -310,11 +322,23 @@ void ldl_global_set_logger(ldl_logger_t logger);
\brief Perform a probe on a given id to resolve the proper Jingle Resource \brief Perform a probe on a given id to resolve the proper Jingle Resource
\param handle the connection handle to use. \param handle the connection handle to use.
\param id the id to probe \param id the id to probe
\param from the from string
\param buf a string to store the result \param buf a string to store the result
\param len the size in bytes of the string \param len the size in bytes of the string
\return a pointer to buf if a successful lookup was made otherwise NULL \return a pointer to buf if a successful lookup was made otherwise NULL
*/ */
char *ldl_handle_probe(ldl_handle_t *handle, char *id, char *buf, unsigned int len); char *ldl_handle_probe(ldl_handle_t *handle, char *id, char *from, char *buf, unsigned int len);
/*!
\brief Perform a discovery on a given id to resolve the proper Jingle Resource
\param handle the connection handle to use.
\param id the id to probe
\param from the from string
\param buf a string to store the result
\param len the size in bytes of the string
\return a pointer to buf if a successful lookup was made otherwise NULL
*/
char *ldl_handle_disco(ldl_handle_t *handle, char *id, char *from, char *buf, unsigned int len);
/*! /*!
\brief Signal a termination request on a given session \brief Signal a termination request on a given session
@ -339,14 +363,25 @@ void *ldl_handle_get_private(ldl_handle_t *handle);
*/ */
void ldl_session_send_msg(ldl_session_t *session, char *subject, char *body); void ldl_session_send_msg(ldl_session_t *session, char *subject, char *body);
/*!
\brief Send a presence notification to a target
\param handle the handle to send with
\param from the from address
\param to the to address
\param type the type of presence
\param message a status message
*/
void ldl_handle_send_presence(ldl_handle_t *handle, char *from, char *to, char *type, char *message);
/*! /*!
\brief Send a message \brief Send a message
\param handle the conection handle \param handle the conection handle
\param from the message sender
\param to the message recipiant \param to the message recipiant
\param subject optional subject \param subject optional subject
\param body body of the message \param body body of the message
*/ */
void ldl_handle_send_msg(ldl_handle_t *handle, char *to, char *subject, char *body); void ldl_handle_send_msg(ldl_handle_t *handle, char *from, char *to, char *subject, char *body);
/*! /*!
\brief Offer candidates to a potential session \brief Offer candidates to a potential session

View File

@ -0,0 +1,203 @@
/*
* libDingaLing XMPP Jingle Library
* Copyright (C) 2005/2006, Anthony Minessale II <anthmct@yahoo.com>
*
* 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 libDingaLing XMPP Jingle Library
*
* The Initial Developer of the Original Code is
* Steve Reid <steve@edmweb.com>
*
* Portions created by the Initial Developer are Copyright (C)
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
*
* Steve Reid <steve@edmweb.com>
*
* sha1.h
*
*/
/*! \file sha1.c
\brief SHA1
*/
/*
ORIGINAL HEADERS
----------------------------------------------------------------------------------------------
SHA-1 in C
By Steve Reid <steve@edmweb.com>
100% Public Domain
Test Vectors (from FIPS PUB 180-1)
"abc"
A9993E36 4706816A BA3E2571 7850C26C 9CD0D89D
"abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq"
84983E44 1C3BD26E BAAE4AA1 F95129E5 E54670F1
A million repetitions of "a"
34AA973C D4C4DAA4 F61EEB2B DBAD2731 6534016F
*/
/* #define LITTLE_ENDIAN * This should be #define'd if true. */
/* #define SHA1HANDSOFF * Copies data before messing with it. */
#include <stdio.h>
#include <string.h>
#include "config.h"
#include "sha1.h"
#define rol(value, bits) (((value) << (bits)) | ((value) >> (32 - (bits))))
/* blk0() and blk() perform the initial expand. */
/* I got the idea of expanding during the round function from SSLeay */
#if __BYTE_ORDER == __LITTLE_ENDIAN
#define blk0(i) (block->l[i] = (rol(block->l[i],24)&0xFF00FF00) \
|(rol(block->l[i],8)&0x00FF00FF))
#else
#define blk0(i) block->l[i]
#endif
#define blk(i) (block->l[i&15] = rol(block->l[(i+13)&15]^block->l[(i+8)&15] \
^block->l[(i+2)&15]^block->l[i&15],1))
/* (R0+R1), R2, R3, R4 are the different operations used in SHA1 */
#define R0(v,w,x,y,z,i) z+=((w&(x^y))^y)+blk0(i)+0x5A827999+rol(v,5);w=rol(w,30);
#define R1(v,w,x,y,z,i) z+=((w&(x^y))^y)+blk(i)+0x5A827999+rol(v,5);w=rol(w,30);
#define R2(v,w,x,y,z,i) z+=(w^x^y)+blk(i)+0x6ED9EBA1+rol(v,5);w=rol(w,30);
#define R3(v,w,x,y,z,i) z+=(((w|x)&y)|(w&x))+blk(i)+0x8F1BBCDC+rol(v,5);w=rol(w,30);
#define R4(v,w,x,y,z,i) z+=(w^x^y)+blk(i)+0xCA62C1D6+rol(v,5);w=rol(w,30);
/* Hash a single 512-bit block. This is the core of the algorithm. */
void SHA1Transform(unsigned long state[5], unsigned char buffer[64])
{
unsigned long a, b, c, d, e;
typedef union {
unsigned char c[64];
unsigned long l[16];
} CHAR64LONG16;
CHAR64LONG16* block;
#ifdef SHA1HANDSOFF
static unsigned char workspace[64];
block = (CHAR64LONG16*)workspace;
memcpy(block, buffer, 64);
#else
block = (CHAR64LONG16*)buffer;
#endif
/* Copy context->state[] to working vars */
a = state[0];
b = state[1];
c = state[2];
d = state[3];
e = state[4];
/* 4 rounds of 20 operations each. Loop unrolled. */
R0(a,b,c,d,e, 0); R0(e,a,b,c,d, 1); R0(d,e,a,b,c, 2); R0(c,d,e,a,b, 3);
R0(b,c,d,e,a, 4); R0(a,b,c,d,e, 5); R0(e,a,b,c,d, 6); R0(d,e,a,b,c, 7);
R0(c,d,e,a,b, 8); R0(b,c,d,e,a, 9); R0(a,b,c,d,e,10); R0(e,a,b,c,d,11);
R0(d,e,a,b,c,12); R0(c,d,e,a,b,13); R0(b,c,d,e,a,14); R0(a,b,c,d,e,15);
R1(e,a,b,c,d,16); R1(d,e,a,b,c,17); R1(c,d,e,a,b,18); R1(b,c,d,e,a,19);
R2(a,b,c,d,e,20); R2(e,a,b,c,d,21); R2(d,e,a,b,c,22); R2(c,d,e,a,b,23);
R2(b,c,d,e,a,24); R2(a,b,c,d,e,25); R2(e,a,b,c,d,26); R2(d,e,a,b,c,27);
R2(c,d,e,a,b,28); R2(b,c,d,e,a,29); R2(a,b,c,d,e,30); R2(e,a,b,c,d,31);
R2(d,e,a,b,c,32); R2(c,d,e,a,b,33); R2(b,c,d,e,a,34); R2(a,b,c,d,e,35);
R2(e,a,b,c,d,36); R2(d,e,a,b,c,37); R2(c,d,e,a,b,38); R2(b,c,d,e,a,39);
R3(a,b,c,d,e,40); R3(e,a,b,c,d,41); R3(d,e,a,b,c,42); R3(c,d,e,a,b,43);
R3(b,c,d,e,a,44); R3(a,b,c,d,e,45); R3(e,a,b,c,d,46); R3(d,e,a,b,c,47);
R3(c,d,e,a,b,48); R3(b,c,d,e,a,49); R3(a,b,c,d,e,50); R3(e,a,b,c,d,51);
R3(d,e,a,b,c,52); R3(c,d,e,a,b,53); R3(b,c,d,e,a,54); R3(a,b,c,d,e,55);
R3(e,a,b,c,d,56); R3(d,e,a,b,c,57); R3(c,d,e,a,b,58); R3(b,c,d,e,a,59);
R4(a,b,c,d,e,60); R4(e,a,b,c,d,61); R4(d,e,a,b,c,62); R4(c,d,e,a,b,63);
R4(b,c,d,e,a,64); R4(a,b,c,d,e,65); R4(e,a,b,c,d,66); R4(d,e,a,b,c,67);
R4(c,d,e,a,b,68); R4(b,c,d,e,a,69); R4(a,b,c,d,e,70); R4(e,a,b,c,d,71);
R4(d,e,a,b,c,72); R4(c,d,e,a,b,73); R4(b,c,d,e,a,74); R4(a,b,c,d,e,75);
R4(e,a,b,c,d,76); R4(d,e,a,b,c,77); R4(c,d,e,a,b,78); R4(b,c,d,e,a,79);
/* Add the working vars back into context.state[] */
state[0] += a;
state[1] += b;
state[2] += c;
state[3] += d;
state[4] += e;
/* Wipe variables */
a = b = c = d = e = 0;
}
/* SHA1Init - Initialize new context */
void SHA1Init(sha_context_t* context)
{
/* SHA1 initialization constants */
context->state[0] = 0x67452301;
context->state[1] = 0xEFCDAB89;
context->state[2] = 0x98BADCFE;
context->state[3] = 0x10325476;
context->state[4] = 0xC3D2E1F0;
context->count[0] = context->count[1] = 0;
}
/* Run your data through this. */
void SHA1Update(sha_context_t* context, unsigned char* data, unsigned int len)
{
unsigned int i, j;
j = (context->count[0] >> 3) & 63;
if ((context->count[0] += len << 3) < (len << 3)) context->count[1]++;
context->count[1] += (len >> 29);
if ((j + len) > 63) {
memcpy(&context->buffer[j], data, (i = 64-j));
SHA1Transform(context->state, context->buffer);
for ( ; i + 63 < len; i += 64) {
SHA1Transform(context->state, &data[i]);
}
j = 0;
}
else i = 0;
memcpy(&context->buffer[j], &data[i], len - i);
}
/* Add padding and return the message digest. */
void SHA1Final(unsigned char digest[20], sha_context_t* context)
{
unsigned long i, j;
unsigned char finalcount[8];
for (i = 0; i < 8; i++) {
finalcount[i] = (unsigned char)((context->count[(i >= 4 ? 0 : 1)]
>> ((3-(i & 3)) * 8) ) & 255); /* Endian independent */
}
SHA1Update(context, (unsigned char *)"\200", 1);
while ((context->count[0] & 504) != 448) {
SHA1Update(context, (unsigned char *)"\0", 1);
}
SHA1Update(context, finalcount, 8); /* Should cause a SHA1Transform() */
for (i = 0; i < 20; i++) {
digest[i] = (unsigned char)
((context->state[i>>2] >> ((3-(i & 3)) * 8) ) & 255);
}
/* Wipe variables */
i = j = 0;
memset(context->buffer, 0, 64);
memset(context->state, 0, 20);
memset(context->count, 0, 8);
memset(&finalcount, 0, 8);
#ifdef SHA1HANDSOFF /* make SHA1Transform overwrite it's own static vars */
SHA1Transform(context->state, context->buffer);
#endif
}

View File

@ -0,0 +1,58 @@
/*
* libDingaLing XMPP Jingle Library
* Copyright (C) 2005/2006, Anthony Minessale II <anthmct@yahoo.com>
*
* 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 libDingaLing XMPP Jingle Library
*
* The Initial Developer of the Original Code is
* Steve Reid <steve@edmweb.com>
* Portions created by the Initial Developer are Copyright (C)
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
*
* Steve Reid <steve@edmweb.com>
*
* sha1.h
*
*/
/*! \file sha1.h
\brief SHA1
*/
#ifndef __SHA1_H
#define __SHA1_H
#ifdef __cplusplus
extern "C" {
#endif
#ifdef __STUPIDFORMATBUG__
}
#endif
typedef struct {
unsigned long state[5];
unsigned long count[2];
unsigned char buffer[64];
} sha_context_t;
void SHA1Transform(unsigned long state[5], unsigned char buffer[64]);
void SHA1Init(sha_context_t* context);
void SHA1Update(sha_context_t* context, unsigned char* data, unsigned int len);
void SHA1Final(unsigned char digest[20], sha_context_t* context);
#ifdef __cplusplus
}
#endif
#endif

View File

@ -841,6 +841,7 @@ SWITCH_DECLARE(switch_status_t) switch_core_timer_destroy(switch_timer_t *timer)
\brief Initialize a codec handle \brief Initialize a codec handle
\param codec the handle to initilize \param codec the handle to initilize
\param codec_name the name of the codec module to use \param codec_name the name of the codec module to use
\param fmtp codec parameters to send
\param rate the desired rate (0 for any) \param rate the desired rate (0 for any)
\param ms the desired number of milliseconds (0 for any) \param ms the desired number of milliseconds (0 for any)
\param channels the desired number of channels (0 for any) \param channels the desired number of channels (0 for any)

View File

@ -97,6 +97,8 @@ struct switch_event {
void *bind_user_data; void *bind_user_data;
/*! user data from the event sender */ /*! user data from the event sender */
void *event_user_data; void *event_user_data;
/*! unique key */
unsigned long key;
struct switch_event *next; struct switch_event *next;
}; };

View File

@ -72,6 +72,7 @@ SWITCH_DECLARE(switch_port_t) switch_rtp_request_port(void);
\param ms_per_packet time in microseconds per packet \param ms_per_packet time in microseconds per packet
\param flags flags to control behaviour \param flags flags to control behaviour
\param crypto_key optional crypto key \param crypto_key optional crypto key
\param timer_name timer interface to use
\param err a pointer to resolve error messages \param err a pointer to resolve error messages
\param pool a memory pool to use for the session \param pool a memory pool to use for the session
\return the new RTP session or NULL on failure \return the new RTP session or NULL on failure
@ -98,6 +99,7 @@ SWITCH_DECLARE(switch_status_t)switch_rtp_create(switch_rtp_t **new_rtp_session,
\param ms_per_packet time in microseconds per packet \param ms_per_packet time in microseconds per packet
\param flags flags to control behaviour \param flags flags to control behaviour
\param crypto_key optional crypto key \param crypto_key optional crypto key
\param timer_name timer interface to use
\param err a pointer to resolve error messages \param err a pointer to resolve error messages
\param pool a memory pool to use for the session \param pool a memory pool to use for the session
\return the new RTP session or NULL on failure \return the new RTP session or NULL on failure

View File

@ -659,6 +659,7 @@ typedef enum {
SWITCH_EVENT_MESSAGE, SWITCH_EVENT_MESSAGE,
SWITCH_EVENT_PRESENCE_IN, SWITCH_EVENT_PRESENCE_IN,
SWITCH_EVENT_PRESENCE_OUT, SWITCH_EVENT_PRESENCE_OUT,
SWITCH_EVENT_ROSTER,
SWITCH_EVENT_CODEC, SWITCH_EVENT_CODEC,
SWITCH_EVENT_BACKGROUND_JOB, SWITCH_EVENT_BACKGROUND_JOB,
SWITCH_EVENT_ALL SWITCH_EVENT_ALL

View File

@ -34,7 +34,7 @@
#define DL_CAND_WAIT 10000000 #define DL_CAND_WAIT 10000000
#define DL_CAND_INITIAL_WAIT 2000000 #define DL_CAND_INITIAL_WAIT 2000000
#define JINGLE_KEY 1
#define DL_EVENT_LOGIN_SUCCESS "dingaling::login_success" #define DL_EVENT_LOGIN_SUCCESS "dingaling::login_success"
#define DL_EVENT_LOGIN_FAILURE "dingaling::login_failure" #define DL_EVENT_LOGIN_FAILURE "dingaling::login_failure"
@ -44,6 +44,13 @@ static const char modname[] = "mod_dingaling";
static switch_memory_pool_t *module_pool = NULL; static switch_memory_pool_t *module_pool = NULL;
static char sub_sql[] =
"CREATE TABLE subscriptions (\n"
" sub_from VARCHAR(255),\n"
" sub_to VARCHAR(255)\n"
");\n";
typedef enum { typedef enum {
TFLAG_IO = (1 << 0), TFLAG_IO = (1 << 0),
TFLAG_INBOUND = (1 << 1), TFLAG_INBOUND = (1 << 1),
@ -104,6 +111,8 @@ struct mdl_profile {
char *exten; char *exten;
char *context; char *context;
char *timer_name; char *timer_name;
char *dbname;
switch_mutex_t *mutex;
ldl_handle_t *handle; ldl_handle_t *handle;
uint32_t flags; uint32_t flags;
uint32_t user_flags; uint32_t user_flags;
@ -173,11 +182,207 @@ static switch_status_t channel_read_frame(switch_core_session_t *session, switch
static switch_status_t channel_write_frame(switch_core_session_t *session, switch_frame_t *frame, int timeout, static switch_status_t channel_write_frame(switch_core_session_t *session, switch_frame_t *frame, int timeout,
switch_io_flag_t flags, int stream_id); switch_io_flag_t flags, int stream_id);
static switch_status_t channel_kill_channel(switch_core_session_t *session, int sig); static switch_status_t channel_kill_channel(switch_core_session_t *session, int sig);
static ldl_status handle_signalling(ldl_handle_t *handle, ldl_session_t *dlsession, ldl_signal_t signal, char *from, char *subject, char *msg); static ldl_status handle_signalling(ldl_handle_t *handle, ldl_session_t *dlsession, ldl_signal_t signal, char *to, char *from, char *subject, char *msg);
static ldl_status handle_response(ldl_handle_t *handle, char *id); static ldl_status handle_response(ldl_handle_t *handle, char *id);
static switch_status_t load_config(void); static switch_status_t load_config(void);
static int sub_callback(void *pArg, int argc, char **argv, char **columnNames)
{
struct mdl_profile *profile = (struct mdl_profile *) pArg;
char *sub_from = argv[0];
char *sub_to = argv[1];
char *type = argv[2];
char *show = argv[3];
if (switch_strlen_zero(type)) {
type = NULL;
} else if (!strcasecmp(type, "unavailable")) {
show = NULL;
}
ldl_handle_send_presence(profile->handle, sub_to, sub_from, type, show);
return 0;
}
static int rost_callback(void *pArg, int argc, char **argv, char **columnNames)
{
struct mdl_profile *profile = (struct mdl_profile *) pArg;
char *sub_from = argv[0];
char *sub_to = argv[1];
char *show = argv[2];
ldl_handle_send_presence(profile->handle, sub_to, sub_from, NULL, show);
return 0;
}
static void pres_event_handler(switch_event_t *event)
{
struct mdl_profile *profile = NULL;
switch_hash_index_t *hi;
void *val;
char *from = switch_event_get_header(event, "from");
char *status= switch_event_get_header(event, "status");
char *show= switch_event_get_header(event, "show");
char *type = NULL;
char *sql;
switch_core_db_t *db;
char *p;
if (event->key == JINGLE_KEY) {
return;
}
if (status && !strcasecmp(status, "n/a")) {
status = show;
if (status && !strcasecmp(status, "n/a")) {
status = NULL;
}
}
switch(event->event_id) {
case SWITCH_EVENT_PRESENCE_IN:
if (!status) {
status = "Available";
}
break;
case SWITCH_EVENT_PRESENCE_OUT:
type = "unavailable";
break;
default:
break;
}
if ((p = strchr(from, '/'))) {
*p = '\0';
}
sql = switch_core_db_mprintf("select *,'%q','%q' from subscriptions where sub_to='%q'", type ? type : "", status ? status : "unavailable", from);
for (hi = switch_hash_first(apr_hash_pool_get(globals.profile_hash), globals.profile_hash); hi; hi = switch_hash_next(hi)) {
switch_hash_this(hi, NULL, NULL, &val);
profile = (struct mdl_profile *) val;
char *errmsg;
if (!(profile->user_flags & LDL_FLAG_COMPONENT)) {
continue;
}
if (sql) {
if (!(db = switch_core_db_open_file(profile->dbname))) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Error Opening DB %s\n", profile->dbname);
continue;
}
switch_mutex_lock(profile->mutex);
switch_core_db_exec(db, sql, sub_callback, profile, &errmsg);
switch_mutex_unlock(profile->mutex);
switch_core_db_close(db);
}
}
switch_safe_free(sql);
}
static void chat_event_handler(switch_event_t *event)
{
char *from = switch_event_get_header(event, "from");
char *to = switch_event_get_header(event, "to");
char *body = switch_event_get_body(event);
char *user, *host, *f_user, *f_host = NULL;
struct mdl_profile *profile = NULL;
if (from && (f_user = strdup(from))) {
if ((f_host = strchr(f_user, '@'))) {
*f_host++ = '\0';
}
}
if (to && (user = strdup(to))) {
if ((host = strchr(user, '@'))) {
*host++ = '\0';
}
if (f_host && (profile = switch_core_hash_find(globals.profile_hash, f_host))) {
ldl_handle_send_msg(profile->handle, from, to, NULL, body);
} else {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Invalid Profile %s\n", f_host ? f_host : "NULL");
return;
}
switch_safe_free(f_host);
free(user);
}
}
static void roster_event_handler(switch_event_t *event)
{
char *status= switch_event_get_header(event, "status");
char *show= switch_event_get_header(event, "show");
char *event_type = switch_event_get_header(event, "event_type");
struct mdl_profile *profile = NULL;
switch_hash_index_t *hi;
void *val;
char *sql;
switch_core_db_t *db;
if (event->key == JINGLE_KEY) {
return;
}
if (status && !strcasecmp(status, "n/a")) {
status = show;
if (status && !strcasecmp(status, "n/a")) {
status = NULL;
}
}
if (switch_strlen_zero(event_type)) {
event_type="presence";
}
sql = switch_core_db_mprintf("select *,'%q' from subscriptions", show ? show : "unavilable");
for (hi = switch_hash_first(apr_hash_pool_get(globals.profile_hash), globals.profile_hash); hi; hi = switch_hash_next(hi)) {
switch_hash_this(hi, NULL, NULL, &val);
profile = (struct mdl_profile *) val;
char *errmsg;
if (!(profile->user_flags & LDL_FLAG_COMPONENT)) {
continue;
}
if (sql) {
if (!(db = switch_core_db_open_file(profile->dbname))) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Error Opening DB %s\n", profile->dbname);
continue;
}
switch_mutex_lock(profile->mutex);
switch_core_db_exec(db, sql, rost_callback, profile, &errmsg);
switch_mutex_unlock(profile->mutex);
switch_core_db_close(db);
}
}
switch_safe_free(sql);
}
static void terminate_session(switch_core_session_t **session, int line, switch_call_cause_t cause) static void terminate_session(switch_core_session_t **session, int line, switch_call_cause_t cause)
{ {
if (*session) { if (*session) {
@ -645,7 +850,7 @@ static switch_status_t channel_on_ring(switch_core_session_t *session)
tech_pvt = switch_core_session_get_private(session); tech_pvt = switch_core_session_get_private(session);
assert(tech_pvt != NULL); assert(tech_pvt != NULL);
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "%s CHANNEL RING\n", switch_channel_get_name(channel)); switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "%s CHANNEL RING\n", switch_channel_get_name(channel));
return SWITCH_STATUS_SUCCESS; return SWITCH_STATUS_SUCCESS;
@ -1079,6 +1284,7 @@ static switch_status_t channel_outgoing_channel(switch_core_session_t *session,
char sess_id[11] = ""; char sess_id[11] = "";
char *dnis = NULL; char *dnis = NULL;
char workspace[1024] = ""; char workspace[1024] = "";
char *p, *u, ubuf[512] = "", *user = NULL;;
switch_copy_string(workspace, outbound_profile->destination_number, sizeof(workspace)); switch_copy_string(workspace, outbound_profile->destination_number, sizeof(workspace));
profile_name = workspace; profile_name = workspace;
@ -1094,13 +1300,23 @@ static switch_status_t channel_outgoing_channel(switch_core_session_t *session,
*dnis++ = '\0'; *dnis++ = '\0';
} }
if ((p = strchr(profile_name, '@'))) {
*p++ = '\0';
u = profile_name;
profile_name = p;
snprintf(ubuf, sizeof(ubuf), "%s@%s/talk", u, profile_name);
user = ubuf;
} else {
user = mdl_profile->login;
}
if ((mdl_profile = switch_core_hash_find(globals.profile_hash, profile_name))) { if ((mdl_profile = switch_core_hash_find(globals.profile_hash, profile_name))) {
if (!ldl_handle_ready(mdl_profile->handle)) { if (!ldl_handle_ready(mdl_profile->handle)) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Doh! we are not logged in yet!\n"); switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Doh! we are not logged in yet!\n");
terminate_session(new_session, __LINE__, SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER); terminate_session(new_session, __LINE__, SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER);
return SWITCH_STATUS_GENERR; return SWITCH_STATUS_GENERR;
} }
if (!(full_id = ldl_handle_probe(mdl_profile->handle, callto, idbuf, sizeof(idbuf)))) { if (!(full_id = ldl_handle_probe(mdl_profile->handle, callto, user, idbuf, sizeof(idbuf)))) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Unknown Recipient!\n"); switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Unknown Recipient!\n");
terminate_session(new_session, __LINE__, SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER); terminate_session(new_session, __LINE__, SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER);
return SWITCH_STATUS_GENERR; return SWITCH_STATUS_GENERR;
@ -1151,7 +1367,7 @@ static switch_status_t channel_outgoing_channel(switch_core_session_t *session,
switch_stun_random_string(sess_id, 10, "0123456789"); switch_stun_random_string(sess_id, 10, "0123456789");
ldl_session_create(&dlsession, mdl_profile->handle, sess_id, full_id, mdl_profile->login); ldl_session_create(&dlsession, mdl_profile->handle, sess_id, full_id, user);
tech_pvt->profile = mdl_profile; tech_pvt->profile = mdl_profile;
ldl_session_set_private(dlsession, *new_session); ldl_session_set_private(dlsession, *new_session);
ldl_session_set_value(dlsession, "dnis", dnis); ldl_session_set_value(dlsession, "dnis", dnis);
@ -1195,6 +1411,26 @@ SWITCH_MOD_DECLARE(switch_status_t) switch_module_load(const switch_loadable_mod
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't register subclass %s!", DL_EVENT_CONNECTED); switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't register subclass %s!", DL_EVENT_CONNECTED);
return SWITCH_STATUS_GENERR; return SWITCH_STATUS_GENERR;
} }
if (switch_event_bind((char *) modname, SWITCH_EVENT_PRESENCE_IN, SWITCH_EVENT_SUBCLASS_ANY, pres_event_handler, NULL) != SWITCH_STATUS_SUCCESS) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't bind!\n");
return SWITCH_STATUS_GENERR;
}
if (switch_event_bind((char *) modname, SWITCH_EVENT_PRESENCE_OUT, SWITCH_EVENT_SUBCLASS_ANY, pres_event_handler, NULL) != SWITCH_STATUS_SUCCESS) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't bind!\n");
return SWITCH_STATUS_GENERR;
}
if (switch_event_bind((char *) modname, SWITCH_EVENT_ROSTER, SWITCH_EVENT_SUBCLASS_ANY, roster_event_handler, NULL) != SWITCH_STATUS_SUCCESS) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't bind!\n");
return SWITCH_STATUS_GENERR;
}
if (switch_event_bind((char *) modname, SWITCH_EVENT_MESSAGE, SWITCH_EVENT_SUBCLASS_ANY, chat_event_handler, NULL) != SWITCH_STATUS_SUCCESS) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't bind!\n");
return SWITCH_STATUS_GENERR;
}
/* connect my internal structure to the blank pointer passed to me */ /* connect my internal structure to the blank pointer passed to me */
*module_interface = &channel_module_interface; *module_interface = &channel_module_interface;
@ -1323,6 +1559,25 @@ static void set_profile_val(struct mdl_profile *profile, char *var, char *val)
if (switch_true(val)) { if (switch_true(val)) {
profile->user_flags |= LDL_FLAG_TLS; profile->user_flags |= LDL_FLAG_TLS;
} }
} else if (!strcasecmp(var, "component")) {
if (switch_true(val)) {
char dbname[256];
switch_core_db_t *db;
profile->user_flags |= LDL_FLAG_COMPONENT;
switch_mutex_init(&profile->mutex, SWITCH_MUTEX_NESTED, module_pool);
snprintf(dbname, sizeof(dbname), "dingaling_%s", profile->name);
profile->dbname = switch_core_strdup(module_pool, dbname);
if ((db = switch_core_db_open_file(profile->dbname))) {
switch_core_db_test_reactive(db, "select * from subscriptions", sub_sql);
} else {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_CRIT, "Cannot Open SQL Database!\n");
return;
}
switch_core_db_close(db);
}
} else if (!strcasecmp(var, "sasl")) { } else if (!strcasecmp(var, "sasl")) {
if (!strcasecmp(val, "plain")) { if (!strcasecmp(val, "plain")) {
profile->user_flags |= LDL_FLAG_SASL_PLAIN; profile->user_flags |= LDL_FLAG_SASL_PLAIN;
@ -1510,8 +1765,29 @@ static switch_status_t load_config(void)
} }
static void execute_sql(char *dbname, char *sql, switch_mutex_t *mutex)
{
switch_core_db_t *db;
static ldl_status handle_signalling(ldl_handle_t *handle, ldl_session_t *dlsession, ldl_signal_t signal, char *from, char *subject, char *msg) if (mutex) {
switch_mutex_lock(mutex);
}
if (!(db = switch_core_db_open_file(dbname))) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Error Opening DB %s\n", dbname);
goto end;
}
switch_core_db_persistant_execute(db, sql, 25);
switch_core_db_close(db);
end:
if (mutex) {
switch_mutex_unlock(mutex);
}
}
static ldl_status handle_signalling(ldl_handle_t *handle, ldl_session_t *dlsession, ldl_signal_t signal, char *to, char *from, char *subject, char *msg)
{ {
struct mdl_profile *profile = NULL; struct mdl_profile *profile = NULL;
switch_core_session_t *session = NULL; switch_core_session_t *session = NULL;
@ -1519,7 +1795,8 @@ static ldl_status handle_signalling(ldl_handle_t *handle, ldl_session_t *dlsessi
struct private_object *tech_pvt = NULL; struct private_object *tech_pvt = NULL;
switch_event_t *event; switch_event_t *event;
ldl_status status = LDL_STATUS_SUCCESS; ldl_status status = LDL_STATUS_SUCCESS;
char *sql;
assert(handle != NULL); assert(handle != NULL);
if (!(profile = ldl_handle_get_private(handle))) { if (!(profile = ldl_handle_get_private(handle))) {
@ -1530,6 +1807,32 @@ static ldl_status handle_signalling(ldl_handle_t *handle, ldl_session_t *dlsessi
if (!dlsession) { if (!dlsession) {
switch(signal) { switch(signal) {
case LDL_SIGNAL_UNSUBSCRIBE:
if ((profile->user_flags & LDL_FLAG_COMPONENT)) {
if ((sql = switch_core_db_mprintf("delete from subscriptions where sub_from='%q' and sub_to='%q';", from, to))) {
execute_sql(profile->dbname, sql, profile->mutex);
switch_core_db_free(sql);
}
}
break;
case LDL_SIGNAL_SUBSCRIBE:
if ((profile->user_flags & LDL_FLAG_COMPONENT)) {
if ((sql = switch_core_db_mprintf("insert into subscriptions values('%q','%q')", from, to))) {
execute_sql(profile->dbname, sql, profile->mutex);
switch_core_db_free(sql);
}
}
break;
case LDL_SIGNAL_ROSTER:
if (switch_event_create(&event, SWITCH_EVENT_ROSTER) == SWITCH_STATUS_SUCCESS) {
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "jingle");
//event->key = JINGLE_KEY;
switch_event_fire(&event);
}
break;
case LDL_SIGNAL_PRESENCE_IN: case LDL_SIGNAL_PRESENCE_IN:
if (switch_event_create(&event, SWITCH_EVENT_PRESENCE_IN) == SWITCH_STATUS_SUCCESS) { if (switch_event_create(&event, SWITCH_EVENT_PRESENCE_IN) == SWITCH_STATUS_SUCCESS) {
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "jingle"); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "jingle");
@ -1537,14 +1840,17 @@ static ldl_status handle_signalling(ldl_handle_t *handle, ldl_session_t *dlsessi
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "from", "%s", from); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "from", "%s", from);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "status", "%s", subject); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "status", "%s", subject);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "show", "%s", msg); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "show", "%s", msg);
//event->key = JINGLE_KEY;
switch_event_fire(&event); switch_event_fire(&event);
} }
break; break;
case LDL_SIGNAL_PRESENCE_OUT: case LDL_SIGNAL_PRESENCE_OUT:
if (switch_event_create(&event, SWITCH_EVENT_PRESENCE_OUT) == SWITCH_STATUS_SUCCESS) { if (switch_event_create(&event, SWITCH_EVENT_PRESENCE_OUT) == SWITCH_STATUS_SUCCESS) {
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "jingle"); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "jingle");
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "login", "%s", profile->login); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "login", "%s", profile->login);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "from", "%s", from); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "from", "%s", from);
//event->key = JINGLE_KEY;
switch_event_fire(&event); switch_event_fire(&event);
} }
break; break;
@ -1553,13 +1859,15 @@ static ldl_status handle_signalling(ldl_handle_t *handle, ldl_session_t *dlsessi
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "jingle"); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "jingle");
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "login", "%s", profile->login); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "login", "%s", profile->login);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "from", "%s", from); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "from", "%s", from);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "to", "%s", to);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "subject", "%s", subject); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "subject", "%s", subject);
event->key = JINGLE_KEY;
if (msg) { if (msg) {
switch_event_add_body(event, msg); switch_event_add_body(event, msg);
} }
if (profile->auto_reply) { if (profile->auto_reply) {
ldl_handle_send_msg(handle, from, "", profile->auto_reply); ldl_handle_send_msg(handle, (profile->user_flags & LDL_FLAG_COMPONENT) ? to : profile->login, from, "", profile->auto_reply);
} }
switch_event_fire(&event); switch_event_fire(&event);
@ -1666,6 +1974,7 @@ static ldl_status handle_signalling(ldl_handle_t *handle, ldl_session_t *dlsessi
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "jingle"); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "jingle");
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "login", "%s", profile->login); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "login", "%s", profile->login);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "from", "%s", from); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "from", "%s", from);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "to", "%s", to);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "subject", "%s", subject); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "subject", "%s", subject);
if (msg) { if (msg) {
switch_event_add_body(event, msg); switch_event_add_body(event, msg);
@ -1803,6 +2112,7 @@ static ldl_status handle_signalling(ldl_handle_t *handle, ldl_session_t *dlsessi
char *context; char *context;
char *cid_name; char *cid_name;
char *cid_num; char *cid_num;
char *t, *them = NULL;
memset(payloads, 0, sizeof(payloads)); memset(payloads, 0, sizeof(payloads));
@ -1814,6 +2124,18 @@ static ldl_status handle_signalling(ldl_handle_t *handle, ldl_session_t *dlsessi
if (!(exten = ldl_session_get_value(dlsession, "dnis"))) { if (!(exten = ldl_session_get_value(dlsession, "dnis"))) {
exten = profile->exten; exten = profile->exten;
if (!strcmp(exten, "_auto_")) {
if ((t = ldl_session_get_callee(dlsession))) {
if ((them = strdup(t))) {
char *p;
if ((p = strchr(them, '/'))) {
*p = '\0';
}
exten = them;
}
}
}
} }
if (!(context = ldl_session_get_value(dlsession, "context"))) { if (!(context = ldl_session_get_value(dlsession, "context"))) {
@ -1851,6 +2173,8 @@ static ldl_status handle_signalling(ldl_handle_t *handle, ldl_session_t *dlsessi
} }
} }
switch_safe_free(them);
if (lanaddr) { if (lanaddr) {
switch_set_flag_locked(tech_pvt, TFLAG_LANADDR); switch_set_flag_locked(tech_pvt, TFLAG_LANADDR);
} }

View File

@ -24,6 +24,7 @@
* Contributor(s): * Contributor(s):
* *
* Anthony Minessale II <anthmct@yahoo.com> * Anthony Minessale II <anthmct@yahoo.com>
* Ken Rice, Asteria Solutions Group, Inc <ken@asteriasgi.com>
* *
* *
* mod_sofia.c -- SOFIA SIP Endpoint * mod_sofia.c -- SOFIA SIP Endpoint
@ -66,7 +67,7 @@ typedef struct private_object private_object_t;
#define MULTICAST_EVENT "multicast::event" #define MULTICAST_EVENT "multicast::event"
#define SOFIA_REPLACES_HEADER "_sofia_replaces_" #define SOFIA_REPLACES_HEADER "_sofia_replaces_"
#define SOFIA_USER_AGENT "FreeSWITCH(mod_sofia)" #define SOFIA_USER_AGENT "FreeSWITCH(mod_sofia)"
#define SIP_KEY 2
#include <sofia-sip/nua.h> #include <sofia-sip/nua.h>
#include <sofia-sip/sip_status.h> #include <sofia-sip/sip_status.h>
@ -251,6 +252,8 @@ struct sofia_profile {
outbound_reg_t *registrations; outbound_reg_t *registrations;
sip_presence_t *presence; sip_presence_t *presence;
su_home_t *home; su_home_t *home;
switch_hash_t *profile_hash;
switch_hash_t *chat_hash;
}; };
@ -296,6 +299,10 @@ struct private_object {
char *xferto; char *xferto;
char *kick; char *kick;
char *origin; char *origin;
char *hash_key;
char *chat_from;
char *chat_to;
char *e_dest;
unsigned long rm_rate; unsigned long rm_rate;
switch_payload_t pt; switch_payload_t pt;
switch_mutex_t *flag_mutex; switch_mutex_t *flag_mutex;
@ -530,7 +537,6 @@ static void execute_sql(char *dbname, char *sql, switch_mutex_t *mutex)
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Error Opening DB %s\n", dbname); switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Error Opening DB %s\n", dbname);
goto end; goto end;
} }
switch_core_db_persistant_execute(db, sql, 25); switch_core_db_persistant_execute(db, sql, 25);
switch_core_db_close(db); switch_core_db_close(db);
@ -840,12 +846,57 @@ static switch_status_t tech_choose_port(private_object_t *tech_pvt)
return SWITCH_STATUS_SUCCESS; return SWITCH_STATUS_SUCCESS;
} }
char *encode_name(char *s)
{
char *ss, *sret;
uint32_t len;
char *at, *resource;
char *user;
if (!strchr(s, '/') && !strchr(s, '@')) {
return NULL;
}
if (!(ss = strdup(s))) {
return NULL;
}
user = ss;
resource = strchr(user, '/');
at = strchr(user, '@');
if (resource) {
*resource++ = '\0';
}
len = strlen(user) + 25;
if (at) {
*at++ = '\0';
}
if (!(sret = (char *) malloc(len))) {
return NULL;
}
memset(sret, 0, len);
snprintf(sret, len, "jingle+%s+%s", user, at);
free(ss);
return sret;
}
static void do_invite(switch_core_session_t *session) static void do_invite(switch_core_session_t *session)
{ {
char rpid[1024]; char rpid[1024];
private_object_t *tech_pvt; private_object_t *tech_pvt;
switch_channel_t *channel = NULL; switch_channel_t *channel = NULL;
switch_caller_profile_t *caller_profile; switch_caller_profile_t *caller_profile;
char *cid_name, *cid_num_p = NULL, *cid_num;
char *e_dest = NULL;
channel = switch_core_session_get_channel(session); channel = switch_core_session_get_channel(session);
assert(channel != NULL); assert(channel != NULL);
@ -855,16 +906,22 @@ static void do_invite(switch_core_session_t *session)
caller_profile = switch_channel_get_caller_profile(channel); caller_profile = switch_channel_get_caller_profile(channel);
cid_name = (char *) caller_profile->caller_id_name;
cid_num = (char *) caller_profile->caller_id_number;
if ((cid_num_p = encode_name(cid_num))) {
cid_num = cid_num_p;
}
if ((tech_pvt->from_str = switch_core_db_mprintf("\"%s\" <sip:%s@%s>", if ((tech_pvt->from_str = switch_core_db_mprintf("\"%s\" <sip:%s@%s>",
(char *) caller_profile->caller_id_name, cid_name,
(char *) caller_profile->caller_id_number, cid_num,
tech_pvt->profile->sipip tech_pvt->profile->sipip
))) { ))) {
char *rep = switch_channel_get_variable(channel, SOFIA_REPLACES_HEADER); char *rep = switch_channel_get_variable(channel, SOFIA_REPLACES_HEADER);
tech_choose_port(tech_pvt); tech_choose_port(tech_pvt);
set_local_sdp(tech_pvt); set_local_sdp(tech_pvt);
@ -899,6 +956,23 @@ static void do_invite(switch_core_session_t *session)
} }
if ((e_dest = strdup(tech_pvt->e_dest))) {
char *user = e_dest, *host = NULL;
char hash_key[256] = "";
if ((host = strchr(user, '@'))) {
*host++ = '\0';
}
snprintf(hash_key, sizeof(hash_key), "%s%s%s", user, host, cid_num);
tech_pvt->chat_from = tech_pvt->from_str;
tech_pvt->chat_to = tech_pvt->dest;
tech_pvt->hash_key = switch_core_session_strdup(tech_pvt->session, hash_key);
switch_core_hash_insert(tech_pvt->profile->chat_hash, tech_pvt->hash_key, tech_pvt);
}
nua_invite(tech_pvt->nh, nua_invite(tech_pvt->nh,
TAG_IF(rpid, SIPTAG_HEADER_STR(rpid)), TAG_IF(rpid, SIPTAG_HEADER_STR(rpid)),
SOATAG_USER_SDP_STR(tech_pvt->local_sdp_str), SOATAG_USER_SDP_STR(tech_pvt->local_sdp_str),
@ -910,6 +984,8 @@ static void do_invite(switch_core_session_t *session)
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Memory Error!\n"); switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Memory Error!\n");
} }
switch_safe_free(cid_num_p);
} }
@ -982,6 +1058,7 @@ static switch_status_t sofia_on_init(switch_core_session_t *session)
tech_pvt->read_frame.buflen = SWITCH_RTP_MAX_BUF_LEN; tech_pvt->read_frame.buflen = SWITCH_RTP_MAX_BUF_LEN;
switch_channel_set_variable(channel, "endpoint_disposition", "INIT"); switch_channel_set_variable(channel, "endpoint_disposition", "INIT");
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "SOFIA INIT\n"); switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "SOFIA INIT\n");
@ -1113,6 +1190,9 @@ static switch_status_t sofia_on_hangup(switch_core_session_t *session)
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Channel %s hanging up, cause: %s\n", switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Channel %s hanging up, cause: %s\n",
switch_channel_get_name(channel), switch_channel_cause2str(cause), sip_cause); switch_channel_get_name(channel), switch_channel_cause2str(cause), sip_cause);
if (tech_pvt->hash_key) {
switch_core_hash_delete(tech_pvt->profile->chat_hash, tech_pvt->hash_key);
}
if (tech_pvt->kick && (asession = switch_core_session_locate(tech_pvt->kick))) { if (tech_pvt->kick && (asession = switch_core_session_locate(tech_pvt->kick))) {
switch_channel_t *a_channel = switch_core_session_get_channel(asession); switch_channel_t *a_channel = switch_core_session_get_channel(asession);
@ -1714,6 +1794,42 @@ static switch_status_t sofia_receive_message(switch_core_session_t *session, swi
return SWITCH_STATUS_SUCCESS; return SWITCH_STATUS_SUCCESS;
} }
static switch_status_t sofia_receive_event(switch_core_session_t *session, switch_event_t *event)
{
switch_channel_t *channel;
struct private_object *tech_pvt;
char *body;
nua_handle_t *msg_nh;
channel = switch_core_session_get_channel(session);
assert(channel != NULL);
tech_pvt = switch_core_session_get_private(session);
assert(tech_pvt != NULL);
if (!(body = switch_event_get_body(event))) {
body = "";
}
if (tech_pvt->hash_key) {
msg_nh = nua_handle(tech_pvt->profile->nua, NULL,
SIPTAG_FROM_STR(tech_pvt->chat_from),
NUTAG_URL(tech_pvt->chat_to),
SIPTAG_TO_STR(tech_pvt->chat_to),
SIPTAG_CONTACT_STR(tech_pvt->profile->url),
TAG_END());
nua_message(msg_nh,
SIPTAG_CONTENT_TYPE_STR("text/html"),
SIPTAG_PAYLOAD_STR(body),
TAG_END());
}
return SWITCH_STATUS_SUCCESS;
}
static const switch_io_routines_t sofia_io_routines = { static const switch_io_routines_t sofia_io_routines = {
/*.outgoing_channel */ sofia_outgoing_channel, /*.outgoing_channel */ sofia_outgoing_channel,
/*.answer_channel */ sofia_answer_channel, /*.answer_channel */ sofia_answer_channel,
@ -1723,7 +1839,8 @@ static const switch_io_routines_t sofia_io_routines = {
/*.waitfor_read */ sofia_waitfor_read, /*.waitfor_read */ sofia_waitfor_read,
/*.waitfor_read */ sofia_waitfor_write, /*.waitfor_read */ sofia_waitfor_write,
/*.send_dtmf*/ sofia_send_dtmf, /*.send_dtmf*/ sofia_send_dtmf,
/*.receive_message*/ sofia_receive_message /*.receive_message*/ sofia_receive_message,
/*.receive_event*/ sofia_receive_event
}; };
static const switch_state_handler_table_t sofia_event_handlers = { static const switch_state_handler_table_t sofia_event_handlers = {
@ -1823,6 +1940,8 @@ static switch_status_t sofia_outgoing_channel(switch_core_session_t *session, sw
if ((host = strchr(dest, '%'))) { if ((host = strchr(dest, '%'))) {
char buf[128]; char buf[128];
*host = '@';
tech_pvt->e_dest = switch_core_session_strdup(nsession, dest);
*host++ = '\0'; *host++ = '\0';
if (find_reg_url(profile, dest, host, buf, sizeof(buf))) { if (find_reg_url(profile, dest, host, buf, sizeof(buf))) {
tech_pvt->dest = switch_core_session_strdup(nsession, buf); tech_pvt->dest = switch_core_session_strdup(nsession, buf);
@ -1976,6 +2095,57 @@ static switch_call_cause_t sip_cause_to_freeswitch(int status) {
} }
} }
static void set_hash_key(char *hash_key, int32_t len, sip_t const *sip)
{
snprintf(hash_key, len, "%s%s%s",
(char *) sip->sip_from->a_url->url_user,
(char *) sip->sip_from->a_url->url_host,
(char *) sip->sip_to->a_url->url_user
);
#if 0
/* nicer one we cant use in both directions >=0 */
snprintf(hash_key, len, "%s%s%s%s%s%s",
(char *) sip->sip_to->a_url->url_user,
(char *) sip->sip_to->a_url->url_host,
(char *) sip->sip_to->a_url->url_params,
(char *) sip->sip_from->a_url->url_user,
(char *) sip->sip_from->a_url->url_host,
(char *) sip->sip_from->a_url->url_params
);
#endif
}
static void set_chat_hash(private_object_t *tech_pvt, sip_t const *sip)
{
char hash_key[256] = "";
char buf[512];
if (!sip || tech_pvt->hash_key) {
return;
}
if (find_reg_url(tech_pvt->profile, (char *) sip->sip_from->a_url->url_user, (char *) sip->sip_from->a_url->url_host, buf, sizeof(buf))) {
tech_pvt->chat_from = sip_header_as_string(tech_pvt->home, (void *)sip->sip_to);
tech_pvt->chat_to = switch_core_session_strdup(tech_pvt->session, buf);
set_hash_key(hash_key, sizeof(hash_key), sip);
} else {
return;
}
tech_pvt->hash_key = switch_core_session_strdup(tech_pvt->session, hash_key);
switch_core_hash_insert(tech_pvt->profile->chat_hash, tech_pvt->hash_key, tech_pvt);
}
static void sip_i_message(int status, static void sip_i_message(int status,
char const *phrase, char const *phrase,
nua_t *nua, nua_t *nua,
@ -1995,7 +2165,7 @@ static void sip_i_message(int status,
sip_subject_t const *sip_subject = sip->sip_subject; sip_subject_t const *sip_subject = sip->sip_subject;
sip_payload_t *payload = sip->sip_payload; sip_payload_t *payload = sip->sip_payload;
const char *subject = "n/a"; const char *subject = "n/a";
char *msg = ""; char *msg = NULL;
if (strstr((char*)sip->sip_content_type->c_subtype, "composing")) { if (strstr((char*)sip->sip_content_type->c_subtype, "composing")) {
return; return;
@ -2020,34 +2190,71 @@ static void sip_i_message(int status,
} }
if (nh) { if (nh) {
char *message = "<b>hello world</b>"; char hash_key[512];
char buf[256] = ""; private_object_t *tech_pvt;
switch_channel_t *channel;
switch_event_t *event;
char *to_addr;
char *from_addr;
char *p;
if (find_reg_url(profile, from_user, from_host, buf, sizeof(buf))) { if ((p=strchr(to_user, '+'))) {
nua_handle_t *msg_nh;
if ((to_addr = strdup(++p))) {
p = strchr(to_addr, '+');
*p = '@';
}
} else {
to_addr = switch_core_db_mprintf("%s@%s", to_user, to_host);
}
from_addr = switch_core_db_mprintf("%s@%s", from_user, from_host);
msg_nh = nua_handle(profile->nua, NULL, set_hash_key(hash_key, sizeof(hash_key), sip);
SIPTAG_FROM(sip->sip_to), if ((tech_pvt = (private_object_t *) switch_core_hash_find(profile->chat_hash, hash_key))) {
SIPTAG_TO_STR(buf), channel = switch_core_session_get_channel(tech_pvt->session);
SIPTAG_CONTACT_STR(profile->url), if (switch_event_create(&event, SWITCH_EVENT_MESSAGE) == SWITCH_STATUS_SUCCESS) {
TAG_END()); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "sip");
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "login", "%s", profile->url);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "from", "%s", tech_pvt->hash_key);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "to", "%s", to_addr);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "subject", "SIMPLE MESSAGE");
event->key = SIP_KEY;
if (msg) {
switch_event_add_body(event, msg);
}
if (switch_core_session_queue_event(tech_pvt->session, &event) != SWITCH_STATUS_SUCCESS) {
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "delivery-failure", "true");
switch_event_fire(&event);
}
}
} else {
if (switch_event_create(&event, SWITCH_EVENT_MESSAGE) == SWITCH_STATUS_SUCCESS) {
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "sip");
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "login", "%s", profile->url);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "from", "%s", from_addr);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "to", "%s", to_addr);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "subject", "SIMPLE MESSAGE");
event->key = SIP_KEY;
if (msg) {
switch_event_add_body(event, msg);
}
nua_message(msg_nh, switch_event_fire(&event);
SIPTAG_CONTENT_TYPE_STR("text/html"),
TAG_IF(message, }
SIPTAG_PAYLOAD_STR(message)),
TAG_END());
} }
switch_safe_free(to_addr);
} switch_safe_free(from_addr);
//printf("==================================\nFrom: %s@%s\nSubject: %s\n\n%s\n\n",from_user,from_host,subject,msg); }
} }
} }
static void sip_i_state(int status, static void sip_i_state(int status,
char const *phrase, char const *phrase,
nua_t *nua, nua_t *nua,
@ -2089,6 +2296,8 @@ static void sip_i_state(int status,
tech_pvt->nh = nh; tech_pvt->nh = nh;
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Channel %s entering state [%s]\n", switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Channel %s entering state [%s]\n",
switch_channel_get_name(channel), switch_channel_get_name(channel),
nua_callstate_name(ss_state)); nua_callstate_name(ss_state));
@ -2097,6 +2306,7 @@ static void sip_i_state(int status,
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Remote SDP:\n%s\n", r_sdp); switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Remote SDP:\n%s\n", r_sdp);
tech_pvt->remote_sdp_str = switch_core_session_strdup(session, (char *)r_sdp); tech_pvt->remote_sdp_str = switch_core_session_strdup(session, (char *)r_sdp);
switch_channel_set_variable(channel, SWITCH_R_SDP_VARIABLE, (char *) r_sdp); switch_channel_set_variable(channel, SWITCH_R_SDP_VARIABLE, (char *) r_sdp);
} }
} }
@ -2201,7 +2411,6 @@ static void sip_i_state(int status,
if (match) { if (match) {
nua_handle_t *bnh; nua_handle_t *bnh;
sip_replaces_t *replaces; sip_replaces_t *replaces;
switch_channel_set_variable(channel, "endpoint_disposition", "RECEIVED"); switch_channel_set_variable(channel, "endpoint_disposition", "RECEIVED");
switch_channel_set_state(channel, CS_INIT); switch_channel_set_state(channel, CS_INIT);
switch_set_flag_locked(tech_pvt, TFLAG_READY); switch_set_flag_locked(tech_pvt, TFLAG_READY);
@ -2447,14 +2656,22 @@ static uint8_t handle_register(nua_t *nua,
uint8_t stale = 0, ret = 0, forbidden = 0; uint8_t stale = 0, ret = 0, forbidden = 0;
auth_res_t auth_res; auth_res_t auth_res;
long exptime = 60; long exptime = 60;
switch_event_t *event;
if (sip->sip_contact) { if (sip->sip_contact) {
char *port = (char *) contact->m_url->url_port;
if (!port) {
port = "5060";
}
if (contact->m_url->url_params) { if (contact->m_url->url_params) {
snprintf(contact_str, sizeof(contact_str), "sip:%s@%s:%s;%s", snprintf(contact_str, sizeof(contact_str), "sip:%s@%s:%s;%s",
contact->m_url->url_user, contact->m_url->url_host, contact->m_url->url_port, contact->m_url->url_params); contact->m_url->url_user, contact->m_url->url_host, port, contact->m_url->url_params);
} else { } else {
snprintf(contact_str, sizeof(contact_str), "sip:%s@%s:%s", snprintf(contact_str, sizeof(contact_str), "sip:%s@%s:%s",
contact->m_url->url_user, contact->m_url->url_host, contact->m_url->url_port); contact->m_url->url_user, contact->m_url->url_host, port);
} }
} }
@ -2600,7 +2817,6 @@ static uint8_t handle_register(nua_t *nua,
} }
if (switch_event_create_subclass(&s_event, SWITCH_EVENT_CUSTOM, MY_EVENT_REGISTER) == SWITCH_STATUS_SUCCESS) { if (switch_event_create_subclass(&s_event, SWITCH_EVENT_CUSTOM, MY_EVENT_REGISTER) == SWITCH_STATUS_SUCCESS) {
switch_event_add_header(s_event, SWITCH_STACK_BOTTOM, "profile-name", "%s", profile->name); switch_event_add_header(s_event, SWITCH_STACK_BOTTOM, "profile-name", "%s", profile->name);
switch_event_add_header(s_event, SWITCH_STACK_BOTTOM, "from-user", "%s", from_user); switch_event_add_header(s_event, SWITCH_STACK_BOTTOM, "from-user", "%s", from_user);
@ -2623,6 +2839,38 @@ static uint8_t handle_register(nua_t *nua,
(long)exptime (long)exptime
); );
if (switch_event_create(&event, SWITCH_EVENT_ROSTER) == SWITCH_STATUS_SUCCESS) {
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "sip");
event->key = SIP_KEY;
switch_event_fire(&event);
}
if (exptime) {
if (switch_event_create(&event, SWITCH_EVENT_PRESENCE_IN) == SWITCH_STATUS_SUCCESS) {
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "sip");
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "login", "%s", profile->url);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "from", "%s@%s", from_user, from_host);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "status", "Registered");
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "show", "Registered");
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "event_type", "presence");
switch_event_fire(&event);
}
} else {
if (switch_event_create(&event, SWITCH_EVENT_PRESENCE_OUT) == SWITCH_STATUS_SUCCESS) {
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "sip");
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "login", "%s", profile->url);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "from", "%s@%s", from_user, from_host);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "status", "unavailable");
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "show", "unavailable");
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "event_type", "presence");
switch_event_fire(&event);
}
}
if (regtype == REG_REGISTER) { if (regtype == REG_REGISTER) {
nua_respond(nh, SIP_200_OK, SIPTAG_CONTACT(contact), nua_respond(nh, SIP_200_OK, SIPTAG_CONTACT(contact),
NUTAG_WITH_THIS(nua), NUTAG_WITH_THIS(nua),
@ -2667,14 +2915,19 @@ static void sip_i_subscribe(int status,
} }
if (contact) { if (contact) {
char *port = (char *) contact->m_url->url_port;
if (!port) {
port = "5060";
}
if (contact->m_url->url_params) { if (contact->m_url->url_params) {
contact_str = switch_core_db_mprintf("sip:%s@%s:%s;%s", contact_str = switch_core_db_mprintf("sip:%s@%s:%s;%s",
contact->m_url->url_user, contact->m_url->url_user,
contact->m_url->url_host, contact->m_url->url_port, contact->m_url->url_params); contact->m_url->url_host, port, contact->m_url->url_params);
} else { } else {
contact_str = switch_core_db_mprintf("sip:%s@%s:%s", contact_str = switch_core_db_mprintf("sip:%s@%s:%s",
contact->m_url->url_user, contact->m_url->url_user,
contact->m_url->url_host, contact->m_url->url_port); contact->m_url->url_host, port);
} }
} }
@ -2737,9 +2990,7 @@ static void sip_i_subscribe(int status,
switch_core_db_free(sql); switch_core_db_free(sql);
} }
nua_respond(nh, SIP_202_ACCEPTED, nua_respond(nh, SIP_202_ACCEPTED,
SIPTAG_SUBSCRIPTION_STATE_STR("active;expires=3600"), SIPTAG_SUBSCRIPTION_STATE_STR("active;expires=3600"),
SIPTAG_FROM(sip->sip_to), SIPTAG_FROM(sip->sip_to),
@ -3095,8 +3346,9 @@ static void sip_i_publish(nua_t *nua,
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "sip"); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "sip");
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "login", "%s", profile->url); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "login", "%s", profile->url);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "from", "%s@%s", from_user, from_host); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "from", "%s@%s", from_user, from_host);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "status", "%s", status_txt);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "show", "%s", note_txt); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "status", "%s", note_txt);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "show", "%s", status_txt);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "event_type", "%s", event_type); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "event_type", "%s", event_type);
switch_event_fire(&event); switch_event_fire(&event);
} }
@ -3105,6 +3357,7 @@ static void sip_i_publish(nua_t *nua,
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "sip"); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "proto", "sip");
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "login", "%s", profile->url); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "login", "%s", profile->url);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "from", "%s@%s", from_user, from_host); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "from", "%s@%s", from_user, from_host);
switch_event_add_header(event, SWITCH_STACK_BOTTOM, "event_type", "%s", event_type); switch_event_add_header(event, SWITCH_STACK_BOTTOM, "event_type", "%s", event_type);
switch_event_fire(&event); switch_event_fire(&event);
} }
@ -3213,10 +3466,13 @@ static void sip_i_invite(nua_t *nua,
return; return;
} }
attach_private(session, profile, tech_pvt, username); attach_private(session, profile, tech_pvt, username);
channel = switch_core_session_get_channel(session); channel = switch_core_session_get_channel(session);
switch_channel_set_variable(channel, "endpoint_disposition", "INBOUND CALL"); switch_channel_set_variable(channel, "endpoint_disposition", "INBOUND CALL");
set_chat_hash(tech_pvt, sip);
if ((tech_pvt->caller_profile = switch_caller_profile_new(switch_core_session_get_pool(session), if ((tech_pvt->caller_profile = switch_caller_profile_new(switch_core_session_get_pool(session),
(char *) from->a_url->url_user, (char *) from->a_url->url_user,
@ -3743,6 +3999,11 @@ static void *SWITCH_THREAD_FUNC profile_thread_run(switch_thread_t *thread, void
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_NOTICE, "Creating presence for %s\n", profile->url); switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_NOTICE, "Creating presence for %s\n", profile->url);
} }
switch_mutex_lock(globals.hash_mutex);
switch_core_hash_insert(globals.profile_hash, profile->name, profile);
switch_mutex_unlock(globals.hash_mutex);
while(globals.running == 1) { while(globals.running == 1) {
if (++ireg_loops >= IREG_SECONDS) { if (++ireg_loops >= IREG_SECONDS) {
check_expire(profile, time(NULL)); check_expire(profile, time(NULL));
@ -3784,9 +4045,6 @@ static void launch_profile_thread(sofia_profile_t *profile)
switch_threadattr_create(&thd_attr, profile->pool); switch_threadattr_create(&thd_attr, profile->pool);
switch_threadattr_detach_set(thd_attr, 1); switch_threadattr_detach_set(thd_attr, 1);
switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE); switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE);
switch_mutex_lock(globals.hash_mutex);
switch_core_hash_insert(globals.profile_hash, profile->name, profile);
switch_mutex_unlock(globals.hash_mutex);
switch_thread_create(&thread, thd_attr, profile_thread_run, profile, profile->pool); switch_thread_create(&thread, thd_attr, profile_thread_run, profile, profile->pool);
} }
@ -3851,6 +4109,7 @@ static switch_status_t config_sofia(int reload)
profile->name = switch_core_strdup(profile->pool, xprofilename); profile->name = switch_core_strdup(profile->pool, xprofilename);
snprintf(url, sizeof(url), "sofia_reg_%s", xprofilename); snprintf(url, sizeof(url), "sofia_reg_%s", xprofilename);
profile->dbname = switch_core_strdup(profile->pool, url); profile->dbname = switch_core_strdup(profile->pool, url);
switch_core_hash_init(&profile->chat_hash, profile->pool);
profile->dtmf_duration = 100; profile->dtmf_duration = 100;
profile->codec_ms = 20; profile->codec_ms = 20;
@ -3970,7 +4229,7 @@ static switch_status_t config_sofia(int reload)
profile->sipdomain = switch_core_strdup(profile->pool, profile->sipip); profile->sipdomain = switch_core_strdup(profile->pool, profile->sipip);
} }
snprintf(url, sizeof(url), "sip:%s@%s:%d", profile->name, profile->sipip, profile->sip_port); snprintf(url, sizeof(url), "sip:mod_sofia@%s:%d", profile->sipip, profile->sip_port);
profile->url = switch_core_strdup(profile->pool, url); profile->url = switch_core_strdup(profile->pool, url);
} }
if (profile) { if (profile) {
@ -4044,6 +4303,7 @@ static switch_status_t config_sofia(int reload)
} }
oreg->next = profile->registrations; oreg->next = profile->registrations;
profile->registrations = oreg; profile->registrations = oreg;
} }
} }
} }
@ -4192,7 +4452,61 @@ static int sub_callback(void *pArg, int argc, char **argv, char **columnNames){
return 0; return 0;
} }
static void msg_event_handler(switch_event_t *event) static void chat_event_handler(switch_event_t *event)
{
char *from = switch_event_get_header(event, "from");
char *to = switch_event_get_header(event, "to");
char *body = switch_event_get_body(event);
char buf[256];
char *user, *host;
sofia_profile_t *profile;
char *from_p = NULL, *from_pp = NULL;
if (event->key == SIP_KEY) {
return;
}
if (to && (user = strdup(to))) {
if ((host = strchr(user, '@'))) {
*host++ = '\0';
}
if (!host || !(profile = (sofia_profile_t *) switch_core_hash_find(globals.profile_hash, host))) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Invalid Profile %s\n", host ? host : "NULL");
return;
}
if (find_reg_url(profile, user, host, buf, sizeof(buf))) {
nua_handle_t *msg_nh;
if ((from_p = encode_name(from))) {
from_pp = switch_core_db_mprintf("\"%s\" <sip:%s@%s>", from, from_p, host);
from = from_pp;
}
msg_nh = nua_handle(profile->nua, NULL,
SIPTAG_FROM_STR(from),
NUTAG_URL(buf),
SIPTAG_TO_STR(buf),
SIPTAG_CONTACT_STR(profile->url),
TAG_END());
nua_message(msg_nh,
SIPTAG_CONTENT_TYPE_STR("text/html"),
SIPTAG_PAYLOAD_STR(body),
TAG_END());
}
switch_safe_free(from_p);
switch_safe_free(from_pp);
free(user);
}
}
static void pres_event_handler(switch_event_t *event)
{ {
sofia_profile_t *profile; sofia_profile_t *profile;
switch_hash_index_t *hi; switch_hash_index_t *hi;
@ -4207,6 +4521,36 @@ static void msg_event_handler(switch_event_t *event)
char *resource; char *resource;
switch_core_db_t *db; switch_core_db_t *db;
if (event->key == SIP_KEY) {
return;
}
if (event->event_id == SWITCH_EVENT_ROSTER) {
sql = switch_core_db_mprintf("select 1,'%q',* from sip_subscriptions where event='presence'", status ? status : "Available");
for (hi = switch_hash_first(apr_hash_pool_get(globals.profile_hash), globals.profile_hash); hi; hi = switch_hash_next(hi)) {
switch_hash_this(hi, NULL, NULL, &val);
profile = (sofia_profile_t *) val;
if (!(profile->pflags & PFLAG_PRESENCE)) {
continue;
}
if (sql) {
if (!(db = switch_core_db_open_file(profile->dbname))) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Error Opening DB %s\n", profile->dbname);
continue;
}
switch_mutex_lock(profile->ireg_mutex);
switch_core_db_exec(db, sql, sub_callback, profile, &errmsg);
switch_mutex_unlock(profile->ireg_mutex);
switch_core_db_close(db);
}
}
return;
}
if (status && !strcasecmp(status, "n/a")) { if (status && !strcasecmp(status, "n/a")) {
status = show; status = show;
if (status && !strcasecmp(status, "n/a")) { if (status && !strcasecmp(status, "n/a")) {
@ -4237,6 +4581,8 @@ static void msg_event_handler(switch_event_t *event)
return; return;
} }
switch(event->event_id) { switch(event->event_id) {
case SWITCH_EVENT_PRESENCE_IN: case SWITCH_EVENT_PRESENCE_IN:
if (!status) { if (!status) {
@ -4308,17 +4654,22 @@ SWITCH_MOD_DECLARE(switch_status_t) switch_module_load(const switch_loadable_mod
config_sofia(0); config_sofia(0);
if (switch_event_bind((char *) modname, SWITCH_EVENT_MESSAGE, SWITCH_EVENT_SUBCLASS_ANY, msg_event_handler, NULL) != SWITCH_STATUS_SUCCESS) { if (switch_event_bind((char *) modname, SWITCH_EVENT_MESSAGE, SWITCH_EVENT_SUBCLASS_ANY, chat_event_handler, NULL) != SWITCH_STATUS_SUCCESS) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't bind!\n"); switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't bind!\n");
return SWITCH_STATUS_GENERR; return SWITCH_STATUS_GENERR;
} }
if (switch_event_bind((char *) modname, SWITCH_EVENT_PRESENCE_IN, SWITCH_EVENT_SUBCLASS_ANY, msg_event_handler, NULL) != SWITCH_STATUS_SUCCESS) { if (switch_event_bind((char *) modname, SWITCH_EVENT_PRESENCE_IN, SWITCH_EVENT_SUBCLASS_ANY, pres_event_handler, NULL) != SWITCH_STATUS_SUCCESS) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't bind!\n"); switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't bind!\n");
return SWITCH_STATUS_GENERR; return SWITCH_STATUS_GENERR;
} }
if (switch_event_bind((char *) modname, SWITCH_EVENT_PRESENCE_OUT, SWITCH_EVENT_SUBCLASS_ANY, msg_event_handler, NULL) != SWITCH_STATUS_SUCCESS) { if (switch_event_bind((char *) modname, SWITCH_EVENT_PRESENCE_OUT, SWITCH_EVENT_SUBCLASS_ANY, pres_event_handler, NULL) != SWITCH_STATUS_SUCCESS) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't bind!\n");
return SWITCH_STATUS_GENERR;
}
if (switch_event_bind((char *) modname, SWITCH_EVENT_ROSTER, SWITCH_EVENT_SUBCLASS_ANY, pres_event_handler, NULL) != SWITCH_STATUS_SUCCESS) {
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't bind!\n"); switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Couldn't bind!\n");
return SWITCH_STATUS_GENERR; return SWITCH_STATUS_GENERR;
} }

View File

@ -1315,19 +1315,19 @@ SWITCH_DECLARE(switch_status_t) switch_core_session_outgoing_channel(switch_core
if (endpoint_interface->io_routines->outgoing_channel) { if (endpoint_interface->io_routines->outgoing_channel) {
if (session) { if (session) {
char *ecaller_id_name = NULL, *ecaller_id_number = NULL;
channel = switch_core_session_get_channel(session); channel = switch_core_session_get_channel(session);
if (caller_profile) {
char *ecaller_id_name = NULL, *ecaller_id_number = NULL;
ecaller_id_name = switch_channel_get_variable(channel, "effective_caller_id_name");
ecaller_id_number = switch_channel_get_variable(channel, "effective_caller_id_number");
ecaller_id_name = switch_channel_get_variable(channel, "effective_caller_id_name"); if (ecaller_id_name || ecaller_id_number) {
ecaller_id_number = switch_channel_get_variable(channel, "effective_caller_id_number");
if (ecaller_id_name || ecaller_id_number) {
if (caller_profile) {
outgoing_profile = switch_caller_profile_new(switch_core_session_get_pool(session), outgoing_profile = switch_caller_profile_new(switch_core_session_get_pool(session),
caller_profile->username, caller_profile->username,
caller_profile->dialplan, caller_profile->dialplan,
ecaller_id_name ? ecaller_id_name : caller_profile->caller_id_name, ecaller_id_name,
ecaller_id_number ? ecaller_id_number : caller_profile->caller_id_number, ecaller_id_number,
caller_profile->network_addr, caller_profile->network_addr,
caller_profile->ani, caller_profile->ani,
caller_profile->aniii, caller_profile->aniii,
@ -1336,7 +1336,10 @@ SWITCH_DECLARE(switch_status_t) switch_core_session_outgoing_channel(switch_core
caller_profile->context, caller_profile->context,
caller_profile->destination_number); caller_profile->destination_number);
outgoing_profile->flags = caller_profile->flags; outgoing_profile->flags = caller_profile->flags;
} }
}
if (!outgoing_profile) {
outgoing_profile = switch_channel_get_caller_profile(channel);
} }
} }
@ -1361,14 +1364,13 @@ SWITCH_DECLARE(switch_status_t) switch_core_session_outgoing_channel(switch_core
if (*new_session) { if (*new_session) {
switch_caller_profile_t *profile = NULL, *peer_profile = NULL, *cloned_profile = NULL; switch_caller_profile_t *profile = NULL, *peer_profile = NULL, *cloned_profile = NULL;
switch_channel_t *peer_channel = NULL;
switch_event_t *event; switch_event_t *event;
switch_channel_t *new_channel = switch_core_session_get_channel(*new_session); switch_channel_t *peer_channel = switch_core_session_get_channel(*new_session);
if (session && channel) { if (session && channel) {
profile = switch_channel_get_caller_profile(channel); profile = switch_channel_get_caller_profile(channel);
} }
if ((peer_channel = switch_core_session_get_channel(*new_session)) != 0) { if (peer_channel) {
peer_profile = switch_channel_get_caller_profile(peer_channel); peer_profile = switch_channel_get_caller_profile(peer_channel);
} }
@ -1386,7 +1388,7 @@ SWITCH_DECLARE(switch_status_t) switch_core_session_outgoing_channel(switch_core
} }
if (switch_event_create(&event, SWITCH_EVENT_CHANNEL_OUTGOING) == SWITCH_STATUS_SUCCESS) { if (switch_event_create(&event, SWITCH_EVENT_CHANNEL_OUTGOING) == SWITCH_STATUS_SUCCESS) {
switch_channel_event_set_data(new_channel, event); switch_channel_event_set_data(peer_channel, event);
switch_event_fire(&event); switch_event_fire(&event);
} }
} }

View File

@ -125,6 +125,7 @@ static char *EVENT_NAMES[] = {
"MESSAGE", "MESSAGE",
"PRESENCE_IN", "PRESENCE_IN",
"PRESENCE_OUT", "PRESENCE_OUT",
"ROSTER",
"CODEC", "CODEC",
"BACKGROUND_JOB", "BACKGROUND_JOB",
"ALL" "ALL"
@ -587,6 +588,8 @@ SWITCH_DECLARE(switch_status_t) switch_event_dup(switch_event_t **event, switch_
(*event)->body = DUP(todup->body); (*event)->body = DUP(todup->body);
} }
(*event)->key = todup->key;
return SWITCH_STATUS_SUCCESS; return SWITCH_STATUS_SUCCESS;
} }

View File

@ -1823,6 +1823,7 @@ SWITCH_DECLARE(switch_status_t) switch_ivr_originate(switch_core_session_t *sess
caller_caller_profile->source, caller_caller_profile->source,
caller_caller_profile->context, caller_caller_profile->context,
chan_data); chan_data);
caller_profiles[i]->flags = caller_caller_profile->flags;
pool = NULL; pool = NULL;
} else { } else {
if (!cid_name_override) { if (!cid_name_override) {