build-system: Allow building with static pjproject
authorGeorge Joseph <george.joseph@fairview5.com>
Tue, 19 Jan 2016 03:54:28 +0000 (20:54 -0700)
committerGeorge Joseph <george.joseph@fairview5.com>
Tue, 1 Mar 2016 16:30:43 +0000 (09:30 -0700)
Background here:
http://lists.digium.com/pipermail/asterisk-dev/2016-January/075266.html

From CHANGES:
 * To help insure that Asterisk is compiled and run with the same known
   version of pjproject, a new option (--with-pjproject-bundled) has been
   added to ./configure.  When specified, the version of pjproject specified
   in third-party/versions.mak will be downloaded and configured.  When you
   make Asterisk, the build process will also automatically build pjproject
   and Asterisk will be statically linked to it.  Once a particular version
   of pjproject is configured and built, it won't be configured or built
   again unless you run a 'make distclean'.

   To facilitate testing, when 'make install' is run, the pjsua and pjsystest
   utilities and the pjproject python bindings will be installed in
   ASTDATADIR/third-party/pjproject.

   The default behavior remains building with the shared pjproject
   installation, if any.

Building:

   All you have to do is include the --with-pjproject-bundled option on
   the ./configure command line (and remove any existing --with-pjproject
   option if specified).  Everything else is automatic.

Behind the scenes:

   The top-level Makefile was modified to include 'third-party' in the
   list of MOD_SUBDIRS.

   The third-party directory was created to contain any third party
   packages that may be needed in the future.  Its Makefile automatically
   iterates over any subdirectories passing on targets.

   The third-party/pjproject directory was created to house the pjproject
   source distribution.  Its Makefile contains targets to download, patch
   configure, generate dependencies, compile libs, apps and python bindings,
   sanitized build.mak and generate a symbols list.

   When bootstrap.sh is run, it automatically includes the configure.m4
   file in third-party/pjproject.  This file has a macro to download and
   conifgure pjproject and get and set PJPROJECT_INCLUDE, PJPROJECT_DIR
   and PJPROJECT_BUNDLED.  It also tests for the capabilities like
   PJ_TRANSACTION_GRP_LOCK by parsing preprocessor output as opposed to
   trying to compile.  Of course, bootstrap.sh is only run once and the
   configure file is incldued in the patch.

   When configure is run with the new options, the macro in configure.m4
   triggers the download, patch, conifgure and tests.  No compilation is
   performed at this time.  The downloaded tarball is cached in /tmp so
   it doesn't get downloaded again on a distclean.

   When make is run in the top-level Asterisk source directory, it will
   automatically descend all the subdirectories in third_party just as it
   does for addons, apps, etc.  The top-level Makefile makes sure that
   the 'third-party' is built before 'main' so that dependencies from the
   other directories are built first.

   When main does build, a new shared library (libasteriskpj) is created that
   links statically to the pjproject .a files and exports all their symbols.
   The asterisk binary links to that, just as it does with libasteriskssl.

   When Asterisk is installed, the pjsua and pjsystest apps, and the pjproject
   python bindings are installed in ASTDATADIR/third-party/pjproject.  This
   will facilitate testing, including running the testsuite which will be
   updated to check that directory for the pjsua module ahead of the system
   python library.

Modules should continue to depend on pjproject if they use pjproject APIs
directly.  They should not care about the implementation.  No changes to any
res_pjsip modules were made.

Change-Id: Ia7a60c28c2e9ba9537c5570f933c1ebcb20a3103

25 files changed:
CHANGES
Makefile
configure
configure.ac
include/asterisk/_private.h
include/asterisk/autoconfig.h.in
main/.gitignore
main/Makefile
main/asterisk.c
main/libasteriskpj.c [new file with mode: 0644]
makeopts.in
third-party/Makefile [new file with mode: 0644]
third-party/Makefile.rules [new file with mode: 0644]
third-party/pjproject/.gitignore [new file with mode: 0644]
third-party/pjproject/Makefile [new file with mode: 0644]
third-party/pjproject/Makefile.rules [new file with mode: 0644]
third-party/pjproject/apply_patches [new file with mode: 0755]
third-party/pjproject/configure.m4 [new file with mode: 0644]
third-party/pjproject/patches/0001-2.4.5-fix-for-tls-async-ops.patch [new file with mode: 0644]
third-party/pjproject/patches/0001-Bump-tcp-tls-and-transaction-log-levels-from-1-to-3.patch [new file with mode: 0644]
third-party/pjproject/patches/0001-ioqueue-Enable-epoll-in-aconfigure.ac.patch [new file with mode: 0644]
third-party/pjproject/patches/0001-sip_transport-Search-for-transport-even-if-listener-.patch [new file with mode: 0644]
third-party/pjproject/patches/config_site.h [new file with mode: 0644]
third-party/pjproject/patches/user.mak [new file with mode: 0644]
third-party/versions.mak [new file with mode: 0644]

diff --git a/CHANGES b/CHANGES
index 91e170f..aaaf3f5 100644 (file)
--- a/CHANGES
+++ b/CHANGES
@@ -221,6 +221,24 @@ res_pjsip_config_wizard
    will export all the pjsip objects it created to the console or a file
    suitable for reuse in a pjsip.conf file.
 
+Build System
+------------------
+ * To help insure that Asterisk is compiled and run with the same known
+   version of pjproject, a new option (--with-pjproject-bundled) has been
+   added to ./configure.  When specified, the version of pjproject specified
+   in third-party/versions.mak will be downloaded and configured.  When you
+   make Asterisk, the build process will also automatically build pjproject
+   and Asterisk will be statically linked to it.  Once a particular version
+   of pjproject is configured and built, it won't be configured or built
+   again unless you run a 'make distclean'.
+
+   To facilitate testing, when 'make install' is run, the pjsua and pjsystest
+   utilities and the pjproject python bindings will be installed in
+   ASTDATADIR/third-party/pjproject.
+
+   The default behavior remains building with the shared pjproject
+   installation, if any.
+
 app_confbridge
 ------------------
  * Added CONFBRIDGE_INFO(muted,) for querying the muted conference state.
index a07a329..7528f83 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -249,7 +249,7 @@ endif
 
 _ASTCFLAGS+=$(OPTIONS)
 
-MOD_SUBDIRS:=channels pbx apps codecs formats cdr cel bridges funcs tests main res addons $(LOCAL_MOD_SUBDIRS)
+MOD_SUBDIRS:=third-party channels pbx apps codecs formats cdr cel bridges funcs tests main res addons $(LOCAL_MOD_SUBDIRS)
 OTHER_SUBDIRS:=utils agi contrib
 SUBDIRS:=$(OTHER_SUBDIRS) $(MOD_SUBDIRS)
 SUBDIRS_INSTALL:=$(SUBDIRS:%=%-install)
@@ -377,8 +377,10 @@ ifeq ($(findstring $(OSARCH), mingw32 cygwin ),)
     # directories containing them must be completed before the main Asterisk
     # binary can be built.
     # If MENUSELECT_EMBED is empty, we don't need this and allow 'main' to be
-    # be built without building all dependencies first.
+    # be built with only third_party first.
 main: $(filter-out main,$(MOD_SUBDIRS))
+  else
+main: third-party
   endif
 else
     # Windows: we need to build main (i.e. the asterisk dll) first,
@@ -568,7 +570,8 @@ INSTALLDIRS="$(ASTLIBDIR)" "$(ASTMODDIR)" "$(ASTSBINDIR)" "$(ASTETCDIR)" "$(ASTV
        "$(ASTDATADIR)/documentation/thirdparty" "$(ASTDATADIR)/firmware" \
        "$(ASTDATADIR)/firmware/iax" "$(ASTDATADIR)/images" "$(ASTDATADIR)/keys" \
        "$(ASTDATADIR)/phoneprov" "$(ASTDATADIR)/rest-api" "$(ASTDATADIR)/static-http" \
-       "$(ASTDATADIR)/sounds" "$(ASTDATADIR)/moh" "$(ASTMANDIR)/man8" "$(AGI_DIR)" "$(ASTDBDIR)"
+       "$(ASTDATADIR)/sounds" "$(ASTDATADIR)/moh" "$(ASTMANDIR)/man8" "$(AGI_DIR)" "$(ASTDBDIR)" \
+       "$(ASTDATADIR)/third-party"
 
 installdirs:
        @for i in $(INSTALLDIRS); do \
@@ -611,7 +614,7 @@ ifeq ($(HAVE_DAHDI),1)
 endif
 
 $(SUBDIRS_INSTALL):
-       +@DESTDIR="$(DESTDIR)" ASTSBINDIR="$(ASTSBINDIR)" $(SUBMAKE) -C $(@:-install=) install
+       +@DESTDIR="$(DESTDIR)" ASTSBINDIR="$(ASTSBINDIR)" ASTDATADIR="$(ASTDATADIR)" $(SUBMAKE) -C $(@:-install=) install
 
 NEWMODS:=$(foreach d,$(MOD_SUBDIRS),$(notdir $(wildcard $(d)/*.so)))
 OLDMODS=$(filter-out $(NEWMODS) $(notdir $(DESTDIR)$(ASTMODDIR)),$(notdir $(wildcard $(DESTDIR)$(ASTMODDIR)/*.so)))
@@ -889,7 +892,7 @@ sounds:
        @[ -f "$(DESTDIR)$(ASTDBDIR)/astdb.sqlite3" ] || [ ! -f "$(DESTDIR)$(ASTDBDIR)/astdb" ] || [ ! -f menuselect.makeopts ] || grep -q MENUSELECT_UTILS=.*astdb2sqlite3 menuselect.makeopts || (sed -i.orig -e's/MENUSELECT_UTILS=\(.*\)/MENUSELECT_UTILS=\1 astdb2sqlite3/' menuselect.makeopts && echo "Updating menuselect.makeopts to include astdb2sqlite3" && echo "Original version backed up to menuselect.makeopts.orig")
 
 $(SUBDIRS_UNINSTALL):
-       +@$(SUBMAKE) -C $(@:-uninstall=) uninstall
+       +@DESTDIR="$(DESTDIR)" ASTSBINDIR="$(ASTSBINDIR)" ASTDATADIR="$(ASTDATADIR)" $(SUBMAKE) -C $(@:-uninstall=) uninstall
 
 main-binuninstall:
        +@DESTDIR="$(DESTDIR)" ASTSBINDIR="$(ASTSBINDIR)" ASTLIBDIR="$(ASTLIBDIR)" $(SUBMAKE) -C main binuninstall
index 2c0f99d..3967cec 100755 (executable)
--- a/configure
+++ b/configure
@@ -915,6 +915,10 @@ PBX_PORTAUDIO
 PORTAUDIO_DIR
 PORTAUDIO_INCLUDE
 PORTAUDIO_LIB
+PBX_POPT
+POPT_DIR
+POPT_INCLUDE
+POPT_LIB
 PBX_PJSIP_EXTERNAL_RESOLVER
 PJSIP_EXTERNAL_RESOLVER_DIR
 PJSIP_EXTERNAL_RESOLVER_INCLUDE
@@ -939,10 +943,7 @@ PBX_PJSIP_DLG_CREATE_UAS_AND_INC_LOCK
 PJSIP_DLG_CREATE_UAS_AND_INC_LOCK_DIR
 PJSIP_DLG_CREATE_UAS_AND_INC_LOCK_INCLUDE
 PJSIP_DLG_CREATE_UAS_AND_INC_LOCK_LIB
-PBX_POPT
-POPT_DIR
-POPT_INCLUDE
-POPT_LIB
+PJPROJECT_BUNDLED
 PBX_PJPROJECT
 PJPROJECT_DIR
 PJPROJECT_INCLUDE
@@ -1362,6 +1363,7 @@ with_osptk
 with_oss
 with_postgres
 with_pjproject
+with_pjproject_bundled
 with_popt
 with_portaudio
 with_pri
@@ -2101,6 +2103,8 @@ Optional Packages:
   --with-oss=PATH         use Open Sound System files in PATH
   --with-postgres=PATH    use PostgreSQL files in PATH
   --with-pjproject=PATH   use PJPROJECT files in PATH
+  --with-pjproject-bundled
+                          Use bundled pjproject libraries
   --with-popt=PATH        use popt files in PATH
   --with-portaudio=PATH   use PortAudio files in PATH
   --with-pri=PATH         use ISDN PRI files in PATH
@@ -10415,6 +10419,7 @@ fi
 
 
 
+
     PJPROJECT_DESCRIP="PJPROJECT"
     PJPROJECT_OPTION="pjproject"
     PBX_PJPROJECT=0
 
 
 
+PJPROJECT_BUNDLED=no
 
-    POPT_DESCRIP="popt"
-    POPT_OPTION="popt"
-    PBX_POPT=0
 
-# Check whether --with-popt was given.
-if test "${with_popt+set}" = set; then :
-  withval=$with_popt;
-       case ${withval} in
-       n|no)
-       USE_POPT=no
-       # -1 is a magic value used by menuselect to know that the package
-       # was disabled, other than 'not found'
-       PBX_POPT=-1
-       ;;
-       y|ye|yes)
-       ac_mandatory_list="${ac_mandatory_list} POPT"
-       ;;
-       *)
-       POPT_DIR="${withval}"
-       ac_mandatory_list="${ac_mandatory_list} POPT"
-       ;;
-       esac
 
+# Check whether --with-pjproject-bundled was given.
+if test "${with_pjproject_bundled+set}" = set; then :
+  withval=$with_pjproject_bundled; case "${enableval}" in
+             n|no) PJPROJECT_BUNDLED=no ;;
+             *) PJPROJECT_BUNDLED=yes ;;
+       esac
 fi
 
 
 
+if test "$PJPROJECT_BUNDLED" = "yes" -a "${ac_mandatory_list#*PJPROJECT*}" != "$ac_mandatory_list" ; then
+   as_fn_error $? "--with-pjproject and --with-pjproject-bundled can't both be specified" "$LINENO" 5
+fi
 
-
-
+if test "$PJPROJECT_BUNDLED" = "yes" ; then
+   ac_mandatory_list="$ac_mandatory_list PJPROJECT"
+   PJPROJECT_DIR="${ac_top_build_prefix}third-party/pjproject"
+fi
 
 
 PJSIP_DLG_CREATE_UAS_AND_INC_LOCK_DESCRIP="PJSIP Dialog Create UAS with Incremented Lock"
@@ -10551,6 +10547,39 @@ PBX_PJSIP_EXTERNAL_RESOLVER=0
 
 
 
+
+    POPT_DESCRIP="popt"
+    POPT_OPTION="popt"
+    PBX_POPT=0
+
+# Check whether --with-popt was given.
+if test "${with_popt+set}" = set; then :
+  withval=$with_popt;
+       case ${withval} in
+       n|no)
+       USE_POPT=no
+       # -1 is a magic value used by menuselect to know that the package
+       # was disabled, other than 'not found'
+       PBX_POPT=-1
+       ;;
+       y|ye|yes)
+       ac_mandatory_list="${ac_mandatory_list} POPT"
+       ;;
+       *)
+       POPT_DIR="${withval}"
+       ac_mandatory_list="${ac_mandatory_list} POPT"
+       ;;
+       esac
+
+fi
+
+
+
+
+
+
+
+
     PORTAUDIO_DESCRIP="PortAudio"
     PORTAUDIO_OPTION="portaudio"
     PBX_PORTAUDIO=0
@@ -24441,6 +24470,244 @@ $as_echo "$as_me: *** including --without-postgres" >&6;}
    fi
 fi
 
+if test "$USE_PJPROJECT" != "no" ; then
+   if test "$PJPROJECT_BUNDLED" = "yes" ; then
+
+
+       { $as_echo "$as_me:${as_lineno-$LINENO}: checking for embedded pjproject (may have to download)" >&5
+$as_echo_n "checking for embedded pjproject (may have to download)... " >&6; }
+       { $as_echo "$as_me:${as_lineno-$LINENO}: result: configuring" >&5
+$as_echo "configuring" >&6; }
+       make --quiet --no-print-directory -C $PJPROJECT_DIR configure
+       if test $? -ne 0 ; then
+               { $as_echo "$as_me:${as_lineno-$LINENO}: result: failed" >&5
+$as_echo "failed" >&6; }
+               { $as_echo "$as_me:${as_lineno-$LINENO}: Unable to configure $PJPROJECT_DIR" >&5
+$as_echo "$as_me: Unable to configure $PJPROJECT_DIR" >&6;}
+               as_fn_error $? "Run \"make -C $PJPROJECT_DIR NOISY_BUILD=yes configure\" to see error details." "$LINENO" 5
+       fi
+
+       PJPROJECT_INCLUDE=$(make --quiet --no-print-directory -C $PJPROJECT_DIR echo_cflags)
+       PJPROJECT_CFLAGS="$PJPROJECT_INCLUDE"
+       PBX_PJPROJECT=1
+       PJPROJECT_BUNDLED=yes
+
+$as_echo "#define HAVE_PJPROJECT 1" >>confdefs.h
+
+
+$as_echo "#define HAVE_PJPROJECT_BUNDLED 1" >>confdefs.h
+
+       { $as_echo "$as_me:${as_lineno-$LINENO}: checking for embedded pjproject" >&5
+$as_echo_n "checking for embedded pjproject... " >&6; }
+       { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
+$as_echo "yes" >&6; }
+
+
+       PJSIP_DLG_CREATE_UAS_AND_INC_LOCK_INCLUDE="$PJPROJECT_INCLUDE"
+    { $as_echo "$as_me:${as_lineno-$LINENO}: checking for pjsip_dlg_create_uas_and_inc_lock declared in pjsip.h" >&5
+$as_echo_n "checking for pjsip_dlg_create_uas_and_inc_lock declared in pjsip.h... " >&6; }
+
+       saved_cpp="$CPPFLAGS"
+       CPPFLAGS="$PJPROJECT_INCLUDE"
+       cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <pjsip.h>
+
+_ACEOF
+if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
+  $EGREP "pjsip_dlg_create_uas_and_inc_lock" >/dev/null 2>&1; then :
+
+               { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
+$as_echo "yes" >&6; }
+               PBX_PJSIP_DLG_CREATE_UAS_AND_INC_LOCK=1
+
+$as_echo "#define HAVE_PJSIP_DLG_CREATE_UAS_AND_INC_LOCK 1" >>confdefs.h
+
+
+else
+
+               { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+
+fi
+rm -f conftest*
+
+
+       CPPGLAGS="$saved_cpp"
+       PJSIP_DLG_CREATE_UAS_AND_INC_LOCK_INCLUDE="$PJPROJECT_INCLUDE"
+
+
+       PJ_TRANSACTION_GRP_LOCK_INCLUDE="$PJPROJECT_INCLUDE"
+    { $as_echo "$as_me:${as_lineno-$LINENO}: checking for pjsip_tsx_create_uac2 declared in pjsip.h" >&5
+$as_echo_n "checking for pjsip_tsx_create_uac2 declared in pjsip.h... " >&6; }
+
+       saved_cpp="$CPPFLAGS"
+       CPPFLAGS="$PJPROJECT_INCLUDE"
+       cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <pjsip.h>
+
+_ACEOF
+if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
+  $EGREP "pjsip_tsx_create_uac2" >/dev/null 2>&1; then :
+
+               { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
+$as_echo "yes" >&6; }
+               PBX_PJ_TRANSACTION_GRP_LOCK=1
+
+$as_echo "#define HAVE_PJ_TRANSACTION_GRP_LOCK 1" >>confdefs.h
+
+
+else
+
+               { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+
+fi
+rm -f conftest*
+
+
+       CPPGLAGS="$saved_cpp"
+       PJ_TRANSACTION_GRP_LOCK_INCLUDE="$PJPROJECT_INCLUDE"
+
+
+       PJSIP_REPLACE_MEDIA_STREAM_INCLUDE="$PJPROJECT_INCLUDE"
+    { $as_echo "$as_me:${as_lineno-$LINENO}: checking for PJMEDIA_SDP_NEG_ALLOW_MEDIA_CHANGE declared in pjmedia.h" >&5
+$as_echo_n "checking for PJMEDIA_SDP_NEG_ALLOW_MEDIA_CHANGE declared in pjmedia.h... " >&6; }
+
+       saved_cpp="$CPPFLAGS"
+       CPPFLAGS="$PJPROJECT_INCLUDE"
+       cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <pjmedia.h>
+
+_ACEOF
+if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
+  $EGREP "PJMEDIA_SDP_NEG_ALLOW_MEDIA_CHANGE" >/dev/null 2>&1; then :
+
+               { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
+$as_echo "yes" >&6; }
+               PBX_PJSIP_REPLACE_MEDIA_STREAM=1
+
+$as_echo "#define HAVE_PJSIP_REPLACE_MEDIA_STREAM 1" >>confdefs.h
+
+
+else
+
+               { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+
+fi
+rm -f conftest*
+
+
+       CPPGLAGS="$saved_cpp"
+       PJSIP_REPLACE_MEDIA_STREAM_INCLUDE="$PJPROJECT_INCLUDE"
+
+
+       PJSIP_GET_DEST_INFO_INCLUDE="$PJPROJECT_INCLUDE"
+    { $as_echo "$as_me:${as_lineno-$LINENO}: checking for pjsip_get_dest_info declared in pjsip.h" >&5
+$as_echo_n "checking for pjsip_get_dest_info declared in pjsip.h... " >&6; }
+
+       saved_cpp="$CPPFLAGS"
+       CPPFLAGS="$PJPROJECT_INCLUDE"
+       cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <pjsip.h>
+
+_ACEOF
+if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
+  $EGREP "pjsip_get_dest_info" >/dev/null 2>&1; then :
+
+               { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
+$as_echo "yes" >&6; }
+               PBX_PJSIP_GET_DEST_INFO=1
+
+$as_echo "#define HAVE_PJSIP_GET_DEST_INFO 1" >>confdefs.h
+
+
+else
+
+               { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+
+fi
+rm -f conftest*
+
+
+       CPPGLAGS="$saved_cpp"
+       PJSIP_GET_DEST_INFO_INCLUDE="$PJPROJECT_INCLUDE"
+
+
+       PJ_SSL_CERT_LOAD_FROM_FILES2_INCLUDE="$PJPROJECT_INCLUDE"
+    { $as_echo "$as_me:${as_lineno-$LINENO}: checking for pj_ssl_cert_load_from_files2 declared in pjlib.h" >&5
+$as_echo_n "checking for pj_ssl_cert_load_from_files2 declared in pjlib.h... " >&6; }
+
+       saved_cpp="$CPPFLAGS"
+       CPPFLAGS="$PJPROJECT_INCLUDE"
+       cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <pjlib.h>
+
+_ACEOF
+if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
+  $EGREP "pj_ssl_cert_load_from_files2" >/dev/null 2>&1; then :
+
+               { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
+$as_echo "yes" >&6; }
+               PBX_PJ_SSL_CERT_LOAD_FROM_FILES2=1
+
+$as_echo "#define HAVE_PJ_SSL_CERT_LOAD_FROM_FILES2 1" >>confdefs.h
+
+
+else
+
+               { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+
+fi
+rm -f conftest*
+
+
+       CPPGLAGS="$saved_cpp"
+       PJ_SSL_CERT_LOAD_FROM_FILES2_INCLUDE="$PJPROJECT_INCLUDE"
+
+
+       PJSIP_EXTERNAL_RESOLVER_INCLUDE="$PJPROJECT_INCLUDE"
+    { $as_echo "$as_me:${as_lineno-$LINENO}: checking for pjsip_endpt_set_ext_resolver declared in pjsip.h" >&5
+$as_echo_n "checking for pjsip_endpt_set_ext_resolver declared in pjsip.h... " >&6; }
+
+       saved_cpp="$CPPFLAGS"
+       CPPFLAGS="$PJPROJECT_INCLUDE"
+       cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h.  */
+#include <pjsip.h>
+
+_ACEOF
+if (eval "$ac_cpp conftest.$ac_ext") 2>&5 |
+  $EGREP "pjsip_endpt_set_ext_resolver" >/dev/null 2>&1; then :
+
+               { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
+$as_echo "yes" >&6; }
+               PBX_PJSIP_EXTERNAL_RESOLVER=1
+
+$as_echo "#define HAVE_PJSIP_EXTERNAL_RESOLVER 1" >>confdefs.h
+
+
+else
+
+               { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
+$as_echo "no" >&6; }
+
+fi
+rm -f conftest*
+
+
+       CPPGLAGS="$saved_cpp"
+       PJSIP_EXTERNAL_RESOLVER_INCLUDE="$PJPROJECT_INCLUDE"
+
+
+   else
 
    if test "x${PBX_PJPROJECT}" != "x1" -a "${USE_PJPROJECT}" != "no"; then
 
@@ -24658,7 +24925,7 @@ if eval \${$as_ac_Lib+:} false; then :
   $as_echo_n "(cached) " >&6
 else
   ac_check_lib_save_LIBS=$LIBS
-LIBS="-lpjsip ${pbxlibdir} $PJPROJECT_LIBS $LIBS"
+LIBS="-lpjsip ${pbxlibdir} $PJPROJECT_LIB $LIBS"
 cat confdefs.h - <<_ACEOF >conftest.$ac_ext
 /* end confdefs.h.  */
 
@@ -24700,7 +24967,7 @@ fi
 
    # now check for the header.
    if test "${AST_PJ_TRANSACTION_GRP_LOCK_FOUND}" = "yes"; then
-      PJ_TRANSACTION_GRP_LOCK_LIB="${pbxlibdir} -lpjsip $PJPROJECT_LIBS"
+      PJ_TRANSACTION_GRP_LOCK_LIB="${pbxlibdir} -lpjsip $PJPROJECT_LIB"
       # if --with-PJ_TRANSACTION_GRP_LOCK=DIR has been specified, use it.
       if test "x${PJ_TRANSACTION_GRP_LOCK_DIR}" != "x"; then
          PJ_TRANSACTION_GRP_LOCK_INCLUDE="-I${PJ_TRANSACTION_GRP_LOCK_DIR}/include"
 
 
 
-saved_cppflags="${CPPFLAGS}"
-saved_libs="${LIBS}"
-CPPFLAGS="${CPPFLAGS} ${PJPROJECT_CFLAGS}"
-LIBS="${LIBS} ${PJPROJECT_LIBS}"
+      saved_cppflags="${CPPFLAGS}"
+      saved_libs="${LIBS}"
+      CPPFLAGS="${CPPFLAGS} ${PJPROJECT_CFLAGS}"
+      LIBS="${LIBS} ${PJPROJECT_LIB}"
 
     if test "x${PBX_PJSIP_REPLACE_MEDIA_STREAM}" != "x1" -a "${USE_PJSIP_REPLACE_MEDIA_STREAM}" != "no"; then
         if test "x" != "x"; then
@@ -24788,8 +25055,8 @@ rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
        CPPFLAGS="${saved_cppflags}"
     fi
 
-LIBS="${saved_libs}"
-CPPFLAGS="${saved_cppflags}"
+      LIBS="${saved_libs}"
+      CPPFLAGS="${saved_cppflags}"
 
 
 if test "x${PBX_PJSIP_GET_DEST_INFO}" != "x1" -a "${USE_PJSIP_GET_DEST_INFO}" != "no"; then
@@ -24815,7 +25082,7 @@ if eval \${$as_ac_Lib+:} false; then :
   $as_echo_n "(cached) " >&6
 else
   ac_check_lib_save_LIBS=$LIBS
-LIBS="-lpjsip ${pbxlibdir} $PJPROJECT_LIBS $LIBS"
+LIBS="-lpjsip ${pbxlibdir} $PJPROJECT_LIB $LIBS"
 cat confdefs.h - <<_ACEOF >conftest.$ac_ext
 /* end confdefs.h.  */
 
@@ -24857,7 +25124,7 @@ fi
 
    # now check for the header.
    if test "${AST_PJSIP_GET_DEST_INFO_FOUND}" = "yes"; then
-      PJSIP_GET_DEST_INFO_LIB="${pbxlibdir} -lpjsip $PJPROJECT_LIBS"
+      PJSIP_GET_DEST_INFO_LIB="${pbxlibdir} -lpjsip $PJPROJECT_LIB"
       # if --with-PJSIP_GET_DEST_INFO=DIR has been specified, use it.
       if test "x${PJSIP_GET_DEST_INFO_DIR}" != "x"; then
          PJSIP_GET_DEST_INFO_INCLUDE="-I${PJSIP_GET_DEST_INFO_DIR}/include"
@@ -24906,7 +25173,7 @@ if test "x${PBX_PJ_SSL_CERT_LOAD_FROM_FILES2}" != "x1" -a "${USE_PJ_SSL_CERT_LOA
          pbxlibdir="-L${PJ_SSL_CERT_LOAD_FROM_FILES2_DIR}"
       fi
    fi
-   pbxfuncname="pj_ssl_cert_load_from_files2"
+   pbxfuncname="pjsip/include/pjsip/sip_util.h"
    if test "x${pbxfuncname}" = "x" ; then   # empty lib, assume only headers
       AST_PJ_SSL_CERT_LOAD_FROM_FILES2_FOUND=yes
    else
@@ -24919,7 +25186,7 @@ if eval \${$as_ac_Lib+:} false; then :
   $as_echo_n "(cached) " >&6
 else
   ac_check_lib_save_LIBS=$LIBS
-LIBS="-lpj ${pbxlibdir} $PJPROJECT_LIBS $LIBS"
+LIBS="-lpj ${pbxlibdir} $PJPROJECT_LIB $LIBS"
 cat confdefs.h - <<_ACEOF >conftest.$ac_ext
 /* end confdefs.h.  */
 
@@ -24961,7 +25228,7 @@ fi
 
    # now check for the header.
    if test "${AST_PJ_SSL_CERT_LOAD_FROM_FILES2_FOUND}" = "yes"; then
-      PJ_SSL_CERT_LOAD_FROM_FILES2_LIB="${pbxlibdir} -lpj $PJPROJECT_LIBS"
+      PJ_SSL_CERT_LOAD_FROM_FILES2_LIB="${pbxlibdir} -lpj $PJPROJECT_LIB"
       # if --with-PJ_SSL_CERT_LOAD_FROM_FILES2=DIR has been specified, use it.
       if test "x${PJ_SSL_CERT_LOAD_FROM_FILES2_DIR}" != "x"; then
          PJ_SSL_CERT_LOAD_FROM_FILES2_INCLUDE="-I${PJ_SSL_CERT_LOAD_FROM_FILES2_DIR}/include"
@@ -25103,6 +25370,8 @@ _ACEOF
 fi
 
 
+   fi
+fi
 
 
 if test "x${PBX_POPT}" != "x1" -a "${USE_POPT}" != "no"; then
index 1ca5eb3..12cc8d2 100644 (file)
@@ -453,14 +453,37 @@ AST_EXT_LIB_SETUP([OPUS], [Opus], [opus])
 AST_EXT_LIB_SETUP([OSPTK], [OSP Toolkit], [osptk])
 AST_EXT_LIB_SETUP([OSS], [Open Sound System], [oss])
 AST_EXT_LIB_SETUP([PGSQL], [PostgreSQL], [postgres])
+
 AST_EXT_LIB_SETUP([PJPROJECT], [PJPROJECT], [pjproject])
-AST_EXT_LIB_SETUP([POPT], [popt], [popt])
+PJPROJECT_BUNDLED=no
+AH_TEMPLATE(m4_bpatsubst([[HAVE_PJPROJECT_BUNDLED]], [(.*)]), [Define to 1 when using the bundled pjproject.])
+
+AC_ARG_WITH([pjproject-bundled],
+       [AS_HELP_STRING([--with-pjproject-bundled],
+               [Use bundled pjproject libraries])],
+       [case "${enableval}" in
+             n|no) PJPROJECT_BUNDLED=no ;;
+             *) PJPROJECT_BUNDLED=yes ;;
+       esac])
+AC_SUBST(PJPROJECT_BUNDLED)
+
+if test "$PJPROJECT_BUNDLED" = "yes" -a "${ac_mandatory_list#*PJPROJECT*}" != "$ac_mandatory_list" ; then
+   AC_MSG_ERROR(--with-pjproject and --with-pjproject-bundled can't both be specified)
+fi
+
+if test "$PJPROJECT_BUNDLED" = "yes" ; then
+   ac_mandatory_list="$ac_mandatory_list PJPROJECT"
+   PJPROJECT_DIR="${ac_top_build_prefix}third-party/pjproject"
+fi
+
 AST_EXT_LIB_SETUP_OPTIONAL([PJSIP_DLG_CREATE_UAS_AND_INC_LOCK], [PJSIP Dialog Create UAS with Incremented Lock], [PJPROJECT], [pjsip])
 AST_EXT_LIB_SETUP_OPTIONAL([PJ_TRANSACTION_GRP_LOCK], [PJSIP Transaction Group Lock Support], [PJPROJECT], [pjsip])
 AST_EXT_LIB_SETUP_OPTIONAL([PJSIP_REPLACE_MEDIA_STREAM], [PJSIP Media Stream Replacement Support], [PJPROJECT], [pjsip])
 AST_EXT_LIB_SETUP_OPTIONAL([PJSIP_GET_DEST_INFO], [pjsip_get_dest_info support], [PJPROJECT], [pjsip])
 AST_EXT_LIB_SETUP_OPTIONAL([PJ_SSL_CERT_LOAD_FROM_FILES2], [pj_ssl_cert_load_from_files2 support], [PJPROJECT], [pjsip])
 AST_EXT_LIB_SETUP_OPTIONAL([PJSIP_EXTERNAL_RESOLVER], [PJSIP External Resolver Support], [PJPROJECT], [pjsip])
+
+AST_EXT_LIB_SETUP([POPT], [popt], [popt])
 AST_EXT_LIB_SETUP([PORTAUDIO], [PortAudio], [portaudio])
 AST_EXT_LIB_SETUP([PRI], [ISDN PRI], [pri])
 AST_EXT_LIB_SETUP_OPTIONAL([PRI_SETUP_ACK_INBAND], [ISDN PRI progress inband ie in SETUP ACK], [PRI], [pri])
@@ -2152,22 +2175,29 @@ if test "${PG_CONFIG}" != No; then
    fi
 fi
 
-AST_PKG_CONFIG_CHECK([PJPROJECT], [libpjproject])
-
-AST_EXT_LIB_CHECK([PJSIP_DLG_CREATE_UAS_AND_INC_LOCK], [pjsip], [pjsip_dlg_create_uas_and_inc_lock], [pjsip.h], [$PJPROJECT_LIBS], [$PJPROJECT_CFLAGS])
-AST_EXT_LIB_CHECK([PJ_TRANSACTION_GRP_LOCK], [pjsip], [pjsip_tsx_create_uac2], [pjsip.h], [$PJPROJECT_LIBS], [$PJPROJECT_CFLAGS])
-
-saved_cppflags="${CPPFLAGS}"
-saved_libs="${LIBS}"
-CPPFLAGS="${CPPFLAGS} ${PJPROJECT_CFLAGS}"
-LIBS="${LIBS} ${PJPROJECT_LIBS}"
-AST_C_COMPILE_CHECK([PJSIP_REPLACE_MEDIA_STREAM], [pjmedia_mod_offer_flag flag = PJMEDIA_SDP_NEG_ALLOW_MEDIA_CHANGE], [pjmedia.h])
-LIBS="${saved_libs}"
-CPPFLAGS="${saved_cppflags}"
-
-AST_EXT_LIB_CHECK([PJSIP_GET_DEST_INFO], [pjsip], [pjsip_get_dest_info], [pjsip.h], [$PJPROJECT_LIBS], [$PJPROJECT_CFLAGS])
-AST_EXT_LIB_CHECK([PJ_SSL_CERT_LOAD_FROM_FILES2], [pj], [pj_ssl_cert_load_from_files2], [pjlib.h], [$PJPROJECT_LIBS], [$PJPROJECT_CFLAGS])
-AST_EXT_LIB_CHECK([PJSIP_EXTERNAL_RESOLVER], [pjsip], [pjsip_endpt_set_ext_resolver], [pjsip.h], [$PJPROJECT_LIBS], [$PJPROJECT_CFLAGS])
+if test "$USE_PJPROJECT" != "no" ; then
+   if test "$PJPROJECT_BUNDLED" = "yes" ; then
+       AC_CONFIG_MACRO_DIR(third-party/pjproject)
+       PJPROJECT_CONFIGURE([$PJPROJECT_DIR])
+   else
+      AST_PKG_CONFIG_CHECK([PJPROJECT], [libpjproject])
+
+      AST_EXT_LIB_CHECK([PJSIP_DLG_CREATE_UAS_AND_INC_LOCK], [pjsip], [pjsip_dlg_create_uas_and_inc_lock], [pjsip.h], [$PJPROJECT_LIBS], [$PJPROJECT_CFLAGS])
+      AST_EXT_LIB_CHECK([PJ_TRANSACTION_GRP_LOCK], [pjsip], [pjsip_tsx_create_uac2], [pjsip.h], [$PJPROJECT_LIB], [$PJPROJECT_CFLAGS])
+
+      saved_cppflags="${CPPFLAGS}"
+      saved_libs="${LIBS}"
+      CPPFLAGS="${CPPFLAGS} ${PJPROJECT_CFLAGS}"
+      LIBS="${LIBS} ${PJPROJECT_LIB}"
+      AST_C_COMPILE_CHECK([PJSIP_REPLACE_MEDIA_STREAM], [pjmedia_mod_offer_flag flag = PJMEDIA_SDP_NEG_ALLOW_MEDIA_CHANGE], [pjmedia.h])
+      LIBS="${saved_libs}"
+      CPPFLAGS="${saved_cppflags}"
+
+      AST_EXT_LIB_CHECK([PJSIP_GET_DEST_INFO], [pjsip], [pjsip_get_dest_info], [pjsip.h], [$PJPROJECT_LIB], [$PJPROJECT_CFLAGS])
+      AST_EXT_LIB_CHECK([PJ_SSL_CERT_LOAD_FROM_FILES2], [pj], [pjsip/include/pjsip/sip_util.h], [pjlib.h], [$PJPROJECT_LIB], [$PJPROJECT_CFLAGS])
+      AST_EXT_LIB_CHECK([PJSIP_EXTERNAL_RESOLVER], [pjsip], [pjsip_endpt_set_ext_resolver], [pjsip.h], [$PJPROJECT_LIBS], [$PJPROJECT_CFLAGS])
+   fi
+fi
 
 AST_EXT_LIB_CHECK([POPT], [popt], [poptStrerror], [popt.h])
 
@@ -2331,11 +2361,11 @@ AC_CHECK_FUNC([crypt], [SYSCRYPT=true], [SYSCRYPT=""])
 if test "x$LIBCRYPT_LIB" != "x" ; then
     CRYPT_LIB="$LIBCRYPT_LIB"
     CRYPT_INCLUDE="$LIBCRYPT_INCLUDE"
-    AC_DEFINE([HAVE_CRYPT], [1], [Define to 1 if you have the `crypt' function.])
+    AC_DEFINE([HAVE_CRYPT], [1], [Define to 1 if you have the 'crypt' function.])
 elif test "x$SYSCRYPT" != "x" ; then
     CRYPT_LIB=""
     CRYPT_INCLUDE=""
-    AC_DEFINE([HAVE_CRYPT], [1], [Define to 1 if you have the `crypt' function.])
+    AC_DEFINE([HAVE_CRYPT], [1], [Define to 1 if you have the 'crypt' function.])
 fi
 
 AC_SUBST(CRYPT_LIB)
@@ -2343,7 +2373,7 @@ AC_SUBST(CRYPT_INCLUDE)
 
 # Find crypt_r support
 AC_CHECK_LIB([crypt], [crypt_r],
-    [AC_DEFINE([HAVE_CRYPT_R], [1], [Define to 1 if you have the `crypt_r' function.])])
+    [AC_DEFINE([HAVE_CRYPT_R], [1], [Define to 1 if you have the 'crypt_r' function.])])
 
 AST_EXT_LIB_CHECK([CRYPTO], [crypto], [AES_encrypt], [openssl/aes.h])
 
index 7963f31..a4a4f1b 100644 (file)
@@ -53,6 +53,7 @@ void ast_stun_init(void);               /*!< Provided by stun.c */
 int ast_cel_engine_init(void);         /*!< Provided by cel.c */
 int ast_cel_engine_reload(void);       /*!< Provided by cel.c */
 int ast_ssl_init(void);                 /*!< Provided by ssl.c */
+int ast_pj_init(void);                 /*!< Provided by libasteriskpj.c */
 int ast_test_init(void);            /*!< Provided by test.c */
 int ast_msg_init(void);             /*!< Provided by message.c */
 void ast_msg_shutdown(void);        /*!< Provided by message.c */
index 6ed96cc..43f86b0 100644 (file)
 /* Define to 1 if you have the `cosl' function. */
 #undef HAVE_COSL
 
-/* Define to 1 if you have the `crypt' function. */
+/* Define to 1 if you have the 'crypt' function. */
 #undef HAVE_CRYPT
 
 /* Define to 1 if you have the OpenSSL Cryptography library. */
 #undef HAVE_CRYPTO
 
-/* Define to 1 if you have the `crypt_r' function. */
+/* Define to 1 if you have the 'crypt_r' function. */
 #undef HAVE_CRYPT_R
 
 /* Define to 1 if you have a functional curl library. */
 /* Define if your system has the PJPROJECT libraries. */
 #undef HAVE_PJPROJECT
 
-/* Define to 1 if PJPROJECT has the PJSIP Dialog Create UAS with Incremented
-   Lock feature. */
+/* Define if your system has PJPROJECT_BUNDLED */
+#undef HAVE_PJPROJECT_BUNDLED
+
+/* Define if your system has pjsip_dlg_create_uas_and_inc_lock declared. */
 #undef HAVE_PJSIP_DLG_CREATE_UAS_AND_INC_LOCK
 
-/* Define to 1 if PJPROJECT has the PJSIP External Resolver Support feature.
-   */
+/* Define if your system has pjsip_endpt_set_ext_resolver declared. */
 #undef HAVE_PJSIP_EXTERNAL_RESOLVER
 
-/* Define to 1 if PJPROJECT has the pjsip_get_dest_info support feature. */
+/* Define if your system has pjsip_get_dest_info declared. */
 #undef HAVE_PJSIP_GET_DEST_INFO
 
 /* Define if your system has the PJSIP_REPLACE_MEDIA_STREAM headers. */
 #undef HAVE_PJSIP_REPLACE_MEDIA_STREAM
 
-/* Define to 1 if PJPROJECT has the pj_ssl_cert_load_from_files2 support
-   feature. */
+/* Define if your system has pj_ssl_cert_load_from_files2 declared. */
 #undef HAVE_PJ_SSL_CERT_LOAD_FROM_FILES2
 
-/* Define to 1 if PJPROJECT has the PJSIP Transaction Group Lock Support
-   feature. */
+/* Define if your system has pjsip_tsx_create_uac2 declared. */
 #undef HAVE_PJ_TRANSACTION_GRP_LOCK
 
 /* Define to 1 if your system defines IP_PKTINFO. */
index 3ff4656..cb90a5e 100644 (file)
@@ -1,4 +1,6 @@
 asterisk
 libasteriskssl.so.1
 libasteriskssl.dylib
+libasteriskpj.so.2
+libasteriskpj.dylib
 version.c
index b25fb45..50fdc57 100644 (file)
@@ -22,6 +22,9 @@ SRC:=$(wildcard *.c) ast_expr2.c ast_expr2f.c
 ifeq ($(AST_ASTERISKSSL),yes)
 SRC:=$(filter-out libasteriskssl.c,$(SRC))
 endif
+ifeq ($(PJPROJECT_BUNDLED),yes)
+SRC:=$(filter-out libasteriskpj.c,$(SRC))
+endif
 OBJSFILTER=fskmodem_int.o fskmodem_float.o cygload.o buildinfo.o
 OBJS=$(filter-out $(OBJSFILTER),$(SRC:.c=.o))
 
@@ -201,7 +204,7 @@ ASTSSL_LDLIBS=-L. -lasteriskssl
 ifeq ($(findstring darwin,$(OSARCH)),) # not Darwin
 ASTSSL_LIB:=libasteriskssl.so
 
-$(ASTSSL_LIB).$(ASTSSL_SO_VERSION): _ASTLDFLAGS+=-Wl,-soname=$(ASTSSL_LIB).$(ASTSSL_SO_VERSION)
+$(ASTSSL_LIB).$(ASTSSL_SO_VERSION): _ASTLDFLAGS+=-Wl,-soname=$(ASTSSL_LIB)
 $(ASTSSL_LIB).$(ASTSSL_SO_VERSION): _ASTCFLAGS+=-fPIC -DAST_MODULE=\"asteriskssl\" -DAST_NOT_MODULE
 $(ASTSSL_LIB).$(ASTSSL_SO_VERSION): LIBS+=$(ASTSSL_LIBS)
 ifeq ($(GNU_LD),1)
@@ -219,12 +222,14 @@ ifeq ($(GNU_LD),1)
 endif
        $(ECHO_PREFIX) echo "   [LD] $^ -> $@"
        $(CMD_PREFIX) $(CC) $(STATIC_BUILD) -o $@ $(CC_LDFLAGS_SO) $^ $(CC_LIBS)
-ifneq ($(LDCONFIG),)
-       $(LDCONFIG) $(LDCONFIG_FLAGS) .
-endif
 
 $(ASTSSL_LIB): $(ASTSSL_LIB).$(ASTSSL_SO_VERSION)
-       $(LN) -sf $< $@
+       $(ECHO_PREFIX) echo "   [LN] $< -> $@"
+ifneq ($(LDCONFIG),)
+       $(CMD_PREFIX) $(LDCONFIG) $(LDCONFIG_FLAGS) . 2>/dev/null
+else
+       $(CMD_PREFIX) $(LN) -sf $< $@
+endif
 
 else # Darwin
 ASTSSL_LIB:=libasteriskssl.dylib
@@ -244,12 +249,92 @@ endif
 
 endif
 
+libasteriskpj.o: _ASTCFLAGS+=$(PJPROJECT_INCLUDE)
+
+ifeq ($(PJPROJECT_BUNDLED),yes)
+
+ASTPJ_SO_VERSION=2
+ASTPJ_LDLIBS=-L. -lasteriskpj
+
+-include $(ASTTOPDIR)/$(PJPROJECT_DIR)/build.mak
+
+PJPROJECT_LDLIBS := \
+-Wl,--whole-archive \
+$(PJSUA_LIB_LDLIB) \
+$(PJSIP_UA_LDLIB) \
+$(PJSIP_SIMPLE_LDLIB) \
+$(PJSIP_LDLIB) \
+$(PJNATH_LDLIB) \
+$(PJMEDIA_CODEC_LDLIB) \
+$(PJMEDIA_VIDEODEV_LDLIB) \
+$(PJMEDIA_AUDIODEV_LDLIB) \
+$(PJMEDIA_LDLIB) \
+$(PJLIB_UTIL_LDLIB) \
+$(PJLIB_LDLIB) \
+-Wl,--no-whole-archive \
+$(APP_THIRD_PARTY_LIBS) \
+$(APP_THIRD_PARTY_EXT)
+
+ifeq ($(findstring darwin,$(OSARCH)),) # not Darwin
+ASTPJ_LIB:=libasteriskpj.so
+
+libasteriskpj.exports: $(ASTTOPDIR)/$(PJPROJECT_DIR)/pjproject.symbols
+       $(ECHO_PREFIX) echo "   [GENERATE] libasteriskpj.exports"
+ifeq ($(GNU_LD),1)
+       $(CMD_PREFIX) echo -e "{\n\tglobal:" > libasteriskpj.exports
+       $(CMD_PREFIX) sed -r -e "s/.*/\t\t$(LINKER_SYMBOL_PREFIX)&;/" $(ASTTOPDIR)/$(PJPROJECT_DIR)/pjproject.symbols >> libasteriskpj.exports
+       $(CMD_PREFIX) echo -e "\t\t$(LINKER_SYMBOL_PREFIX)ast_pj_init;\n" >> libasteriskpj.exports
+       $(CMD_PREFIX) echo -e "\tlocal:\n\t\t*;\n};" >> libasteriskpj.exports
+endif
+
+$(ASTPJ_LIB).$(ASTPJ_SO_VERSION): _ASTLDFLAGS+=-Wl,-soname=$(ASTPJ_LIB) $(PJ_LDFLAGS)
+$(ASTPJ_LIB).$(ASTPJ_SO_VERSION): _ASTCFLAGS+=-fPIC -DAST_MODULE=\"asteriskpj\" $(PJ_CFLAGS)
+$(ASTPJ_LIB).$(ASTPJ_SO_VERSION): LIBS+=$(PJPROJECT_LDLIBS) -lssl -lcrypto -luuid -lm -lrt -lpthread
+ifeq ($(GNU_LD),1)
+    $(ASTPJ_LIB).$(ASTPJ_SO_VERSION): SO_SUPPRESS_SYMBOLS=-Wl,--version-script,libasteriskpj.exports,--warn-common
+endif
+$(ASTPJ_LIB).$(ASTPJ_SO_VERSION): SOLINK=$(DYLINK)
+
+# These rules are duplicated from $(ASTTOPDIR)/Makefile.rules because the library name
+# being built does not match the "%.so" pattern; there are also additional steps
+# required to build a proper shared library (as opposed to the 'loadable module'
+# type that are built by the standard rules)
+$(ASTPJ_LIB).$(ASTPJ_SO_VERSION): libasteriskpj.o libasteriskpj.exports
+       $(ECHO_PREFIX) echo "   [LD] $< -> $@"
+       $(CMD_PREFIX) $(CC) $(STATIC_BUILD) -o $@ $(CC_LDFLAGS_SO) $< $(CC_LIBS)
+
+$(ASTPJ_LIB): $(ASTPJ_LIB).$(ASTPJ_SO_VERSION)
+       $(ECHO_PREFIX) echo "   [LN] $< -> $@"
+ifneq ($(LDCONFIG),)
+       $(CMD_PREFIX) $(LDCONFIG) $(LDCONFIG_FLAGS) . 2>/dev/null
+else
+       $(CMD_PREFIX) $(LN) -sf $< $@
+endif
+
+else # Darwin
+ASTPJ_LIB:=libasteriskpj.dylib
+
+# -install_name allows library to be found if installed somewhere other than
+# /lib or /usr/lib
+$(ASTPJ_LIB): _ASTLDFLAGS+=-dynamiclib -install_name $(ASTLIBDIR)/$(ASTPJ_LIB) $(PJ_LDFLAGS)
+$(ASTPJ_LIB): _ASTCFLAGS+=-fPIC -DAST_MODULE=\"asteriskpj\" $(PJ_CFLAGS)
+$(ASTPJ_LIB): LIBS+=$(PJPROJECT_LIBS)  -lssl -lcrypto -luuid -lm -lrt -lpthread
+$(ASTPJ_LIB): SOLINK=$(DYLINK)
+
+# Special rules for building a shared library (not a dynamically loadable module)
+$(ASTPJ_LIB): libasteriskpj.o
+       $(ECHO_PREFIX) echo "   [LD] $^ -> $@"
+       $(CMD_PREFIX) $(CC) $(STATIC_BUILD) -o $@ $(CC_LDFLAGS_SO) $^ $(CC_LIBS)
+endif
+
+endif
+
 tcptls.o: _ASTCFLAGS+=$(OPENSSL_INCLUDE)
 
-$(MAIN_TGT): $(OBJS) $(ASTSSL_LIB) $(LIBEDIT_OBJ) $(AST_EMBED_LDSCRIPTS)
+$(MAIN_TGT): $(OBJS) $(ASTSSL_LIB) $(ASTPJ_LIB) $(LIBEDIT_OBJ) $(AST_EMBED_LDSCRIPTS)
        @$(CC) -c -o buildinfo.o $(_ASTCFLAGS) buildinfo.c $(ASTCFLAGS)
        $(ECHO_PREFIX) echo "   [LD] $(OBJS) $(LIBEDIT_OBJ) $(AST_EMBED_LDSCRIPTS) -> $@"
-       $(CMD_PREFIX) $(CXX) $(STATIC_BUILD) -o $@ $(ASTLINK) $(AST_EMBED_LDFLAGS) $(_ASTLDFLAGS) $(ASTLDFLAGS) $(OBJS) $(ASTSSL_LDLIBS) $(LIBEDIT_OBJ) $(AST_EMBED_LDSCRIPTS) buildinfo.o $(AST_LIBS) $(AST_EMBED_LIBS) $(GMIMELDFLAGS) $(LIBEDIT_LIB)
+       $(CMD_PREFIX) $(CXX) $(STATIC_BUILD) -o $@ $(ASTLINK) $(AST_EMBED_LDFLAGS) $(_ASTLDFLAGS) $(ASTLDFLAGS) $(OBJS) $(ASTSSL_LDLIBS) $(ASTPJ_LDLIBS) $(LIBEDIT_OBJ) $(AST_EMBED_LDSCRIPTS) buildinfo.o $(AST_LIBS) $(AST_EMBED_LIBS) $(GMIMELDFLAGS) $(LIBEDIT_LIB)
 
 ifeq ($(GNU_LD),1)
 $(MAIN_TGT): asterisk.exports
@@ -266,16 +351,29 @@ ifeq ($(findstring darwin,$(OSARCH)),) # not Darwin
 else # Darwin
        $(INSTALL) -m 755 $(ASTSSL_LIB) "$(DESTDIR)$(ASTLIBDIR)/"
 endif
+endif
+ifeq ($(PJPROJECT_BUNDLED),yes)
+ifeq ($(findstring darwin,$(OSARCH)),) # not Darwin
+       $(INSTALL) -m 755 $(ASTPJ_LIB).$(ASTPJ_SO_VERSION) "$(DESTDIR)$(ASTLIBDIR)/"
+       $(LN) -sf $(ASTPJ_LIB).$(ASTPJ_SO_VERSION) "$(DESTDIR)$(ASTLIBDIR)/$(ASTPJ_LIB)"
+else # Darwin
+       $(INSTALL) -m 755 $(ASTPJ_LIB) "$(DESTDIR)$(ASTLIBDIR)/"
+endif
+endif
 ifneq ($(LDCONFIG),)
        $(LDCONFIG) $(LDCONFIG_FLAGS) "$(DESTDIR)$(ASTLIBDIR)/"
 endif
-endif
        $(LN) -sf asterisk "$(DESTDIR)$(ASTSBINDIR)/rasterisk"
 
 binuninstall:
        rm -f "$(DESTDIR)$(ASTSBINDIR)/$(MAIN_TGT)"
        rm -f "$(DESTDIR)$(ASTSBINDIR)/rasterisk"
+ifneq ($(ASTSSL_LIB).$(ASTSSL_SO_VERSION),.)
        rm -f "$(DESTDIR)$(ASTLIBDIR)/$(ASTSSL_LIB).$(ASTSSL_SO_VERSION)"
+endif
+ifneq ($(ASTPJ_LIB).$(ASTPJ_SO_VERSION),.)
+       rm -f "$(DESTDIR)$(ASTLIBDIR)/$(ASTPJ_LIB).$(ASTPJ_SO_VERSION)"
+endif
 ifneq ($(LDCONFIG),)
        $(LDCONFIG) $(LDCONFIG_FLAGS) "$(DESTDIR)$(ASTLIBDIR)/"
 endif
@@ -285,7 +383,12 @@ clean::
 ifeq ($(AST_ASTERISKSSL),yes)
        rm -f $(ASTSSL_LIB) $(ASTSSL_LIB).*
 endif
-       rm -f asterisk.exports libasteriskssl.exports
+       rm -f libasteriskpj.o
+       rm -f libasteriskpj.so* libasteriskpj.dynlib
+       rm -f .libasteriskpj*
+
+       rm -f asterisk.exports libasteriskssl.exports libasteriskpj.exports
        @if [ -f editline/Makefile ]; then $(MAKE) -C editline distclean ; fi
        @$(MAKE) -C stdtime clean
        rm -f libresample/src/*.o
+       rm -f *.tmp
index ca560cd..da804e1 100644 (file)
@@ -4478,6 +4478,11 @@ static void asterisk_daemon(int isroot, const char *runuser, const char *rungrou
                exit(1);
        }
 
+       if (ast_pj_init()) {
+               printf("Failed: ast_pj_init\n%s", term_quit());
+               exit(1);
+       }
+
        if (app_init()) {
                printf("App core initialization failed.\n%s", term_quit());
                exit(1);
diff --git a/main/libasteriskpj.c b/main/libasteriskpj.c
new file mode 100644 (file)
index 0000000..aed0ec8
--- /dev/null
@@ -0,0 +1,52 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2009-2012, Digium, Inc.
+ * Copyright (C) 2015, Fairview 5 Engineering, LLC
+ *
+ * Russell Bryant <russell@digium.com>
+ * George Joseph <george.joseph@fairview5.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+/*!
+ * \file
+ * \brief Loader stub for static pjproject libraries
+ *
+ * \author George Joseph <george.joseph@fairview5.com>
+ */
+
+/*** MODULEINFO
+       <support_level>core</support_level>
+ ***/
+
+#include "asterisk.h"
+
+ASTERISK_REGISTER_FILE()
+
+#ifdef HAVE_PJPROJECT
+#include <pjlib.h>
+#endif
+
+#include "asterisk/_private.h" /* ast_pj_init() */
+
+/*!
+ * \internal
+ * \brief Initialize static pjproject implementation
+ */
+int ast_pj_init(void)
+{
+#ifdef HAVE_PJPROJECT_BUNDLED
+       pj_init();
+#endif
+       return 0;
+}
index f606ace..6baef1b 100644 (file)
@@ -229,8 +229,10 @@ OSS_LIB=@OSS_LIB@ @FFMPEG_LIB@ @SDL_LIB@ @SDL_IMAGE_LIB@ @X11_LIB@
 PGSQL_INCLUDE=@PGSQL_INCLUDE@
 PGSQL_LIB=@PGSQL_LIB@
 
+PJPROJECT_BUNDLED=@PJPROJECT_BUNDLED@
 PJPROJECT_INCLUDE=@PJPROJECT_INCLUDE@
 PJPROJECT_LIB=@PJPROJECT_LIB@
+PJPROJECT_DIR=@PJPROJECT_DIR@
 
 POPT_INCLUDE=@POPT_INCLUDE@
 POPT_LIB=@POPT_LIB@
diff --git a/third-party/Makefile b/third-party/Makefile
new file mode 100644 (file)
index 0000000..0aca21e
--- /dev/null
@@ -0,0 +1,21 @@
+
+include Makefile.rules
+
+TP_SUBDIRS := pjproject
+# Sub directories that contain special install/uninstall targets must be explicitly listed
+# to prevent accidentally running the package's default install target.
+TP_INSTALL_SUBDIRS := pjproject
+
+.PHONY: all dist-clean distclean install clean moduleinfo makeopts uninstall __embed_libs __embed_ldscript __embed_ldflags $(TP_SUBDIRS)
+
+override MAKECMDGOALS?=all
+
+MAKECMDGOALS:=$(subst dist-clean,distclean,$(MAKECMDGOALS))
+MAKECMDGOALS:=$(subst tpclean,clean,$(MAKECMDGOALS))
+
+all distclean dist-clean install tpclean : $(TP_SUBDIRS)
+install uninstall: $(TP_INSTALL_SUBDIRS)
+
+$(TP_SUBDIRS):
+       +$(CMD_PREFIX) $(SUBMAKE) -C $@ $(MAKECMDGOALS)
+
diff --git a/third-party/Makefile.rules b/third-party/Makefile.rules
new file mode 100644 (file)
index 0000000..ac4189a
--- /dev/null
@@ -0,0 +1,37 @@
+
+ifeq ($(NOISY_BUILD),)
+       SUBMAKE?=$(MAKE) --quiet --no-print-directory
+    ECHO_PREFIX?=@
+    CMD_PREFIX?=@
+    QUIET_CONFIGURE=-q
+    REALLY_QUIET=&>/dev/null
+else
+       SUBMAKE?=$(MAKE)
+    ECHO_PREFIX?=@\#
+    CMD_PREFIX?=
+    QUIET_CONFIGURE=
+    REALLY_QUIET=
+endif
+
+DOWNLOAD :=
+DOWNLOAD != which wget 2>/dev/null
+DOWNLOAD:=$(if $(DOWNLOAD),$(DOWNLOAD) -O- ,)
+
+ifeq ($(DOWNLOAD),)
+DOWNLOAD != which curl 2>/dev/null
+DOWNLOAD:=$(if $(DOWNLOAD), $(DOWNLOAD) -L ,)
+endif
+
+ifeq ($(DOWNLOAD),)
+DOWNLOAD := echo "No download program available" ; exit 1;
+endif
+
+export SUBMAKE
+export ECHO_PREFIX
+export CMD_PREFIX
+export QUIET_CONFIGURE
+export REALLY_QUIET
+export ASTTOPDIR
+export ASTSBINDIR
+export DESTDIR
+export ASTDATADIR
diff --git a/third-party/pjproject/.gitignore b/third-party/pjproject/.gitignore
new file mode 100644 (file)
index 0000000..5079dee
--- /dev/null
@@ -0,0 +1,4 @@
+source/
+**.bz2
+build.mak
+pjproject.symbols
diff --git a/third-party/pjproject/Makefile b/third-party/pjproject/Makefile
new file mode 100644 (file)
index 0000000..3100951
--- /dev/null
@@ -0,0 +1,110 @@
+.SUFFIXES:
+.PHONY: _all all _install install clean distclean echo_cflags configure
+
+ifeq ($(MAKECMDGOALS),install)
+include ../../makeopts
+else
+-include ../../makeopts
+endif
+
+include ../versions.mak
+include ../Makefile.rules
+include Makefile.rules
+
+ECHO_PREFIX := $(ECHO_PREFIX) echo '[pjproject] '
+
+ifeq ($(MAKECMDGOALS),echo_cflags)
+-include build.mak
+ECHO_PREFIX=@\#
+endif
+
+ifneq ($(PJPROJECT_BUNDLED),yes)
+all install:
+       @echo '[pjproject] Not enabled'
+else
+
+ifneq ($(findstring clean,$(MAKECMDGOALS)),clean)
+include build.mak
+endif
+
+all: _all
+install: _install
+endif
+
+ifndef $(TMPDIR)
+ifneq ($(wildcard /tmp),)
+TMPDIR=/tmp
+else
+TMPDIR=.
+endif
+endif
+
+$(TMPDIR)/pjproject-$(PJPROJECT_VERSION).tar.bz2 : ../versions.mak
+       $(ECHO_PREFIX) Downloading $@ with $(DOWNLOAD)
+       $(CMD_PREFIX) $(DOWNLOAD) $(PJPROJECT_URL)/$(@F) > $@
+
+source/user.mak source/pjlib/include/pj/config_site.h: $(TMPDIR)/pjproject-$(PJPROJECT_VERSION).tar.bz2 patches/config_site.h patches/user.mak 
+       $(ECHO_PREFIX) Unpacking $<
+       -@rm -rf source &>/dev/null
+       -@mkdir source &>/dev/null
+       $(CMD_PREFIX) tar --strip-components=1 -C source -xjf $<
+       $(ECHO_PREFIX) Applying patches and custom files
+       $(CMD_PREFIX) ./apply_patches $(QUIET_CONFIGURE) ./patches ./source
+       $(CMD_PREFIX) cp -f ./patches/config_site.h ./source/pjlib/include/pj/
+       $(CMD_PREFIX) cp -f ./patches/user.mak ./source/
+
+build.mak: source/pjlib/include/pj/config_site.h source/user.mak Makefile.rules
+       $(ECHO_PREFIX) Configuring with $(PJPROJECT_CONFIG_OPTS)
+       $(CMD_PREFIX) (cd source ; autoconf aconfigure.ac > aconfigure && ./aconfigure $(QUIET_CONFIGURE) $(PJPROJECT_CONFIG_OPTS))
+       @sed -r -e "/prefix|export PJ_SHARED_LIBRARIES|MACHINE_NAME|OS_NAME|HOST_NAME|CC_NAME|CROSS_COMPILE|LINUX_POLL/d" source/build.mak > build.mak
+
+configure: build.mak
+
+echo_cflags: build.mak
+       @echo $(PJ_CFLAGS)
+
+source/pjlib/build/.pjlib-$(TARGET_NAME).depend: build.mak
+       $(ECHO_PREFIX) "Making dependencies"
+       +$(CMD_PREFIX) $(SUBMAKE) -C source dep
+
+source/pjlib/lib/libpj-$(TARGET_NAME).a: source/pjlib/build/.pjlib-$(TARGET_NAME).depend
+       $(ECHO_PREFIX) Compiling libs
+       +$(CMD_PREFIX) $(SUBMAKE) -C source lib $(REALLY_QUIET)
+
+pjproject.symbols: source/pjlib/lib/libpj-$(TARGET_NAME).a
+       $(ECHO_PREFIX) Generating symbols
+       $(CMD_PREFIX) nm -Pog $(PJ_LIB_FILES) | sed -n -r -e "s/.+: ([pP][jJ][^ ]+) .+/\1/gp" | sort -u > pjproject.symbols
+
+source/pjsip-apps/bin/pjsua-$(TARGET_NAME): source/pjlib/lib/libpj-$(TARGET_NAME).a
+       $(ECHO_PREFIX) Compiling apps
+       $(CMD_PREFIX) $(SUBMAKE) -C source/pjsip-apps/build pjsua pjsystest $(REALLY_QUIET)
+
+source/pjsip-apps/src/python/build/_pjsua.so: source/pjlib/lib/libpj-$(TARGET_NAME).a
+       $(ECHO_PREFIX) Compiling python bindings
+       $(CMD_PREFIX) (cd source/pjsip-apps/src/python ; python setup.py build --build-platlib=./build $(REALLY_QUIET))
+
+_all: pjproject.symbols source/pjsip-apps/bin/pjsua-$(TARGET_NAME) source/pjsip-apps/src/python/build/_pjsua.so
+
+_install: _all
+       $(ECHO_PREFIX) Installing apps and python bindings
+       @if [ ! -d "$(DESTDIR)$(ASTDATADIR)/third-party/pjproject" ]; then \
+               $(INSTALL) -d "$(DESTDIR)$(ASTDATADIR)/third-party/pjproject"; \
+       fi;
+       $(CMD_PREFIX) $(INSTALL) -m 755 source/pjsip-apps/bin/pjsua-$(TARGET_NAME) "$(DESTDIR)$(ASTDATADIR)/third-party/pjproject/pjsua"
+       $(CMD_PREFIX) $(INSTALL) -m 755 source/pjsip-apps/bin/pjsystest-$(TARGET_NAME) "$(DESTDIR)$(ASTDATADIR)/third-party/pjproject/pjsystest"
+       $(CMD_PREFIX) $(INSTALL) -m 755 source/pjsip-apps/src/python/build/_pjsua.so "$(DESTDIR)$(ASTDATADIR)/third-party/pjproject/"
+       $(CMD_PREFIX) $(INSTALL) -m 644 source/pjsip-apps/src/python/build/pjsua.py "$(DESTDIR)$(ASTDATADIR)/third-party/pjproject/"
+
+uninstall:
+       $(ECHO_PREFIX) Uninstalling apps and python bindings
+       $(CMD_PREFIX) rm -rf "$(DESTDIR)$(ASTDATADIR)/third-party/pjproject"
+
+clean:
+       $(ECHO_PREFIX) Cleaning
+       -$(CMD_PREFIX) test -d source && ($(SUBMAKE) -C source clean ; find source -name *.a -delete ; rm -rf source/pjsip-apps/src/python/build) || :
+       -$(CMD_PREFIX) rm -rf pjproject.symbols
+
+distclean:
+       $(ECHO_PREFIX) Distcleaning
+       -$(CMD_PREFIX) rm -rf source pjproject.symbols pjproject-*.tar.bz2 build.mak
+
diff --git a/third-party/pjproject/Makefile.rules b/third-party/pjproject/Makefile.rules
new file mode 100644 (file)
index 0000000..d6e4be0
--- /dev/null
@@ -0,0 +1,7 @@
+PJPROJECT_URL = http://www.pjsip.org/release/$(PJPROJECT_VERSION)
+
+# Even though we're not installing pjproject, we're setting prefix to /opt/pjproject to be safe
+PJPROJECT_CONFIG_OPTS = --prefix=/opt/pjproject --with-external-speex --with-external-gsm --with-external-srtp \
+       --with-external-pa --disable-video --disable-v4l2 --disable-sound --disable-resample \
+       --disable-opencore-amr --disable-ilbc-codec --without-libyuv --disable-g7221-codec \
+       --enable-epoll
diff --git a/third-party/pjproject/apply_patches b/third-party/pjproject/apply_patches
new file mode 100755 (executable)
index 0000000..1b72d14
--- /dev/null
@@ -0,0 +1,39 @@
+#!/bin/bash
+
+if [ "$1" = "-q" ] ; then
+       quiet=1
+       shift
+fi
+
+patchdir=${1:?You must supply a patches directory}
+sourcedir=${2?:You must supply a source directory}
+
+patchdir=`readlink -f $patchdir`
+sourcedir=`readlink -f $sourcedir`
+
+if [ ! -d "$patchdir" ] ; then
+       echo "$patchdir is not a directory" >&2
+       exit 1
+fi
+
+if [ ! -d "$sourcedir" ] ; then
+       echo "$sourcedir is not a directory"  >&2
+       exit 1
+fi
+
+if [ ! "$(ls -A $patchdir/*.patch 2>/dev/null)" ] ; then
+       echo "No patches in $patchdir"  >&2
+       exit 0
+fi
+
+for patchfile in $patchdir/*.patch ; do
+       patch -d $sourcedir -p1 -s -r- -f -N --dry-run -i "$patchfile" || (echo "Patchfile $(basename $patchfile) failed to apply >&2" ; exit 1) || exit 1
+done
+
+for patchfile in "$patchdir"/*.patch ; do
+       [ -z $quiet ] && echo "Applying patch $(basename $patchfile)"
+       patch -d "$sourcedir" -p1 -s -i "$patchfile" || exit 1
+done
+
+exit 0
+
diff --git a/third-party/pjproject/configure.m4 b/third-party/pjproject/configure.m4
new file mode 100644 (file)
index 0000000..3351527
--- /dev/null
@@ -0,0 +1,46 @@
+AC_DEFUN([PJPROJECT_SYMBOL_CHECK],
+[
+       $1_INCLUDE="$PJPROJECT_INCLUDE"
+    AC_MSG_CHECKING([for $2 declared in $3])
+
+       saved_cpp="$CPPFLAGS"
+       CPPFLAGS="$PJPROJECT_INCLUDE"
+       AC_EGREP_HEADER($2, $3, [
+               AC_MSG_RESULT(yes)
+               PBX_$1=1
+               AC_DEFINE([HAVE_$1], 1, [Define if your system has $2 declared.])
+       ], [
+               AC_MSG_RESULT(no)
+       ])
+
+       CPPGLAGS="$saved_cpp"
+       $1_INCLUDE="$PJPROJECT_INCLUDE"
+])
+
+AC_DEFUN([PJPROJECT_CONFIGURE],
+[
+       AC_MSG_CHECKING(for embedded pjproject (may have to download))
+       AC_MSG_RESULT(configuring)
+       make --quiet --no-print-directory -C $1 configure
+       if test $? -ne 0 ; then
+               AC_MSG_RESULT(failed)
+               AC_MSG_NOTICE(Unable to configure $1)
+               AC_MSG_ERROR(Run "make -C $1 NOISY_BUILD=yes configure" to see error details.)
+       fi
+
+       PJPROJECT_INCLUDE=$(make --quiet --no-print-directory -C $1 echo_cflags)
+       PJPROJECT_CFLAGS="$PJPROJECT_INCLUDE"
+       PBX_PJPROJECT=1
+       PJPROJECT_BUNDLED=yes
+       AC_DEFINE([HAVE_PJPROJECT], 1, [Define if your system has PJPROJECT])
+       AC_DEFINE([HAVE_PJPROJECT_BUNDLED], 1, [Define if your system has PJPROJECT_BUNDLED])
+       AC_MSG_CHECKING(for embedded pjproject)
+       AC_MSG_RESULT(yes)
+
+       PJPROJECT_SYMBOL_CHECK([PJSIP_DLG_CREATE_UAS_AND_INC_LOCK], [pjsip_dlg_create_uas_and_inc_lock], [pjsip.h])
+       PJPROJECT_SYMBOL_CHECK([PJ_TRANSACTION_GRP_LOCK], [pjsip_tsx_create_uac2], [pjsip.h])
+       PJPROJECT_SYMBOL_CHECK([PJSIP_REPLACE_MEDIA_STREAM], [PJMEDIA_SDP_NEG_ALLOW_MEDIA_CHANGE], [pjmedia.h])
+       PJPROJECT_SYMBOL_CHECK([PJSIP_GET_DEST_INFO], [pjsip_get_dest_info], [pjsip.h])
+       PJPROJECT_SYMBOL_CHECK([PJ_SSL_CERT_LOAD_FROM_FILES2], [pj_ssl_cert_load_from_files2], [pjlib.h])
+       PJPROJECT_SYMBOL_CHECK([PJSIP_EXTERNAL_RESOLVER], [pjsip_endpt_set_ext_resolver], [pjsip.h])
+])
diff --git a/third-party/pjproject/patches/0001-2.4.5-fix-for-tls-async-ops.patch b/third-party/pjproject/patches/0001-2.4.5-fix-for-tls-async-ops.patch
new file mode 100644 (file)
index 0000000..33fc8ea
--- /dev/null
@@ -0,0 +1,224 @@
+diff --git a/pjlib/include/pj/ssl_sock.h b/pjlib/include/pj/ssl_sock.h
+index 1682bda..a69af32 100644
+--- a/pjlib/include/pj/ssl_sock.h
++++ b/pjlib/include/pj/ssl_sock.h
+@@ -864,6 +864,18 @@ PJ_DECL(void) pj_ssl_sock_param_default(pj_ssl_sock_param *param);
+ /**
++ * Duplicate pj_ssl_sock_param.
++ *
++ * @param pool        Pool to allocate memory.
++ * @param dst Destination parameter.
++ * @param src Source parameter.
++ */
++PJ_DECL(void) pj_ssl_sock_param_copy(pj_pool_t *pool, 
++                                   pj_ssl_sock_param *dst,
++                                   const pj_ssl_sock_param *src);
++
++
++/**
+  * Create secure socket instance.
+  *
+  * @param pool                The pool for allocating secure socket instance.
+@@ -1115,6 +1127,30 @@ PJ_DECL(pj_status_t) pj_ssl_sock_start_accept(pj_ssl_sock_t *ssock,
+ /**
++ * Same as #pj_ssl_sock_start_accept(), but application can provide
++ * a secure socket parameter, which will be used to create a new secure
++ * socket reported in \a on_accept_complete() callback when there is
++ * an incoming connection.
++ *
++ * @param ssock               The secure socket.
++ * @param pool                Pool used to allocate some internal data for the
++ *                    operation.
++ * @param localaddr   Local address to bind on.
++ * @param addr_len    Length of buffer containing local address.
++ * @param newsock_param       Secure socket parameter for new accepted sockets.
++ *
++ * @return            PJ_SUCCESS if the operation has been successful,
++ *                    or the appropriate error code on failure.
++ */
++PJ_DECL(pj_status_t)
++pj_ssl_sock_start_accept2(pj_ssl_sock_t *ssock,
++                        pj_pool_t *pool,
++                        const pj_sockaddr_t *local_addr,
++                        int addr_len,
++                        const pj_ssl_sock_param *newsock_param);
++
++
++/**
+  * Starts asynchronous socket connect() operation and SSL/TLS handshaking 
+  * for this socket. Once the connection is done (either successfully or not),
+  * the \a on_connect_complete() callback will be called.
+diff --git a/pjlib/src/pj/ssl_sock_common.c b/pjlib/src/pj/ssl_sock_common.c
+index 913efee..717ab1d 100644
+--- a/pjlib/src/pj/ssl_sock_common.c
++++ b/pjlib/src/pj/ssl_sock_common.c
+@@ -19,6 +19,7 @@
+ #include <pj/ssl_sock.h>
+ #include <pj/assert.h>
+ #include <pj/errno.h>
++#include <pj/pool.h>
+ #include <pj/string.h>
+ /*
+@@ -48,6 +49,31 @@ PJ_DEF(void) pj_ssl_sock_param_default(pj_ssl_sock_param *param)
+ }
++/*
++ * Duplicate SSL socket parameter.
++ */
++PJ_DEF(void) pj_ssl_sock_param_copy( pj_pool_t *pool, 
++                                   pj_ssl_sock_param *dst,
++                                   const pj_ssl_sock_param *src)
++{
++    /* Init secure socket param */
++    pj_memcpy(dst, src, sizeof(*dst));
++    if (src->ciphers_num > 0) {
++      unsigned i;
++      dst->ciphers = (pj_ssl_cipher*)
++                      pj_pool_calloc(pool, src->ciphers_num, 
++                                     sizeof(pj_ssl_cipher));
++      for (i = 0; i < src->ciphers_num; ++i)
++          dst->ciphers[i] = src->ciphers[i];
++    }
++
++    if (src->server_name.slen) {
++        /* Server name must be null-terminated */
++        pj_strdup_with_null(pool, &dst->server_name, &src->server_name);
++    }
++}
++
++
+ PJ_DEF(pj_status_t) pj_ssl_cert_get_verify_status_strings(
+                                               pj_uint32_t verify_status, 
+                                               const char *error_strings[],
+diff --git a/pjlib/src/pj/ssl_sock_ossl.c b/pjlib/src/pj/ssl_sock_ossl.c
+index 40a5a1e..6a701b7 100644
+--- a/pjlib/src/pj/ssl_sock_ossl.c
++++ b/pjlib/src/pj/ssl_sock_ossl.c
+@@ -141,6 +141,7 @@ struct pj_ssl_sock_t
+     pj_pool_t          *pool;
+     pj_ssl_sock_t      *parent;
+     pj_ssl_sock_param   param;
++    pj_ssl_sock_param   newsock_param;
+     pj_ssl_cert_t      *cert;
+     
+     pj_ssl_cert_info    local_cert_info;
+@@ -1757,11 +1758,9 @@ static pj_bool_t asock_on_accept_complete (pj_activesock_t *asock,
+     unsigned i;
+     pj_status_t status;
+-    PJ_UNUSED_ARG(src_addr_len);
+-
+     /* Create new SSL socket instance */
+-    status = pj_ssl_sock_create(ssock_parent->pool, &ssock_parent->param,
+-                              &ssock);
++    status = pj_ssl_sock_create(ssock_parent->pool,
++                              &ssock_parent->newsock_param, &ssock);
+     if (status != PJ_SUCCESS)
+       goto on_return;
+@@ -2183,20 +2182,8 @@ PJ_DEF(pj_status_t) pj_ssl_sock_create (pj_pool_t *pool,
+       return status;
+     /* Init secure socket param */
+-    ssock->param = *param;
++    pj_ssl_sock_param_copy(pool, &ssock->param, param);
+     ssock->param.read_buffer_size = ((ssock->param.read_buffer_size+7)>>3)<<3;
+-    if (param->ciphers_num > 0) {
+-      unsigned i;
+-      ssock->param.ciphers = (pj_ssl_cipher*)
+-                             pj_pool_calloc(pool, param->ciphers_num, 
+-                                            sizeof(pj_ssl_cipher));
+-      for (i = 0; i < param->ciphers_num; ++i)
+-          ssock->param.ciphers[i] = param->ciphers[i];
+-    }
+-
+-    /* Server name must be null-terminated */
+-    pj_strdup_with_null(pool, &ssock->param.server_name, 
+-                      &param->server_name);
+     /* Finally */
+     *p_ssock = ssock;
+@@ -2617,12 +2604,36 @@ PJ_DEF(pj_status_t) pj_ssl_sock_start_accept (pj_ssl_sock_t *ssock,
+                                             const pj_sockaddr_t *localaddr,
+                                             int addr_len)
+ {
++    return pj_ssl_sock_start_accept2(ssock, pool, localaddr, addr_len,
++                                   &ssock->param);
++}
++
++
++/**
++ * Same as #pj_ssl_sock_start_accept(), but application provides parameter
++ * for new accepted secure sockets.
++ */
++PJ_DEF(pj_status_t)
++pj_ssl_sock_start_accept2(pj_ssl_sock_t *ssock,
++                        pj_pool_t *pool,
++                        const pj_sockaddr_t *localaddr,
++                        int addr_len,
++                        const pj_ssl_sock_param *newsock_param)
++{
+     pj_activesock_cb asock_cb;
+     pj_activesock_cfg asock_cfg;
+     pj_status_t status;
+     PJ_ASSERT_RETURN(ssock && pool && localaddr && addr_len, PJ_EINVAL);
++    /* Verify new socket parameters */
++    if (newsock_param->grp_lock != ssock->param.grp_lock ||
++        newsock_param->sock_af != ssock->param.sock_af ||
++        newsock_param->sock_type != ssock->param.sock_type)
++    {
++        return PJ_EINVAL;
++    }
++
+     /* Create socket */
+     status = pj_sock_socket(ssock->param.sock_af, ssock->param.sock_type, 0, 
+                           &ssock->sock);
+@@ -2691,6 +2702,7 @@ PJ_DEF(pj_status_t) pj_ssl_sock_start_accept (pj_ssl_sock_t *ssock,
+       goto on_error;
+     /* Start accepting */
++    pj_ssl_sock_param_copy(pool, &ssock->newsock_param, newsock_param);
+     status = pj_activesock_start_accept(ssock->asock, pool);
+     if (status != PJ_SUCCESS)
+       goto on_error;
+diff --git a/pjsip/src/pjsip/sip_transport_tls.c b/pjsip/src/pjsip/sip_transport_tls.c
+index a9e95fb..91d99a7 100644
+--- a/pjsip/src/pjsip/sip_transport_tls.c
++++ b/pjsip/src/pjsip/sip_transport_tls.c
+@@ -314,7 +314,7 @@ PJ_DEF(pj_status_t) pjsip_tls_transport_start2( pjsip_endpoint *endpt,
+     int af, sip_ssl_method;
+     pj_uint32_t sip_ssl_proto;
+     struct tls_listener *listener;
+-    pj_ssl_sock_param ssock_param;
++    pj_ssl_sock_param ssock_param, newsock_param;
+     pj_sockaddr *listener_addr;
+     pj_bool_t has_listener;
+     pj_status_t status;
+@@ -473,9 +473,14 @@ PJ_DEF(pj_status_t) pjsip_tls_transport_start2( pjsip_endpoint *endpt,
+      */
+     has_listener = PJ_FALSE;
+-    status = pj_ssl_sock_start_accept(listener->ssock, pool, 
++    pj_memcpy(&newsock_param, &ssock_param, sizeof(newsock_param));
++    newsock_param.async_cnt = 1;
++    newsock_param.cb.on_data_read = &on_data_read;
++    newsock_param.cb.on_data_sent = &on_data_sent;
++    status = pj_ssl_sock_start_accept2(listener->ssock, pool, 
+                         (pj_sockaddr_t*)listener_addr, 
+-                        pj_sockaddr_get_len((pj_sockaddr_t*)listener_addr));
++                        pj_sockaddr_get_len((pj_sockaddr_t*)listener_addr),
++                        &newsock_param);
+     if (status == PJ_SUCCESS || status == PJ_EPENDING) {
+       pj_ssl_sock_info info;
+       has_listener = PJ_TRUE;
+-- 
+cgit v0.11.2
+
diff --git a/third-party/pjproject/patches/0001-Bump-tcp-tls-and-transaction-log-levels-from-1-to-3.patch b/third-party/pjproject/patches/0001-Bump-tcp-tls-and-transaction-log-levels-from-1-to-3.patch
new file mode 100644 (file)
index 0000000..9873abf
--- /dev/null
@@ -0,0 +1,70 @@
+From a147b72df1ec150c1d733e882225db86142fb339 Mon Sep 17 00:00:00 2001
+From: George Joseph <george.joseph@fairview5.com>
+Date: Sun, 21 Feb 2016 10:01:53 -0700
+Subject: [PATCH] Bump tcp/tls and transaction log levels from 1 to 3
+
+sip_transport_tcp, sip_transport_tls and sip_transaction are printing messages
+at log level 1 or 2 for things that are transient, recoverable, possibly
+expected, or are handled with return codes. A good example of this is if we're
+trying to send an OPTIONS message to a TCP client that has disappeared.  Both
+sip_transport_tcp and sip_transaction are printing "connection refused"
+messages because the remote client isn't listening.  This is generally expected
+behavior and it should be up to the app caller to determine if an error message
+is warranted.
+---
+ pjsip/src/pjsip/sip_transaction.c   | 4 ++--
+ pjsip/src/pjsip/sip_transport_tcp.c | 2 +-
+ pjsip/src/pjsip/sip_transport_tls.c | 2 +-
+ 3 files changed, 4 insertions(+), 4 deletions(-)
+
+diff --git a/pjsip/src/pjsip/sip_transaction.c b/pjsip/src/pjsip/sip_transaction.c
+index 46bd971..1b4fdb7 100644
+--- a/pjsip/src/pjsip/sip_transaction.c
++++ b/pjsip/src/pjsip/sip_transaction.c
+@@ -1898,7 +1898,7 @@ static void send_msg_callback( pjsip_send_state *send_state,
+           err =pj_strerror((pj_status_t)-sent, errmsg, sizeof(errmsg));
+-          PJ_LOG(2,(tsx->obj_name,
++          PJ_LOG(3,(tsx->obj_name,
+                     "Failed to send %s! err=%d (%s)",
+                     pjsip_tx_data_get_info(send_state->tdata), -sent,
+                     errmsg));
+@@ -1938,7 +1938,7 @@ static void send_msg_callback( pjsip_send_state *send_state,
+           }
+       } else {
+-          PJ_PERROR(2,(tsx->obj_name, (pj_status_t)-sent,
++          PJ_PERROR(3,(tsx->obj_name, (pj_status_t)-sent,
+                        "Temporary failure in sending %s, "
+                        "will try next server",
+                        pjsip_tx_data_get_info(send_state->tdata)));
+diff --git a/pjsip/src/pjsip/sip_transport_tcp.c b/pjsip/src/pjsip/sip_transport_tcp.c
+index 222cb13..1bbb324 100644
+--- a/pjsip/src/pjsip/sip_transport_tcp.c
++++ b/pjsip/src/pjsip/sip_transport_tcp.c
+@@ -164,7 +164,7 @@ static void tcp_perror(const char *sender, const char *title,
+     pj_strerror(status, errmsg, sizeof(errmsg));
+-    PJ_LOG(1,(sender, "%s: %s [code=%d]", title, errmsg, status));
++    PJ_LOG(3,(sender, "%s: %s [code=%d]", title, errmsg, status));
+ }
+diff --git a/pjsip/src/pjsip/sip_transport_tls.c b/pjsip/src/pjsip/sip_transport_tls.c
+index 617d7f5..a83ac32 100644
+--- a/pjsip/src/pjsip/sip_transport_tls.c
++++ b/pjsip/src/pjsip/sip_transport_tls.c
+@@ -170,7 +170,7 @@ static void tls_perror(const char *sender, const char *title,
+     pj_strerror(status, errmsg, sizeof(errmsg));
+-    PJ_LOG(1,(sender, "%s: %s [code=%d]", title, errmsg, status));
++    PJ_LOG(3,(sender, "%s: %s [code=%d]", title, errmsg, status));
+ }
+-- 
+2.5.0
+
diff --git a/third-party/pjproject/patches/0001-ioqueue-Enable-epoll-in-aconfigure.ac.patch b/third-party/pjproject/patches/0001-ioqueue-Enable-epoll-in-aconfigure.ac.patch
new file mode 100644 (file)
index 0000000..36b6c65
--- /dev/null
@@ -0,0 +1,80 @@
+From b5c0bc905911f75e08987e6833075481fe16dab2 Mon Sep 17 00:00:00 2001
+From: George Joseph <george.joseph@fairview5.com>
+Date: Mon, 22 Feb 2016 13:05:59 -0700
+Subject: [PATCH] ioqueue:  Enable epoll in aconfigure.ac
+
+Although the --enable-epoll option was being accepted, the result
+was always forced to select.  This patch updates aconfigure.ac
+to properly set the value of ac_linux_poll if --enable-epoll is
+specified.
+---
+ README.txt                           |  1 +
+ aconfigure                           | 11 +++++++----
+ aconfigure.ac                        |  7 +++++--
+ pjlib/include/pj/compat/os_auto.h.in |  3 +++
+ 4 files changed, 16 insertions(+), 6 deletions(-)
+
+diff --git a/README.txt b/README.txt
+index bc45da8..48415fd 100644
+--- a/README.txt
++++ b/README.txt
+@@ -463,6 +463,7 @@ Using Default Settings
+    $ ./configure --help
+    ...
+    Optional Features:
++   --enable-epoll           Use epoll on Linux instead of select
+    --disable-floating-point   Disable floating point where possible
+    --disable-sound            Exclude sound (i.e. use null sound)
+    --disable-small-filter     Exclude small filter in resampling
+diff --git a/aconfigure.ac b/aconfigure.ac
+index 2f71abb..3e88124 100644
+--- a/aconfigure.ac
++++ b/aconfigure.ac
+@@ -410,6 +410,7 @@ dnl ######################
+ dnl # ioqueue selection
+ dnl # 
+ AC_SUBST(ac_os_objs)
++AC_SUBST(ac_linux_poll)
+ AC_MSG_CHECKING([ioqueue backend])
+ AC_ARG_ENABLE(epoll,
+             AC_HELP_STRING([--enable-epoll],
+@@ -417,10 +418,13 @@ AC_ARG_ENABLE(epoll,
+             [
+               ac_os_objs=ioqueue_epoll.o
+               AC_MSG_RESULT([/dev/epoll])
++              AC_DEFINE(PJ_HAS_LINUX_EPOLL,1)
++              ac_linux_poll=epoll
+             ],
+             [
+               ac_os_objs=ioqueue_select.o
+-              AC_MSG_RESULT([select()]) 
++              AC_MSG_RESULT([select()])
++              ac_linux_poll=select
+             ])
+ AC_SUBST(ac_shared_libraries)
+@@ -1879,7 +1883,6 @@ esac
+ AC_SUBST(target)
+-AC_SUBST(ac_linux_poll,select)
+ AC_SUBST(ac_host,unix)
+ AC_SUBST(ac_main_obj)
+ case $target in
+diff --git a/pjlib/include/pj/compat/os_auto.h.in b/pjlib/include/pj/compat/os_auto.h.in
+index 77980d3..c8e73b2 100644
+--- a/pjlib/include/pj/compat/os_auto.h.in
++++ b/pjlib/include/pj/compat/os_auto.h.in
+@@ -128,6 +128,9 @@
+  */
+ #undef PJ_SELECT_NEEDS_NFDS
++/* Was Linux epoll support enabled */
++#undef PJ_HAS_LINUX_EPOLL
++
+ /* Is errno a good way to retrieve OS errors?
+  */
+ #undef PJ_HAS_ERRNO_VAR
+-- 
+2.5.0
+
diff --git a/third-party/pjproject/patches/0001-sip_transport-Search-for-transport-even-if-listener-.patch b/third-party/pjproject/patches/0001-sip_transport-Search-for-transport-even-if-listener-.patch
new file mode 100644 (file)
index 0000000..001912c
--- /dev/null
@@ -0,0 +1,114 @@
+From 552194179eb6deae8326eb0fef446e69240ea41b Mon Sep 17 00:00:00 2001
+From: George Joseph <george.joseph@fairview5.com>
+Date: Fri, 19 Feb 2016 17:05:53 -0700
+Subject: [PATCH] sip_transport:  Search for transport even if listener was
+ specified.
+
+If a listener was specified when calling pjsip_tpmgr_acquire_transport2,
+a new transport was always created instead of using an existing one.  This
+caused several issues mostly related to the remote end not expecting a new
+connection.  I.E.  A TCP client who registered to a server is not going to
+be listening for connections coming back from the server and refuses the
+connection.
+
+Now when pjsip_tpmgr_acquire_transport2 is called with a listener, the
+registry is still searched for an existing transport and the listener
+is used as a factory only if no existing transport can be found.
+---
+ pjsip/src/pjsip/sip_transport.c | 68 ++++++++++++++++++++---------------------
+ 1 file changed, 34 insertions(+), 34 deletions(-)
+
+diff --git a/pjsip/src/pjsip/sip_transport.c b/pjsip/src/pjsip/sip_transport.c
+index 0410324..620b9c0 100644
+--- a/pjsip/src/pjsip/sip_transport.c
++++ b/pjsip/src/pjsip/sip_transport.c
+@@ -1999,29 +1999,11 @@ PJ_DEF(pj_status_t) pjsip_tpmgr_acquire_transport2(pjsip_tpmgr *mgr,
+       TRACE_((THIS_FILE, "Transport %s acquired", seltp->obj_name));
+       return PJ_SUCCESS;
+-
+-
+-    } else if (sel && sel->type == PJSIP_TPSELECTOR_LISTENER &&
+-             sel->u.listener)
+-    {
+-      /* Application has requested that a specific listener is to
+-       * be used. In this case, skip transport hash table lookup.
+-       */
+-
+-      /* Verify that the listener type matches the destination type */
+-      if (sel->u.listener->type != type) {
+-          pj_lock_release(mgr->lock);
+-          return PJSIP_ETPNOTSUITABLE;
+-      }
+-
+-      /* We'll use this listener to create transport */
+-      factory = sel->u.listener;
+-
+     } else {
+       /*
+        * This is the "normal" flow, where application doesn't specify
+-       * specific transport/listener to be used to send message to.
++       * specific transport to be used to send message to.
+        * In this case, lookup the transport from the hash table.
+        */
+       pjsip_transport_key key;
+@@ -2081,22 +2063,40 @@ PJ_DEF(pj_status_t) pjsip_tpmgr_acquire_transport2(pjsip_tpmgr *mgr,
+           return PJ_SUCCESS;
+       }
+-      /*
+-       * Transport not found!
+-       * Find factory that can create such transport.
+-       */
+-      factory = mgr->factory_list.next;
+-      while (factory != &mgr->factory_list) {
+-          if (factory->type == type)
+-              break;
+-          factory = factory->next;
+-      }
++      if (sel && sel->type == PJSIP_TPSELECTOR_LISTENER &&
++              sel->u.listener)
++              {
++              /* Application has requested that a specific listener is to
++               * be used.
++               */
++
++              /* Verify that the listener type matches the destination type */
++              if (sel->u.listener->type != type) {
++                      pj_lock_release(mgr->lock);
++                      return PJSIP_ETPNOTSUITABLE;
++              }
+-      if (factory == &mgr->factory_list) {
+-          /* No factory can create the transport! */
+-          pj_lock_release(mgr->lock);
+-          TRACE_((THIS_FILE, "No suitable factory was found either"));
+-          return PJSIP_EUNSUPTRANSPORT;
++              /* We'll use this listener to create transport */
++              factory = sel->u.listener;
++
++      } else {
++              /*
++               * Transport not found!
++               * Find factory that can create such transport.
++               */
++              factory = mgr->factory_list.next;
++              while (factory != &mgr->factory_list) {
++                      if (factory->type == type)
++                              break;
++                      factory = factory->next;
++              }
++
++              if (factory == &mgr->factory_list) {
++                      /* No factory can create the transport! */
++                      pj_lock_release(mgr->lock);
++                      TRACE_((THIS_FILE, "No suitable factory was found either"));
++                      return PJSIP_EUNSUPTRANSPORT;
++              }
+       }
+     }
+-- 
+2.5.0
+
diff --git a/third-party/pjproject/patches/config_site.h b/third-party/pjproject/patches/config_site.h
new file mode 100644 (file)
index 0000000..544c1e8
--- /dev/null
@@ -0,0 +1,34 @@
+/*
+ * Asterisk config_site.h
+ */
+
+#include <sys/select.h>
+
+#define PJ_HAS_IPV6 1
+#define NDEBUG 1
+#define PJ_MAX_HOSTNAME (256)
+#define PJSIP_MAX_URL_SIZE (512)
+#ifdef PJ_HAS_LINUX_EPOLL
+#define PJ_IOQUEUE_MAX_HANDLES (5000)
+#else
+#define PJ_IOQUEUE_MAX_HANDLES (FD_SETSIZE)
+#endif
+#define PJ_IOQUEUE_HAS_SAFE_UNREG 1
+#define PJ_IOQUEUE_MAX_EVENTS_IN_SINGLE_POLL (16)
+
+#define PJ_SCANNER_USE_BITWISE 0
+#define PJ_OS_HAS_CHECK_STACK  0
+#define PJ_LOG_MAX_LEVEL               3
+#define PJ_ENABLE_EXTRA_CHECK  0
+#define PJSIP_MAX_TSX_COUNT            ((64*1024)-1)
+#define PJSIP_MAX_DIALOG_COUNT ((64*1024)-1)
+#define PJSIP_UDP_SO_SNDBUF_SIZE       (512*1024)
+#define PJSIP_UDP_SO_RCVBUF_SIZE       (512*1024)
+#define PJ_DEBUG                       0
+#define PJSIP_SAFE_MODULE              0
+#define PJ_HAS_STRICMP_ALNUM           0
+#define PJ_HASH_USE_OWN_TOLOWER                1
+#define PJSIP_UNESCAPE_IN_PLACE                1
+
+#undef PJ_TODO
+#define PJ_TODO(x)
diff --git a/third-party/pjproject/patches/user.mak b/third-party/pjproject/patches/user.mak
new file mode 100644 (file)
index 0000000..31579d1
--- /dev/null
@@ -0,0 +1,2 @@
+
+CFLAGS += -fPIC -Wno-unused-but-set-variable -Wno-unused-variable -Wno-unused-label -Wno-unused-function -Wno-strict-aliasing
diff --git a/third-party/versions.mak b/third-party/versions.mak
new file mode 100644 (file)
index 0000000..7b8b59c
--- /dev/null
@@ -0,0 +1,2 @@
+
+PJPROJECT_VERSION = 2.4.5