Compare commits

...

No commits in common. "master" and "debian-packaging" have entirely different histories.

380 changed files with 4434 additions and 13207 deletions

29
.gitignore vendored
View File

@ -1,29 +0,0 @@
*.cache
Makefile
YateLocal*
configure
config.*
*-stamp
yatepaths.h
yateversn.h
yateiss.inc
run
yate.spec
yate
yate-config
yate-config.in
yate.pc
core*
yate.core*
*.o
*.a
*.so
*.so.*
*.yate
*.orig
*~
.*.swp
*.log
*.out
*.csv
*.tsv

View File

@ -81,10 +81,6 @@ DOCGEN := $(DOCGEN_D)
APIDOCS := apidocs
endif
GIT_TAG := $(shell LANG=C LC_MESSAGES=C git tag 2>/dev/null | tail -1)
GIT_HASH := $(shell LANG=C LC_MESSAGES=C git rev-list -n1 HEAD 2>/dev/null)
.PHONY: all everything debug ddebug xdebug ndebug
all: engine modules clients ilibs
@ -295,9 +291,9 @@ uninstall uninstall-root:
install-root uninstall-root: LDCONFIG:=ldconfig
.PHONY: snapshot tarball rpm srpm rpm-tag srpm-tag rpm-head srpm-head revision check-gittag
.PHONY: snapshot tarball rpm srpm revision
snapshot tarball: check-topdir revision clean windows apidocs
@if [ $@ = snapshot ]; then ver="`date '+GIT-%Y%m%d'`"; else ver="@PACKAGE_VERSION@-@PACKAGE_STATUS@@PACKAGE_RELEASE@"; fi ; \
@if [ $@ = snapshot ]; then ver="`date '+SVN-%Y%m%d'`"; else ver="@PACKAGE_VERSION@-@PACKAGE_STATUS@@PACKAGE_RELEASE@"; fi ; \
wd=`pwd|sed 's,^.*/,,'`; \
mkdir -p packing/tarballs; cd ..; \
echo $$wd/tar-exclude >$$wd/tar-exclude; \
@ -311,8 +307,6 @@ snapshot tarball: check-topdir revision clean windows apidocs
find $$wd -name .svn >>$$wd/tar-exclude; \
find $$wd -name CVS >>$$wd/tar-exclude; \
find $$wd -name .cvsignore >>$$wd/tar-exclude; \
find $$wd -name .gitignore >>$$wd/tar-exclude; \
find $$wd -name .git >>$$wd/tar-exclude; \
else \
echo "$$wd/packing/rpm/yate.spec" >>$$wd/tar-exclude; \
fi ; \
@ -329,47 +323,15 @@ snapshot tarball: check-topdir revision clean windows apidocs
$$wd; \
rm $$wd/tar-exclude
# rpm and sprm will check that head is at the last tag
rpm: check-gittag tarball
rpm: tarball
rpmbuild -tb $(RPMOPT) packing/tarballs/@PACKAGE_TARNAME@-@PACKAGE_VERSION@-@PACKAGE_STATUS@@PACKAGE_RELEASE@.tar.gz
srpm: check-gittag tarball
srpm: tarball
rpmbuild -ta $(RPMOPT) packing/tarballs/@PACKAGE_TARNAME@-@PACKAGE_VERSION@-@PACKAGE_STATUS@@PACKAGE_RELEASE@.tar.gz
#build rpm/srpm with tag in revision number
rpm-tag: check-gittag tarball
rpmbuild -tb --define 'revision $(GIT_TAG)git' $(RPMOPT) packing/tarballs/@PACKAGE_TARNAME@-@PACKAGE_VERSION@-@PACKAGE_STATUS@@PACKAGE_RELEASE@.tar.gz
srpm-tag: check-gittag tarball
rpmbuild -ta --define 'revision $(GIT_TAG)git' $(RPMOPT) packing/tarballs/@PACKAGE_TARNAME@-@PACKAGE_VERSION@-@PACKAGE_STATUS@@PACKAGE_RELEASE@.tar.gz
# build packages from GIT HEAD
rpm-head: tarball
rpmbuild -tb --define 'revision $(GIT_HASH)git' $(RPMOPT) packing/tarballs/@PACKAGE_TARNAME@-@PACKAGE_VERSION@-@PACKAGE_STATUS@@PACKAGE_RELEASE@.tar.gz
srpm-head: tarball
rpmbuild -ta --define 'revision $(GIT_HASH)git' $(RPMOPT) packing/tarballs/@PACKAGE_TARNAME@-@PACKAGE_VERSION@-@PACKAGE_STATUS@@PACKAGE_RELEASE@.tar.gz
check-gittag revision: check-topdir
@tag_hash=""; \
if [ "" != "$(GIT_TAG)" ]; then \
tag_hash=`LANG=C LC_MESSAGES=C git rev-list -n1 $(GIT_TAG) 2>/dev/null`; \
elif [ $@ = check-gittag ]; then \
echo "No available GIT tag"; \
exit 1; \
fi; \
if [ "x$(GIT_HASH)" != "x$$tag_hash" ]; then \
if [ $@ = check-gittag ]; then \
echo "Current commit hash $(GIT_HASH) different from expected hash for tag $(GIT_TAG) ($$tag_hash)"; \
exit 1; \
fi; \
tag=""; \
fi; \
test -z "$(GIT_TAG)" || echo "$(GIT_TAG)" > packing/revision.txt ; \
test -z "$(GIT_HASH)" || echo "$(GIT_HASH)" > packing/git_commit.txt
revision: check-topdir
@-rev=`LANG=C LC_MESSAGES=C svn info 2>/dev/null | sed -n 's,^Last Changed Rev: *,,p'`; \
test -z "$$rev" || echo "$$rev" > packing/revision.txt
%.o: @srcdir@/%.cpp $(MKDEPS) @srcdir@/yatengine.h
$(COMPILE) -c $<

11
clients/.gitignore vendored
View File

@ -1,11 +0,0 @@
Makefile
YateLocal*
.xvpics
core*
yate-*
*.o
*.a
*.so
*.orig
*~
.*.swp

View File

@ -5,7 +5,7 @@
* A Qt-4 based universal telephony client
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -1,9 +0,0 @@
Makefile
YateLocal.mak
core*
*.moc
*.o
*.a
*.orig
*~
.*.swp

View File

@ -5,7 +5,7 @@
* A Qt-4 based universal telephony client
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -5,7 +5,7 @@
* A Qt-4 based universal telephony client
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

8
conf.d/.gitignore vendored
View File

@ -1,8 +0,0 @@
*.bind
Makefile
YateLocal.mak
core*
*.conf
*.orig
*~
.*.swp

View File

@ -39,13 +39,6 @@
; Default true
; sips: Boolean. Use SIPS URI for register/contact. Transport defaults to TLS if enabled
;
; For TCP SIP HEP3 capturing, setup the following parameters:
; capture_filter: Boolean, default false. Enable it if you want HEP3 capture of packets
; capture_agent: String, mandatory if capture_filter is set to true. Name of capture
; capture_server: String, mandatory if capture_filter is set to true. Name of HEP3 server where to send packets
; capture_compress: Boolean, default false. Set to true to compress captured packets
; If not set, capture settings will default to SIP global capture settings.
;
; NOTE: Default port is 5060 for udp/tcp and 5061 for tls
;
; Jabber:

View File

@ -1,52 +0,0 @@
; each section starting with 'server' configures a connection
; to a HEP3 server
; The string after 'server' is the server name
[server hep_server]
; enable: boolean: True to enable this connection. False to disable it
; This setting is applicable on reload.
;enable=yes
; auth_key: string: Authentication key string. If not set, it will look at
; value of auth_key_hex.
; This setting is applicable on reload.
;auth_key=
; auth_key_hex: Hexified string: Authentication key in hexadecimal octet string.
; If auth_key is not set and neither is this, authentication key will not be set
; in HEP3 packets.
; This setting is applicable on reload.
;auth_key_hex=
; capture_id: unsigned 4 byte integer: HEP3 Capture agent ID for this connection
; This setting is applicable on reload.
;capture_id=0
; compress: boolean: Compress HEP3 packet payload
; This setting can be overridden by entities that request a HEP3 capture
; for its own instance.
;compress=false
; socket_type: keyword (udp, tcp). Type of socket to create for communication
; with this server.
; Not applicable on reload.
;socket_type=udp
; remote_host: destination IPv4 address, mandatory to set. IPv4 address of the
; server where to send HEP3 packets
; Not applicable on reload.
;remote_host=
; remote_port: destination port, mandatory to set. Port where to send HEP3 packets
; Not applicable on reload.
;remote_port=
; local_host: local IPv4 address, mandatory to set. IPv4 address to use for
; sending HEP3 packets
; Not applicable on reload.
;local_host=
; remote_port: source port, mandatory to set. Port to use for sending HEP3 packets
; Not applicable on reload.
;local_port=

View File

@ -74,46 +74,3 @@ eliza=eliza.js
; These scripts are loaded only after the engine and modules have initialized, immediately
; after the dispatching of the "engine.start" message.
; The names must be unique and different from any in the [scripts] section.
[handlers]
; Install singleton message handlers
; These handlers are running using a separate context for each handled message
;
; Description:
; name=filename,callback,priority,trackname,parameters_prefix,filter,context,script_name
;
; Parameters (optional, unless otherwise specified):
; name: Required. Name of the message to handle
; Names starting with 'handlerparam:' are ignored
; filename: Required. Script to load
; callback: Required. Callback function. Function is required to be present in script code
; priority: Handler priority. Default: 100
; trackname: Track name to be put in handled message 'handlers' parameter
; parameters_prefix: Prefix for handler parameters specified in separate section parameters
; filter: Message handler filter.
; Format: filter_param=filter_value. Ignored if 'filter_param' is empty.
; filter_value starting with '^' char is handled as regular expression
; context: String to be passed to callback function
; script_name: Name of the script. Used internally for debug purposes. Use 'script_file_name' if empty
;
; Notes:
; - The following parameters are used to identify a handler:
; name,filename,callback,priority,trackname,filter,context,script_name
; An existing handler whose identity changed (not found in config) is removed at reload
; - Multiple handlers for the same message may be installed
; handlerparam:<parameters_prefix>:<param_name>: string: Configure a parameters for a handler
; Some of these parameters may be set in message handler description also (ignored here if so)
; They may be configured here since they may contain ',' in their contents
; Parameters:
; debug: string: Script debug (e.g. 'level 10'). This parameter is applied on reload
; context: string: Context to be passed to callback function
; filter: string: Message handler filter. See handler description for format
; track_priority: boolean: Add priority to tracked name. Default: true
; load_extensions: boolean: Load extension in script context when a message is handled
; This parameter is applied on reload
; Default: [general] 'auto_extensions'
; keep_old_on_fail: boolean: Keep old code if failed to parse the new one
; This parameter is used when handler is re-loaded and script changed
; Default: [general] 'keep_old_on_fail'

View File

@ -53,9 +53,3 @@
; poolsize: int: Number of connections to establish for this account
; Minimum number of connections is 1
;poolsize=1
; warn_query_duration: integer: Warn if query duration (database query and result fetch)
; exceeds this value (in milliseconds)
; This parameter is applied on reload and can be overridden in query database message
; Minium allowed interval is 50
;warn_query_duration=0

View File

@ -148,14 +148,10 @@
[extra]
; This section allows installing handlers for any message name.
; Each line must be of the form:
; message.name=priority[,[paramname][,context][,filter_param][,filter_match]]]
; message.name=priority[,[paramname][,context]]
; For each handler create a corresponding [context] or [message.name] section
; in which implement handling for that specific message. If paramname is not
; set you will need to match parameters explicitely or set a new match string.
; For filters, filter_param is the name of the parameter you want to match.
; filter_match is the value that filter_param parameter has to match. It can be
; an exact value to match or a regular expression. For regular expressions,
; filter_match must start with the character '^'.
; Examples:
; engine.command=90
; call.execute=120,callto

View File

@ -21,13 +21,9 @@
; If empty it will match all messages
; Example for a filter matching all chan.Anything messages and engine.halt:
; filter=^\(chan\.\|engine\.halt$\)
;filter=
;filter
; timer: boolean: True to sniff engine.timer messages, false otherwise
;timer=false
; max_buf_size: integer: Maximum admitted length of an encoded message.
; If encoded message length exceeds this length, message will not be sniffed
; Acceptable range is 2048 .. 65507
;max_buf_size=2048

View File

@ -110,18 +110,16 @@
; filtersniff: regexp: Default filter to apply to message sniffer at initialization
; If empty it will match all messages except engine.timer which is never displayed
; Example for a filter matching all chan.Anything messages and engine.halt:
; filtersniff=^\(chan\.\|engine\.halt\)$
; filtersniff=^\(chan\.\|engine\.halt$\)
;filtersniff=
; agesniff: float: Display only messages whose age or delay is higher than this value
; This is a floating point number in seconds (1.5 means 1500msec)
;agesniff=0
; filtersniffparams: string: Default parameter(s) filter to apply to message sniffer at initialization
; If empty it will not attempt to match message parameters
; Format: [any] [negated] param1=value1 [param2=value2 ...]
; any: message matches if at least one configured parameter matches
; negated: message matches if list does not match
; Format: [any] param1=value1 [param2=value2 ...]
; 'any' indicates that message matches if at least one configured parameter matches
; Value to match is handled as regexp. It may end with '^' to revert match (i.e. matches if regexp don't match)
; Value may be empty. In this case the parameter matches if missing in message or present with empty value
; Example for a filter matching messages with empty route_type or route_type=call
@ -130,16 +128,6 @@
; filtersniffparams=any caller=^123$ called=^123$
;filtersniffparams=
; msgsniff:<NAME>: string: Add a message sniffer rule
; <NAME> is optional. If missing the rule is handled as the one set using filtersniff/agesniff/filtersniffparams
; This parameter may be repeated with different <NAME> value to add multiple rules
; A rule will replace a previously defined rule with the same name
; Format: [filter=[value]] [age=[value]] [params [any negated] [name=value]]
; Examples:
; msgsniff:=filter=^\(chan\.\) age=0.5 params id=^sip/
; msgsniff:extra=filter=^\(call\.cdr\)$ params any caller=123 called=^2
;msgsniff:<NAME>=
; trace_msg_time: boolean: Instruct message dispatcher to set message event(s) time (enqueue / dispatch)
;trace_msg_time=no
@ -241,19 +229,3 @@ h323chan.yate=yes
; dtmfdups: bool: Allow duplicate DTMFs (detected with different methods)
;dtmfdups=disable
[configuration]
; Options for Configuration files
; These parameters are handled on first load only (repeated parameters are ignored)
; This section should be the first handled section if you need to apply parameters on this file also
; max_depth: integer: Maximum file include depth
; Allowed interval: 3..10
;max_depth=3
; disable_include_silent: boolean: Disable silent include in Configuration files
; The '$includesilent' directives of configuration file will be handled as '$include' if this
; parameter is set to boolean true
; Same applies for '$includesectionsilent': handled as '$includesection'
;disable_include_silent=no

View File

@ -155,9 +155,6 @@
; OBSOLETE - please use "enable" in section [options]
;options=enable
; update: bool: Enable receiving UPDATE transactions (RFC 3311)
;update=disable
; prack: bool: Enable acknowledging provisional 1xx answers (RFC 3262)
;prack=disable
@ -250,15 +247,10 @@
; Defaults to enable
;honor_dtmf_detect=enable
; rfc2833: bool: Offer RFC2833 telephone-event 8KHz by default
; rfc2833: bool: Offer RFC2833 telephone-event by default
; A numeric payload >= 96 can be provided
;rfc2833=yes
; rfc2833_RATE: bool: Offer RFC2833 telephone-event for specific rate (non 8KHz) by default
; A numeric payload >= 96 can be provided
; Supported rates (parameters): rfc2833_16000, rfc2833_32000
;rfc2833_RATE=yes
; privacy: bool: Process and generate privacy related SIP headers
;privacy=disable
@ -268,9 +260,6 @@
; forward_sdp: bool: Include the raw SDP body to be used as-is for forwarding RTP
;forward_sdp=disable
; forward_gpmd: bool: Propagate GPMD even when not forwarding RTP
;forward_gpmd=disable
; rtp_start: bool: Start RTP when sending 200 on incoming instead of receiving ACK
;rtp_start=disable
@ -381,73 +370,12 @@
; If set this parameter must be less than 'tcp_keepalive'
;tcp_keepalive_first=0
; ssdp_prefix: string: Prefix to use when handling SDP session level parameters
; This parameter is used when setting them in yate messages or handling them from there
; This parameter is applied on reload
; Prefix used to set parsed SDP: <ssdp_prefix>_ (default: ssdp_)
; Prefix used to update from yate messages: o<ssdp_prefix>_ (default: ossdp_)
; When updated from yate messages the prefix must be set in 'ossdp-prefix' message parameter
;ssdp_prefix=ssdp
; initial_headers: boolean: Put all headers from initial requests in yate message
; Handled for incoming channel preroute, user (un)register and messages sent on SIP
; requests received outside a dialog
; This parameter is applied on reload
;initial_headers=no
; reinvite_wait_initial: boolean: Wait for answered initial transaction termination when need to send
; a re-INVITE and initial transaction was not terminated
; Applicable for the inbound call leg
; This parameter is handled when answer (200 OK) was sent to initial transaction
; If enabled the module will not send an UPDATE even if supported by remote
; This parameter can be overridden from routing
; This parameter is applied on reload
;reinvite_wait_initial=no
; mixed_provisional: boolean: Accept mixed (non)reliable provisional responses to initial transaction
; When enabled (default) the dialog will accept non reliable provisional messages
; after receiving a reliable one
; This parameter can be overridden from routing
; This parameter is applied on reload
;mixed_provisional=yes
; warn_bind_fail_delay: integer/string: Delay failed to bind debug message
; This parameter may be used when listener is going to bind on an IP which may become
; available later
; Values:
; integer: Delay in milliseconds. Interval: 500..60000
; 'start': Delay until engine starts (engine.start message is handled by module)
;warn_bind_fail_delay=0
; warn_no_default_udp_transport: boolean: Warn if there is not default UDP transport
; This parameter is applied on reload
;warn_no_default_udp_transport=yes
; capture_filter: boolean. Enable global HEP3 capture of SIP packets
; NOTE: This setting can be overridden by listener settings or by account settings
; in case of outgoing TCP connections.
; This setting applies on reload.
;capture_filter=false
; capture_agent: string, mandatory if capture_filter is set to true. Name of capture agent.
; NOTE: This setting can be overridden by listener settings or by account settings
; in case of outgoing TCP connections.
; This is for internal tracking.
;capture_agent=
; capture_server: string, mandatory if capture_filter is set to true.
; Name of HEP3 server where to send packets. The server with this name must be configured
; in HEP3 module configuration.
; NOTE: This setting can be overridden by listener settings or by account settings
; in case of outgoing TCP connections.
;capture_server=
; capture_compress: boolean. Set to true to compress captured packets.
; If not set, it will use the HEP server configuration 'compress' configured value.
; NOTE: This setting can be overridden by listener settings or by account settings
; in case of outgoing TCP connections.
;capture_compress=false
[options]
; Controls the behaviour for SIP options retrieval
@ -521,9 +449,6 @@
; alaw: bool: Companded-only G711 a-law (PCMU/8000)
;alaw=default
; clearmode: bool: Transparent 64kbit/s B channel (RFC4040)
;clearmode=default
; gsm: bool: European GSM 06.10 (GSM/8000)
;gsm=default
@ -623,7 +548,6 @@
; The following parameters can be overridden from 'general' section:
; UDP: maxpkt, buffer
; TCP/TLS: tcp_maxpkt
; All: warn_bind_fail_delay
; type: keyword: Listener type
; Allowed values:
@ -688,21 +612,3 @@
; role: string: Role to be set in messages sent by connections using this listener
; This parameter is applied on reload
;role=
; capture_filter: boolean. Enable HEP3 capture of packets on this listener.
; NOTE: for outgoing TCP connections, these settings must be made in accfile.conf.
; This setting applies on reload.
;capture_filter=false
; capture_agent: string, mandatory if capture_filter is set to true. Name of capture agent
; This is for internal tracking.
;capture_agent=
; capture_server: string, mandatory if capture_filter is set to true.
; Name of HEP3 server where to send packets. The server with this name must be configured
; in HEP3 module configuration
;capture_server=
; capture_compress: boolean. Set to true to compress captured packets.
; If not set, it will use the HEP server configuration 'compress' configured value
;capture_compress=false

View File

@ -9,11 +9,8 @@ fi
PACKAGE_RELEASE="1"
PACKAGE_STATUS="devel"
PACKAGE_REVISION=`cd "$srcdir"; LANG=C LC_MESSAGES=C git rev-list -n 1 HEAD 2>/dev/null`
PACKAGE_REVISION=`cd "$srcdir"; LANG=C LC_MESSAGES=C svn info 2>/dev/null | sed -n 's,^Last Changed Rev: *,,p'`
test -z "$PACKAGE_REVISION" && PACKAGE_REVISION=`cat "$srcdir/packing/revision.txt" 2>/dev/null`
test -z "$PACKAGE_REVISION" && PACKAGE_REVISION=`cat "$srcdir/packing/git_commit.txt" 2>/dev/null`
PACKAGE_GIT_HASH=`cd "$srcdir"; LANG=C LC_MESSAGES=C git rev-list -n 1 HEAD 2>/dev/null`
test -z "$PACKAGE_REVISION" && PACKAGE_REVISION=`cat "$srcdir/packing/git_commit.txt" 2>/dev/null`
AC_ARG_WITH(status,AC_HELP_STRING([--with-status=NAME],[use NAME as package status]),[PACKAGE_STATUS=$withval])
PACKAGE_VERSION_MAJOR="${PACKAGE_VERSION%%.*}"
@ -28,7 +25,6 @@ AC_SUBST(PACKAGE_VERSION_RELEASE)
AC_SUBST(PACKAGE_RELEASE)
AC_SUBST(PACKAGE_STATUS)
AC_SUBST(PACKAGE_REVISION)
AC_SUBST(PACKAGE_GIT_HASH)
# We may need the host OS type but avoid the overhead of AC_CANONICAL_SYSTEM
AC_MSG_CHECKING([for local operating system type])
@ -313,25 +309,6 @@ MUTEX_HACK="$MUTEX_HACK -DHAVE_TIMEDWAIT"
fi
AC_MSG_RESULT([$have_sem_timedwait])
have_rd_timedlock=""
AC_CHECK_LIB([pthread], [pthread_rwlock_timedrdlock], [have_rd_timedlock="yes"])
if [[ "x$have_rd_timedlock" = "x" ]]; then
AC_CHECK_LIB([c], [pthread_rwlock_timedrdlock],[have_rd_timedlock="yes"])
fi
if [[ "x$have_rd_timedlock" = "xyes" ]]; then
MUTEX_HACK="$MUTEX_HACK -DHAVE_TIMEDRDLOCK"
fi
have_wr_timedlock=""
AC_CHECK_LIB([pthread], [pthread_rwlock_timedwrlock], [have_wr_timedlock="yes"])
if [[ "x$have_wr_timedlock" = "x" ]]; then
AC_CHECK_LIB([c], [pthread_rwlock_timedwrlock], [have_wr_timedlock="yes"])
fi
if [[ "x$have_rd_timedlock" = "xyes" ]]; then
MUTEX_HACK="$MUTEX_HACK -DHAVE_TIMEDWRLOCK"
fi
CFLAGS="$SAVE_CFLAGS"
LIBS="$SAVE_LIBS"
AC_LANG_RESTORE
@ -1204,7 +1181,7 @@ AC_SUBST(SPEEX_LIB)
HAVE_AMRNB=no
AMRNB_INC=""
AMRNB_LIB="-lopencore-amrnb"
AMRNB_LIB="-lamrnb"
AC_ARG_WITH(amrnb,AC_HELP_STRING([--with-amrnb=DIR],[use AMR-NB if available (default)]),[ac_cv_use_amrnb=$withval],[ac_cv_use_amrnb=/usr])
if [[ "x$ac_cv_use_amrnb" = "xstatic" ]]; then
ac_cv_use_amrnb=/usr
@ -1213,9 +1190,9 @@ fi
if [[ "x$ac_cv_use_amrnb" != "xno" ]]; then
AC_MSG_CHECKING([for AMR-NB in $ac_cv_use_amrnb])
local_lib="$ARCHLIB"
amrinc="$ac_cv_use_amrnb/include/opencore-amrnb"
test -f "$ac_cv_use_amrnb/$local_lib/libopencore-amrnb.so" || local_lib="lib"
if [[ -f "$ac_cv_use_amrnb/$local_lib/libopencore-amrnb.so" -a -f "$amrinc/interf_dec.h" ]]; then
amrinc="$ac_cv_use_amrnb/include/amrnb"
test -f "$ac_cv_use_amrnb/$local_lib/libamrnb.so" || local_lib="lib"
if [[ -f "$ac_cv_use_amrnb/$local_lib/libamrnb.so" -a -f "$amrinc/interf_rom.h" ]]; then
HAVE_AMRNB=yes
AMRNB_LIB="-L$ac_cv_use_amrnb/$local_lib $AMRNB_LIB"
AMRNB_INC="-I$amrinc"
@ -1824,7 +1801,7 @@ AC_SUBST(INSTALL_L)
INSTALL_D="install -D"
CFLAGS=`echo "$CFLAGS" | sed 's/\(^\| \+\)-g[[0-9]]*//' | sed 's/[[[:space:]]]\{2,\}/ /g'`
MODULE_CFLAGS="-fno-exceptions -fPIC $HAVE_GCC_FORMAT_CHECK $HAVE_BLOCK_RETURN $ATOMIC_OPS"
MODULE_CFLAGS="-fno-exceptions -fPIC $HAVE_GCC_FORMAT_CHECK $HAVE_BLOCK_RETURN"
MODULE_CPPFLAGS="$HAVE_NO_OVERLOAD_VIRT_WARN $RTTI_OPT $MODULE_CFLAGS"
MODULE_LDRELAX="-rdynamic -shared"
MODULE_SYMBOLS="-Wl,--retain-symbols-file,/dev/null"

10
debian/.gitignore vendored Normal file
View File

@ -0,0 +1,10 @@
*.log
*.debhelper
*.substvars
NOT-INSTALLED-LIST
yate-*/
libyate/
libyate-dbg/
files

793
debian/changelog vendored Normal file
View File

@ -0,0 +1,793 @@
yate (5.5.1~vir2016070901) UNRELEASED; urgency=medium
* Merged upstream fixes (SVN r6126)
* Yate.pm version 0.27: response_handler parameter support in message()
* Fixed unescaping of handler filter parameters
* Fixed invalid Suggests line in debian control file
-- Vasily i. Redkin <vir@ctm.ru> Sat, 09 Jul 2016 08:43:57 +0300
yate (5.5.1~vir2016070301) UNRELEASED; urgency=medium
* "status moh list" console command added
-- Vasily i. Redkin <vir@ctm.ru> Sun, 03 Jul 2016 01:02:12 +0300
yate (5.5.1~vir2016070101) UNRELEASED; urgency=medium
* Merged upstream updates (SVN r6124)
* Fixed queue_out.php
-- Vasily i. Redkin <vir@ctm.ru> Fri, 01 Jul 2016 22:50:38 +0300
yate (5.5.1~vir2016053101) UNRELEASED; urgency=medium
* Merged upstream updates (SVN r6121)
-- Vasily i. Redkin <vir@ctm.ru> Tue, 31 May 2016 17:44:56 +0300
yate (5.5.1~vir2016031502) UNRELEASED; urgency=medium
* Fix build
-- Vasily i. Redkin <vir@ctm.ru> Tue, 15 Mar 2016 14:41:09 +0300
yate (5.5.1~vir2016031501) UNRELEASED; urgency=medium
* Fix build.
* Fix yate qt client icons.
-- Vasily i. Redkin <vir@ctm.ru> Tue, 15 Mar 2016 06:26:48 +0300
yate (5.5.1~vir2016031101) UNRELEASED; urgency=medium
* Merged upstream updates (SVN r6103)
-- Vasily i. Redkin <vir@ctm.ru> Fri, 11 Mar 2016 22:38:18 +0300
yate (5.5.1~vir2016021001) UNRELEASED; urgency=medium
* Sangoma hardware support enabled (requires Wanpipe)
-- Vasily i. Redkin <vir@ctm.ru> Wed, 10 Feb 2016 18:00:35 +0300
yate (5.5.1~vir2016020501) UNRELEASED; urgency=medium
* Yate.pm: Autoflush fixed. Fixed retval corruption if message was not handled.
* Use 'copyparams' to populate dumb channel's chan.startup (see Yate issue
* Merged upstream updates (SVN r6087)
-- Vasily i. Redkin <vir@ctm.ru> Fri, 05 Feb 2016 00:10:28 +0300
yate (5.5.1~vir2016011302) UNRELEASED; urgency=medium
* Fixed faxhan module packaging
-- Vasily i. Redkin <vir@ctm.ru> Wed, 13 Jan 2016 23:28:05 +0300
yate (5.5.1~vir2016011301) UNRELEASED; urgency=medium
* Fixed spandsp include file location on debian
-- Vasily i. Redkin <vir@ctm.ru> Wed, 13 Jan 2016 06:46:46 +0300
yate (5.5.1~vir2015112701) UNRELEASED; urgency=medium
* Merged upstream updates (SVN r6073)
-- Vasily i. Redkin <vir@ctm.ru> Fri, 27 Nov 2015 17:45:07 +0300
yate (5.5.1~vir2015080501) UNRELEASED; urgency=medium
* Merged upstream updates (SVN r6015)
-- Vasily i. Redkin <vir@ctm.ru> Wed, 05 Aug 2015 14:14:10 +0300
yate (5.5.1~vir2015070801) UNRELEASED; urgency=medium
* Fixed Yate.pm
-- Vasily i. Redkin <vir@ctm.ru> Wed, 08 Jul 2015 17:18:30 +0300
yate (5.5.1~vir2015061301) UNRELEASED; urgency=medium
* Fixed init script (jessie support)
-- Vasily i. Redkin <vir@ctm.ru> Sat, 13 Jun 2015 06:34:51 +0300
yate (5.5.1~vir2015061001) UNRELEASED; urgency=medium
* Added /etc/defaults/yate file
* Appended ".log" to log file name
-- Vasily i. Redkin <vir@ctm.ru> Wed, 10 Jun 2015 16:39:54 +0300
yate (5.5.1~vir2015060801) UNRELEASED; urgency=medium
* Fix build
-- Vasily i. Redkin <vir@ctm.ru> Mon, 08 Jun 2015 09:43:53 +0300
yate (5.5.1~vir2015060701) UNRELEASED; urgency=medium
* Merged upstream updates (SVN r5977)
-- Vasily i. Redkin <vir@ctm.ru> Sun, 07 Jun 2015 08:00:29 +0300
yate (5.4.1~vir2015020901) UNRELEASED; urgency=medium
* Merged upstream updates (SVN r5936)
* Fixed libyatescript.so symlink in yate-dev package
-- Vasily i. Redkin <vir@ctm.ru> Mon, 09 Feb 2015 23:29:50 +0300
yate (5.4.1~vir2014121401) UNRELEASED; urgency=low
* Added non-blocking mode for external scripts
-- Vasily i. Redkin <vir@ctm.ru> Sun, 14 Dec 2014 00:05:58 +0300
yate (5.4.1~vir2014121201) UNRELEASED; urgency=low
* Upstream fixes, crypto-related improvements.
* Multiple params setting for queued calls.
-- Vasily i. Redkin <vir@ctm.ru> Fri, 12 Dec 2014 10:06:50 +0300
yate (5.4.1~vir2014111601) UNRELEASED; urgency=low
* Fix for defer_incoming option :)
-- Vasily i. Redkin <vir@ctm.ru> Sun, 16 Nov 2014 17:18:32 +0300
yate (5.4.1~vir2014111102) UNRELEASED; urgency=low
* Added 'defer_incoming' to cdrbuild.conf
-- Vasily i. Redkin <vir@ctm.ru> Tue, 11 Nov 2014 18:03:37 +0300
yate (5.4.1~vir2014111101) UNRELEASED; urgency=low
* Merged upstream updates (SVN r5923):
* Better javascript
* SQLite database support
* iSAC codec fix
-- Vasily i. Redkin <vir@ctm.ru> Tue, 11 Nov 2014 13:45:09 +0300
yate (5.4.1~vir2014082101) UNRELEASED; urgency=low
* More video codecs support (VP8, VP9)
-- Vasily i. Redkin <vir@ctm.ru> Thu, 21 Aug 2014 12:08:42 +0400
yate (5.4.1~vir2014082001) UNRELEASED; urgency=low
* Deps fixed
-- Vasily i. Redkin <vir@ctm.ru> Wed, 20 Aug 2014 13:04:40 +0400
yate (5.4.1~vir2014081801) UNRELEASED; urgency=low
* Fixed new files packaging (most notably, javascripts
and faxchan module).
-- Vasily i. Redkin <vir@ctm.ru> Mon, 18 Aug 2014 17:16:30 +0400
yate (5.4.1~vir2014081201) UNRELEASED; urgency=low
* Merged upstream updates (SVN r5904)
-- Vasily i. Redkin <vir@ctm.ru> Tue, 12 Aug 2014 09:00:43 +0400
yate (5.3.1~vir2014071801) UNRELEASED; urgency=low
* Merged upstream updates (SVN r5869), most notably it is
JSON javascript object, SDP version number calculation fixes,
CSEq numbers generation fix, several other fixes.
-- Vasily i. Redkin <vir@ctm.ru> Fri, 18 Jul 2014 13:22:32 +0400
yate (5.3.1~vir2014061601) UNRELEASED; urgency=low
* Merged upstream updates (svn r5844)
-- Vasily i. Redkin <vir@ctm.ru> Mon, 16 Jun 2014 09:48:46 +0400
yate (5.3.1~vir2014052001) UNRELEASED; urgency=low
* Merged upstream updates and fixes (SVN r5835)
* Applied fix for bug 0000367 (crypto tag)
* Applied SDP attributes separation patch
-- Vasily i. Redkin <vir@ctm.ru> Tue, 20 May 2014 12:05:02 +0400
yate (5.2.1~vir2014041801) UNRELEASED; urgency=low
* Merged upsetream updates and fixes
-- Vasily i. Redkin <vir@ctm.ru> Fri, 18 Apr 2014 14:11:15 +0400
yate (5.1.1~vir2014030101) UNRELEASED; urgency=low
* Merged upsetream updates and fixes (like eliza chat bot)
-- Vasily i. Redkin <vir@ctm.ru> Sat, 01 Mar 2014 22:56:37 +0400
yate (5.0.1~vir2014021001) UNRELEASED; urgency=low
* Merged upsetream updates (gsm library and fixes)
* Fixed PATH in init script
-- Vasily i. Redkin <vir@ctm.ru> Mon, 10 Feb 2014 13:31:01 +0400
yate (5.0.1~vir2013121601) UNRELEASED; urgency=low
* Yate.pm: full control over message's reponses
-- Vasily i. Redkin <vir@ctm.ru> Mon, 16 Dec 2013 12:05:26 +0400
yate (5.0.1~vir2013121002) UNRELEASED; urgency=low
* external module: allow setting "scriptname" of global script
from '%%>connect' line (using optional "id" parameter).
-- Vasily i. Redkin <vir@ctm.ru> Tue, 10 Dec 2013 00:52:35 +0400
yate (5.0.1~vir2013121001) UNRELEASED; urgency=low
* external module: "scriptname" local variable added
to allow tcp-connected global script to set it's name
* enabled coredumps
* debug timestamps now will be in local timezone
-- Vasily i. Redkin <vir@ctm.ru> Tue, 10 Dec 2013 00:31:09 +0400
yate (5.0.1~vir2013120801) UNRELEASED; urgency=low
* Fixed pidfile creation after reboot.
* Merged upstream fixes.
-- Vasily i. Redkin <vir@ctm.ru> Sun, 08 Dec 2013 01:42:07 +0400
yate (5.0.1~vir2013110501) UNRELEASED; urgency=low
* Merged upstream changes: IPv6 and bugfixes.
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 05 Nov 2013 16:18:20 +0400
yate (4.3.1~vir2013102201) UNRELEASED; urgency=low
* Fix Yate.pm bug (inproper handling of "0" values)
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 22 Oct 2013 23:33:33 +0400
yate (4.3.1~vir2013100902) UNRELEASED; urgency=low
* Fix event subscription
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 09 Oct 2013 23:19:11 +0400
yate (4.3.1~vir2013100901) UNRELEASED; urgency=low
* ysnmpdata moved into /var/cache/yate and symlinked into /etc/yate
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 09 Oct 2013 09:37:43 +0400
yate (4.3.1~vir2013100801) UNRELEASED; urgency=low
* Fixed H264 codec support :)
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 08 Oct 2013 13:36:11 +0400
yate (4.3.1~vir2013093001) UNRELEASED; urgency=low
* New setting in register.conf: unregister_expired.
-- Vasily i. Redkin <vir@vir.otvt.ru> Mon, 30 Sep 2013 15:20:42 +0400
yate (4.3.1~vir2013092601) UNRELEASED; urgency=low
* Added H264 codec support
-- Vasily i. Redkin <vir@vir.otvt.ru> Thu, 26 Sep 2013 10:06:37 +0400
yate (4.3.1~vir2013092003) UNRELEASED; urgency=low
* one more inband dtmf fix
-- Vasily i. Redkin <vir@vir.otvt.ru> Fri, 20 Sep 2013 17:42:56 +0400
yate (4.3.1~vir2013092002) UNRELEASED; urgency=low
* dtmfinband=force support for buggy E1 cards
-- Vasily i. Redkin <vir@vir.otvt.ru> Fri, 20 Sep 2013 16:21:08 +0400
yate (4.3.1~vir2013092001) UNRELEASED; urgency=low
* Merged upstream fixes.
-- Vasily i. Redkin <vir@vir.otvt.ru> Fri, 20 Sep 2013 09:20:18 +0400
yate (4.3.1~vir2013080901) UNRELEASED; urgency=low
* Merged upstream fixes.
-- Vasily i. Redkin <vir@vir.otvt.ru> Fri, 09 Aug 2013 14:50:24 +0400
yate (4.3.1~vir2013080701) UNRELEASED; urgency=low
* new package "libyate-perl"
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 07 Aug 2013 06:20:35 +0400
yate (4.3.1~vir2013073001) UNRELEASED; urgency=low
* Added "negative" mode for message sniffer filter
* Merged upstream SIP NAT and MIB fixes.
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 30 Jul 2013 09:30:19 +0400
yate (4.3.1~vir2013072201) UNRELEASED; urgency=low
* Merged upstream changes, most notably SNMP traps-related.
* Added lazyrec.yate module for those who want to give it a try.
-- Vasily i. Redkin <vir@vir.otvt.ru> Mon, 22 Jul 2013 18:13:09 +0400
yate (4.3.1~vir2013062702) UNRELEASED; urgency=low
* Fix build (again)
-- Vasily i. Redkin <vir@vir.otvt.ru> Thu, 27 Jun 2013 16:27:01 +0400
yate (4.3.1~vir2013062701) UNRELEASED; urgency=low
* Fix build
-- Vasily i. Redkin <vir@vir.otvt.ru> Thu, 27 Jun 2013 10:44:30 +0400
yate (4.3.1~vir2013062601) UNRELEASED; urgency=low
* Merged upstream changes
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 26 Jun 2013 16:34:03 +0400
yate (4.3.1~vir2013051401) UNRELEASED; urgency=low
* Merged upstream changes
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 14 May 2013 15:47:23 +0400
yate (4.3.1~vir2013041701) UNRELEASED; urgency=low
* Added postgres async notifications support
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 17 Apr 2013 09:26:09 +0400
yate (4.3.1~vir2013041501) UNRELEASED; urgency=low
* Merged my 'hstore' branch - postgres 'hstore' type support.
* Merged my 'tranposedb' branch - support for multile 'field', 'value'
records returned by routing query.
-- Vasily i. Redkin <vir@vir.otvt.ru> Mon, 15 Apr 2013 14:22:13 +0400
yate (4.3.1~vir2013040202) UNRELEASED; urgency=low
* Fixed debug symbols package creation.
* Removed libyate-dbg and yate-telhw-dbg packages.
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 02 Apr 2013 16:14:09 +0400
yate (4.3.1~vir2013040201) UNRELEASED; urgency=low
* Merged upstream changes
* Added missing script 'banbrutes.php' packaging
* Added module 'lksctp' building and packaging
* Added new module 'cdrcombine' packageing
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 02 Apr 2013 15:11:15 +0400
yate (4.3.1~vir2013011501) UNRELEASED; urgency=low
* Merged upstream changes (version 4.3.1)
4.3 brings many minor features, improvements and problem fixes.
* ISDN+SS7 - fixes in subcomponent configuration handling
* SIGTRAN - better SCTP error condition handling, added heartbeat support
* ISUP - fixed handling of several circuit blocking scenarios, added charging
message handling
* SCCP - support for GTT routing between different networks
* CAMEL+MAP - support for operations having different structure per version
* Javascript - added XML support, fixed some parsing errors and error reporting
* SIP - improved DTMF configuration and negotiation, fixed REGISTER interval
handling and keepalives
* RTP - fixed a memory leak, fixed timestamps when data is repacked
* IAX - fixes in handling logic for various frame types and audio timestamps
* Jingle - added support for more minor protocol variations
* H.323 - support for setting some protocol timeouts
* RADIUS - support for interim updates and Quintum attributes
* Unspecific - fixed a number of infrequent crashes, deadlocks and performance
issues
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 15 Jan 2013 10:23:51 +0400
yate (4.2.1~vir2012110201) UNRELEASED; urgency=low
* Merged upstream fixes and improvements, including
* Recording both channels into single file.
* General sip listener configuration change.
* H323 and Javascript fixes.
-- Vasily i. Redkin <vir@vir.otvt.ru> Fri, 02 Nov 2012 13:29:46 +0400
yate (4.2.1~vir2012102303) UNRELEASED; urgency=low
* Undone last change - it was never needed.
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 23 Oct 2012 13:26:02 +0400
yate (4.2.1~vir2012102302) UNRELEASED; urgency=low
* Special handling for sipdroid's sdp added
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 23 Oct 2012 13:15:04 +0400
yate (4.2.1~vir2012102301) UNRELEASED; urgency=low
* Added H263-1998 payload mapping
* Merge upstream fixes and improvements, most notabely:
* Postgresql database connection pooling
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 23 Oct 2012 11:06:14 +0400
yate (4.2.1~vir2012100401) UNRELEASED; urgency=low
* Merge upstream fixes, including new DTMF sending method selection
* Fix building on debian testing and unstable
-- Vasily i. Redkin <vir@vir.otvt.ru> Thu, 04 Oct 2012 16:21:36 +0400
yate (4.2.1~vir2012090501) UNRELEASED; urgency=low
* Merged upstream fixes, including the following:
* reINVITE fix
* SIP flood prevention and 'floodevents' new meaning (dropping packaets)
* maxchans setting sip/iax/jingle/h323 chans
* a number of jingle and IAX fixes
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 05 Sep 2012 13:37:18 +0400
yate (4.1.1~vir2012071201) UNRELEASED; urgency=low
* Merged upstream fixes
-- Vasily i. Redkin <vir@vir.otvt.ru> Thu, 12 Jul 2012 10:45:39 +0400
yate (4.1.1~vir2012070902) UNRELEASED; urgency=low
* yate-h323 package restored
-- Vasily i. Redkin <vir@vir.otvt.ru> Mon, 09 Jul 2012 12:40:34 +0400
yate (4.1.1~vir2012070901) UNRELEASED; urgency=low
* Merged upstream fixes, webrtc-based iLBC codec really added.
-- Vasily i. Redkin <vir@vir.otvt.ru> Mon, 09 Jul 2012 12:09:04 +0400
yate (4.1.1~vir2012070601) UNRELEASED; urgency=low
* Merged upstream changes: bugfixes, webrtc-based iLBC codec.
* Trying to fix building on unstable (without libopenh323)
-- Vasily i. Redkin <vir@vir.otvt.ru> Fri, 06 Jul 2012 14:57:01 +0400
yate (4.1.1~vir2012062601) UNRELEASED; urgency=low
* Merged upstream changes: Javascript improvements, various bugfixes
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 26 Jun 2012 10:48:39 +0400
yate (4.1.1~vir2012061301) UNRELEASED; urgency=low
* Merged upstream changes: messages tracking, several fixes.
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 13 Jun 2012 11:03:18 +0400
yate (4.1.1~vir2012050701) UNRELEASED; urgency=low
* Merged upstream changed: gvoice module, bugfixes.
* Version scheme change (~virXXXXXXXXXX suffix).
-- Vasily i. Redkin <vir@vir.otvt.ru> Mon, 07 May 2012 00:12:08 +0400
yate (4.0.1.vir2012040401) UNRELEASED; urgency=low
* Merged lots of upstream changes: jabber component, rtp dejitter,
rmanager line editing, iSAC codec, many small fixes.
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 04 Apr 2012 23:49:36 +0400
yate (4.0.1.vir2012022101) UNRELEASED; urgency=low
* Merged upstream changes: major version change!
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 21 Feb 2012 19:19:41 +0400
yate (3.3.3.vir2012021602) UNRELEASED; urgency=low
* library filename fix
-- Vasily i. Redkin <vir@vir.otvt.ru> Thu, 16 Feb 2012 11:51:15 +0400
yate (3.3.3.vir2012021601) UNRELEASED; urgency=low
* Merged upstream changes. Javascript module name typo fixed.
-- Vasily i. Redkin <vir@vir.otvt.ru> Thu, 16 Feb 2012 11:39:37 +0400
yate (3.3.3.vir2012021501) UNRELEASED; urgency=low
* Merged upstream changes: new client UI design, Javascript module
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 15 Feb 2012 18:56:58 +0400
yate (3.3.3.vir2012012801) UNRELEASED; urgency=low
* Merged upstream changes
-- Vasily i. Redkin <vir@vir.otvt.ru> Sat, 28 Jan 2012 10:56:43 +0400
yate (3.3.3.vir2011120704) UNRELEASED; urgency=low
* Fixed UU IE duplication
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 07 Dec 2011 16:50:23 +0400
yate (3.3.3.vir2011120703) UNRELEASED; urgency=low
* Fixed UUS IE encoding (missing protocol discrimrnator added)
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 07 Dec 2011 15:17:12 +0400
yate (3.3.3.vir2011120702) UNRELEASED; urgency=low
* Added UUS encoding mplementation
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 07 Dec 2011 14:23:50 +0400
yate (3.3.3.vir2011120701) UNRELEASED; urgency=low
* Merged upstream changes.
* Fix outgoing UUS
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 07 Dec 2011 11:35:17 +0400
yate (3.3.3.vir2011111801) UNRELEASED; urgency=low
* Experimantal ISDN UUS support
-- Vasily i. Redkin <vir@vir.otvt.ru> Fri, 18 Nov 2011 16:10:15 +0400
yate (3.3.3.vir2011111501) UNRELEASED; urgency=low
* Merge upstream
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 15 Nov 2011 09:03:57 +0400
yate (3.3.3.vir2011110903) UNRELEASED; urgency=low
* new package version finally
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 09 Nov 2011 16:23:23 +0400
yate (3.3.3.vir2011110902) UNRELEASED; urgency=low
* Fix wrong package version
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 09 Nov 2011 16:22:34 +0400
yate (3.3.3.vir2011110901) UNRELEASED; urgency=low
* Added more new files
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 09 Nov 2011 16:17:31 +0400
yate (3.3.3.vir2011110902) UNRELEASED; urgency=low
* added Build-Depends: build-essential
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 09 Nov 2011 13:43:13 +0400
yate (3.3.3.vir2011110901) UNRELEASED; urgency=low
* Merged lates upstream changes
* Fix building (failed due to isupmangler module path change)
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 09 Nov 2011 12:05:56 +0400
yate (3.3.3.vir2011090601) UNRELEASED; urgency=low
* Fixed overlapdial timer threads leak on reload
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 06 Sep 2011 17:43:09 +0400
yate (3.3.3.vir2011080801) UNRELEASED; urgency=low
* Merged upstream updates
-- Vasily i. Redkin <vir@vir.otvt.ru> Mon, 08 Aug 2011 11:47:56 +0400
yate (3.3.3.vir2011072601) UNRELEASED; urgency=low
* Fixed crash on overlapdial module unload
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 26 Jul 2011 18:41:41 +0400
yate (3.3.3.vir2011072501) UNRELEASED; urgency=low
* Fix timeout-based overlap dialing lost in prev. versions.
* Merged upstream changes and fixes.
-- Vasily i. Redkin <vir@vir.otvt.ru> Mon, 25 Jul 2011 16:07:30 +0400
yate (3.3.3.vir2011071301) UNRELEASED; urgency=low
* Merged a lot of upstream changes, most notably, SIP over TCP/TLS
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 13 Jul 2011 21:32:27 +0400
yate (3.3.3.vir2011063001) UNRELEASED; urgency=low
* SDP FMTP lines forwarding should now work as expected
-- Vasily i. Redkin <vir@vir.otvt.ru> Thu, 30 Jun 2011 15:18:17 +0400
yate (3.3.3.vir2011062601) UNRELEASED; urgency=low
* Fixed SDP fmtp lines forwarding.
* Merged latest upstream changes: fixes and new module 'cache'
-- Vasily i. Redkin <vir@vir.otvt.ru> Sun, 26 Jun 2011 09:42:52 +0400
yate (3.3.3.vir2011052702) UNRELEASED; urgency=low
* Crash fix
-- Vasily i. Redkin <vir@vir.otvt.ru> Fri, 27 May 2011 12:33:26 +0400
yate (3.3.3.vir2011052701) UNRELEASED; urgency=low
* SDP fmtp lines forwarding fix
-- Vasily i. Redkin <vir@vir.otvt.ru> Fri, 27 May 2011 12:13:46 +0400
yate (3.3.3.vir2011052601) UNRELEASED; urgency=low
* SDP fmtp lines forwarding
-- Vasily i. Redkin <vir@vir.otvt.ru> Thu, 26 May 2011 18:52:34 +0400
yate (3.3.3.vir2011051601) UNRELEASED; urgency=low
* Merged marian's QOP implementation
-- Vasily i. Redkin <vir@vir.otvt.ru> Mon, 16 May 2011 14:08:31 +0400
yate (3.3.3.vir2011051401) UNRELEASED; urgency=low
* Merge SIP QOP handling with upstream
* New Yate.pm
-- Vasily i. Redkin <vir@vir.otvt.ru> Sat, 14 May 2011 10:49:42 +0400
yate (3.3.3.vir2011050401) UNRELEASED; urgency=low
* Merged upstream updates
-- Vasily i. Redkin <vir@vir.otvt.ru> Wed, 04 May 2011 23:03:00 +0400
yate (3.3.3.vir2011050305) UNRELEASED; urgency=low
* Support "xsip_body_encoding" parameter in xsip.generate message
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 03 May 2011 22:34:03 +0400
yate (3.3.3.vir2011050304) UNRELEASED; urgency=low
* FAKE
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 03 May 2011 14:23:35 +0400
yate (3.3.3.vir2011043001) UNRELEASED; urgency=low
* Merged upstream fixes
-- Vasily i. Redkin <vir@vir.otvt.ru> Sat, 30 Apr 2011 10:39:21 +0400
yate (3.3.3.vir2011042801) UNRELEASED; urgency=low
* Merged upstream fixes
-- Vasily i. Redkin <vir@vir.otvt.ru> Thu, 28 Apr 2011 22:30:19 +0400
yate (3.3.3.vir2011041701) UNRELEASED; urgency=low
* New debian package. Fixed pidfile-related troubles.
* Merged a lot of upstream fixes.
-- Vasily i. Redkin <vir@vir.otvt.ru> Sun, 17 Apr 2011 00:09:18 +0400
yate (3.2.1.vir2011032102) UNRELEASED; urgency=low
* Moved jabberclient.yate from yate-qt4 into libyate package
-- Vasily i. Redkin <vir@vir.otvt.ru> Mon, 21 Mar 2011 20:52:22 +0300
yate (3.2.1.vir2011032101) UNRELEASED; urgency=low
* pulled in upstramm changes (tel: uri support and bug fixes)
-- Vasily i. Redkin <vir@vir.otvt.ru> Mon, 21 Mar 2011 16:05:12 +0300
yate (3.2.1.vir2011031401) UNRELEASED; urgency=low
* Fix bug introduced by recent history rewrite
-- Vasily i. Redkin <vir@vir.otvt.ru> Mon, 14 Mar 2011 06:57:58 +0300
yate (3.2.1.vir2011031101) UNRELEASED; urgency=low
* pulled in upstramm changes
-- Vasily i. Redkin <vir@vir.otvt.ru> Fri, 11 Mar 2011 11:29:59 +0300
yate (3.1.1.vir2011021901) UNRELEASED; urgency=low
* pulled in upstream changes
-- Vasily i. Redkin <vir@vir.otvt.ru> Sat, 19 Feb 2011 13:55:49 +0300
yate (3.1.1.vir2011020601) UNRELEASED; urgency=low
* New Debian stable release out there, we have new versioning scheme for testing and stable ports
-- Vasily i. Redkin <yatedeb@vir.otvt.ru> Sun, 06 Feb 2011 13:29:09 +0300
yate (3.1.1.vir2011020102) UNRELEASED; urgency=low
* Pulled in upstream changes
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 01 Feb 2011 11:22:30 +0300
yate (3.0.1.vir2011020101) UNRELEASED; urgency=low
* Changed debian package versioning scheme to YYYYMMDDRR
-- Vasily i. Redkin <vir@vir.otvt.ru> Tue, 01 Feb 2011 10:16:25 +0300
yate (3.0.0.vir12647) unstable; urgency=low
* Fixed dependency packages versions
-- Vasily i. Redkin <vir@vir.otvt.ru> Thu, 29 Apr 2010 13:17:26 +0400
yate (3.0.0.vir12646) unstable; urgency=low
* Changed version scheme to include svk revision
-- Vasily i. Redkin <vir@vir.ctm.ru> Thu, 29 Apr 2010 10:52:57 +0400
yate (3.0.0) unstable; urgency=low
* Updated to new version
-- Vasily i. Redkin <vir@vir.ctm.ru> Fri, 23 Apr 2010 17:46:14 +0400
yate (2.0.0) unstable; urgency=low
* Initial Release.
-- Vasily i. Redkin <vir@ctm.ru> Mon, 06 Oct 2008 13:28:44 +0400

30
debian/checkinstall.sh vendored Executable file
View File

@ -0,0 +1,30 @@
#!/bin/bash
#
# (c) vir
#
# Last modified: 2010-12-23 10:33:10 +0300
#
D=debian/tmp
LIST=debian/NOT-INSTALLED-LIST
ALLFILES=`find $D -type f -print | cut -d/ -f3- | grep -v '^usr/share/doc'`
echo -n > $LIST
for f in $ALLFILES
do
# some files moved from .../client/, some not - check both
f2=`echo $f | sed 's/usr\/lib\/yate\/client\//usr\/lib\/yate\//'`
if [ ! -e debian/*yate*/$f -a ! -e debian/*yate*/$f2 ]
then
echo "$f" >> $LIST
fi
done
echo "*** *** *** NOT PACKAGED FILES: *** *** ***"
cat $LIST
echo "~~~ ~~~ ~~~ ~~~ ~~~ ~~~ ~~~ ~~~ ~~~ ~~~ ~~~"

1
debian/compat vendored Normal file
View File

@ -0,0 +1 @@
7

113
debian/control vendored Normal file
View File

@ -0,0 +1,113 @@
Source: yate
Section: comm
Priority: optional
Maintainer: Vasily i. Redkin <vir@ctm.ru>
Build-Depends: build-essential, debhelper (>= 7), pkg-config,
libasound2-dev, libqt4-dev, libpt-dev,
libpq-dev, libmysqlclient-dev, libssl-dev|libssl1.0-dev, zaptel-source|dahdi-source,
libgsm1-dev, libspeex-dev, libspandsp-dev, doxygen, autoconf, libsctp-dev,
libsqlite3-dev
Standards-Version: 3.7.3
Homepage: http://yate.null.ro/
Package: yate
Architecture: any
Suggests: yate-telhw, yate-pgsql
Depends: libyate (= ${binary:Version}), ${shlibs:Depends}, ${misc:Depends},
libsctp1
Description: The YATE project aims to be a fully featured software PBX.
.
YATE is a next-generation telephony engine; while currently focused on Voice
over Internet Protocol (VoIP) and PSTN, its power lies in its ability to be
easily extended. Voice, video, data and instant messenging can all be unified
under Yate's flexible routing engine, maximizing communications efficiency and
minimizing infrastructure costs for businesses.
.
This most recent version from the Yate software has bring several improvements
over the previous versions:
.
* SCCP, TCAP, MAP and CAMEL, TCP and TLS in SIP
* Jabber client and server
* Support for more hardware interfaces and protocols - added SS7, analogic
support, RBS, better ISDN, passive recording
* Clustering, balancing and failover support, Linux-HA integration
* Added MGCP and Jingle support
Package: libyate
Section: libs
Conflicts: yate (<< 4.0.0)
Replaces: libyate (<< 4.0.0)
Breaks: libyate (<< 4.0.0)
Architecture: any
Depends: ${shlibs:Depends}, ${misc:Depends}, libspeex1, libgsm1
Description: YATE shared library
Package: yate-dev
Section: libdevel
Architecture: any
Suggests: yate-dbg, yate-doc
Depends: libyate (= ${binary:Version}), ${shlibs:Depends}, ${misc:Depends}
Description: YATE library development files
Package: yate-qt4
Architecture: any
Recommends: yate-alsa
Depends: ${shlibs:Depends}, ${misc:Depends}
Description: Qt4 software VoIP and Jabber client, based on YATE
Package: yate-alsa
Architecture: any
Recommends: yate (= ${binary:Version}) | yate-qt4 (= ${binary:Version})
Depends: ${shlibs:Depends}, ${misc:Depends}, libasound2
Description: ALSA channel driver for YATE
Package: yate-mysql
Architecture: any
Recommends: yate (= ${binary:Version})
Depends: libyate(= ${binary:Version}), ${shlibs:Depends}, ${misc:Depends}
Description: MySQL database support for yate
Package: yate-pgsql
Architecture: any
Recommends: yate (= ${binary:Version})
Depends: libyate(= ${binary:Version}), ${shlibs:Depends}, ${misc:Depends},
libpq5
Description: Postgres database support for yate
Package: yate-sqlite
Architecture: any
Recommends: yate (= ${binary:Version})
Depends: libyate(= ${binary:Version}), ${shlibs:Depends}, ${misc:Depends},
libsqlite3-0
Suggests: sqlite3
Description: SQLite database support for yate
Package: yate-telhw
Architecture: any
Recommends: yate (= ${binary:Version}) | yate-qt4 (= ${binary:Version}),
dahdi | zaptel | wanpipe
Depends: libyate (= ${binary:Version}), ${shlibs:Depends}, ${misc:Depends}
Description: Telephony hardware support for yate server
Also MGCP CA module.
Package: yate-doc
Section: doc
Architecture: all
Description: Documentation for yate
Package: yate-dbg
Section: devel
Architecture: any
Depends: libyate (= ${Source-Version})
Recommends: gdb
Replaces: libyate-dbg, yate-telhw-dbg
Description: Debug symbols for all yate applications and libraries
Package: libyate-perl
Section: devel
Architecture: any
Depends: perl (>= 5)
Description: Perl module

1
debian/docs vendored Normal file
View File

@ -0,0 +1 @@
README

1
debian/libyate-perl.install vendored Normal file
View File

@ -0,0 +1 @@
debian/tmp/usr/share/yate/scripts/Yate.pm /usr/share/perl5

76
debian/libyate.install vendored Normal file
View File

@ -0,0 +1,76 @@
debian/tmp/usr/lib/libyate.so.*
debian/tmp/etc/yate/callfork.conf
debian/tmp/etc/yate/cdrbuild.conf
debian/tmp/etc/yate/cdrfile.conf
#debian/tmp/etc/yate/dsoundchan.conf
debian/tmp/etc/yate/enumroute.conf
debian/tmp/etc/yate/extmodule.conf
debian/tmp/etc/yate/moh.conf
debian/tmp/etc/yate/mux.conf
debian/tmp/etc/yate/providers.conf
debian/tmp/etc/yate/regexroute.conf
debian/tmp/etc/yate/rmanager.conf
debian/tmp/etc/yate/yate.conf
debian/tmp/etc/yate/yiaxchan.conf
debian/tmp/etc/yate/yjinglechan.conf
debian/tmp/etc/yate/yrtpchan.conf
debian/tmp/etc/yate/ysipchan.conf
debian/tmp/etc/yate/ystunchan.conf
debian/tmp/etc/yate/openssl.conf
debian/tmp/etc/yate/tonegen.conf
debian/tmp/usr/lib/yate/*codec.yate
debian/tmp/usr/lib/yate/client/osschan.yate usr/lib/yate
debian/tmp/usr/lib/yate/cdrbuild.yate
debian/tmp/usr/lib/yate/cdrfile.yate
debian/tmp/usr/lib/yate/regexroute.yate
debian/tmp/usr/lib/yate/tonegen.yate
debian/tmp/usr/lib/yate/tonedetect.yate
debian/tmp/usr/lib/yate/wavefile.yate
debian/tmp/usr/lib/yate/extmodule.yate
debian/tmp/usr/lib/yate/conference.yate
debian/tmp/usr/lib/yate/moh.yate
debian/tmp/usr/lib/yate/pbx.yate
debian/tmp/usr/lib/yate/dumbchan.yate
debian/tmp/usr/lib/yate/callfork.yate
debian/tmp/usr/lib/yate/mux.yate
debian/tmp/usr/lib/yate/yrtpchan.yate
debian/tmp/usr/lib/yate/ystunchan.yate
debian/tmp/usr/lib/yate/ysipchan.yate
debian/tmp/usr/lib/yate/yiaxchan.yate
debian/tmp/usr/lib/yate/callgen.yate
debian/tmp/usr/lib/yate/analyzer.yate
debian/tmp/usr/lib/yate/rmanager.yate
debian/tmp/usr/lib/yate/msgsniff.yate
debian/tmp/usr/lib/yate/enumroute.yate
debian/tmp/usr/lib/yate/openssl.yate
debian/tmp/usr/lib/yate/ilbcwebrtc.yate
debian/tmp/etc/yate/ysockschan.conf
debian/tmp/usr/lib/yate/ysockschan.yate
debian/tmp/etc/yate/filetransfer.conf
debian/tmp/usr/lib/yate/filetransfer.yate
debian/tmp/usr/share/yate/sounds/ring.wav
debian/tmp/usr/share/yate/sounds/tone.wav
debian/tmp/usr/lib/libyatejabber.so.*
debian/tmp/usr/lib/yate/yjinglechan.yate
debian/tmp/etc/yate/zlibcompress.conf
debian/tmp/usr/lib/yate/zlibcompress.yate
debian/tmp/etc/yate/jabberclient.conf
debian/tmp/usr/lib/yate/client/jabberclient.yate usr/lib/yate
debian/tmp/etc/yate/javascript.conf
debian/tmp/usr/lib/libyatescript.so.*
debian/tmp/usr/lib/yate/javascript.yate
debian/tmp/etc/yate/gvoice.conf
debian/tmp/usr/lib/yate/gvoice.yate
debian/tmp/usr/lib/yate/cdrcombine.yate

40
debian/newver.pl vendored Executable file
View File

@ -0,0 +1,40 @@
#!/usr/bin/perl
use strict;
use warnings;
my $verbose = @ARGV;
open CL, "< debian/changelog" or die;
my $firstline = <CL>;
$firstline =~/^.*?\([\d\.]+~?vir(\d{10})\)/i or die;
my $lastrev = $1;
close CL;
print "Found last seen revision $lastrev\n";
my $yatever;
my $conf_in = (-f 'configure.ac') ? 'configure.ac' : 'configure.in';
open CF, "< $conf_in" or die;
while(<CF>) {
chomp;
if(/^\s*AC_INIT\(Yate, ([\d\.]+)\)/) {
$yatever = $1;
last;
}
}
close CF;
my($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst) = localtime(time);
my $suff = sprintf("%04d%02d%02d%02d", 1900+$year, 1+$mon, $mday, 1);
++$suff while $suff le $lastrev;
my $newver="$yatever~vir$suff";
print "New version: $newver\n";
my $rc = system qw( debchange -b --preserve --distribution UNRELEASED --release-heuristic log --newversion ), "$newver";
if($rc == 0) {
exec "git commit -m 'New debian package $newver' debian/changelog";
}

126
debian/rules vendored Executable file
View File

@ -0,0 +1,126 @@
#!/usr/bin/make -f
# -*- makefile -*-
# Sample debian/rules that uses debhelper.
#
# This file was originally written by Joey Hess and Craig Small.
# As a special exception, when this file is copied by dh-make into a
# dh-make output file, you may use that output file without restriction.
# This special exception was added by Craig Small in version 0.37 of dh-make.
#
# Modified to make a template file for a multi-binary package with separated
# build-arch and build-indep targets by Bill Allombert 2001
# Uncomment this to turn on verbose mode.
#export DH_VERBOSE=1
# This has to be exported to make some magic below work.
export DH_OPTIONS
configure:
./autogen.sh
config: configure-stamp
configure-stamp: configure yate-config.in
dh_testdir
# Add here commands to configure the package.
./configure $(confflags) --prefix=/usr --mandir=\$${prefix}/share/man --infodir=\$${prefix}/share/info --sysconfdir=/etc --disable-ilbc --enable-sctp
touch configure-stamp
yate-config.in: configure yate-config.sh
./yate-config.sh
#Architecture
build: build-arch build-indep
build-arch: build-arch-stamp
build-arch-stamp: configure-stamp
# Add here commands to compile the arch part of the package.
#$(MAKE)
touch $@
build-indep: build-indep-stamp
build-indep-stamp: configure-stamp
# Add here commands to compile the indep part of the package.
#$(MAKE) doc
touch $@
clean: config
dh_testdir
dh_testroot
rm -f build-arch-stamp build-indep-stamp configure-stamp
# Add here commands to clean up after the build process.
$(MAKE) clean
dh_clean
install: install-indep install-arch
install-indep:
dh_testdir
dh_testroot
dh_clean -k -i
dh_installdirs -i
# Add here commands to install the indep part of the package into
# debian/<package>-doc.
#INSTALLDOC#
# $(MAKE) DESTDIR=$(CURDIR)/debian/tmp install
dh_install -i
install-arch:
dh_testdir
dh_testroot
dh_clean -k -s
dh_installdirs -s
# Add here commands to install the arch part of the package into
# debian/tmp.
$(MAKE) DESTDIR=$(CURDIR)/debian/tmp debug install
dh_install -s
debian/checkinstall.sh
# Must not depend on anything. This is to be called by
# binary-arch/binary-indep
# in another 'make' thread.
binary-common:
dh_testdir
dh_testroot
dh_installchangelogs ChangeLog
dh_installdocs
# dh_installexamples
# dh_installmenu
# dh_installdebconf
dh_installlogrotate
# dh_installemacsen
# dh_installpam
# dh_installmime
# dh_python
dh_installinit
# dh_installcron
# dh_installinfo
dh_installman
dh_link
# dh_strip
dh_strip --dbg-package=yate-dbg
dh_compress
dh_fixperms
# dh_perl
dh_makeshlibs
dh_installdeb
dh_shlibdeps
dh_gencontrol
dh_md5sums
dh_builddeb
# Build architecture independant packages using the common target.
binary-indep: build-indep install-indep
$(MAKE) -f debian/rules DH_OPTIONS=-i binary-common
# Build architecture dependant packages using the common target.
binary-arch: build-arch install-arch
$(MAKE) -f debian/rules DH_OPTIONS=-s binary-common
binary: binary-arch binary-indep
.PHONY: build clean binary-indep binary-arch binary install install-indep install-arch config

1
debian/source/format vendored Normal file
View File

@ -0,0 +1 @@
3.0 (native)

23
debian/upgrade_local.sh vendored Executable file
View File

@ -0,0 +1,23 @@
#!/bin/sh
#
# (c) vir
#
# Last modified: 2013-04-15 15:10:46 +0400
#
DIR=../
ARCH=i386
INSTALLED=`dpkg -l | awk '/^ii/ && /yate/ { print $2 }'`
VERSION=`dpkg-parsechangelog | awk '/^Version:/ { print $2 }'`
LINE='sudo dpkg -i'
for p in $INSTALLED
do
LINE="${LINE} ${DIR}${p}_${VERSION}_${ARCH}.deb"
done
echo "Executing: ${LINE}"
exec ${LINE}

3
debian/yate-alsa.install vendored Normal file
View File

@ -0,0 +1,3 @@
debian/tmp/usr/lib/yate/client/alsachan.yate usr/lib/yate

8
debian/yate-dev.install vendored Normal file
View File

@ -0,0 +1,8 @@
debian/tmp/usr/lib/libyate.so
debian/tmp/usr/lib/libyatejabber.so
debian/tmp/usr/lib/libyatescript.so
debian/tmp/usr/lib/pkgconfig/yate.pc
debian/tmp/usr/bin/yate-config
debian/tmp/usr/share/man/man8/yate-config.8
debian/tmp/usr/include/yate/*.h

7
debian/yate-doc.docs vendored Normal file
View File

@ -0,0 +1,7 @@
docs/api
docs/dataflow.html
docs/extmodule.html
docs/index.html
docs/messages.html

2
debian/yate-doc.install vendored Normal file
View File

@ -0,0 +1,2 @@

3
debian/yate-h323.install vendored Normal file
View File

@ -0,0 +1,3 @@
debian/tmp/etc/yate/h323chan.conf
debian/tmp/usr/lib/yate/h323chan.yate

3
debian/yate-mysql.install vendored Normal file
View File

@ -0,0 +1,3 @@
debian/tmp/etc/yate/mysqldb.conf
debian/tmp/usr/lib/yate/server/mysqldb.yate

3
debian/yate-pgsql.install vendored Normal file
View File

@ -0,0 +1,3 @@
debian/tmp/etc/yate/pgsqldb.conf
debian/tmp/usr/lib/yate/server/pgsqldb.yate

355
debian/yate-qt4.install vendored Normal file
View File

@ -0,0 +1,355 @@
debian/tmp/usr/bin/yate-qt4
debian/tmp/usr/lib/yate/qt4/customtable.yate
debian/tmp/usr/lib/yate/qt4/customtext.yate
debian/tmp/usr/lib/yate/qt4/customtree.yate
debian/tmp/usr/lib/yate/qt4/widgetlist.yate
debian/tmp/usr/lib/yate/qt4/clientarchive.yate
debian/tmp/usr/lib/libyateqt4.so.*
debian/tmp/usr/share/icons/hicolor/16x16/apps/null_team.png
debian/tmp/usr/share/icons/hicolor/32x32/apps/null_team.png
debian/tmp/usr/share/icons/hicolor/48x48/apps/null_team.png
debian/tmp/usr/lib/menu/yate-qt4.menu
debian/tmp/usr/share/applications/yate-qt4.desktop
debian/tmp/usr/share/yate/sounds/ring.au
debian/tmp/usr/share/yate/help/0.yhlp
debian/tmp/usr/share/yate/help/1.yhlp
debian/tmp/usr/share/yate/help/2.yhlp
debian/tmp/usr/share/yate/help/3.yhlp
debian/tmp/usr/share/yate/help/4.yhlp
debian/tmp/usr/share/yate/help/99.yhlp
debian/tmp/usr/share/yate/skins/default/account.ui
debian/tmp/usr/share/yate/skins/default/accountlist.ui
debian/tmp/usr/share/yate/skins/default/addchatroom.png
debian/tmp/usr/share/yate/skins/default/addrbook.ui
debian/tmp/usr/share/yate/skins/default/book.png
debian/tmp/usr/share/yate/skins/default/close.png
debian/tmp/usr/share/yate/skins/default/configure.png
debian/tmp/usr/share/yate/skins/default/confirm.ui
debian/tmp/usr/share/yate/skins/default/down.png
debian/tmp/usr/share/yate/skins/default/events.ui
debian/tmp/usr/share/yate/skins/default/help.ui
debian/tmp/usr/share/yate/skins/default/ok.png
debian/tmp/usr/share/yate/skins/default/phone.png
debian/tmp/usr/share/yate/skins/default/qt4client.rc
debian/tmp/usr/share/yate/skins/default/qt4client.ui
debian/tmp/usr/share/yate/skins/default/quest.png
debian/tmp/usr/share/yate/skins/default/settings.ui
debian/tmp/usr/share/yate/skins/default/up.png
debian/tmp/usr/share/yate/skins/default/user.png
debian/tmp/usr/share/yate/skins/default/answer.png
debian/tmp/usr/share/yate/skins/default/bell.png
debian/tmp/usr/share/yate/skins/default/cdr.png
debian/tmp/usr/share/yate/skins/default/chan_idle.png
debian/tmp/usr/share/yate/skins/default/chan_progress.png
debian/tmp/usr/share/yate/skins/default/chan_ringing.png
debian/tmp/usr/share/yate/skins/default/chan_routed.png
debian/tmp/usr/share/yate/skins/default/conference.png
debian/tmp/usr/share/yate/skins/default/down_active.png
debian/tmp/usr/share/yate/skins/default/edit.png
debian/tmp/usr/share/yate/skins/default/events.png
debian/tmp/usr/share/yate/skins/default/handshake.png
debian/tmp/usr/share/yate/skins/default/handshake_x.png
debian/tmp/usr/share/yate/skins/default/hangup.png
debian/tmp/usr/share/yate/skins/default/hold.png
debian/tmp/usr/share/yate/skins/default/home.png
debian/tmp/usr/share/yate/skins/default/keyboard.png
debian/tmp/usr/share/yate/skins/default/message.ui
debian/tmp/usr/share/yate/skins/default/next.png
debian/tmp/usr/share/yate/skins/default/null_team-16.png
debian/tmp/usr/share/yate/skins/default/null_team-32.png
debian/tmp/usr/share/yate/skins/default/null_team-48.png
debian/tmp/usr/share/yate/skins/default/prev.png
debian/tmp/usr/share/yate/skins/default/speaker.png
debian/tmp/usr/share/yate/skins/default/speaker_x.png
debian/tmp/usr/share/yate/skins/default/transfer.png
debian/tmp/usr/share/yate/skins/default/tray_info.png
debian/tmp/usr/share/yate/skins/default/up_active.png
debian/tmp/usr/share/yate/skins/default/update.png
debian/tmp/usr/share/yate/skins/default/updater.ui
debian/tmp/usr/share/yate/skins/default/accountwizard.ui
debian/tmp/usr/share/yate/skins/default/addaccount.png
debian/tmp/usr/share/yate/skins/default/addaccountwiz.png
debian/tmp/usr/share/yate/skins/default/addcontact.png
debian/tmp/usr/share/yate/skins/default/answer_20.png
debian/tmp/usr/share/yate/skins/default/arch_contact_item.ui
debian/tmp/usr/share/yate/skins/default/archive.png
debian/tmp/usr/share/yate/skins/default/archive.ui
debian/tmp/usr/share/yate/skins/default/arch_session_item.ui
debian/tmp/usr/share/yate/skins/default/ask_32.png
debian/tmp/usr/share/yate/skins/default/ask.png
debian/tmp/usr/share/yate/skins/default/book_32.png
debian/tmp/usr/share/yate/skins/default/busy.ui
debian/tmp/usr/share/yate/skins/default/cdr_32.png
debian/tmp/usr/share/yate/skins/default/chat.png
debian/tmp/usr/share/yate/skins/default/chat.ui
debian/tmp/usr/share/yate/skins/default/chatroomedit.ui
debian/tmp/usr/share/yate/skins/default/clear.png
debian/tmp/usr/share/yate/skins/default/collapsed.png
debian/tmp/usr/share/yate/skins/default/conference_20.png
debian/tmp/usr/share/yate/skins/default/contactedit.ui
debian/tmp/usr/share/yate/skins/default/contactinfo.ui
debian/tmp/usr/share/yate/skins/default/contactfs.ui
debian/tmp/usr/share/yate/skins/default/contactfsd.ui
debian/tmp/usr/share/yate/skins/default/digit0_hover.png
debian/tmp/usr/share/yate/skins/default/digit0.png
debian/tmp/usr/share/yate/skins/default/digit0_pressed.png
debian/tmp/usr/share/yate/skins/default/digit1_hover.png
debian/tmp/usr/share/yate/skins/default/digit1.png
debian/tmp/usr/share/yate/skins/default/digit1_pressed.png
debian/tmp/usr/share/yate/skins/default/digit2_hover.png
debian/tmp/usr/share/yate/skins/default/digit2.png
debian/tmp/usr/share/yate/skins/default/digit2_pressed.png
debian/tmp/usr/share/yate/skins/default/digit3_hover.png
debian/tmp/usr/share/yate/skins/default/digit3.png
debian/tmp/usr/share/yate/skins/default/digit3_pressed.png
debian/tmp/usr/share/yate/skins/default/digit4_hover.png
debian/tmp/usr/share/yate/skins/default/digit4.png
debian/tmp/usr/share/yate/skins/default/digit4_pressed.png
debian/tmp/usr/share/yate/skins/default/digit5_hover.png
debian/tmp/usr/share/yate/skins/default/digit5.png
debian/tmp/usr/share/yate/skins/default/digit5_pressed.png
debian/tmp/usr/share/yate/skins/default/digit6_hover.png
debian/tmp/usr/share/yate/skins/default/digit6.png
debian/tmp/usr/share/yate/skins/default/digit6_pressed.png
debian/tmp/usr/share/yate/skins/default/digit7_hover.png
debian/tmp/usr/share/yate/skins/default/digit7.png
debian/tmp/usr/share/yate/skins/default/digit7_pressed.png
debian/tmp/usr/share/yate/skins/default/digit8_hover.png
debian/tmp/usr/share/yate/skins/default/digit8.png
debian/tmp/usr/share/yate/skins/default/digit8_pressed.png
debian/tmp/usr/share/yate/skins/default/digit9_hover.png
debian/tmp/usr/share/yate/skins/default/digit9.png
debian/tmp/usr/share/yate/skins/default/digit9_pressed.png
debian/tmp/usr/share/yate/skins/default/digitpound_hover.png
debian/tmp/usr/share/yate/skins/default/digitpound.png
debian/tmp/usr/share/yate/skins/default/digitpound_pressed.png
debian/tmp/usr/share/yate/skins/default/digitstar_hover.png
debian/tmp/usr/share/yate/skins/default/digitstar.png
debian/tmp/usr/share/yate/skins/default/digitstar_pressed.png
debian/tmp/usr/share/yate/skins/default/dockedchat.ui
debian/tmp/usr/share/yate/skins/default/expanded.png
debian/tmp/usr/share/yate/skins/default/fileprogress_item.ui
debian/tmp/usr/share/yate/skins/default/fileprogress.ui
debian/tmp/usr/share/yate/skins/default/findnext.png
debian/tmp/usr/share/yate/skins/default/find.png
debian/tmp/usr/share/yate/skins/default/findprev.png
debian/tmp/usr/share/yate/skins/default/hangup_20.png
debian/tmp/usr/share/yate/skins/default/hold_20.png
debian/tmp/usr/share/yate/skins/default/info_32.png
debian/tmp/usr/share/yate/skins/default/info.png
debian/tmp/usr/share/yate/skins/default/inputacccred.ui
debian/tmp/usr/share/yate/skins/default/inputpwd.ui
debian/tmp/usr/share/yate/skins/default/input.ui
debian/tmp/usr/share/yate/skins/default/joinmucwizard.ui
debian/tmp/usr/share/yate/skins/default/messages_header.ui
debian/tmp/usr/share/yate/skins/default/messages_loginfail.ui
debian/tmp/usr/share/yate/skins/default/messages_okrejignore.ui
debian/tmp/usr/share/yate/skins/default/messages_generic.ui
debian/tmp/usr/share/yate/skins/default/mucchat.ui
debian/tmp/usr/share/yate/skins/default/mucinvite.ui
debian/tmp/usr/share/yate/skins/default/muc.png
debian/tmp/usr/share/yate/skins/default/muc_16.png
debian/tmp/usr/share/yate/skins/default/mucprivchat.ui
debian/tmp/usr/share/yate/skins/default/mucs.ui
debian/tmp/usr/share/yate/skins/default/phone_32.png
debian/tmp/usr/share/yate/skins/default/progress.gif
debian/tmp/usr/share/yate/skins/default/room_member.ui
debian/tmp/usr/share/yate/skins/default/sendchat.png
debian/tmp/usr/share/yate/skins/default/sendfile.png
debian/tmp/usr/share/yate/skins/default/status_away.png
debian/tmp/usr/share/yate/skins/default/status_busy.png
debian/tmp/usr/share/yate/skins/default/status_connecting.png
debian/tmp/usr/share/yate/skins/default/status_dnd.png
debian/tmp/usr/share/yate/skins/default/status_offline.png
debian/tmp/usr/share/yate/skins/default/status_online.png
debian/tmp/usr/share/yate/skins/default/status_xa.png
debian/tmp/usr/share/yate/skins/default/transfer_20.png
debian/tmp/usr/share/yate/skins/default/tray_incomingcall.png
debian/tmp/usr/share/yate/skins/default/tray_notification.png
debian/tmp/usr/share/yate/skins/default/tray_incomingchat.png
debian/tmp/usr/share/yate/skins/default/arch_room_item.ui
debian/tmp/usr/share/yate/skins/default/arch_roompriv_item.ui
debian/tmp/usr/share/yate/skins/default/minus.png
debian/tmp/usr/share/yate/skins/default/plus.png
debian/tmp/usr/share/yate/skins/default/save.png
debian/tmp/usr/share/yate/skins/default/account_title.png
debian/tmp/usr/share/yate/skins/default/accountlist_title.png
debian/tmp/usr/share/yate/skins/default/accountwizard_title.png
debian/tmp/usr/share/yate/skins/default/activ.png
debian/tmp/usr/share/yate/skins/default/add.png
debian/tmp/usr/share/yate/skins/default/add_hover.png
debian/tmp/usr/share/yate/skins/default/add_menu.png
debian/tmp/usr/share/yate/skins/default/add_pressed.png
debian/tmp/usr/share/yate/skins/default/addaccount_menu.png
debian/tmp/usr/share/yate/skins/default/addaccountwiz_menu.png
debian/tmp/usr/share/yate/skins/default/addchatroom_menu.png
debian/tmp/usr/share/yate/skins/default/addrbook_title.png
debian/tmp/usr/share/yate/skins/default/answer_20_hover.png
debian/tmp/usr/share/yate/skins/default/answer_20_pressed.png
debian/tmp/usr/share/yate/skins/default/archive_hover.png
debian/tmp/usr/share/yate/skins/default/archive_menu.png
debian/tmp/usr/share/yate/skins/default/archive_pressed.png
debian/tmp/usr/share/yate/skins/default/archive_title.png
debian/tmp/usr/share/yate/skins/default/call.png
debian/tmp/usr/share/yate/skins/default/call_hover.png
debian/tmp/usr/share/yate/skins/default/call_pressed.png
debian/tmp/usr/share/yate/skins/default/calls_tab.png
debian/tmp/usr/share/yate/skins/default/calls_tab_hover.png
debian/tmp/usr/share/yate/skins/default/calls_tab_pressed.png
debian/tmp/usr/share/yate/skins/default/cancel.png
debian/tmp/usr/share/yate/skins/default/cancel_hover.png
debian/tmp/usr/share/yate/skins/default/cancel_pressed.png
debian/tmp/usr/share/yate/skins/default/cancel_transfer_20.png
debian/tmp/usr/share/yate/skins/default/cancel_transfer_20_hover.png
debian/tmp/usr/share/yate/skins/default/cancel_transfer_20_pressed.png
debian/tmp/usr/share/yate/skins/default/cb_arrow.png
debian/tmp/usr/share/yate/skins/default/cdr_tab.png
debian/tmp/usr/share/yate/skins/default/cdr_tab_hover.png
debian/tmp/usr/share/yate/skins/default/cdr_tab_pressed.png
debian/tmp/usr/share/yate/skins/default/channel_conf_add.ui
debian/tmp/usr/share/yate/skins/default/channel_conf_item.ui
debian/tmp/usr/share/yate/skins/default/channel_item.ui
debian/tmp/usr/share/yate/skins/default/channel_transfer_item.ui
debian/tmp/usr/share/yate/skins/default/channel_transfer_start.ui
debian/tmp/usr/share/yate/skins/default/chat_menu.png
debian/tmp/usr/share/yate/skins/default/chat_tab.png
debian/tmp/usr/share/yate/skins/default/chat_tab_hover.png
debian/tmp/usr/share/yate/skins/default/chat_tab_pressed.png
debian/tmp/usr/share/yate/skins/default/chat_title.png
debian/tmp/usr/share/yate/skins/default/chatroomedit_title.png
debian/tmp/usr/share/yate/skins/default/checkbox_off.png
debian/tmp/usr/share/yate/skins/default/checkbox_on.png
debian/tmp/usr/share/yate/skins/default/checkmark_menu.png
debian/tmp/usr/share/yate/skins/default/clear_hover.png
debian/tmp/usr/share/yate/skins/default/clear_pressed.png
debian/tmp/usr/share/yate/skins/default/close_16.png
debian/tmp/usr/share/yate/skins/default/close_16_hover.png
debian/tmp/usr/share/yate/skins/default/close_16_pressed.png
debian/tmp/usr/share/yate/skins/default/conf_bg.png
debian/tmp/usr/share/yate/skins/default/conference_20_hover.png
debian/tmp/usr/share/yate/skins/default/conference_20_pressed.png
debian/tmp/usr/share/yate/skins/default/configure_menu.png
debian/tmp/usr/share/yate/skins/default/contactedit_title.png
debian/tmp/usr/share/yate/skins/default/contactinfo_title.png
debian/tmp/usr/share/yate/skins/default/contacts_tab.png
debian/tmp/usr/share/yate/skins/default/contacts_tab_hover.png
debian/tmp/usr/share/yate/skins/default/contacts_tab_pressed.png
debian/tmp/usr/share/yate/skins/default/delete.png
debian/tmp/usr/share/yate/skins/default/delete_hover.png
debian/tmp/usr/share/yate/skins/default/delete_menu.png
debian/tmp/usr/share/yate/skins/default/delete_pressed.png
debian/tmp/usr/share/yate/skins/default/dialpad_20.png
debian/tmp/usr/share/yate/skins/default/dialpad_20_hover.png
debian/tmp/usr/share/yate/skins/default/dialpad_20_pressed.png
debian/tmp/usr/share/yate/skins/default/dockedchat_title.png
debian/tmp/usr/share/yate/skins/default/down_small.png
debian/tmp/usr/share/yate/skins/default/down_small_off.png
debian/tmp/usr/share/yate/skins/default/edit_hover.png
debian/tmp/usr/share/yate/skins/default/edit_menu.png
debian/tmp/usr/share/yate/skins/default/edit_pressed.png
debian/tmp/usr/share/yate/skins/default/events_menu.png
debian/tmp/usr/share/yate/skins/default/events_title.png
debian/tmp/usr/share/yate/skins/default/file_trans.png
debian/tmp/usr/share/yate/skins/default/file_trans_menu.png
debian/tmp/usr/share/yate/skins/default/fileprogress_title.png
debian/tmp/usr/share/yate/skins/default/folder_16.png
debian/tmp/usr/share/yate/skins/default/folder_open_16.png
debian/tmp/usr/share/yate/skins/default/hangup_20_hover.png
debian/tmp/usr/share/yate/skins/default/hangup_20_pressed.png
debian/tmp/usr/share/yate/skins/default/help_title.png
debian/tmp/usr/share/yate/skins/default/hold_20_hover.png
debian/tmp/usr/share/yate/skins/default/hold_20_pressed.png
debian/tmp/usr/share/yate/skins/default/home_hover.png
debian/tmp/usr/share/yate/skins/default/home_pressed.png
debian/tmp/usr/share/yate/skins/default/incoming.png
debian/tmp/usr/share/yate/skins/default/info_menu.png
debian/tmp/usr/share/yate/skins/default/inputacccred_title.png
debian/tmp/usr/share/yate/skins/default/inputpwd_title.png
debian/tmp/usr/share/yate/skins/default/joinmucwizard_title.png
debian/tmp/usr/share/yate/skins/default/left.png
debian/tmp/usr/share/yate/skins/default/left_hover.png
debian/tmp/usr/share/yate/skins/default/left_pressed.png
debian/tmp/usr/share/yate/skins/default/muc_hover.png
debian/tmp/usr/share/yate/skins/default/muc_menu.png
debian/tmp/usr/share/yate/skins/default/muc_pressed.png
debian/tmp/usr/share/yate/skins/default/mucs_title.png
debian/tmp/usr/share/yate/skins/default/notif.png
debian/tmp/usr/share/yate/skins/default/notif_menu.png
debian/tmp/usr/share/yate/skins/default/notification.ui
debian/tmp/usr/share/yate/skins/default/ok_hover.png
debian/tmp/usr/share/yate/skins/default/ok_pressed.png
debian/tmp/usr/share/yate/skins/default/outgoing.png
debian/tmp/usr/share/yate/skins/default/phone_menu.png
debian/tmp/usr/share/yate/skins/default/phone_tab.png
debian/tmp/usr/share/yate/skins/default/phone_tab_hover.png
debian/tmp/usr/share/yate/skins/default/phone_tab_pressed.png
debian/tmp/usr/share/yate/skins/default/pointer.png
debian/tmp/usr/share/yate/skins/default/quest_hover.png
debian/tmp/usr/share/yate/skins/default/quest_pressed.png
debian/tmp/usr/share/yate/skins/default/quit.png
debian/tmp/usr/share/yate/skins/default/radio_off.png
debian/tmp/usr/share/yate/skins/default/radio_on.png
debian/tmp/usr/share/yate/skins/default/right.png
debian/tmp/usr/share/yate/skins/default/right_hover.png
debian/tmp/usr/share/yate/skins/default/right_pressed.png
debian/tmp/usr/share/yate/skins/default/room_subject.png
debian/tmp/usr/share/yate/skins/default/room_subject_hover.png
debian/tmp/usr/share/yate/skins/default/room_subject_pressed.png
debian/tmp/usr/share/yate/skins/default/save_hover.png
debian/tmp/usr/share/yate/skins/default/save_pressed.png
debian/tmp/usr/share/yate/skins/default/scroll_down.png
debian/tmp/usr/share/yate/skins/default/scroll_left.png
debian/tmp/usr/share/yate/skins/default/scroll_right.png
debian/tmp/usr/share/yate/skins/default/scroll_up.png
debian/tmp/usr/share/yate/skins/default/search.png
debian/tmp/usr/share/yate/skins/default/send_transfer_20.png
debian/tmp/usr/share/yate/skins/default/send_transfer_20_hover.png
debian/tmp/usr/share/yate/skins/default/send_transfer_20_pressed.png
debian/tmp/usr/share/yate/skins/default/sendchat_hover.png
debian/tmp/usr/share/yate/skins/default/sendchat_pressed.png
debian/tmp/usr/share/yate/skins/default/sendfile_menu.png
debian/tmp/usr/share/yate/skins/default/settings_title.png
debian/tmp/usr/share/yate/skins/default/stylesheet.css
debian/tmp/usr/share/yate/skins/default/stylesheet_mac.css
debian/tmp/usr/share/yate/skins/default/stylesheet_oswindows.css
debian/tmp/usr/share/yate/skins/default/trans_bg.png
debian/tmp/usr/share/yate/skins/default/transfer_20_hover.png
debian/tmp/usr/share/yate/skins/default/transfer_20_pressed.png
debian/tmp/usr/share/yate/skins/default/up_small.png
debian/tmp/usr/share/yate/skins/default/up_small_off.png
debian/tmp/usr/share/yate/skins/default/user_hover.png
debian/tmp/usr/share/yate/skins/default/user_menu.png
debian/tmp/usr/share/yate/skins/default/user_pressed.png
debian/tmp/usr/share/yate/skins/default/sendfile_20.png
debian/tmp/usr/share/yate/skins/default/sendfile_hover_20.png
debian/tmp/usr/share/yate/skins/default/sendfile_pressed_20.png
debian/tmp/usr/share/yate/skins/default/sharedfile_20.png
debian/tmp/usr/share/yate/skins/default/sharedfile_hover_20.png
debian/tmp/usr/share/yate/skins/default/sharedfile_menu.png
debian/tmp/usr/share/yate/skins/default/sharedfile_pressed_20.png
debian/tmp/usr/share/yate/skins/default/sharedfile_title.png
debian/tmp/usr/share/yate/skins/default/sharefile_20.png
debian/tmp/usr/share/yate/skins/default/sharefile_hover_20.png
debian/tmp/usr/share/yate/skins/default/sharefile_menu.png
debian/tmp/usr/share/yate/skins/default/sharefile_none_20.png
debian/tmp/usr/share/yate/skins/default/sharefile_none_hover_20.png
debian/tmp/usr/share/yate/skins/default/sharefile_none_pressed_20.png
debian/tmp/usr/share/yate/skins/default/sharefile_pressed_20.png
debian/tmp/usr/share/yate/skins/default/sharefile_title.png
debian/tmp/usr/share/yate/skins/default/status_away_menu.png
debian/tmp/usr/share/yate/skins/default/status_busy_menu.png
debian/tmp/usr/share/yate/skins/default/status_dnd_menu.png
debian/tmp/usr/share/yate/skins/default/status_offline_menu.png
debian/tmp/usr/share/yate/skins/default/status_online_menu.png
debian/tmp/usr/share/yate/skins/default/status_xa_menu.png
debian/tmp/usr/share/yate/skins/default/waiting_32.gif
debian/tmp/etc/yate/yate-qt4.conf
debian/tmp/usr/lib/yate/qt4/updater.yate
debian/tmp/etc/yate/fileinfo.conf
debian/tmp/usr/lib/yate/fileinfo.yate

3
debian/yate-sqlite.install vendored Normal file
View File

@ -0,0 +1,3 @@
debian/tmp/etc/yate/sqlitedb.conf
debian/tmp/usr/lib/yate/server/sqlitedb.yate

28
debian/yate-telhw.install vendored Normal file
View File

@ -0,0 +1,28 @@
## analog and isdn cards ##
debian/tmp/usr/lib/libyatesig.so.*
debian/tmp/usr/lib/libyatesig.so
debian/tmp/usr/lib/libyateasn.so.*
debian/tmp/usr/lib/libyateasn.so
debian/tmp/etc/yate/analog.conf
debian/tmp/usr/lib/yate/server/analog.yate
debian/tmp/etc/yate/wpcard.conf
debian/tmp/usr/lib/yate/server/tdmcard.yate
debian/tmp/etc/yate/tdmcard.conf
debian/tmp/usr/lib/yate/server/wpcard.yate
debian/tmp/etc/yate/zapcard.conf
debian/tmp/usr/lib/yate/server/zapcard.yate
debian/tmp/etc/yate/ysigchan.conf
debian/tmp/usr/lib/yate/server/ysigchan.yate
debian/tmp/etc/yate/ciscosm.conf
debian/tmp/usr/lib/yate/server/ciscosm.yate
debian/tmp/etc/yate/mgcpca.conf
debian/tmp/usr/lib/yate/server/mgcpca.yate
debian/tmp/etc/yate/sigtransport.conf
debian/tmp/usr/lib/yate/server/sigtransport.yate
debian/tmp/etc/yate/isupmangler.conf
debian/tmp/usr/lib/yate/sig/isupmangler.yate
debian/tmp/etc/yate/ss7_lnp_ansi.conf
debian/tmp/usr/lib/yate/sig/ss7_lnp_ansi.yate
debian/tmp/etc/yate/camel_map.conf
debian/tmp/usr/lib/yate/sig/camel_map.yate

38
debian/yate-telhw.postinst vendored Executable file
View File

@ -0,0 +1,38 @@
#!/bin/sh
# vim: set ts=4 sw=4 sts=4 et:
set -e
# summary of how this script can be called:
# * <postinst> `configure' <most-recently-configured-version>
# * <old-postinst> `abort-upgrade' <new version>
# * <conflictor's-postinst> `abort-remove' `in-favour' <package>
# <new-version>
# * <postinst> `abort-remove'
# * <deconfigured's-postinst> `abort-deconfigure' `in-favour'
# <failed-install-package> <version> `removing'
# <conflicting-package> <version>
# for details, see http://www.debian.org/doc/debian-policy/ or
# the debian-policy package
case "$1" in
configure)
/usr/sbin/usermod -a -G dialout yate
;;
abort-upgrade|abort-remove|abort-deconfigure)
;;
*)
echo "postinst called with unknown argument \`$1'" >&2
exit 1
;;
esac
# dh_installdeb will replace this with shell code automatically
# generated by other debhelper scripts.
#DEBHELPER#
exit 0

16
debian/yate.default vendored Normal file
View File

@ -0,0 +1,16 @@
# Defaults for yate initscript
# sourced by /etc/init.d/yate
# installed at /etc/default/yate by the maintainer scripts
#
# This is a POSIX shell fragment
#
# Paths
#DAEMON=/usr/bin/yate
#PIDFILE=/var/run/yate/yate.pid
#LOGFILE=/var/log/yate.log
# Extra Yate command line options
#OPTS="-C -Dz -rs -vvv"

160
debian/yate.init vendored Executable file
View File

@ -0,0 +1,160 @@
#!/bin/sh
#
# yate: Starts the Yet Another Telephony Engine
#
# chkconfig: 345 95 10
# description: Starts and stops YATE used as Telephony Server
#
# processname: yate
# pidfile: /var/run/yate/yate.pid
#
### BEGIN INIT INFO
# Provides: yate
# Required-Start: $local_fs $network
# Required-Stop: $local_fs $network
# Default-Start: 2 3 4 5
# Default-Stop: 0 1 6
# Short-Description: Yate server
# Description: Yet another telephony engine
### END INIT INFO
PATH=/sbin:/bin:/usr/sbin:/usr/bin
DESC="Yet another telephony engine"
NAME=yate
SCRIPTNAME=/etc/init.d/$NAME
DAEMON=/usr/bin/yate
PIDFILE=/var/run/${NAME}/${NAME}.pid
LOGFILE=/var/log/${NAME}.log
# Extra Yate command line options
OPTS="-C -Dz -rs -vvv"
# Exit if the package is not installed
[ -x "$DAEMON" ] || exit 0
# Read configuration variable file if it is present
[ -r /etc/default/$NAME ] && . /etc/default/$NAME
# Load the VERBOSE setting and other rcS variables
. /lib/init/vars.sh
# Define LSB log_* functions.
# Depend on lsb-base (>= 3.2-14) to ensure that this file is present
# and status_of_proc is working.
. /lib/lsb/init-functions
#
# Function that starts the daemon/service
#
do_start()
{
# Return
# 0 if daemon has been started
# 1 if daemon was already running
# 2 if daemon could not be started
unset DISPLAY
PIDDIR=`dirname ${PIDFILE}`
mkdir -p ${PIDDIR}
chown yate:yate ${PIDDIR}
touch $LOGFILE
chown yate:yate $LOGFILE
start-stop-daemon --start --quiet --pidfile $PIDFILE --exec $DAEMON --chuid yate:yate --test > /dev/null \
|| return 1
start-stop-daemon --start --quiet --pidfile $PIDFILE --exec $DAEMON --chuid yate:yate -- -d -p $PIDFILE -l $LOGFILE $OPTS \
|| return 2
# XXX Add code here, that waits for the process to be ready
# to handle requests. As a last resort, sleep for some time.
}
#
# Function that stops the daemon/service
#
do_stop()
{
# Return
# 0 if daemon has been stopped
# 1 if daemon was already stopped
# 2 if daemon could not be stopped
# other if a failure occurred
start-stop-daemon --stop --quiet --retry=TERM/30/KILL/5 --pidfile $PIDFILE --name $NAME
RETVAL="$?"
[ "$RETVAL" = 2 ] && return 2
# Wait for children to finish too if this is a daemon that forks
# and if the daemon is only ever run from this initscript.
# If the above conditions are not satisfied then add some other code
# that waits for the process to drop all resources that could be
# needed by services started subsequently. A last resort is to
# sleep for some time.
start-stop-daemon --stop --quiet --oknodo --retry=0/30/KILL/5 --exec $DAEMON
[ "$?" = 2 ] && return 2
# Many daemons don't delete their pidfiles when they exit.
rm -f $PIDFILE
return "$RETVAL"
}
#
# Function that sends a SIGHUP to the daemon/service
#
do_reload() {
start-stop-daemon --stop --signal 1 --quiet --pidfile $PIDFILE --name $NAME
#start-stop-daemon --stop --signal HUP --quiet --pidfile $PIDFILE --exec $DAEMON
return 0
}
# See how we were called.
case "$1" in
start)
[ "$VERBOSE" != no ] && log_daemon_msg "Starting $DESC" "$NAME"
do_start
case "$?" in
0|1) [ "$VERBOSE" != no ] && log_end_msg 0 ;;
2) [ "$VERBOSE" != no ] && log_end_msg 1 ;;
esac
;;
stop)
[ "$VERBOSE" != no ] && log_daemon_msg "Stopping $DESC" "$NAME"
do_stop
case "$?" in
0|1) [ "$VERBOSE" != no ] && log_end_msg 0 ;;
2) [ "$VERBOSE" != no ] && log_end_msg 1 ;;
esac
;;
reload|force-reload)
log_daemon_msg "Reloading $DESC" "$NAME"
do_reload
log_end_msg $?
;;
status)
status_of_proc "$DAEMON" "$NAME" && exit 0 || exit $?
;;
restart)
log_daemon_msg "Restarting $DESC" "$NAME"
do_stop
case "$?" in
0|1)
do_start
case "$?" in
0) log_end_msg 0 ;;
1) log_end_msg 1 ;; # Old process is still running
*) log_end_msg 1 ;; # Failed to start
esac
;;
*)
# Failed to stop
log_end_msg 1
;;
esac
;;
*)
echo "Usage: $SCRIPTNAME {start|stop|status|restart|reload|force-reload}" >&2
exit 3
;;
esac
exit 0
# vim: noexpandtab shiftwidth=8

94
debian/yate.install vendored Normal file
View File

@ -0,0 +1,94 @@
debian/tmp/usr/bin/yate
debian/tmp/usr/share/man/man8/yate.8
## scripts ##
debian/tmp/usr/share/yate/scripts/*.php
debian/tmp/usr/share/yate/scripts/*.py
debian/tmp/usr/share/yate/scripts/*.js
debian/tmp/usr/share/yate/scripts/*.sh
## server-only conf files ##
debian/tmp/etc/yate/pbxassist.conf
debian/tmp/usr/lib/yate/server/pbxassist.yate
debian/tmp/etc/yate/dbpbx.conf
debian/tmp/usr/lib/yate/server/dbpbx.yate
debian/tmp/etc/yate/lateroute.conf
debian/tmp/usr/lib/yate/server/lateroute.yate
debian/tmp/usr/lib/yate/server/park.yate
debian/tmp/etc/yate/queues.conf
debian/tmp/usr/lib/yate/server/queues.yate
debian/tmp/etc/yate/regfile.conf
debian/tmp/usr/lib/yate/server/regfile.yate
debian/tmp/etc/yate/accfile.conf
debian/tmp/usr/lib/yate/server/accfile.yate
debian/tmp/etc/yate/register.conf
debian/tmp/usr/lib/yate/server/register.yate
debian/tmp/etc/yate/yradius.conf
debian/tmp/usr/lib/yate/server/yradius.yate
debian/tmp/etc/yate/sipfeatures.conf
debian/tmp/usr/lib/yate/server/sipfeatures.yate
debian/tmp/etc/yate/heartbeat.conf
debian/tmp/usr/lib/yate/server/heartbeat.yate
debian/tmp/etc/yate/clustering.conf
debian/tmp/usr/lib/yate/server/clustering.yate
debian/tmp/usr/lib/libyatemgcp.so*
debian/tmp/etc/yate/mgcpgw.conf
debian/tmp/usr/lib/yate/server/mgcpgw.yate
debian/tmp/usr/lib/yate/server/mrcpspeech.yate
debian/tmp/usr/lib/yate/server/analogdetect.yate
debian/tmp/usr/lib/yate/server/dbwave.yate
debian/tmp/etc/yate/queuesnotify.conf
debian/tmp/usr/lib/yate/server/queuesnotify.yate
debian/tmp/etc/yate/callcounters.conf
debian/tmp/usr/lib/yate/server/callcounters.yate
debian/tmp/etc/yate/presence.conf
debian/tmp/usr/lib/yate/server/presence.yate
debian/tmp/etc/yate/subscription.conf
debian/tmp/usr/lib/yate/server/subscription.yate
debian/tmp/etc/yate/users.conf
debian/tmp/usr/lib/yate/server/users.yate
debian/tmp/etc/yate/jabberserver.conf
debian/tmp/usr/lib/yate/jabber/jabberserver.yate
debian/tmp/etc/yate/jbfeatures.conf
debian/tmp/usr/lib/yate/jabber/jbfeatures.yate
debian/tmp/etc/yate/ysnmpagent.conf
debian/tmp/usr/lib/yate/server/ysnmpagent.yate
debian/tmp/usr/share/yate/data/snmp_mib.conf
debian/tmp/usr/share/yate/data/NULL-TEAM-MIB.txt
debian/tmp/usr/share/yate/data/YATE-MIB.txt
debian/tmp/etc/yate/monitoring.conf
debian/tmp/usr/lib/yate/server/monitoring.yate
debian/tmp/etc/yate/cpuload.conf
debian/tmp/usr/lib/yate/server/cpuload.yate
debian/tmp/etc/yate/ccongestion.conf
debian/tmp/usr/lib/yate/server/ccongestion.yate
debian/tmp/usr/lib/yate/server/overlapdial.yate
debian/tmp/etc/yate/sip_cnam_lnp.conf
debian/tmp/usr/lib/yate/sip/sip_cnam_lnp.yate
debian/tmp/etc/yate/cache.conf
debian/tmp/usr/lib/yate/server/cache.yate
debian/tmp/etc/yate/eventlogs.conf
debian/tmp/usr/lib/yate/server/eventlogs.yate
debian/tmp/etc/yate/lksctp.conf
debian/tmp/usr/lib/yate/server/lksctp.yate
debian/tmp/usr/lib/yate/lazyrec.yate
debian/tmp/usr/lib/yate/faxchan.yate
debian/tmp/usr/lib/libyateradio.so.*

2
debian/yate.links vendored Normal file
View File

@ -0,0 +1,2 @@
/var/cache/yate/snmp_data.conf /etc/yate/snmp_data.conf

14
debian/yate.logrotate vendored Normal file
View File

@ -0,0 +1,14 @@
# Have to rotate the log file before it reaches 2GB in size
/var/log/yate.log {
size=100M
rotate 7
missingok
notifempty
sharedscripts
compress
create 640 yate yate
postrotate
[ -f /var/run/yate/yate.pid ] && kill -HUP `cat /var/run/yate/yate.pid`
endscript
}

61
debian/yate.postinst vendored Normal file
View File

@ -0,0 +1,61 @@
#!/bin/sh
# postinst script for yate
#
# see: dh_installdeb(1)
set -e
# summary of how this script can be called:
# * <postinst> `configure' <most-recently-configured-version>
# * <old-postinst> `abort-upgrade' <new version>
# * <conflictor's-postinst> `abort-remove' `in-favour' <package>
# <new-version>
# * <postinst> `abort-remove'
# * <deconfigured's-postinst> `abort-deconfigure' `in-favour'
# <failed-install-package> <version> `removing'
# <conflicting-package> <version>
# for details, see http://www.debian.org/doc/debian-policy/ or
# the debian-policy package
H=/var/lib/yate
P=/var/run/yate
C=/var/cache/yate
case "$1" in
configure)
if ! getent passwd yate >/dev/null; then
echo "Creating user 'yate' and group 'yate'..."
addgroup --system yate
adduser --system --ingroup yate --home $H --gecos "YATE daemon" --shell /bin/sh --disabled-password yate
fi
for DIR in $H $P $C
do
mkdir -p ${DIR}
dpkg-statoverride --list ${DIR} >/dev/null || chown yate:yate ${DIR}
done
if [ -e /var/log/yate -a ! -e /var/log/yate.log ]
then
/usr/bin/rename.ul -v yate yate.log /var/log/yate*
fi
;;
abort-upgrade|abort-remove|abort-deconfigure)
;;
*)
echo "postinst called with unknown argument \`$1'" >&2
exit 1
;;
esac
# dh_installdeb will replace this with shell code automatically
# generated by other debhelper scripts.
#DEBHELPER#
exit 0
# vim: ts=4 sw=4 sts=4 et

45
debian/yate.postrm vendored Normal file
View File

@ -0,0 +1,45 @@
#!/bin/sh
# postrm script for yate
#
# see: dh_installdeb(1)
#set -e
# summary of how this script can be called:
# * <postrm> `remove'
# * <postrm> `purge'
# * <old-postrm> `upgrade' <new-version>
# * <new-postrm> `failed-upgrade' <old-version>
# * <new-postrm> `abort-install'
# * <new-postrm> `abort-install' <old-version>
# * <new-postrm> `abort-upgrade' <old-version>
# * <disappearer's-postrm> `disappear' <overwriter>
# <overwriter-version>
# for details, see http://www.debian.org/doc/debian-policy/ or
# the debian-policy package
case "$1" in
remove|upgrade|failed-upgrade|abort-install|abort-upgrade|disappear)
;;
purge)
rm -rf /var/lib/yate /var/run/yate
deluser --system --quiet yate
delgroup --system --quiet yate
;;
*)
echo "postrm called with unknown argument \`$1'" >&2
exit 1
;;
esac
# dh_installdeb will replace this with shell code automatically
# generated by other debhelper scripts.
#DEBHELPER#
exit 0
# vim: ts=4 sw=4 sts=4 et

4
docs/.gitignore vendored
View File

@ -1,4 +0,0 @@
core*
*.orig
*~
.*.swp

3
docs/api/.gitignore vendored
View File

@ -1,3 +0,0 @@
core*
*.*
*~

8
engine/.gitignore vendored
View File

@ -1,8 +0,0 @@
Makefile
YateLocal*
core*
*.o
*.a
*.orig
*~
.*.swp

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -5,7 +5,7 @@
* Base64 data encoding and decoding
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing
@ -1333,17 +1333,28 @@ bool Module::setDebug(Message& msg, const String& target)
return false;
NamedCounter* counter = objectsCounter();
const String& line = msg[YSTRING("line")];
debugSet(line);
String str = line;
if (str.startSkip("level"))
;
else if (str == YSTRING("reset")) {
String str = msg.getValue("line");
if (str.startSkip("level")) {
int dbg = debugLevel();
str >> dbg;
if (str == "+") {
if (debugLevel() > dbg)
dbg = debugLevel();
}
else if (str == "-") {
if (debugLevel() < dbg)
dbg = debugLevel();
}
debugLevel(dbg);
}
else if (str == "reset") {
debugLevel(TelEngine::debugLevel());
debugEnabled(true);
if (counter)
counter->enable(getObjCounting());
}
else if (str.startSkip("objects")) {
bool dbg = (str == YSTRING("reset")) ? getObjCounting() : (counter && counter->enabled());
bool dbg = (str == "reset") ? getObjCounting() : (counter && counter->enabled());
str >> dbg;
if (counter)
counter->enable(dbg);

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -5,7 +5,7 @@
* Default client logic
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2020 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing
@ -22,159 +22,10 @@
#include <stdio.h>
#include <string.h>
#define MAX_DEPTH 3
using namespace TelEngine;
static unsigned int s_maxDepth = 3;
static int s_disableIncludeSilent = -1;
class ConfigurationPrivate
{
public:
enum Include {
IncludeNone = 0,
Include = 1,
IncludeSilent = 2,
IncludeRequire = 3,
};
inline ConfigurationPrivate(Configuration& cfg, bool isMain)
: m_cfg(cfg), m_main(isMain)
{}
inline void addingParam(const String& sect, const String& name, const String& value) {
if (!m_main || sect != YSTRING("configuration"))
return;
if (s_maxDepthInit && name == YSTRING("max_depth")) {
s_maxDepthInit = false;
s_maxDepth = value.toInteger(3,0,3,10);
}
else if (s_disableIncludeSilent < 0 && name == YSTRING("disable_include_silent"))
s_disableIncludeSilent = value.toBoolean() ? 1 : 0;
}
inline bool prepareIncludeSection(const String& sect, String& s, const char* file, bool warn,
bool& ok) {
int inc = getIncludeSect(s);
if (!inc)
return false;
NamedList* nl = sect ? m_cfg.getSection(sect) : 0;
if (nl) {
nl->addParam("[]",s);
if (!m_includeSections.find(nl))
m_includeSections.append(nl)->setDelete(false);
XDebug(DebugAll,"Config '%s' prepared section '%s' include '%s' file='%s'",
m_cfg.safe(),sect.safe(),s.safe(),(file == m_cfg.c_str() ? "<same>" : file));
}
else {
if (inc == IncludeRequire)
ok = false;
if (getWarn(warn,inc == IncludeSilent)) {
String tmp;
if (file != m_cfg.c_str())
tmp.printf(" in included file '%s'",file);
Debug(DebugNote,"Config '%s' found '%s' outside any section%s",
m_cfg.safe(),s.safe(),tmp.safe());
}
}
return true;
}
inline void processIncludeSections(bool warn, bool& ok) {
for (ObjList* o = m_includeSections.skipNull(); o; o = o->skipNext()) {
ObjList stack;
processInclude(static_cast<NamedList*>(o->get()),stack,warn,ok);
}
}
inline bool getWarn(bool warn, bool silent)
{ return (warn && silent) ? (s_disableIncludeSilent > 0) : warn; }
static inline int getIncludeSect(String& buf, bool setName = false) {
if (buf.startsWith("$includesection",true))
{ if (setName) buf = buf.substr(16,buf.length() - 16); return Include; }
if (buf.startsWith("$includesectionsilent",true))
{ if (setName) buf = buf.substr(22,buf.length() - 22); return IncludeSilent; }
if (buf.startsWith("$requiresection",true))
{ if (setName) buf = buf.substr(16,buf.length() - 16); return IncludeRequire; }
return 0;
}
static bool s_maxDepthInit;
private:
void processInclude(NamedList* sect, ObjList& stack, bool warn, bool& ok);
Configuration& m_cfg;
bool m_main;
ObjList m_includeSections;
ObjList m_includeSectProcessed;
};
bool ConfigurationPrivate::s_maxDepthInit = true;
void ConfigurationPrivate::processInclude(NamedList* sect, ObjList& stack, bool warn, bool& ok)
{
if (!sect || m_includeSectProcessed.find(sect))
return;
stack.append(sect)->setDelete(false);
#ifdef XDEBUG
String tmp;
tmp.append(stack," -> ");
Debug(DebugInfo,"Config '%s' processing include section stack: %s",
m_cfg.safe(),tmp.safe());
#endif
for (ObjList* o = sect->paramList()->skipNull(); o;) {
NamedString* s = static_cast<NamedString*>(o->get());
int inc = 0;
if ('[' == s->name()[0] && ']' == s->name()[1])
inc = getIncludeSect(*s,true);
if (!inc) {
o = o->skipNext();
continue;
}
Engine::runParams().replaceParams(*s);
if (*s) {
String error;
if (!stack[*s]) {
// NOTE: We are adding current section to processed after processing it
// Handle already processed sections whithout checking for recursive include
NamedList* incSect = static_cast<NamedList*>(m_includeSectProcessed[*s]);
if (!incSect) {
incSect = m_cfg.getSection(*s);
if (incSect && incSect != sect)
processInclude(incSect,stack,warn,ok);
else
error = incSect ? "recursive include" : "not found";
}
if (!error) {
XDebug(DebugAll,"Config '%s' including section '%s' in '%s'",
m_cfg.safe(),incSect->safe(),sect->safe());
for (ObjList* p = incSect->paramList()->skipNull(); p; p = p->skipNext()) {
NamedString* ns = static_cast<NamedString*>(p->get());
o->insert(new NamedString(ns->name(),*ns));
// Update current element (replaced by insert)
o = o->next();
}
}
}
else {
error.append(stack," -> ");
error = "recursive include stack=" + error;
}
if (error) {
if (inc == IncludeRequire)
ok = false;
if (getWarn(warn,inc == IncludeSilent))
Debug(DebugNote,"Config '%s' not including section '%s' in '%s': %s",
m_cfg.safe(),s->safe(),sect->safe(),error.c_str());
}
}
o->remove();
o = o->skipNull();
if (o)
continue;
sect->paramList()->compact();
break;
}
stack.remove(sect,false);
m_includeSectProcessed.insert(sect)->setDelete(false);
}
// Text sort callback
static int textSort(GenObject* obj1, GenObject* obj2, void* context)
{
@ -189,12 +40,11 @@ static int textSort(GenObject* obj1, GenObject* obj2, void* context)
Configuration::Configuration()
: m_main(false)
{
}
Configuration::Configuration(const char* filename, bool warn)
: String(filename), m_main(false)
: String(filename)
{
load(warn);
}
@ -335,8 +185,7 @@ bool Configuration::load(bool warn)
m_sections.clear();
if (null())
return false;
ConfigurationPrivate priv(*this,m_main);
return loadFile(c_str(),"",0,warn,&priv);
return loadFile(c_str(),"",0,warn);
}
static inline char* cfgReadLine(FILE* f, char* buf, int rd,
@ -391,14 +240,12 @@ static inline char* cfgReadLine(FILE* f, char* buf, int rd,
return pc;
}
bool Configuration::loadFile(const char* file, String sect, unsigned int depth, bool warn, void* priv)
bool Configuration::loadFile(const char* file, String sect, unsigned int depth, bool warn)
{
ConfigurationPrivate& cfg = *(ConfigurationPrivate*)priv;
DDebug(DebugInfo,"Configuration::loadFile(\"%s\",[%s],%u,%s)",
file,sect.c_str(),depth,String::boolText(warn));
if (depth > s_maxDepth) {
Debug(DebugWarn,"Config '%s' refusing to load config file '%s' at include depth %u",
c_str(),file,depth);
if (depth > MAX_DEPTH) {
Debug(DebugWarn,"Refusing to open config file '%s' at include depth %u",file,depth);
return false;
}
FILE *f = ::fopen(file,"r");
@ -453,12 +300,8 @@ bool Configuration::loadFile(const char* file, String sect, unsigned int depth,
}
if (!enabled)
continue;
if (cfg.prepareIncludeSection(sect,s,file,warn,ok))
continue;
bool noerr = false;
bool silent = false;
if (s.startSkip("$require") || (noerr = s.startSkip("$include"))
|| (silent = noerr = s.startSkip("$includesilent"))) {
if (s.startSkip("$require") || (noerr = s.startSkip("$include"))) {
Engine::runParams().replaceParams(s);
String path;
if (!s.startsWith(Engine::pathSeparator())) {
@ -483,7 +326,6 @@ bool Configuration::loadFile(const char* file, String sect, unsigned int depth,
}
path << s;
ObjList files;
bool doWarn = cfg.getWarn(warn,silent);
if (File::listDirectory(path,0,&files)) {
path << Engine::pathSeparator();
DDebug(DebugAll,"Configuration loading up to %u files from '%s'",
@ -492,7 +334,7 @@ bool Configuration::loadFile(const char* file, String sect, unsigned int depth,
while (String* it = static_cast<String*>(files.remove(false))) {
if (!(it->startsWith(".") || it->endsWith("~")
|| it->endsWith(".bak") || it->endsWith(".tmp")))
ok = (loadFile(path + *it,sect,depth+1,doWarn,priv) || noerr) && ok;
ok = (loadFile(path + *it,sect,depth+1,warn) || noerr) && ok;
#ifdef DEBUG
else
Debug(DebugAll,"Configuration skipping over file '%s'",it->c_str());
@ -501,7 +343,7 @@ bool Configuration::loadFile(const char* file, String sect, unsigned int depth,
}
}
else
ok = (loadFile(path,sect,depth+1,doWarn,priv) || noerr) && ok;
ok = (loadFile(path,sect,depth+1,warn) || noerr) && ok;
continue;
}
Engine::runParams().replaceParams(s);
@ -529,20 +371,16 @@ bool Configuration::loadFile(const char* file, String sect, unsigned int depth,
break;
s += pc;
}
s.trimBlanks();
cfg.addingParam(sect,key,s);
addValue(sect,key,s);
addValue(sect,key,s.trimBlanks());
}
::fclose(f);
if (!depth)
cfg.processIncludeSections(warn,ok);
return ok;
}
if (warn) {
int err = errno;
if (depth)
Debug(DebugNote,"Config '%s' failed to open included config file '%s' (%d: %s)",
c_str(),file,err,strerror(err));
Debug(DebugNote,"Failed to open included config file '%s' (%d: %s)",
file,err,strerror(err));
else
Debug(DebugNote,"Failed to open config file '%s', using defaults (%d: %s)",
file,err,strerror(err));

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing
@ -77,14 +77,6 @@ static InitG711 s_initG711;
static const DataBlock s_empty;
static inline void* dbAlloc(unsigned int n, void* oldBuf = 0)
{
void* data = ::realloc(oldBuf,n);
if (!data)
Debug("DataBlock",DebugFail,"realloc(%u) returned NULL!",n);
return data;
}
const DataBlock& DataBlock::empty()
{
return s_empty;
@ -130,7 +122,6 @@ void* DataBlock::getObject(const String& name) const
void DataBlock::clear(bool deleteData)
{
m_length = 0;
m_allocated = 0;
if (m_data) {
void *data = m_data;
m_data = 0;
@ -139,91 +130,6 @@ void DataBlock::clear(bool deleteData)
}
}
// Change (insert or append data) the current block
bool DataBlock::change(unsigned int pos, const void* buf, unsigned int bufLen,
unsigned int extra, int extraVal, bool mayOverlap)
{
unsigned int addLen = (buf ? bufLen : 0) + extra;
if (!addLen)
return true;
XDebug("DataBlock",DebugAll,
"change(%u,%p,%u,%d,%d,%u) add_lenlen=%u m_data=%p m_length=%u allocated=%u [%p]",
pos,buf,bufLen,extra,extraVal,mayOverlap,addLen,m_data,m_length,m_allocated,this);
if (!(buf && bufLen)) {
buf = 0;
bufLen = 0;
}
if (pos > m_length)
pos = m_length;
unsigned int newLen = m_length + addLen;
void* data = 0;
unsigned int aLen = 0;
// Allocate a new buffer if input data may overlap with existing
bool overlap = buf && (mayOverlap || buf == m_data);
if (!m_data || overlap || newLen > m_allocated) {
aLen = allocLen(newLen);
// Append to existing: Realloc data. Avoid free
void* reallocAppend = (!overlap && pos == m_length) ? m_data : 0;
data = dbAlloc(aLen,reallocAppend);
if (!data)
return false;
if (reallocAppend)
clear(false);
else
copyData(data,m_data,m_length,pos,addLen);
}
else {
moveData(m_data,m_length,pos,addLen);
data = m_data;
}
if (bufLen)
::memcpy((uint8_t*)data + pos,buf,bufLen);
if (extra)
::memset((uint8_t*)data + pos + bufLen,extraVal,extra);
if (aLen)
assign(data,newLen,false,aLen);
else
m_length = newLen;
return true;
}
#define DB_CHANGE_UINT_FUNC \
unsigned int n = 0; \
if (lsb) { \
while (len--) { \
buf[n++] = (uint8_t)value; \
value = value >> 8; \
} \
} \
else { \
uint8_t sh = (len - 1) * 8; \
while (len--) { \
buf[n++] = (uint8_t)(value >> sh); \
sh -= 8; \
} \
} \
return change(pos,(const void*)buf,n,0,0,false)
bool DataBlock::change8(unsigned int pos, uint64_t value, unsigned int len, bool lsb)
{
if (!len)
return true;
if (len > 8)
len = 8;
uint8_t buf[8] = {0,0,0,0,0,0,0,0};
DB_CHANGE_UINT_FUNC;
}
bool DataBlock::change4(unsigned int pos, uint32_t value, unsigned int len, bool lsb)
{
if (!len)
return true;
if (len > 4)
len = 4;
uint8_t buf[4] = {0,0,0,0};
DB_CHANGE_UINT_FUNC;
}
DataBlock& DataBlock::assign(void* value, unsigned int len, bool copyData, unsigned int allocated)
{
if ((value != m_data) || (len != m_length)) {
@ -292,6 +198,76 @@ DataBlock& DataBlock::operator=(const DataBlock& value)
return *this;
}
void DataBlock::append(const DataBlock& value)
{
if (m_length) {
if (value.length()) {
unsigned int len = m_length+value.length();
if (len <= m_allocated) {
::memcpy(m_length+(char*)m_data,value.data(),value.length());
m_length = len;
return;
}
unsigned int aLen = allocLen(len);
void *data = ::malloc(aLen);
if (data) {
::memcpy(data,m_data,m_length);
::memcpy(m_length+(char*)data,value.data(),value.length());
assign(data,len,false,aLen);
}
else
Debug("DataBlock",DebugFail,"malloc(%d) returned NULL!",aLen);
}
}
else
assign(value.data(),value.length());
}
void DataBlock::append(const String& value)
{
if (m_length) {
if (value.length()) {
unsigned int len = m_length+value.length();
if (len <= m_allocated) {
::memcpy(m_length+(char*)m_data,value.safe(),value.length());
m_length = len;
return;
}
unsigned int aLen = allocLen(len);
void *data = ::malloc(aLen);
if (data) {
::memcpy(data,m_data,m_length);
::memcpy(m_length+(char*)data,value.safe(),value.length());
assign(data,len,false,aLen);
}
else
Debug("DataBlock",DebugFail,"malloc(%d) returned NULL!",aLen);
}
}
else
assign((void*)value.c_str(),value.length());
}
void DataBlock::insert(const DataBlock& value)
{
unsigned int vl = value.length();
if (m_length) {
if (vl) {
unsigned int len = m_length+vl;
void *data = ::malloc(len);
if (data) {
::memcpy(data,value.data(),vl);
::memcpy(vl+(char*)data,m_data,m_length);
assign(data,len,false);
}
else
Debug("DataBlock",DebugFail,"malloc(%d) returned NULL!",len);
}
}
else
assign(value.data(),vl);
}
unsigned int DataBlock::allocLen(unsigned int len) const
{
// allocate a multiple of 8 bytes
@ -390,24 +366,60 @@ inline signed char hexDecode(char c)
return -1;
}
static inline bool retResult(bool ok, int result, int* res)
{
if (res)
*res = result;
return ok;
}
// Change data from a hexadecimal string representation.
// Build this data block from a hexadecimal string representation.
// Each octet must be represented in the input string with 2 hexadecimal characters.
// If a separator is specified, the octets in input string must be separated using
// exactly 1 separator. Only 1 leading or 1 trailing separators are allowed
bool DataBlock::changeHex(unsigned int pos, const char* data, unsigned int len, char sep,
bool guessSep, bool emptyOk, int* res)
bool DataBlock::unHexify(const char* data, unsigned int len, char sep)
{
clear();
if (!(data && len))
return retResult(emptyOk,0,res);
return true;
if (!sep && guessSep && len > 2) {
// Calculate the destination buffer length
unsigned int n = 0;
if (!sep) {
if (0 != (len % 2))
return false;
n = len / 2;
}
else {
// Remove leading and trailing separators
if (data[0] == sep) {
data++;
len--;
}
if (len && data[len-1] == sep)
len--;
// No more leading and trailing separators allowed
if (2 != (len % 3))
return (bool)(len == 0);
n = (len + 1) / 3;
}
if (!n)
return true;
char* buf = (char*)::malloc(n);
unsigned int iBuf = 0;
for (unsigned int i = 0; i < len; i += (sep ? 3 : 2)) {
signed char c1 = hexDecode(data[i]);
signed char c2 = hexDecode(data[i+1]);
if (c1 == -1 || c2 == -1 || (sep && (iBuf != n - 1) && (sep != data[i+2])))
break;
buf[iBuf++] = (c1 << 4) | c2;
}
if (iBuf >= n)
assign(buf,n,false);
else
::free(buf);
return (iBuf >= n);
}
// This variant of unHexify automatically detects presence of separators
bool DataBlock::unHexify(const char* data, unsigned int len)
{
char sep = 0;
if (len > 2) {
const char* s = " :;.,-/|";
while (char c = *s++) {
unsigned int offs = 2;
@ -419,140 +431,38 @@ bool DataBlock::changeHex(unsigned int pos, const char* data, unsigned int len,
}
}
}
// Calculate the destination buffer length
unsigned int n = 0;
if (!sep) {
if (0 != (len % 2))
return retResult(false,-3,res);
n = len / 2;
}
else {
// Remove leading and trailing separators
if (data[0] == sep) {
data++;
len--;
}
if (len && data[len - 1] == sep)
len--;
// No more leading and trailing separators allowed
if (!len)
return retResult(emptyOk,0,res);
if (2 != (len % 3))
return retResult(false,-3,res);
n = (len + 1) / 3;
}
if (!n)
return retResult(emptyOk,0,res);
unsigned int newLen = m_length + n;
unsigned int aLen = allocLen(newLen);
void* newData = dbAlloc(aLen);
if (!newData)
return retResult(false,-1,res);
if (pos > m_length)
pos = m_length;
char* buf = (char*)newData + pos;
unsigned int iBuf = 0;
for (unsigned int i = 0; i < len; i += (sep ? 3 : 2)) {
signed char c1 = hexDecode(*data++);
signed char c2 = hexDecode(*data++);
if (c1 == -1 || c2 == -1 || (sep && (iBuf != n - 1) && (sep != *data++)))
break;
buf[iBuf++] = (c1 << 4) | c2;
}
if (iBuf < n) {
::free(newData);
return retResult(false,-2,res);
}
copyData(newData,m_data,m_length,pos,n);
assign(newData,newLen,false,aLen);
return retResult(true,n,res);
return unHexify(data,len,sep);
}
static inline bool dbIsEscape(char c, char extraEsc)
String DataBlock::sqlEscape(char extraEsc) const
{
return c == '\0' || c == '\r' || c == '\n' || c == '\\' || c == '\'' || c == extraEsc;
}
String& DataBlock::sqlEscape(String& str, const void* data, unsigned int len, char extraEsc)
{
if (!(data && len))
return str;
unsigned int useLen = len;
char* ds = (char*)data;
for (unsigned int i = 0; i < len; i++) {
if (dbIsEscape(*ds++,extraEsc))
useLen++;
unsigned int len = m_length;
unsigned int i;
for (i = 0; i < m_length; i++) {
char c = static_cast<char*>(m_data)[i];
if (c == '\0' || c == '\r' || c == '\n' || c == '\\' || c == '\'' || c == extraEsc)
len++;
}
// No escape needed ?
if (useLen == len)
return str.append((const char*)data,len);
unsigned int sLen = str.length();
str.append(' ',useLen);
char* d = ((char*)(str.c_str())) + sLen;
ds = (char*)data;
for (unsigned int i = 0; i < len; i++) {
char c = *ds++;
if (dbIsEscape(c,extraEsc)) {
String tmp(' ',len);
char* d = const_cast<char*>(tmp.c_str());
for (i = 0; i < m_length; i++) {
char c = static_cast<char*>(m_data)[i];
if (c == '\0' || c == '\r' || c == '\n' || c == '\\' || c == '\'' || c == extraEsc)
*d++ = '\\';
switch (c) {
case '\0':
c = '0';
break;
case '\r':
c = 'r';
break;
case '\n':
c = 'n';
break;
}
switch (c) {
case '\0':
c = '0';
break;
case '\r':
c = 'r';
break;
case '\n':
c = 'n';
break;
}
*d++ = c;
}
return str;
}
void DataBlock::moveData(void* buf, unsigned int len, unsigned int pos, unsigned int space)
{
if (!buf || pos >= len)
return;
unsigned int delta = pos + space;
if (!delta)
return;
uint8_t* src = (uint8_t*)buf;
uint8_t* dest = (uint8_t*)buf + delta;
if (pos) {
// Insert middle. Keep old data until pos. Copy the rest
len -= pos;
src += pos;
}
if (delta < len)
::memmove(dest,src,len);
else
::memcpy(dest,src,len);
}
void DataBlock::copyData(void* dest, const void* src, unsigned int len, unsigned int pos,
unsigned int space)
{
if (!(src && dest && len))
return;
uint8_t* d = (uint8_t*)dest;
const uint8_t* s = (const uint8_t*)src;
if (!pos)
// Data insert before existing, copy old data after it
::memcpy(d + space,s,len);
else if (pos == len)
// Data added to existing, copy old at start
::memcpy(d,s,len);
else if (space) {
// Insert middle
::memcpy(d,s,pos);
::memcpy(d + pos + space,s + pos,len - pos);
}
else
::memcpy(d,s,len);
return tmp;
}
/* vi: set ts=8 sw=4 sts=4 noet: */

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing
@ -44,7 +44,6 @@ static const FormatInfo s_formats[] = {
FormatInfo("ilbc30", 50, 30000),
// FormatInfo("speex", 0),
FormatInfo("g729", 10, 10000),
FormatInfo("clearmode", 80, 20000, "data", 0, 1, false),
FormatInfo("plain", 0, 0, "text", 0),
FormatInfo("raw", 0, 0, "data", 0),
};

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2020 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing
@ -305,7 +305,6 @@ static int s_exit = -1;
unsigned int Engine::s_congestion = 0;
static Mutex s_congMutex(false,"Congestion");
static bool s_debug = true;
static NamedList s_debugInit("");
static bool s_capture = CAPTURE_EVENTS;
static int s_maxevents = 25;
static Mutex s_eventsMutex(false,"EventsList");
@ -544,35 +543,11 @@ bool EngineStatusHandler::received(Message &msg)
objects(msg.retValue(),details);
return true;
}
if (sel.startSkip("dispatcher")) {
bool byMsg = sel.startSkip("handlers");
if ((byMsg || sel.startSkip("handlers-trackname")) && sel) {
String str;
unsigned int count = 0;
unsigned int total = 0;
MessageDispatcher* d = Engine::dispatcher();
if (d) {
if (sel[0] == '^')
count = d->fillHandlersInfo(byMsg,Regexp(sel),details ? &str : 0,&total);
else
count = d->fillHandlersInfo(byMsg,sel,details ? &str : 0,&total);
}
msg.retValue()
<< "name=dispatcher,type=system,format=Priority|TrackName|Filtered;"
<< "handlers=" << total << ",count=" << count;
if (details)
msg.retValue() << ';' << str;
msg.retValue() << "\r\n";
return true;
}
return false;
}
return false;
}
msg.retValue() << "name=engine,type=system";
msg.retValue() << ",version=" << YATE_VERSION;
msg.retValue() << ",revision=" << YATE_REVISION;
msg.retValue() << ",githash=" << YATE_GIT_HASH;
msg.retValue() << ",nodename=" << Engine::nodeName();
msg.retValue() << ";plugins=" << plugins.count();
msg.retValue() << ",inuse=" << Engine::self()->usedPlugins();
@ -674,8 +649,6 @@ static const char s_runpOpt[] = " runparam name=value\r\n";
static const char s_runpMsg[] = "Add a new parameter to the Engine's runtime list\r\n";
static const char s_dispatcherOpt[] = " dispatcher {trace_msg_time|trace_msg_handler_time} <on|off>\r\n";
static const char s_dispatcherMsg[] = "Enable or disable dispatcher debugging options\r\n";
static const char s_dispatcherStatusOpt[] = " status dispatcher {handlers|handlers-trackname} <match>\r\n";
static const char s_dispatcherStatusMsg[] = "Show installed handlers by message name or track name. Matching value starting with ^ is handled as basic regular expression\r\n";
// get the base name of a module file
static String moduleBase(const String& fname)
@ -778,32 +751,27 @@ void completeModule(String& ret, const String& part, ObjList& mods, bool reload,
void EngineCommand::doCompletion(Message &msg, const String& partLine, const String& partWord)
{
if (partLine.null() || (partLine == YSTRING("help"))) {
completeOne(msg.retValue(),YSTRING("module"),partWord);
completeOne(msg.retValue(),YSTRING("events"),partWord);
completeOne(msg.retValue(),YSTRING("logview"),partWord);
completeOne(msg.retValue(),YSTRING("runparam"),partWord);
completeOne(msg.retValue(),YSTRING("dispatcher"),partWord);
completeOne(msg.retValue(),"module",partWord);
completeOne(msg.retValue(),"events",partWord);
completeOne(msg.retValue(),"logview",partWord);
completeOne(msg.retValue(),"runparam",partWord);
completeOne(msg.retValue(),"dispatcher",partWord);
}
else if (partLine == YSTRING("status")) {
completeOne(msg.retValue(),YSTRING("engine"),partWord);
completeOne(msg.retValue(),YSTRING("objects"),partWord);
completeOne(msg.retValue(),YSTRING("dispatcher"),partWord);
completeOne(msg.retValue(),"engine",partWord);
completeOne(msg.retValue(),"objects",partWord);
}
else if (partLine == YSTRING("status objects")) {
for (ObjList* l = getObjCounters().skipNull();l;l = l->skipNext())
completeOne(msg.retValue(),l->get()->toString(),partWord);
}
else if (partLine == YSTRING("status dispatcher")) {
completeOne(msg.retValue(),YSTRING("handlers"),partWord);
completeOne(msg.retValue(),YSTRING("handlers-trackname"),partWord);
}
else if (partLine == YSTRING("module")) {
completeOne(msg.retValue(),YSTRING("load"),partWord);
completeOne(msg.retValue(),"load",partWord);
if (!s_nounload) {
completeOne(msg.retValue(),YSTRING("unload"),partWord);
completeOne(msg.retValue(),YSTRING("reload"),partWord);
completeOne(msg.retValue(),"unload",partWord);
completeOne(msg.retValue(),"reload",partWord);
}
completeOne(msg.retValue(),YSTRING("list"),partWord);
completeOne(msg.retValue(),"list",partWord);
}
else if (partLine == YSTRING("module load"))
completeModule(msg.retValue(),partWord,Engine::self()->m_libs,false);
@ -828,29 +796,28 @@ void EngineCommand::doCompletion(Message &msg, const String& partLine, const Str
const EngineEventList* e = static_cast<const EngineEventList*>(l->get());
completeOne(msg.retValue(),e->toString(),partWord);
}
completeOne(msg.retValue(),YSTRING("log"),partWord);
completeOne(msg.retValue(),"log",partWord);
if (partLine == YSTRING("events"))
completeOne(msg.retValue(),YSTRING("clear"),partWord);
completeOne(msg.retValue(),"clear",partWord);
}
else if (partLine == YSTRING("dispatcher")) {
completeOne(msg.retValue(),YSTRING("trace_msg_time"),partWord);
completeOne(msg.retValue(),YSTRING("trace_msg_handler_time"),partWord);
completeOne(msg.retValue(),"trace_msg_time",partWord);
completeOne(msg.retValue(),"trace_msg_handler_time",partWord);
}
else if ((partLine == YSTRING("dispatcher trace_msg_time"))
|| (partLine == YSTRING("dispatcher trace_msg_handler_time"))) {
completeOne(msg.retValue(),YSTRING("on"),partWord);
completeOne(msg.retValue(),YSTRING("off"),partWord);
completeOne(msg.retValue(),"on",partWord);
completeOne(msg.retValue(),"off",partWord);
}
}
bool EngineCommand::received(Message &msg)
{
const String& l = msg[YSTRING("line")];
if (!l) {
String line = msg.getValue("line");
if (line.null()) {
doCompletion(msg,msg.getValue("partline"),msg.getValue("partword"));
return false;
}
String line = l;
if (line.startSkip("control")) {
int pos = line.find(' ');
String id = line.substr(0,pos).trimBlanks();
@ -914,19 +881,17 @@ bool EngineCommand::received(Message &msg)
}
return false;
}
if (line.startSkip("dispatcher")) {
bool traceMsgTime = line.startSkip("trace_msg_time");
if (traceMsgTime || line.startSkip("trace_msg_handler_time")) {
MessageDispatcher* d = Engine::dispatcher();
if (d) {
if (traceMsgTime)
d->traceTime(line.toBoolean());
else
d->traceHandlerTime(line.toBoolean());
return true;
}
}
return false;
if (line.startSkip("dispatcher trace_msg_time")) {
MessageDispatcher* d = Engine::dispatcher();
if (d)
d->traceTime(line.toBoolean());
return 0 != d;
}
if (line.startSkip("dispatcher trace_msg_handler_time")) {
MessageDispatcher* d = Engine::dispatcher();
if (d)
d->traceHandlerTime(line.toBoolean());
return 0 != d;
}
return false;
}
@ -1007,8 +972,7 @@ bool EngineHelp::received(Message &msg)
else if (line == YSTRING("runparam"))
msg.retValue() << s_runpOpt << s_runpMsg;
else if (line == YSTRING("dispatcher"))
msg.retValue() << s_dispatcherOpt << s_dispatcherMsg
<< s_dispatcherStatusOpt << s_dispatcherStatusMsg;
msg.retValue() << s_dispatcherOpt << s_dispatcherMsg;
else
return false;
return true;
@ -1619,7 +1583,7 @@ int Engine::engineInit()
#endif
CapturedEvent::capturing(s_capture);
s_cfg = configFile(s_cfgfile);
s_cfg.loadMain();
s_cfg.load();
s_capture = s_cfg.getBoolValue("general","startevents",s_capture);
CapturedEvent::capturing(s_capture);
if (s_capture && s_startMsg)
@ -1790,9 +1754,6 @@ int Engine::engineInit()
}
// Reload configuration file so conditionals will take into account runtime parameters
s_cfg.load();
NamedList* sect = s_cfg.getSection(YSTRING("debug"));
if (sect)
s_debugInit.copyParams(false,*sect);
vars = s_cfg.getSection("variables");
if (vars) {
unsigned int n = vars->length();
@ -1898,14 +1859,18 @@ int Engine::run()
if (s_debug) {
// one-time sending of debug setup messages
s_debug = false;
for (ObjList* o = s_debugInit.paramList()->skipNull(); o; o = o->skipNext()) {
const NamedString* str = static_cast<NamedString*>(o->get());
if (!(str->name() && *str))
continue;
Message* m = new Message("engine.debug");
m->addParam("module",str->name());
m->addParam("line",*str);
enqueue(m);
const NamedList* sect = s_cfg.getSection("debug");
if (sect) {
unsigned int n = sect->length();
for (unsigned int i = 0; i < n; i++) {
const NamedString* str = sect->getParam(i);
if (!(str && str->name() && *str))
continue;
Message* m = new Message("engine.debug");
m->addParam("module",str->name());
m->addParam("line",*str);
enqueue(m);
}
}
}
else if (s_capture) {
@ -2313,8 +2278,6 @@ void Engine::initPlugins()
for (; l; l = l->skipNext()) {
Plugin *p = static_cast<Plugin *>(l->get());
TempObjectCounter cnt(p->objectsCounter(),true);
if (s_debug)
p->debugSet(s_debugInit[p->toString()]);
p->initialize();
if (exiting()) {
Output("Initialization aborted, exiting...");
@ -2600,7 +2563,6 @@ void Engine::initLibrary(const String& line, String* output)
ENGINE_SET_VAL_BREAK('s',s_lateabrt,true);
ENGINE_INSTR_BREAK('m',setLockableWait());
ENGINE_INSTR_BREAK('d',Lockable::enableSafety());
ENGINE_INSTR_BREAK('r',RWLock::disableRWLock(true));
default:
unkArgs.append("-D" + String(*pc)," ");
}
@ -2939,9 +2901,6 @@ int Engine::main(int argc, const char** argv, const char** env, RunMode mode, En
case 'd':
Lockable::enableSafety();
break;
case 'r':
RWLock::disableRWLock(true);
break;
#ifdef RTLD_GLOBAL
case 'l':
s_localsymbol = true;

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* Idea and initial implementation (as HashTable) by Maciek Kaminski
*

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2013-2023 Null Team
* Copyright (C) 2013-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -115,7 +115,7 @@ Thread.o: @srcdir@/Thread.cpp $(MKDEPS) $(CINC)
$(COMPILE) @THREAD_KILL@ @THREAD_AFFINITY@ @HAVE_PRCTL@ -c $<
TelEngine.o: @srcdir@/TelEngine.cpp $(MKDEPS) $(CINC)
$(COMPILE) @HAVE_GMTOFF@ @HAVE_INT_TZ@ -c $<
$(COMPILE) @ATOMIC_OPS@ @HAVE_GMTOFF@ @HAVE_INT_TZ@ -c $<
Client.o: @srcdir@/Client.cpp $(MKDEPS) $(CLINC)
$(COMPILE) -c $<

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2015-2023 Null Team
* Copyright (C) 2015 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing
@ -57,14 +57,10 @@ static inline void unpackMsb8(uint8_t*& d, uint8_t val)
}
// Copy string, advance dest and src, return src
static inline const char* copyInc(char*& dest, const char* src, unsigned int n,
bool strLen = false)
static inline const char* copyInc(char*& dest, const char* src, unsigned int n)
{
if (n) {
if (strLen)
::strcpy(dest,src);
else
::strncpy(dest,src,n);
::strncpy(dest,src,n);
dest += n;
}
return src + n;
@ -104,11 +100,11 @@ String& RefStorage::dumpSplit(String& buf, const String& str, unsigned int lineL
const char* src = str.c_str();
src = copyInc(dest,src,firstLineLen);
for (; nFullLines; nFullLines--) {
copyInc(dest,linePrefix,linePrefLen,true);
copyInc(dest,linePrefix,linePrefLen);
src = copyInc(dest,src,lineLen);
}
if (lastLineLen) {
copyInc(dest,linePrefix,linePrefLen,true);
copyInc(dest,linePrefix,linePrefLen);
src = copyInc(dest,src,lastLineLen);
}
copyInc(dest,suffix,suffixLen);

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing
@ -237,8 +237,8 @@ int Message::commonDecode(const char* str, int offs)
MessageHandler::MessageHandler(const char* name, unsigned priority,
const char* trackName, bool addPriority)
: String(name),
m_trackName(trackName), m_trackNameOnly(trackName), m_priority(priority),
m_dispatcher(0), m_filter(0), m_counter(0)
m_trackName(trackName), m_priority(priority),
m_unsafe(0), m_dispatcher(0), m_filter(0), m_filterRegexp(0), m_counter(0)
{
DDebug(DebugAll,"MessageHandler::MessageHandler('%s',%u,'%s',%s) [%p]",
name,priority,trackName,String::boolText(addPriority),this);
@ -271,12 +271,9 @@ void MessageHandler::destruct()
void MessageHandler::safeNowInternal()
{
WLock lck(m_dispatcher ? &m_dispatcher->handlersLock() : 0);
Lock lock(m_dispatcher);
// when the unsafe counter reaches zero we're again safe to destroy
int v = --m_unsafe;
if (v < 0)
Debug(DebugFail,"MessageHandler(%s) unsafe=%d dispatcher=(%p) [%p]",
safe(),v,m_dispatcher,this);
m_unsafe--;
}
bool MessageHandler::receivedInternal(Message& msg)
@ -288,23 +285,19 @@ bool MessageHandler::receivedInternal(Message& msg)
void MessageHandler::setFilter(NamedString* filter)
{
Regexp* r = YOBJECT(Regexp,filter);
if (r)
setFilter(new MatchingItemRegexp(filter->name(),*r));
else if (filter)
setFilter(new MatchingItemString(filter->name(),*filter));
else
clearFilter();
TelEngine::destruct(filter);
clearFilter();
m_filter = filter;
m_filterRegexp = YOBJECT(Regexp,filter);
}
void MessageHandler::clearFilter()
{
if (!m_filter)
return;
MatchingItemBase* tmp = m_filter;
m_filter = 0;
TelEngine::destruct(tmp);
if (m_filter) {
NamedString* tmp = m_filter;
m_filter = 0;
m_filterRegexp = 0;
delete tmp;
}
}
@ -318,8 +311,8 @@ bool MessageRelay::receivedInternal(Message& msg)
MessageDispatcher::MessageDispatcher(const char* trackParam)
: m_handlersLock("DispatcherHandlers"), m_messagesLock("DispatcherMsgs"),
m_hooksLock("DispatcherHooks"),
: Mutex(false,"MessageDispatcher"),
m_hookMutex(false,"PostHooks"),
m_msgAppend(&m_messages), m_hookAppend(&m_hooks),
m_trackParam(trackParam), m_changes(0), m_warnTime(0),
m_enqueueCount(0), m_dequeueCount(0), m_dispatchCount(0),
@ -333,16 +326,9 @@ MessageDispatcher::MessageDispatcher(const char* trackParam)
MessageDispatcher::~MessageDispatcher()
{
XDebug(DebugInfo,"MessageDispatcher::~MessageDispatcher() [%p]",this);
lock();
clear();
}
void MessageDispatcher::clear()
{
WLock lck(m_handlersLock);
m_handlers.clear();
lck.acquire(m_hooksLock);
m_hookAppend = &m_hooks;
m_hooks.clear();
unlock();
}
bool MessageDispatcher::install(MessageHandler* handler)
@ -350,7 +336,7 @@ bool MessageDispatcher::install(MessageHandler* handler)
DDebug(DebugAll,"MessageDispatcher::install(%p)",handler);
if (!handler)
return false;
WLock lck(m_handlersLock);
Lock lock(this);
ObjList *l = m_handlers.find(handler);
if (l)
return false;
@ -386,7 +372,7 @@ bool MessageDispatcher::install(MessageHandler* handler)
bool MessageDispatcher::uninstall(MessageHandler* handler)
{
DDebug(DebugAll,"MessageDispatcher::uninstall(%p)",handler);
WLock lck(m_handlersLock);
lock();
handler = static_cast<MessageHandler *>(m_handlers.remove(handler,false));
if (handler) {
m_changes++;
@ -395,15 +381,16 @@ bool MessageDispatcher::uninstall(MessageHandler* handler)
handler,handler->c_str());
// wait until handler is again safe to destroy
do {
lck.drop();
unlock();
Thread::yield();
lck.acquire(m_handlersLock);
lock();
} while (handler->m_unsafe > 0);
}
if (handler->m_unsafe != 0)
Debug(DebugFail,"MessageHandler %p has unsafe=%d",handler,(int)handler->m_unsafe);
Debug(DebugFail,"MessageHandler %p has unsafe=%d",handler,handler->m_unsafe);
handler->m_dispatcher = 0;
}
unlock();
return (handler != 0);
}
@ -429,13 +416,19 @@ bool MessageDispatcher::dispatch(Message& msg)
unsigned int hTrackPos = 0;
bool hTrackTime = m_traceHandlerTime;
ObjList *l = &m_handlers;
RLock lck(m_handlersLock);
Lock mylock(this);
m_dispatchCount++;
for (; l; l=l->next()) {
MessageHandler *h = static_cast<MessageHandler*>(l->get());
if (h && (h->null() || *h == msg)) {
if (h->filter() && !h->filter()->matchListParam(msg))
continue;
if (h->filter()) {
if (h->filterRegexp()) {
if (!h->filterRegexp()->matches(msg.getValue(h->filter()->name())))
continue;
}
else if (*(h->filter()) != msg[h->filter()->name()])
continue;
}
if (counting)
Thread::setCurrentObjCounter(h->objectsCounter());
@ -454,7 +447,7 @@ bool MessageDispatcher::dispatch(Message& msg)
}
// mark handler as unsafe to destroy / uninstall
h->m_unsafe++;
lck.drop();
mylock.drop();
u_int64_t tm = (m_warnTime || hTrackTime) ? Time::now() : 0;
@ -463,7 +456,7 @@ bool MessageDispatcher::dispatch(Message& msg)
if (tm) {
tm = Time::now() - tm;
if (m_warnTime && tm > m_warnTime) {
lck.acquire(m_handlersLock);
mylock.acquire(this);
const char* name = (c == m_changes) ? h->trackName().c_str() : 0;
Debug(DebugInfo,"Message '%s' [%p] passed through %p%s%s%s in " FMT64U " usec",
msg.c_str(),&msg,h,
@ -489,7 +482,7 @@ bool MessageDispatcher::dispatch(Message& msg)
if (retv && !msg.broadcast())
break;
lck.acquire(m_handlersLock);
mylock.acquire(this);
if (c == m_changes)
continue;
// the handler list has changed - find again
@ -518,7 +511,7 @@ bool MessageDispatcher::dispatch(Message& msg)
break;
}
}
lck.drop();
mylock.drop();
if (counting)
Thread::setCurrentObjCounter(msg.getObjCounter());
msg.dispatched(retv);
@ -541,7 +534,7 @@ bool MessageDispatcher::dispatch(Message& msg)
}
}
lck.acquire(m_hooksLock);
m_hookMutex.lock();
if (m_hookHole && !m_hookCount) {
// compact the list, remove the holes
for (l = &m_hooks; l; l = l->next()) {
@ -559,16 +552,16 @@ bool MessageDispatcher::dispatch(Message& msg)
for (l = m_hooks.skipNull(); l; l = l->skipNext()) {
RefPointer<MessagePostHook> ph = static_cast<MessagePostHook*>(l->get());
if (ph) {
lck.drop();
m_hookMutex.unlock();
if (counting)
Thread::setCurrentObjCounter(ph->getObjCounter());
ph->dispatched(msg,retv);
ph = 0;
lck.acquire(m_hooksLock);
m_hookMutex.lock();
}
}
m_hookCount--;
lck.drop();
m_hookMutex.unlock();
if (counting)
Thread::setCurrentObjCounter(saved);
@ -577,7 +570,7 @@ bool MessageDispatcher::dispatch(Message& msg)
bool MessageDispatcher::enqueue(Message* msg)
{
WLock lck(m_messagesLock);
Lock lock(this);
if (!msg || m_messages.find(msg))
return false;
if (m_traceTime)
@ -591,17 +584,19 @@ bool MessageDispatcher::enqueue(Message* msg)
bool MessageDispatcher::dequeueOne()
{
WLock lck(m_messagesLock);
lock();
if (m_messages.next() == m_msgAppend)
m_msgAppend = &m_messages;
Message* msg = static_cast<Message *>(m_messages.remove(false));
if (msg) {
m_dequeueCount++;
uint64_t age = Time::now() - msg->msgTime();
if (age < 60000000)
m_msgAvgAge = (3 * m_msgAvgAge + age) >> 2;
}
unlock();
if (!msg)
return false;
m_dequeueCount++;
uint64_t age = Time::now() - msg->msgTime();
if (age < 60000000)
m_msgAvgAge = (3 * m_msgAvgAge + age) >> 2;
lck.drop();
dispatch(*msg);
msg->destruct();
return true;
@ -615,35 +610,35 @@ void MessageDispatcher::dequeue()
unsigned int MessageDispatcher::messageCount()
{
RLock lck(m_messagesLock);
Lock lock(this);
return (unsigned int)(m_enqueueCount - m_dequeueCount);
}
unsigned int MessageDispatcher::handlerCount()
{
RLock lck(m_handlersLock);
Lock lock(this);
return m_handlers.count();
}
unsigned int MessageDispatcher::postHookCount()
{
RLock lck(m_hooksLock);
Lock lock(m_hookMutex);
return m_hooks.count();
}
void MessageDispatcher::getStats(u_int64_t& enqueued, u_int64_t& dequeued, u_int64_t& dispatched, u_int64_t& queueMax)
{
RLock lck(m_messagesLock);
lock();
enqueued = m_enqueueCount;
dequeued = m_dequeueCount;
queueMax = m_queuedMax;
lck.acquire(m_handlersLock);
dispatched = m_dispatchCount;
queueMax = m_queuedMax;
unlock();
}
void MessageDispatcher::setHook(MessagePostHook* hook, bool remove)
{
WLock lck(m_hooksLock);
m_hookMutex.lock();
if (remove) {
// zero the hook, we'll compact it later when safe
ObjList* l = m_hooks.find(hook);
@ -654,30 +649,7 @@ void MessageDispatcher::setHook(MessagePostHook* hook, bool remove)
}
else
m_hookAppend = m_hookAppend->append(hook);
}
unsigned int MessageDispatcher::fillHandlersInfo(bool byName, const String& match,
String* details, unsigned int* total)
{
unsigned int n = 0;
unsigned int matched = 0;
String tmp;
RLock lck(m_handlersLock);
for (ObjList* o = m_handlers.skipNull(); o; o = o->skipNext()) {
n++;
MessageHandler *h = static_cast<MessageHandler*>(o->get());
if (!match.matches(byName ? (const String&)(*h): h->trackNameOnly()))
continue;
matched++;
if (!details)
continue;
tmp.printf("%s=%u|%s|%s",h->safe(),h->priority(),h->trackNameOnly().safe(),
h->filter() ? "yes" : "no");
details->append(tmp,",");
}
if (total)
*total = n;
return matched;
m_hookMutex.unlock();
}

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing
@ -43,7 +43,6 @@ extern int pthread_mutexattr_settype(pthread_mutexattr_t *__attr, int __kind) __
typedef pthread_mutex_t HMUTEX;
typedef sem_t HSEMAPHORE;
typedef pthread_rwlock_t rwlock_t;
#endif /* ! _WINDOWS */
@ -56,32 +55,7 @@ typedef pthread_rwlock_t rwlock_t;
namespace TelEngine {
class LockablePrivateBase
{
public:
inline LockablePrivateBase(const char* name)
: m_name(name ? name : ""), m_owner(0), m_ownerName(0)
{}
inline const char* name() const
{ return m_name; }
inline Thread* owner() const
{ return m_owner; }
inline const char* ownerName() const
{ return m_ownerName; }
protected:
inline void setOwner(Thread* th = 0) {
m_owner = th;
m_ownerName = th ? th->name() : "";
}
private:
const char* m_name;
Thread* m_owner;
const char* m_ownerName;
};
class MutexPrivate : public LockablePrivateBase
{
class MutexPrivate {
public:
MutexPrivate(bool recursive, const char* name);
~MutexPrivate();
@ -91,6 +65,10 @@ public:
{ if (!--m_refcount) delete this; }
inline bool recursive() const
{ return m_recursive; }
inline const char* name() const
{ return m_name; }
inline const char* owner() const
{ return m_owner; }
bool locked() const
{ return (m_locked > 0); }
bool lock(long maxwait);
@ -103,6 +81,8 @@ private:
volatile unsigned int m_locked;
volatile unsigned int m_waiting;
bool m_recursive;
const char* m_name;
const char* m_owner;
};
class SemaphorePrivate {
@ -129,40 +109,6 @@ private:
const char* m_name;
};
class RWLockPrivate : public LockablePrivateBase
{
public:
RWLockPrivate(const char* name);
~RWLockPrivate();
inline void ref()
{ ++m_refcount; }
inline void deref()
{ if (!--m_refcount) delete this; }
inline Thread* owner() const
{ return m_nonRWLck ? m_nonRWLck->owner() : LockablePrivateBase::owner(); }
inline const char* ownerName() const
{ return m_nonRWLck ? m_nonRWLck->ownerName() : LockablePrivateBase::ownerName(); }
inline bool locked() const
{ return m_nonRWLck ? m_nonRWLck->locked() : (m_locked > 0); }
bool readLock(long maxWait = -1);
bool writeLock(long maxWwait = -1);
bool unlock();
static volatile int s_count;
static volatile int s_locks;
private:
#ifdef _WINDOWS
// we use m_nonRWLck
#else
rwlock_t m_lock;
#endif
MutexPrivate* m_nonRWLck;
int m_refcount;
unsigned int m_locked;
#ifndef ATOMIC_OPS
Mutex m_mutex;
#endif
};
class GlobalMutex {
public:
GlobalMutex();
@ -183,18 +129,11 @@ static GlobalMutex s_global;
static unsigned long s_maxwait = 0;
static bool s_unsafe = MUTEX_STATIC_UNSAFE;
static bool s_safety = false;
#ifdef _WINDOWS
static bool s_rwLockDisabled = true;
#else
static bool s_rwLockDisabled = false;
#endif
volatile int MutexPrivate::s_count = 0;
volatile int MutexPrivate::s_locks = 0;
volatile int SemaphorePrivate::s_count = 0;
volatile int SemaphorePrivate::s_locks = 0;
volatile int RWLockPrivate::s_count = 0;
volatile int RWLockPrivate::s_locks = 0;
bool GlobalMutex::s_init = true;
// WARNING!!!
@ -247,8 +186,8 @@ void GlobalMutex::unlock()
MutexPrivate::MutexPrivate(bool recursive, const char* name)
: LockablePrivateBase(name),
m_refcount(1), m_locked(0), m_waiting(0), m_recursive(recursive)
: m_refcount(1), m_locked(0), m_waiting(0), m_recursive(recursive),
m_name(name), m_owner(0)
{
GlobalMutex::lock();
s_count++;
@ -293,11 +232,11 @@ MutexPrivate::~MutexPrivate()
#endif
GlobalMutex::unlock();
if (m_locked || m_waiting)
Debug(DebugFail,"MutexPrivate '%s' owned by '%s' (%p) destroyed with %u locks, %u waiting [%p]",
name(),ownerName(),owner(),m_locked,m_waiting,this);
Debug(DebugFail,"MutexPrivate '%s' owned by '%s' destroyed with %u locks, %u waiting [%p]",
m_name,m_owner,m_locked,m_waiting,this);
else if (warn)
Debug(DebugCrit,"MutexPrivate '%s' owned by '%s' (%p) unlocked in destructor [%p]",
name(),ownerName(),owner(),this);
Debug(DebugCrit,"MutexPrivate '%s' owned by '%s' unlocked in destructor [%p]",
m_name,m_owner,this);
}
bool MutexPrivate::lock(long maxwait)
@ -368,16 +307,18 @@ bool MutexPrivate::lock(long maxwait)
if (safety)
s_locks++;
m_locked++;
setOwner(thr);
if (thr)
if (thr) {
thr->m_locks++;
m_owner = thr->name();
}
else
m_owner = 0;
}
if (safety)
GlobalMutex::unlock();
if (warn && !rval)
Debug(DebugFail,
"Thread '%s' could not lock mutex '%s' owned by '%s' (%p) waited by %u others for %lu usec!",
Thread::currentName(),name(),ownerName(),owner(),m_waiting,maxwait);
Debug(DebugFail,"Thread '%s' could not lock mutex '%s' owned by '%s' waited by %u others for %lu usec!",
Thread::currentName(),m_name,m_owner,m_waiting,maxwait);
return rval;
}
@ -393,10 +334,11 @@ bool MutexPrivate::unlock()
if (thr)
thr->m_locks--;
if (!--m_locked) {
if (thr != owner())
Debug(DebugFail,"MutexPrivate '%s' unlocked by '%s' (%p) but owned by '%s' (%p) [%p]",
name(),thr ? thr->name() : "",thr,ownerName(),owner(),this);
setOwner();
const char* tname = thr ? thr->name() : 0;
if (tname != m_owner)
Debug(DebugFail,"MutexPrivate '%s' unlocked by '%s' but owned by '%s' [%p]",
m_name,tname,m_owner,this);
m_owner = 0;
}
if (safety) {
int locks = --s_locks;
@ -413,10 +355,10 @@ bool MutexPrivate::unlock()
ok = s_unsafe || !::pthread_mutex_unlock(&m_mutex);
#endif
if (!ok)
Debug(DebugFail,"Failed to unlock mutex '%s' [%p]",name(),this);
Debug(DebugFail,"Failed to unlock mutex '%s' [%p]",m_name,this);
}
else
Debug(DebugFail,"MutexPrivate::unlock called on unlocked '%s' [%p]",name(),this);
Debug(DebugFail,"MutexPrivate::unlock called on unlocked '%s' [%p]",m_name,this);
if (safety)
GlobalMutex::unlock();
return ok;
@ -664,7 +606,7 @@ bool Mutex::locked() const
const char* Mutex::owner() const
{
return m_private ? m_private->ownerName() : static_cast<const char*>(0);
return m_private ? m_private->owner() : static_cast<const char*>(0);
}
int Mutex::count()
@ -827,376 +769,4 @@ void Lock2::drop()
mx1->unlock();
}
RWLockPrivate::RWLockPrivate(const char* name)
: LockablePrivateBase(name),
m_nonRWLck(0), m_refcount(1), m_locked(0)
#ifndef ATOMIC_OPS
, m_mutex(true,"RWLockPrivate")
#endif
{
if (s_rwLockDisabled) {
m_nonRWLck = new MutexPrivate(true,name);
return;
}
GlobalMutex::lock();
s_count++;
#ifdef _WINDOWS
// not implemented, uses m_nonRWLck
#else
::pthread_rwlock_init(&m_lock,0);
#endif
GlobalMutex::unlock();
}
RWLockPrivate::~RWLockPrivate()
{
if (m_nonRWLck) {
delete m_nonRWLck;
m_nonRWLck = 0;
return;
}
bool warn = false;
GlobalMutex::lock();
if (m_locked) {
warn = true;
--m_locked;
if (s_safety)
--s_locks;
#ifdef _WINDOWS
// not implemented, uses m_nonRWLck
#else
::pthread_rwlock_unlock(&m_lock);
#endif
}
s_count--;
#ifdef _WINDOWS
// not implemented, uses m_nonRWLck
#else
::pthread_rwlock_destroy(&m_lock);
#endif
GlobalMutex::unlock();
if (m_locked)
Debug(DebugFail,"RWLockPrivate '%s' owned by '%s' (%p) destroyed with %u locks [%p]",
name(),ownerName(),owner(),m_locked,this);
else if (warn)
Debug(DebugCrit,"RWLockPrivate '%s' owned by '%s' (%p) unlocked in destructor [%p]",
name(),ownerName(),owner(),this);
}
bool RWLockPrivate::readLock(long maxwait)
{
if (m_nonRWLck)
return m_nonRWLck->lock(maxwait);
int ret = -1;
bool warn = false;
if (s_maxwait && (maxwait < 0)) {
maxwait = (long)s_maxwait;
warn = true;
}
bool safety = s_safety;
if (safety)
GlobalMutex::lock();
Thread* thr = Thread::current();
if (thr)
thr->m_locking = true;
if (safety)
GlobalMutex::unlock();
#ifdef _WINDOWS
// not implemented, uses m_nonRWLck
#else
if (s_unsafe)
ret = 0;
if (maxwait < 0)
ret = ::pthread_rwlock_rdlock(&m_lock);
else if (!maxwait)
ret = ::pthread_rwlock_tryrdlock(&m_lock);
else {
u_int64_t t = Time::now() + maxwait;
#ifdef HAVE_TIMEDRDLOCK
struct timeval tv;
struct timespec ts;
Time::toTimeval(&tv,t);
ts.tv_sec = tv.tv_sec;
ts.tv_nsec = 1000 * tv.tv_usec;
ret = ::pthread_rwlock_timedrdlock(&m_lock,&ts);
#else
bool dead = false;
do {
if (!dead) {
dead = Thread::check(false);
// give up only if caller asked for a limited wait
if (dead && !warn)
break;
}
ret = ::pthread_rwlock_tryrdlock(&m_lock);
if (!ret)
break;
Thread::yield();
} while (t > Time::now());
#endif
}
#endif // _WINDOWS
if (safety)
GlobalMutex::lock();
if (thr)
thr->m_locking = false;
if (!ret) {
if (safety)
++s_locks;
#ifdef ATOMIC_OPS
#ifdef _WINDOWS
InterlockedIncrement((LONG*)&m_locked);
#else
__sync_add_and_fetch(&m_locked,1);
#endif
#else
m_mutex.lock();
++m_locked;
m_mutex.unlock();
#endif
if (thr)
++thr->m_locks;
}
if (safety)
GlobalMutex::unlock();
if (warn && ret)
Debug(DebugFail,"Thread '%s' could not lock for read RW lock '%s'"
" writing-owned by '%s' (%p) after waiting for %ld usec! [%p]",
Thread::currentName(),name(),ownerName(),owner(),maxwait,this);
return ret == 0;
}
bool RWLockPrivate::writeLock(long maxwait)
{
if (m_nonRWLck)
return m_nonRWLck->lock(maxwait);
int ret = -1;
bool warn = false;
if (s_maxwait && (maxwait < 0)) {
maxwait = (long)s_maxwait;
warn = true;
}
bool safety = s_safety;
if (safety)
GlobalMutex::lock();
Thread* thr = Thread::current();
if (thr)
thr->m_locking = true;
if (safety)
GlobalMutex::unlock();
#ifdef _WINDOWS
// not implemented, uses m_nonRWLck
#else
if (s_unsafe)
ret = 0;
if (maxwait < 0)
ret = ::pthread_rwlock_wrlock(&m_lock);
else if (!maxwait)
ret = ::pthread_rwlock_trywrlock(&m_lock);
else {
u_int64_t t = Time::now() + maxwait;
#ifdef HAVE_TIMEDWRLOCK
struct timeval tv;
struct timespec ts;
Time::toTimeval(&tv,t);
ts.tv_sec = tv.tv_sec;
ts.tv_nsec = 1000 * tv.tv_usec;
ret = ::pthread_rwlock_timedwrlock(&m_lock,&ts);
#else
bool dead = false;
do {
if (!dead) {
dead = Thread::check(false);
// give up only if caller asked for a limited wait
if (dead && !warn)
break;
}
ret = ::pthread_rwlock_trywrlock(&m_lock);
if (!ret)
break;
Thread::yield();
} while (t > Time::now());
#endif
}
#endif
if (safety)
GlobalMutex::lock();
if (thr)
thr->m_locking = false;
if (!ret) {
if (safety)
++s_locks;
#ifdef ATOMIC_OPS
#ifdef _WINDOWS
InterlockedIncrement((LONG*)&m_locked);
#else
__sync_add_and_fetch(&m_locked,1);
#endif
#else
m_mutex.lock();
++m_locked;
m_mutex.unlock();
#endif
setOwner(thr);
if (thr)
++thr->m_locks;
}
if (safety)
GlobalMutex::unlock();
if (warn && ret)
Debug(DebugFail,"Thread '%s' could not lock for write RW lock '%s'"
" writing-owned by '%s' (%p) after waiting for %ld usec! [%p]",
Thread::currentName(),name(),ownerName(),name(),maxwait,this);
return ret == 0;
}
bool RWLockPrivate::unlock()
{
if (m_nonRWLck)
return m_nonRWLck->unlock();
int ok = -1;
bool safety = s_safety;
if (safety)
GlobalMutex::lock();
if (m_locked) {
Thread* thr = Thread::current();
if (thr)
--thr->m_locks;
#ifdef ATOMIC_OPS
#ifdef _WINDOWS
int l = InterlockedDecrement((LONG*)&m_locked);
#else
int l = __sync_sub_and_fetch(&m_locked,1);
#endif
#else
m_mutex.lock();
int l = --m_locked;
m_mutex.unlock();
#endif
if (!l) {
if (owner() && owner() != thr)
Debug(DebugFail,"RWLockPrivate '%s' unlocked by '%s' (%p) but owned by '%s' (%p) [%p]",
name(),thr ? thr->name() : "",thr,ownerName(),owner(),this);
setOwner();
}
if (safety) {
int locks = --s_locks;
if (locks < 0) {
// this is very very bad - abort right now
abortOnBug(true);
s_locks = 0;
Debug(DebugFail,"RWLockPrivate::locks() is %d [%p]",locks,this);
}
}
#ifdef _WINDOWS
// not implemented, uses m_nonRWLck
#else
ok = s_unsafe ? 0 : ::pthread_rwlock_unlock(&m_lock);
#endif
if (ok)
Debug(DebugFail,"Thread '%s' failed to unlock RW lock '%s' owned by '%s' (%p) [%p]",
Thread::currentName(),name(),ownerName(),owner(),this);
}
else {
Debug(DebugFail,
"Thread '%s' could not unlock already unlocked RW lock '%s' writing-owned by '%s' (%p) [%p]",
Thread::currentName(),name(),ownerName(),owner(),this);
}
if (safety)
GlobalMutex::unlock();
return ok == 0;
}
/**
* class RWLock
*/
RWLock::RWLock(const char* name)
{
m_private = new RWLockPrivate(name ? name : "?");
}
RWLock::RWLock(const RWLock& original)
: Lockable(),
m_private(original.privDataCopy())
{
}
RWLock::~RWLock()
{
RWLockPrivate* priv = m_private;
m_private = 0;
if (priv)
priv->deref();
}
bool RWLock::readLock(long maxwait)
{
return m_private && m_private->readLock(maxwait);
}
bool RWLock::writeLock(long maxwait)
{
return m_private && m_private->writeLock(maxwait);
}
bool RWLock::unlock()
{
return m_private && m_private->unlock();
}
bool RWLock::locked() const
{
return m_private && m_private->locked();
}
void RWLock::disableRWLock(bool disable)
{
#ifdef _WINDOWS
// we disable RWLock usage as it is not implemented
s_rwLockDisabled = true;
#else
s_rwLockDisabled = disable;
#endif
}
RWLockPrivate* RWLock::privDataCopy() const
{
if (m_private)
m_private->ref();
return m_private;
}
RWLockPool::RWLockPool(unsigned int len, const char* name)
: m_name(0), m_data(0), m_length(len ? len : 1)
{
if (TelEngine::null(name))
name = "Pool";
m_name = new String[m_length];
m_data = new RWLock*[m_length];
for (unsigned int i = 0; i < m_length; i++) {
m_name[i] << name << "::" << (i + 1);
m_data[i] = new RWLock(m_name[i]);
}
}
RWLockPool::~RWLockPool()
{
if (m_data) {
for (unsigned int i = 0; i < m_length; i++)
delete m_data[i];
delete[] m_data;
}
if (m_name)
delete[] m_name;
}
/* vi: set ts=8 sw=4 sts=4 noet: */

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing
@ -18,7 +18,6 @@
*/
#include "yateclass.h"
#include "yatexml.h"
using namespace TelEngine;
@ -37,7 +36,11 @@ NamedList::NamedList(const char* name)
NamedList::NamedList(const NamedList& original)
: String(original)
{
copyParams(false,original);
ObjList* dest = &m_params;
for (const ObjList* l = original.m_params.skipNull(); l; l = l->skipNext()) {
const NamedString* p = static_cast<const NamedString*>(l->get());
dest = dest->append(new NamedString(p->name(),*p));
}
}
NamedList::NamedList(const char* name, const NamedList& original, const String& prefix)
@ -77,135 +80,30 @@ NamedList& NamedList::addParam(const char* name, const char* value, bool emptyOK
return *this;
}
NamedList& NamedList::setParam(NamedString* param)
NamedList& NamedList::setParam(const String& name, const char* value)
{
XDebug(DebugAll,"NamedList::setParam(%p) [%p]",param,this);
if (!param)
return *this;
ObjList* o = m_params.skipNull();
while (o) {
NamedString* s = static_cast<NamedString*>(o->get());
if (s->name() == param->name()) {
o->set(param);
XDebug(DebugInfo,"NamedList::setParam(\"%s\",\"%s\")",name.c_str(),value);
ObjList *p = m_params.skipNull();
while (p) {
NamedString *s = static_cast<NamedString*>(p->get());
if (s->name() == name) {
*s = value;
return *this;
}
ObjList* next = o->skipNext();
ObjList* next = p->skipNext();
if (next)
o = next;
p = next;
else
break;
}
if (o)
o->append(param);
if (p)
p->append(new NamedString(name,value));
else
m_params.append(param);
return *this;
m_params.append(new NamedString(name,value));
return *this;
}
static inline NamedString* nlSetParamCreate(NamedList& list, const String& name, ObjList*& append)
{
append = list.paramList()->skipNull();
while (append) {
NamedString* ns = static_cast<NamedString*>(append->get());
if (ns->name() == name) {
append = 0;
return ns;
}
ObjList* next = append->skipNext();
if (!next)
return new NamedString(name);
append = next;
}
append = list.paramList();
return new NamedString(name);
}
NamedList& NamedList::setParam(const String& name, unsigned int flags, const TokenDict* tokens,
bool unknownflag)
{
XDebug(DebugAll,"NamedList::setParam(%s) flags=%u tokens=%p unkFlag=%u [%p]",
name.safe(),flags,tokens,unknownflag,this);
ObjList* append = 0;
NamedString* ns = nlSetParamCreate(*this,name,append);
*static_cast<String*>(ns) = "";
ns->decodeFlags(flags,tokens,unknownflag);
if (append)
append->append(ns);
return *this;
}
NamedList& NamedList::setParam(const String& name, uint64_t flags, const TokenDict64* tokens,
bool unknownflag)
{
XDebug(DebugAll,"NamedList::setParam(%s) flags64=" FMT64U " tokens=%p unkFlag=%u [%p]",
name.safe(),flags,tokens,unknownflag,this);
ObjList* append = 0;
NamedString* ns = nlSetParamCreate(*this,name,append);
*static_cast<String*>(ns) = "";
ns->decodeFlags(flags,tokens,unknownflag);
if (append)
append->append(ns);
return *this;
}
NamedList& NamedList::setParamHex(const String& name, const void* buf, unsigned int len, char sep)
{
XDebug(DebugAll,"NamedList::setParamHex(%s,%p,%u,%c) [%p]",name.safe(),buf,len,sep,this);
ObjList* append = 0;
NamedString* ns = nlSetParamCreate(*this,name,append);
ns->hexify((void*)buf,len,sep);
if (append)
append->append(ns);
return *this;
}
template <class Obj> NamedList& nlSetParamValue(NamedList& list, const String& name, Obj& value)
{
ObjList* append = 0;
NamedString* ns = nlSetParamCreate(list,name,append);
*static_cast<String*>(ns) = value;
if (append)
append->append(ns);
return list;
}
NamedList& NamedList::setParam(const String& name, const char* value)
{
XDebug(DebugAll,"NamedList::setParam('%s','%s') [%p]",name.c_str(),value,this);
return nlSetParamValue(*this,name,value);
}
NamedList& NamedList::setParam(const String& name, int64_t value)
{
XDebug(DebugAll,"NamedList::setParam(%s) INT64=" FMT64 " [%p]",name.c_str(),value,this);
return nlSetParamValue(*this,name,value);
}
NamedList& NamedList::setParam(const String& name, uint64_t value)
{
XDebug(DebugAll,"NamedList::setParam(%s) UINT64=" FMT64U " [%p]",name.c_str(),value,this);
return nlSetParamValue(*this,name,value);
}
NamedList& NamedList::setParam(const String& name, int32_t value)
{
XDebug(DebugAll,"NamedList::setParam(%s) INT32=%d [%p]",name.c_str(),value,this);
return nlSetParamValue(*this,name,value);
}
NamedList& NamedList::setParam(const String& name, uint32_t value)
{
XDebug(DebugAll,"NamedList::setParam(%s) UINT32=%u [%p]",name.c_str(),value,this);
return nlSetParamValue(*this,name,value);
}
NamedList& NamedList::setParam(const String& name, double value)
{
XDebug(DebugAll,"NamedList::setParam(%s) DOUBLE=%f [%p]",name.c_str(),value,this);
return nlSetParamValue(*this,name,value);
}
NamedList& NamedList::clearParam(const String& name, char childSep, const String* value)
NamedList& NamedList::clearParam(const String& name, char childSep)
{
XDebug(DebugInfo,"NamedList::clearParam(\"%s\",'%.1s')",
name.c_str(),&childSep);
@ -215,8 +113,7 @@ NamedList& NamedList::clearParam(const String& name, char childSep, const String
ObjList *p = &m_params;
while (p) {
NamedString *s = static_cast<NamedString *>(p->get());
if (s && ((s->name() == name) || s->name().startsWith(tmp))
&& (!value || value->matches(*s)))
if (s && ((s->name() == name) || s->name().startsWith(tmp)))
p->remove();
else
p = p->next();
@ -257,37 +154,12 @@ NamedList& NamedList::copyParam(const NamedList& original, const String& name, c
return *this;
}
static inline NamedString* nlCopyParam(const NamedString& param)
NamedList& NamedList::copyParams(const NamedList& original)
{
NamedPointer* np = YOBJECT(NamedPointer,&param);
if (!(np && np->userData()))
return 0;
GenObject* ud = 0;
#define NP_COPY_PARAM_INTERNAL(Type) \
ud = YOBJECT(Type,np->userData()); \
if (ud) \
return new NamedPointer(np->name(),new Type(*(Type*)ud),*np)
NP_COPY_PARAM_INTERNAL(DataBlock);
NP_COPY_PARAM_INTERNAL(XmlElement);
#undef NP_COPY_PARAM_INTERNAL
return 0;
}
NamedList& NamedList::copyParams(bool replace, const NamedList& original, bool copyUserData)
{
XDebug(DebugInfo,"NamedList::copyParams(%p,%u) [%p]",&original,replace,this);
ObjList* append = replace ? 0 : &m_params;
XDebug(DebugInfo,"NamedList::copyParams(%p) [%p]",&original,this);
for (const ObjList* l = original.m_params.skipNull(); l; l = l->skipNext()) {
const NamedString* p = static_cast<const NamedString*>(l->get());
NamedString* ns = 0;
if (copyUserData)
ns = nlCopyParam(*p);
if (!ns)
ns = new NamedString(p->name(),*p);
if (append)
append = append->append(ns);
else
setParam(ns);
setParam(p->name(),*p);
}
return *this;
}

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing
@ -18,7 +18,6 @@
*/
#include "yateclass.h"
#include <string.h>
using namespace TelEngine;
@ -487,47 +486,6 @@ unsigned int ObjVector::assign(ObjList& list, bool move, unsigned int maxLen)
return maxLen;
}
static inline void clearObjVector(GenObject** objs, unsigned int len)
{
while (len--) {
TelEngine::destruct(*objs);
objs++;
}
}
unsigned int ObjVector::resize(unsigned int len, bool keepData)
{
if (!len) {
clear();
return length();
}
if (len == length()) {
if (!keepData) {
if (m_delete)
clearObjVector(m_objects,length());
::memset(m_objects,0,length() * sizeof(GenObject*));
}
return length();
}
GenObject** buf = new GenObject*[len];
if (!(keepData && length()))
::memset(buf,0,len * sizeof(GenObject*));
else if (len < length()) {
::memcpy(buf,m_objects,len * sizeof(GenObject*));
::memset(m_objects,0,len * sizeof(GenObject*));
}
else {
::memcpy(buf,m_objects,length() * sizeof(GenObject*));
::memset(m_objects,0,length() * sizeof(GenObject*));
if (len > length())
::memset(buf + length(),0,(len - length()) * sizeof(GenObject*));
}
clear();
m_objects = buf;
m_length = len;
return length();
}
unsigned int ObjVector::count() const
{
if (!m_objects)
@ -600,8 +558,10 @@ void ObjVector::clear()
unsigned int len = m_length;
m_length = 0;
m_objects = 0;
if (m_delete && objs)
clearObjVector(objs,len);
if (m_delete && objs) {
for (unsigned int i = 0; i < len; i++)
TelEngine::destruct(objs[i]);
}
delete[] objs;
}

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing
@ -231,8 +231,6 @@ const TokenDict SocketAddr::s_familyName[] = {
{0,0},
};
const char* SocketAddr::s_ifaceNameExtraEscape = ".:[]";
SocketAddr::SocketAddr(const struct sockaddr* addr, socklen_t len)
: m_address(0), m_length(0)
{
@ -267,9 +265,7 @@ void SocketAddr::clear()
{
m_length = 0;
m_host.clear();
m_iface.clear();
m_addr.clear();
m_addrFull.clear();
void* tmp = m_address;
m_address = 0;
if (tmp)
@ -436,15 +432,7 @@ bool SocketAddr::host(const String& name)
}
switch (family()) {
case AF_INET:
if (name.find('%') >= 0) {
String tmp, ifc;
splitIface(name,tmp,&ifc);
if (host(tmp)) {
iface(ifc,true);
return true;
}
}
else {
{
in_addr_t a = inet_addr(name);
if (a == INADDR_NONE) {
#ifdef HAVE_GHBN_R
@ -470,7 +458,6 @@ bool SocketAddr::host(const String& name)
}
if (a != INADDR_NONE) {
((struct sockaddr_in*)m_address)->sin_addr.s_addr = a;
m_iface.clear();
stringify();
return true;
}
@ -479,30 +466,25 @@ bool SocketAddr::host(const String& name)
#ifdef AF_INET6
case AF_INET6:
if (name.find('%') >= 0) {
String tmp, ifc;
splitIface(name,tmp,&ifc);
String tmp, iface;
splitIface(name,tmp,&iface);
if (!host(tmp))
break;
if (ifc && iface(ifc,true)) {
return false;
if (iface)
#ifndef _WINDOWS
scopeId(if_nametoindex(m_iface));
scopeId(if_nametoindex(iface));
#else
scopeId(m_iface.toInteger(0,0,0));
scopeId(iface.toInteger(0,0,0));
#endif
}
else
m_iface.clear();
return true;
}
#ifdef HAVE_PTON
if (inet_pton(family(),name,&((struct sockaddr_in6*)m_address)->sin6_addr) > 0) {
m_iface.clear();
stringify();
return true;
}
#endif
if (resolveIPv6(m_address,name)) {
m_iface.clear();
stringify();
return true;
}
@ -511,12 +493,11 @@ bool SocketAddr::host(const String& name)
#ifdef HAS_AF_UNIX
case AF_UNIX:
if (name.length() >= (UNIX_PATH_MAX-1))
break;
return false;
::strcpy(((struct sockaddr_un*)m_address)->sun_path,name.c_str());
stringify();
return true;
#endif
break;
}
return false;
}
@ -527,20 +508,15 @@ int SocketAddr::family(const String& addr)
if (!addr)
return Unknown;
bool ipv6 = false;
int percent = -1;
for (unsigned int i = 0; i < addr.length(); i++) {
if (addr[i] == '/')
return Unix;
if (addr[i] == ':')
ipv6 = true;
else if (percent < 0 && addr[i] == '%')
percent = i;
}
if (ipv6)
return IPv6;
if (!percent)
return Unknown;
in_addr_t a = percent < 0 ? inet_addr(addr) : inet_addr(addr.substr(0,percent));
in_addr_t a = inet_addr(addr);
if (a != INADDR_NONE || addr == YSTRING("255.255.255.255"))
return IPv4;
return Unknown;
@ -607,23 +583,13 @@ int SocketAddr::copyAddr(uint8_t* buf, struct sockaddr* addr)
}
// Append an address to a buffer
String& SocketAddr::appendAddr(String& buf, const String& addr, int family, const String& iface)
String& SocketAddr::appendAddr(String& buf, const String& addr, int family)
{
if (!addr)
return buf;
// Address already starts with [
if (addr[0] == '[') {
if (!iface)
return buf << addr;
char last = (addr[addr.length() - 1] == ']') ? ']' : 0;
if (last)
buf.append(addr.c_str(),addr.length() - 1);
else
buf << addr;
buf << '%';
escapeIface(buf,iface);
if (last)
buf << last;
buf << addr;
return buf;
}
if (family == Unknown) {
@ -635,19 +601,10 @@ String& SocketAddr::appendAddr(String& buf, const String& addr, int family, cons
family = IPv6;
}
}
if (!iface) {
if (family != IPv6)
return buf << addr;
return buf << '[' << addr << ']';
}
char last = (family != IPv6) ? 0 : ']';
if (last)
buf << '[' << addr << '%';
if (family != IPv6)
buf << addr;
else
buf << addr << '%';
escapeIface(buf,iface);
if (last)
buf << last;
buf << "[" << addr << "]";
return buf;
}
@ -683,8 +640,8 @@ void SocketAddr::splitIface(const String& buf, String& addr, String* iface)
}
else {
if (iface)
iface->assign(buf.c_str() + pos + 1,buf.length() - pos - 1);
addr.assign(buf.c_str(),pos);
*iface = buf.substr(pos + 1);
addr = buf.substr(0,pos);
}
}
@ -699,7 +656,7 @@ void SocketAddr::split(const String& buf, String& addr, int& port, bool portPres
if (buf[0] == '[') {
int p = buf.find(']',1);
if (p >= 1) {
if (buf[p + 1] == ':')
if (p < ((int)buf.length() - 1) && buf[p + 1] == ':')
port = buf.substr(p + 2).toInteger();
addr.assign(buf.c_str() + 1,p - 1);
return;
@ -740,22 +697,15 @@ void SocketAddr::stringify()
{
m_host.clear();
m_addr.clear();
m_addrFull.clear();
if (m_length && m_address)
stringify(m_host,m_address);
}
// Store host:port in m_addr
void SocketAddr::updateAddr(bool full) const
void SocketAddr::updateAddr() const
{
if (full) {
m_addrFull.clear();
appendTo(m_addrFull,host(),port(),family(),m_iface);
}
else {
m_addr.clear();
appendTo(m_addr,host(),port(),family());
}
m_addr.clear();
appendTo(m_addr,host(),port(),family());
}
int SocketAddr::port() const
@ -790,7 +740,6 @@ bool SocketAddr::port(int newport)
return false;
}
m_addr.clear();
m_addrFull.clear();
return true;
}
@ -1624,24 +1573,6 @@ bool File::listDirectory(const char* path, ObjList* dirs, ObjList* files, int* e
}
unsigned int Socket::s_features = 0
#ifdef IPPROTO_IPV6
| FProtoIpv6
#endif
#ifdef IPV6_V6ONLY
| FIpv6Only
#endif
#ifdef SO_BINDTODEVICE
| FBindToIface
#endif
#if defined(_WINDOWS) || defined(HAVE_POLL)
| FEfficientSelect
#endif
#ifdef SO_EXCLUSIVEADDRUSE
| FExclusiveAddrUse
#endif
;
Socket::Socket()
: m_handle(invalidHandle())
{
@ -1814,32 +1745,6 @@ bool Socket::bind(struct sockaddr* addr, socklen_t addrlen)
return checkError(::bind(m_handle,addr,addrlen));
}
bool Socket::bind(struct sockaddr* addr, socklen_t addrlen,
const char* iface, int ifLen)
{
if (iface && ifLen &&
!bindIface(iface,ifLen,addr ? addr->sa_family : SocketAddr::Unknown))
return false;
return bind(addr,addrlen);
}
bool Socket::bindIface(const char* name, int len, int family)
{
// IPv6 interface should be set in address header
if (!(name && len) || family == SocketAddr::IPv6)
return true;
#ifdef SO_BINDTODEVICE
if (len < 0)
len = strlen(name);
if (!setOption(SOL_SOCKET,SO_BINDTODEVICE,name,len))
return false;
#else
m_error = EINVAL;
return false;
#endif // SO_BINDTODEVICE
return true;
}
bool Socket::listen(unsigned int backlog)
{
if ((backlog == 0) || (backlog > SOMAXCONN))
@ -1979,19 +1884,6 @@ bool Socket::getPeerName(SocketAddr& addr)
return ok;
}
bool Socket::getBoundIface(String& buf)
{
#ifdef SO_BINDTODEVICE
char tmp[IF_NAMESIZE];
socklen_t len = IF_NAMESIZE;
if (getOption(SOL_SOCKET,SO_BINDTODEVICE,tmp,&len)) {
buf << tmp;
return true;
}
#endif
return false;
}
int Socket::sendTo(const void* buffer, int length, const struct sockaddr* addr, socklen_t adrlen, int flags)
{
if (!addr)
@ -2000,7 +1892,6 @@ int Socket::sendTo(const void* buffer, int length, const struct sockaddr* addr,
length = 0;
int res = ::sendto(m_handle,(const char*)buffer,length,flags,addr,adrlen);
checkError(res,true);
applyFilters(buffer,res,flags,addr,adrlen,false);
return res;
}
@ -2010,7 +1901,6 @@ int Socket::send(const void* buffer, int length, int flags)
length = 0;
int res = ::send(m_handle,(const char*)buffer,length,flags);
checkError(res,true);
applyFilters(buffer,res,flags,0,0,false);
return res;
}
@ -2023,7 +1913,6 @@ int Socket::writeData(const void* buffer, int length)
length = 0;
int res = ::write(m_handle,buffer,length);
checkError(res,true);
applyFilters(buffer,res,0,0,0,false);
return res;
#endif
}
@ -2073,7 +1962,6 @@ int Socket::readData(void* buffer, int length)
length = 0;
int res = ::read(m_handle,buffer,length);
checkError(res,true);
applyFilters(buffer,res,0);
return res;
#endif
}
@ -2333,18 +2221,12 @@ void Socket::removeFilter(SocketFilter* filter, bool delobj)
filter->m_socket = 0;
}
void Socket::clearFilters(bool del)
void Socket::clearFilters()
{
for (ObjList* l = m_filters.skipNull(); l; l = l->skipNext()) {
SocketFilter* filter = static_cast<SocketFilter*>(l->get());
filter->m_socket = 0;
}
m_filters.setDelete(del);
m_filters.clear();
}
bool Socket::applyFilters(const void* buffer, int length, int flags, const struct sockaddr* addr,
socklen_t adrlen, bool rx)
bool Socket::applyFilters(void* buffer, int length, int flags, const struct sockaddr* addr, socklen_t adrlen)
{
if ((length <= 0) || !buffer)
return false;
@ -2352,9 +2234,7 @@ bool Socket::applyFilters(const void* buffer, int length, int flags, const struc
adrlen = 0;
for (ObjList* l = &m_filters; l; l = l->next()) {
SocketFilter* filter = static_cast<SocketFilter*>(l->get());
if (filter &&
(rx ? filter->received(buffer, length, flags, addr, adrlen)
: filter->sent(buffer, length, flags, addr, adrlen)))
if (filter && filter->received(buffer,length,flags,addr,adrlen))
return true;
}
return false;

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing
@ -36,14 +36,6 @@
namespace TelEngine {
static inline char* strAlloc(unsigned int n, char* old = 0)
{
char* data = (char*)::realloc(old,n + 1);
if (!data)
Debug("String",DebugFail,"realloc(%u) returned NULL!",n + 1);
return data;
}
// String to regular integer conversion, takes into account overflows
static int strtoi(const char* nptr, char** endptr, int base)
{
@ -684,7 +676,7 @@ String& String::assign(char value, unsigned int repeat)
return *this;
}
String& String::hexify(const void* data, unsigned int len, char sep, bool upCase)
String& String::hexify(void* data, unsigned int len, char sep, bool upCase)
{
const char* hex = upCase ? "0123456789ABCDEF" : "0123456789abcdef";
if (data && len) {
@ -1263,35 +1255,6 @@ String& String::insert(unsigned int pos, const char* value, int len)
return *this;
}
// Insert characters in string into current string
String& String::insert(unsigned int pos, char value, unsigned int len)
{
if (!(value && len))
return *this;
if (pos > m_length)
pos = m_length;
unsigned int newLen = len + m_length;
char* data = strAlloc(newLen,pos < m_length ? 0 : m_string);
if (!data)
return *this;
if (m_string) {
if (!pos)
// Insert before existing, copy old data after it
::memcpy(data + len,m_string,m_length);
else if (pos == m_length)
// Data reallocated. Reset held pointer
m_string = 0;
else {
// Insert middle
::memcpy(data,m_string,pos);
::memcpy(data + pos + len,m_string + pos,m_length - pos);
}
}
::memset(data + pos,value,len);
return changeStringData(data,newLen);
}
static char* string_printf(unsigned int& length, const char* format, va_list& va)
{
if (TelEngine::null(format) || !length)
@ -1376,33 +1339,6 @@ String& String::printf(const char* format, ...)
return *this;
}
String& String::printfAppend(unsigned int length, const char* format, ...)
{
va_list va;
va_start(va,format);
char* buf = string_printf(length,format,va);
va_end(va);
if (buf) {
*this << buf;
::free(buf);
}
return *this;
}
String& String::printfAppend(const char* format, ...)
{
va_list va;
va_start(va,format);
unsigned int len = TelEngine::null(format) ? 0 : (128 + ::strlen(format));
char* buf = string_printf(len,format,va);
va_end(va);
if (buf) {
*this << buf;
::free(buf);
}
return *this;
}
String& String::appendFixed(unsigned int fixedLength, const char* str, unsigned int len, char fill, int align)
{
if (len == (unsigned int)-1)
@ -1758,147 +1694,71 @@ String String::sqlEscape(const char* str, char extraEsc)
return s;
}
static inline bool isUriNoEsc(char c, const char* noEsc)
{
return (c == ' ' || c == '+' || c == '?' || c == '&') && !(noEsc && ::strchr(noEsc,c));
}
static inline char isUriEscape(char c, char extraEsc, const char* noEsc)
{
if ((unsigned char)c < ' ' || c == '%' || c == extraEsc || isUriNoEsc(c,noEsc))
return c;
return 0;
}
static inline char isUriEscape(char c, const char* extraEsc, const char* noEsc)
{
if ((unsigned char)c < ' ' || c == '%' || (extraEsc && ::strchr(extraEsc,c))
|| isUriNoEsc(c,noEsc))
return c;
return 0;
}
static inline String& uriEscapeFunc(String& buf, const char* str, const char* noEsc,
char extraCh, const char* extraStr)
String String::uriEscape(const char* str, char extraEsc, const char* noEsc)
{
String s;
if (TelEngine::null(str))
return buf;
unsigned int escape = 0;
return s;
char c;
const char* strPtr = str;
if (extraStr) {
while ((c = *strPtr++)) {
if (isUriEscape(c,extraStr,noEsc))
escape++;
}
while ((c=*str++)) {
if ((unsigned char)c < ' ' || c == '%' || c == extraEsc ||
((c == ' ' || c == '+' || c == '?' || c == '&') && !(noEsc && ::strchr(noEsc,c))))
s << '%' << hexEncode(c >> 4) << hexEncode(c);
else
s += c;
}
else {
while ((c = *strPtr++)) {
if (isUriEscape(c,extraCh,noEsc))
escape++;
}
}
if (!escape)
return buf << str;
unsigned int oldLen = buf.length();
buf.append(' ',(escape * 2) + (strPtr - str - 1));
if (buf.length() == oldLen)
return buf;
char* dest = (char*)buf.c_str() + oldLen;
if (extraStr) {
while ((c = *str++)) {
if (isUriEscape(c,extraStr,noEsc)) {
*dest++ = '%';
*dest++ = hexEncode(c >> 4);
*dest++ = hexEncode(c);
}
else
*dest++ = c;
}
}
else {
while ((c = *str++)) {
if (isUriEscape(c,extraCh,noEsc)) {
*dest++ = '%';
*dest++ = hexEncode(c >> 4);
*dest++ = hexEncode(c);
}
else
*dest++ = c;
}
}
return buf;
return s;
}
String& String::uriEscapeTo(String& buf, const char* str, char extraEsc, const char* noEsc)
{
return uriEscapeFunc(buf,str,noEsc,extraEsc,0);
}
String& String::uriEscapeTo(String& buf, const char* str, const char* extraEsc, const char* noEsc)
{
return uriEscapeFunc(buf,str,noEsc,0,extraEsc);
}
String& String::uriUnescapeTo(String& buf, const char* str, bool setPartial, int* errptr)
String String::uriEscape(const char* str, const char* extraEsc, const char* noEsc)
{
String s;
if (TelEngine::null(str))
return buf;
return s;
char c;
bool unescape = false;
const char* pos = str;
while ((c = *pos++)) {
if ((unsigned char)c < ' ' || c == '%') {
unescape = true;
break;
}
while ((c=*str++)) {
if ((unsigned char)c < ' ' || c == '%' || (extraEsc && ::strchr(extraEsc,c)) ||
((c == ' ' || c == '+' || c == '?' || c == '&') && !(noEsc && ::strchr(noEsc,c))))
s << '%' << hexEncode(c >> 4) << hexEncode(c);
else
s += c;
}
int ePtr = -1;
if (unescape) {
char* newData = strAlloc(::strlen(str));
if (!newData) {
return s;
}
String String::uriUnescape(const char* str, int* errptr)
{
String s;
if (TelEngine::null(str))
return s;
const char *pos = str;
char c;
while ((c=*pos++)) {
if ((unsigned char)c < ' ') {
if (errptr)
*errptr = 0;
return buf;
*errptr = (pos-str) - 1;
return s;
}
char* set = newData;
pos = str;
while ((c = *pos++)) {
if ((unsigned char)c < ' ') {
ePtr = (pos - str) - 1;
break;
else if (c == '%') {
int hiNibble = hexDecode(*pos++);
if (hiNibble < 0) {
if (errptr)
*errptr = (pos-str) - 1;
return s;
}
if (c == '%') {
int hiNibble = hexDecode(*pos++);
if (hiNibble < 0) {
ePtr = (pos - str) - 1;
break;
}
int loNibble = hexDecode(*pos++);
if (loNibble < 0) {
ePtr = (pos - str) - 1;
break;
}
c = ((hiNibble << 4) | loNibble) & 0xff;
int loNibble = hexDecode(*pos++);
if (loNibble < 0) {
if (errptr)
*errptr = (pos-str) - 1;
return s;
}
*set++ = c;
c = ((hiNibble << 4) | loNibble) & 0xff;
}
if (ePtr < 0 || setPartial) {
*set = 0;
if (buf.c_str() != str)
buf << newData;
else
buf = newData;
}
::free(newData);
s += c;
}
else if (buf.c_str() != str)
buf << str;
else
buf = str;
if (errptr)
*errptr = ePtr;
return buf;
*errptr = -1;
return s;
}
unsigned int String::hash(const char* value, unsigned int h)
@ -2120,90 +1980,6 @@ const String* String::atom(const String*& str, const char* val)
return str;
}
static unsigned int c_find_str(bool start, const char* str, const char* what,
int lenStr, int lenWhat, bool caseInsensitive)
{
if (!lenStr || !lenWhat || TelEngine::null(str) || TelEngine::null(what))
return 0;
if (lenStr < 0)
lenStr = ::strlen(str);
if (lenWhat < 0)
lenWhat = ::strlen(what);
if (lenStr < lenWhat)
return 0;
if (!start)
str += lenStr - lenWhat - 1;
if (caseInsensitive) {
if (::strncasecmp(str,what,lenWhat))
return 0;
}
else if (::strncmp(str,what,lenWhat))
return 0;
return lenWhat;
}
unsigned int String::c_starts_with(const char* str, const char* what, int lenStr, int lenWhat,
bool caseInsensitive)
{
return c_find_str(true,str,what,lenStr,lenWhat,caseInsensitive);
}
unsigned int String::c_ends_with(const char* str, const char* what, int lenStr, int lenWhat,
bool caseInsensitive)
{
return c_find_str(false,str,what,lenStr,lenWhat,caseInsensitive);
}
unsigned int String::c_skip_chars(const char*& str, const char* what, int len, bool skipFound)
{
if (!len || TelEngine::null(str) || TelEngine::null(what))
return 0;
const char* orig = str;
if (skipFound) {
if (len < 0) {
if (what[1])
while (*str) {
if (!::strchr(what,*str))
break;
str++;
}
else
while (*str == *what)
str++;
}
else if (what[1])
while (len-- && *str) {
if (!::strchr(what,*str))
break;
str++;
}
else
while (len-- && *str == *what)
str++;
}
else if (len < 0) {
if (what[1])
while (*str) {
if (::strchr(what,*str))
break;
str++;
}
else
while (*str && *str != *what)
str++;
}
else if (what[1])
while (len-- && *str) {
if (::strchr(what,*str))
break;
str++;
}
else
while (len-- && *str && *str != *what)
str++;
return (unsigned int)(str - orig);
}
Regexp::Regexp()
: m_regexp(0), m_compile(true), m_flags(0)
@ -2440,348 +2216,4 @@ const String& String::decodeFlags(uint64_t flags, const TokenDict64* tokens, boo
return *this;
}
String& String::changeStringData(char* data, unsigned int len)
{
char* tmp = m_string;
if (data)
data[len] = 0;
m_string = data;
m_length = len;
if (tmp)
::free(tmp);
changed();
return *this;
}
//
// MatchingItemDump
//
static inline void addFlags(String& buf, const String& flags)
{
if (flags)
buf << '[' << flags << "] ";
}
static inline const char* miType(const MatchingItemBase* item)
{
if (!item)
return "";
if (item->itemList())
return "list";
if (item->itemString())
return "string";
if (item->itemRegexp())
return "regexp";
if (item->itemRandom())
return "random";
if (item->itemCustom())
return item->itemCustom()->type().safe("custom");
return "unknown";
}
static const TokenDict s_miDumpFlags[] = {
{"no_initial_list_desc", MatchingItemDump::NoInitialListDesc},
{0,0}
};
static inline String dumpIndent(const String& buf)
{
String s;
for (const char* ss = buf; (ss && *ss); ++ss)
if (*ss == '\r')
s << "\\r";
else if (*ss == '\n')
s << "\\n";
else
s << *ss;
return s;
}
void MatchingItemDump::init(const NamedList& params)
{
for (ObjList* o = params.paramList()->skipNull(); o; o = o->skipNext()) {
NamedString* ns = static_cast<NamedString*>(o->get());
if (ns->name() == YSTRING("flags"))
m_flags = ns->encodeFlags(s_miDumpFlags);
else if (ns->name() == YSTRING("rex_enclose"))
m_rexEnclose = (*ns)[0];
else if (ns->name() == YSTRING("str_enclose"))
m_strEnclose = (*ns)[0];
else if (ns->name() == YSTRING("name_value_sep"))
m_nameValueSep = *ns;
else if (ns->name() == YSTRING("prop_negated"))
m_negated = (*ns)[0];
else if (ns->name() == YSTRING("prop_caseinsensitive"))
m_caseInsentive = (*ns)[0];
else if (ns->name() == YSTRING("prop_rex_basic"))
m_regexpBasic = (*ns)[0];
else if (ns->name() == YSTRING("prop_rex_extended"))
m_regexpExtended = (*ns)[0];
}
}
String& MatchingItemDump::dumpValue(const MatchingItemBase* item, String& buf,
const String& indent, const String& origIndent, unsigned int depth) const
{
if (!item)
return buf;
String tmp;
// Done if already dumped (item implements dumpValue())
if (item->dumpValue(tmp,this,indent,origIndent,depth))
return buf << tmp;
XDebug("MatchingItemDump",DebugAll,
"dumpValue (%p) %s '%s' depth=%u indent='%s'/'%s' [%p]",
item,miType(item),item->name().safe(),depth,dumpIndent(indent).safe(),
dumpIndent(origIndent).safe(),this);
if (item->itemList()) {
for (unsigned int i = 0; i < item->itemList()->length(); ++i) {
String tmp;
buf << dump(item->itemList()->at(i),tmp,indent,origIndent,depth);
}
}
else {
const MatchingItemString* str = item->itemString();
const MatchingItemRegexp* rex = str ? 0 : item->itemRegexp();
String flags;
if (item->negated())
flags << m_negated;
if (str) {
if (str->caseInsensitive())
flags << m_caseInsentive;
addFlags(buf,flags);
buf << m_strEnclose << item->itemString()->value() << m_strEnclose;
}
else if (rex) {
if (rex->value().isCaseInsensitive())
flags << m_caseInsentive;
if (rex->value().isExtended())
flags << m_regexpExtended;
else
flags << m_regexpBasic;
addFlags(buf,flags);
buf << m_rexEnclose << item->itemRegexp()->value() << m_rexEnclose;
}
else {
addFlags(buf,flags);
if (item->itemRandom()) {
buf << "RANDOM " << item->itemRandom()->value();
if (item->itemRandom()->maxValue() == 100)
buf << '%';
else
buf << '/' << item->itemRandom()->maxValue();
}
else if (item->itemCustom())
buf << "<CUSTOM " << item->itemCustom()->type() << '>';
else
buf << "<UNKNOWN>";
}
}
XDebug("MatchingItemDump",DebugAll,"Dumped value (%p) '%s' [%p]\r\n-----\r\n%s\r\n-----",
item,item->name().safe(),this,buf.safe());
return buf;
}
String& MatchingItemDump::dump(const MatchingItemBase* item, String& buf,
const String& indent, const String& origIndent, unsigned int depth) const
{
if (!item)
return buf;
XDebug("MatchingItemDump",DebugAll,
"dump (%p) %s '%s' flags=0x%x depth=%u indent='%s'/'%s' [%p]",
item,miType(item),item->name().safe(),m_flags,depth,
dumpIndent(indent).safe(),dumpIndent(origIndent).safe(),this);
unsigned int oLen = buf.length();
item->dump(buf,this,indent,origIndent,depth);
// Done if already dumped (item implements dump())
if (oLen != buf.length())
return buf;
const MatchingItemList* list = item->itemList();
if (list) {
String tmp;
if (depth || 0 == (m_flags & NoInitialListDesc)) {
String flags;
if (list->negated())
flags.append("negated",",");
if (!list->matchAll())
flags.append("any",",");
if (flags)
flags.printf(" [%s]",flags.safe());
if (depth || flags || item->name())
tmp << item->name().safe("List") << ':' << flags;
}
// Nothing dumped at first level:
// print the rest of the list at same alignment
String newIndent = indent;
if (tmp) {
buf << indent << tmp;
newIndent += origIndent;
}
for (unsigned int i = 0; i < list->length(); ++i) {
tmp.clear();
buf << dump(list->at(i),tmp,newIndent,origIndent,depth + 1);
}
}
else {
String val;
dumpValue(item,val);
if (item->name() || val) {
buf << indent;
if (item->name())
buf << item->name() << m_nameValueSep.safe("=");
buf << val;
}
}
XDebug("MatchingItemDump",DebugAll,"Dumped (%p) '%s' [%p]\r\n-----\r\n%s\r\n-----",
item,item->name().safe(),this,buf.safe());
return buf;
}
//
// MatchingItemRegexp
//
MatchingItemRegexp* MatchingItemRegexp::build(const char* name, const String& str,
int negated, bool insensitive, bool extended, int fail)
{
Regexp rex(0,extended,insensitive);
if (str) {
if (negated >= 0)
rex.assign(str);
else {
unsigned int pos = str.length() - 1;
negated = (str[pos] == '^') ? 1 : 0;
if (negated)
rex.assign(str.substr(0,pos));
else
rex.assign(str);
}
}
else if (negated < 0)
negated = 0;
if (fail > 1) {
if (!rex.compile())
return 0;
}
else if (fail < 0 && !rex.c_str())
return 0;
return new MatchingItemRegexp(name,rex,negated);
}
//
// MatchingItemList
//
bool MatchingItemList::change(MatchingItemBase* item, int pos, bool ins, unsigned int overAlloc)
{
if (!item) {
unsigned int n = count();
if (ins || pos < 0 || pos >= (int)n)
return false;
// Remove
GenObject* gen = m_value.take(pos);
if (gen) {
for (; pos < (int)n; ++pos)
m_value.set(m_value.take(pos + 1),pos);
TelEngine::destruct(gen);
}
return true;
}
// Detect first free position
unsigned int firstFree = 0;
while (m_value.at(firstFree))
firstFree++;
if (firstFree >= m_value.length()) {
if (firstFree >= m_value.resize(m_value.length() + 1 + overAlloc,true)) {
TelEngine::destruct(item);
return false;
}
}
if (pos < 0 || pos >= (int)firstFree)
pos = firstFree;
else if (ins) {
for (; (int)firstFree > pos; --firstFree)
m_value.set(m_value.take(firstFree - 1),firstFree);
}
m_value.set(item,pos);
return true;
}
MatchingItemBase* MatchingItemList::copy() const
{
MatchingItemList* lst = new MatchingItemList(name(),matchAll(),negated());
if (length()) {
unsigned int overAlloc = length() - 1;
for (unsigned int i = 0; i < length(); ++i) {
const MatchingItemBase* it = at(i);
MatchingItemBase* item = it ? it->copy() : 0;
if (item) {
lst->append(item,overAlloc);
overAlloc = 0;
}
}
}
return lst;
}
static inline bool matchingListRun(const MatchingItemList& mil, MatchingParams* params,
const NamedList* list, const String& str = String::empty())
{
bool allMatch = mil.matchAll();
#ifdef XDEBUG
Debugger dbg(DebugAll,"MatchingItemList MATCHING",
" name='%s' all=%s negated=%s input='%s' params=(%p) [%p]",
mil.name().safe(),String::boolText(allMatch),String::boolText(mil.negated()),
list ? list->safe("list") : "<string>",params,&mil);
#endif
int pos = -1;
while (true) {
const MatchingItemBase* item = const_cast<MatchingItemBase*>(mil.at(++pos));
if (!item)
break;
bool ok = list ? item->matchListParam(*list,params) : item->matchString(str,params);
XDebug("MatchingItemList",DebugAll,"matched [%s] idx=%d (%p) '%s' type=%s [%p]",
String::boolText(ok),pos,item,item->name().safe(),miType(item),&mil);
// Matched: done if not all match (any match)
// Not matched: done if all match is required
if (ok) {
if (!allMatch)
return true;
}
else if (allMatch)
return false;
}
// End of list reached
// Empty list or match any: not matched
// Otherwise: matched
XDebug("MatchingItemList",DebugAll,"End of matching [%s] pos=%d [%p]",
String::boolText(pos && allMatch),pos,&mil);
return pos && allMatch;
}
bool MatchingItemList::runMatchString(const String& str, MatchingParams* params) const
{
return matchingListRun(*this,params,0,str);
}
bool MatchingItemList::runMatchListParam(const NamedList& list, MatchingParams* params) const
{
return matchingListRun(*this,params,&list);
}
MatchingItemBase* MatchingItemList::optimize(MatchingItemList* list)
{
if (!list || list->at(1))
return list;
MatchingItemBase* ret = static_cast<MatchingItemBase*>(list->m_value.take(0));
if (ret) {
// Reverse item (not)negated flag if list is negated to keep the same matching behaviour
if (list->negated())
ret->m_notNegated = !ret->m_notNegated;
}
TelEngine::destruct(list);
return ret;
}
/* vi: set ts=8 sw=4 sts=4 noet: */

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing
@ -104,15 +104,7 @@ namespace TelEngine {
#define DebugDef DebugNote
#define DebugMax DebugAll
#ifndef OUT_BUFFER_SIZE
#define OUT_BUFFER_SIZE 16384
#elif OUT_BUFFER_SIZE < 4096
#undef OUT_BUFFER_SIZE
#define OUT_BUFFER_SIZE 4096
#elif OUT_BUFFER_SIZE > 32768
#undef OUT_BUFFER_SIZE
#define OUT_BUFFER_SIZE 32768
#endif
#define OUT_BUFFER_SIZE 8192
#define OUT_HEADER_SIZE 112
// RefObject mutex pool array size
@ -692,31 +684,6 @@ void DebugEnabler::debugCopy(const DebugEnabler* original)
m_chain = 0;
}
void DebugEnabler::debugSet(const char* desc)
{
if (TelEngine::null(desc))
return;
String s(desc);
if (s.startSkip("level")) {
int dbg = debugLevel();
s >> dbg;
if (s == YSTRING("+")) {
if (debugLevel() > dbg)
dbg = debugLevel();
}
else if (s == YSTRING("-")) {
if (debugLevel() < dbg)
dbg = debugLevel();
}
debugLevel(dbg);
}
else if (s == YSTRING("reset")) {
debugLevel(TelEngine::debugLevel());
debugEnabled(true);
}
}
Debugger::Debugger(const char* name, const char* format, ...)
: m_name(name), m_level(DebugAll)
{
@ -1295,6 +1262,7 @@ ObjList& GenObject::getObjCounters()
return s_counters;
}
#ifndef ATOMIC_OPS
static MutexPool s_refMutex(REFOBJECT_MUTEX_COUNT,false,"RefObject");
#endif
@ -1432,6 +1400,58 @@ void RefPointerBase::assign(RefObject* oldptr, RefObject* newptr, void* pointer)
}
NamedCounter::NamedCounter(const String& name)
: String(name), m_count(0), m_enabled(getObjCounting()), m_mutex(0)
{
#ifndef ATOMIC_OPS
m_mutex = s_refMutex.mutex(this);
#endif
}
int NamedCounter::inc()
{
#ifdef ATOMIC_OPS
#ifdef _WINDOWS
return InterlockedIncrement((LONG*)&m_count);
#else
return __sync_add_and_fetch(&m_count,1);
#endif
#else
Lock lock(m_mutex);
return ++m_count;
#endif
}
int NamedCounter::dec()
{
#ifdef ATOMIC_OPS
#ifdef _WINDOWS
return InterlockedDecrement((LONG*)&m_count);
#else
return __sync_fetch_and_sub(&m_count,1);
#endif
#else
Lock lock(m_mutex);
return --m_count;
#endif
}
int NamedCounter::add(int val)
{
#ifdef ATOMIC_OPS
#ifdef _WINDOWS
return InterlockedExchangeAdd((LONG*)&m_count,(LONG)val);
#else
return __sync_add_and_fetch(&m_count,val);
#endif
#else
Lock lock(m_mutex);
m_count += val;
return m_count;
#endif
}
void SysUsage::init()
{
if (!s_startTime)
@ -1505,35 +1525,6 @@ double SysUsage::runTime(Type type)
#endif
}
//
// AtomicOp
//
#ifndef ATOMIC_OP_LOCK_COUNT
#define ATOMIC_OP_LOCK_COUNT 101
#endif
#ifdef YATOMIC_LOCK
static RWLockPool s_atomicLock(ATOMIC_OP_LOCK_COUNT,"AtomicOp");
#endif
AtomicOp::AtomicOp()
: m_lock(0)
{
#ifdef YATOMIC_LOCK
m_lock = s_atomicLock.lock(this);
#endif
}
bool AtomicOp::efficient()
{
#ifdef YATOMIC_LOCK
return false;
#else
return true;
#endif
}
};
/* vi: set ts=8 sw=4 sts=4 noet: */

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing
@ -1965,6 +1965,14 @@ unsigned int XmlElement::copyAttributes(NamedList& list, const String& prefix) c
return copy;
}
void XmlElement::setAttributes(NamedList& list, const String& prefix, bool skipPrefix)
{
if (prefix)
m_element.copySubParams(list,prefix,skipPrefix);
else
m_element.copyParams(list);
}
// Retrieve a namespace attribute. Search in parent or inherited for it
String* XmlElement::xmlnsAttribute(const String& name) const
{
@ -2278,7 +2286,7 @@ void XmlDoctype::toString(String& dump, const String& indent) const
*/
// Maximul number of predicates in step
#ifndef XPATH_MAX_PREDICATES
#define XPATH_MAX_PREDICATES 10
#define XPATH_MAX_PREDICATES 5
#endif
#ifdef XDEBUG
@ -2591,15 +2599,10 @@ protected:
class XPathEscapedString
{
YNOCOPY(XPathEscapedString);
public:
inline XPathEscapedString(String* str, bool literal = false)
: m_delimiter(0), m_esc(false), m_literal(literal), m_str(str)
{}
inline XPathEscapedString(const XPathEscapedString& other, String* str)
: m_delimiter(other.m_delimiter), m_esc(other.m_esc), m_literal(other.m_literal),
m_str(str)
{}
inline void setLiteral(bool on)
{ m_literal = on; }
inline char delimiter() const
@ -2642,12 +2645,6 @@ public:
}
protected:
inline void copy(const XPathEscapedString& other) {
m_delimiter = other.m_delimiter;
m_esc = other.m_esc;
m_literal = other.m_literal;
}
char m_delimiter; // Delimiter. Non 0 indicates data is used
bool m_esc; // String contains escaped chars
bool m_literal; // String is an XPATH literal
@ -2661,17 +2658,8 @@ public:
inline XPathString(bool literal = false)
: XPathEscapedString(this,literal)
{}
inline XPathString(const XPathString& other)
: String(*static_cast<const String*>(&other)),
XPathEscapedString(*static_cast<const XPathEscapedString*>(&other),this)
{}
inline String& dump(String& buf, bool escape = false) const
{ return dumpString(buf,escape); }
inline XPathString& operator=(const XPathString& other) {
String::assign(other.c_str());
XPathEscapedString::copy(other);
return *this;
}
};
// XPath regexp literal
@ -2682,12 +2670,6 @@ public:
: XPathEscapedString(this),
m_match(true)
{}
inline XPathRegexp(const XPathRegexp& other)
: Regexp(*static_cast<const Regexp*>(&other)),
XPathEscapedString(*static_cast<const XPathEscapedString*>(&other),this),
m_match(other.m_match),
m_flags(other.m_flags)
{}
inline bool matches(const char* value) const
{ return m_match == Regexp::matches(value); }
inline const XPathString& flags() const
@ -2723,15 +2705,6 @@ public:
}
return buf;
}
inline XPathRegexp& operator=(const XPathRegexp& other) {
String::assign(other.c_str());
Regexp::setFlags(other.isExtended(),other.isCaseInsensitive());
Regexp::assign(other.c_str());
m_match = other.m_match;
m_flags = other.m_flags;
XPathEscapedString::copy(other);
return *this;
}
protected:
bool m_match; // (Reverse) match
@ -2739,103 +2712,6 @@ protected:
};
namespace TelEngine {
class XPathStep;
class XPathNodeCheck
{
public:
enum Process {
Xml,
Attribute,
Text,
ChildText,
};
inline XPathNodeCheck(XPathStep* step, ObjList* resList)
: m_step(step), m_nameCheck(0), m_resList(resList),
m_type(Xml), m_index(0), m_count(0), m_next(0), m_nextChild(0)
{}
inline unsigned int index() const
{ return m_index; }
inline void setType(int t)
{ m_type = t; }
inline XmlElement* startXml(const XmlElement& xml, bool root = false) {
if (!root) {
m_next = xml.getChildren().skipNull();
return advanceXml();
}
m_count = 1;
return (!m_nameCheck || *m_nameCheck == xml.getTag()) ? (XmlElement*)&xml : 0;
}
inline XmlText* startText(const XmlElement& xml) {
m_nextChild = xml.getChildren().skipNull();
return advanceText();
}
inline NamedString* startAttr(const XmlElement& xml) {
m_next = xml.attributes().paramList()->skipNull();
return advanceAttr();
}
inline XmlElement* advanceXml()
{ return XmlFragment::getElement(m_next,m_nameCheck); }
inline XmlText* advanceText()
{ return XmlFragment::getText(m_nextChild); }
inline NamedString* advanceAttr() {
m_next = findAttr(m_next,m_nameCheck);
if (!m_next)
return 0;
ObjList* tmp = m_next;
m_next = m_next->skipNext();
return static_cast<NamedString*>(tmp->get());
}
inline void advanceIndex()
{ m_index++; }
inline int checkIndex(unsigned int idx) {
if (m_index == idx)
return XPathProcHandleStop;
return m_index < idx ? XPathProcCont : XPathProcStop;
}
inline int checkPosLast() {
if (Xml == m_type) {
if (m_count)
return checkIndex(m_count);
return procNotLastPos(XmlFragment::findElement(m_next,m_nameCheck,0));
}
if (Attribute == m_type)
return procNotLastPos(findAttr(m_next,m_nameCheck));
// Text process
if (ChildText == m_type && m_next) {
XmlElement* next = XmlFragment::findElement(m_next,0,0);
if (next && XmlFragment::findText(next->getChildren().skipNull()))
return XPathProcCont;
// No next element or next element has no text child. Check current element
}
return procNotLastPos(XmlFragment::findText(m_nextChild));
}
static inline int procNotLastPos(bool notLast)
{ return notLast ? XPathProcCont : XPathProcHandleStop; }
static inline ObjList* findAttr(ObjList* lst, const String* name) {
if (!(lst && name))
return lst;
for (; lst; lst = lst->skipNext()) {
if (*name == static_cast<NamedString*>(lst->get())->name())
return lst;
}
return 0;
}
XPathStep* m_step;
const String* m_nameCheck;
ObjList* m_resList;
protected:
int m_type;
unsigned int m_index;
unsigned int m_count;
ObjList* m_next; // Next item (Xml or Attribute)
ObjList* m_nextChild; // Next child (XML text)
};
class XPathPredicate
{
public:
@ -2849,8 +2725,6 @@ public:
XmlName = 0x10,
Attribute, // XML element attribute match
Child, // XML child match (presence or text),
Position = 0x20,
PosLast, // Node position in list: last item
};
// Operators
enum Opc {
@ -2863,10 +2737,6 @@ public:
inline XPathPredicate()
: m_type(0), m_opc(0)
{}
inline XPathPredicate(const XPathPredicate& other)
: m_type(other.m_type), m_opc(other.m_opc),
m_name(other.m_name), m_value(other.m_value), m_regexp(other.m_regexp)
{}
inline int type() const
{ return m_type; }
inline unsigned int opc() const
@ -2878,15 +2748,13 @@ public:
inline bool valid() const
{ return 0 != type(); }
inline bool isPosition() const
{ return 0 != (Position & type()); }
inline bool sameIndex(const XPathPredicate& other) const
{ return opc() == other.opc(); }
inline int check(XPathNodeCheck& data, const XmlElement* xml = 0,
const NamedString* attr = 0) const {
if (Index == m_type)
return data.checkIndex(m_opc);
if (PosLast == m_type)
return data.checkPosLast();
{ return Index == type(); }
inline int check(unsigned int index, const XmlElement* xml = 0, const NamedString* attr = 0) const {
if (Index == m_type) {
if (index == m_opc)
return XPathProcHandleStop;
return index < m_opc ? XPathProcCont : XPathProcStop;
}
if (Text == m_type || Child == m_type) {
const String* txt = xml ?
((Child == m_type) ? xml->childText(m_name) : &(xml->getText())) : 0;
@ -2954,14 +2822,6 @@ public:
m_value.dump(buf,escape);
}
}
inline XPathPredicate& operator=(const XPathPredicate& other) {
m_type = other.m_type;
m_opc = other.m_opc;
m_name = other.m_name;
m_value = other.m_value;
m_regexp = other.m_regexp;
return *this;
}
static inline const char* opcName(int opc)
{ return lookup(opc,s_opcAll); }
@ -3011,44 +2871,36 @@ const TokenDict XPathPredicate::s_typeName[] = {
{"attribute", Attribute},
{"child", Child},
{"text", Text},
{"last", PosLast},
{0,0},
};
typedef GenericVector<XPathPredicate> XPathPredicateVector;
class XPathPredicateList
{
public:
inline XPathPredicateList()
: m_predicates(2), m_indexPredicate(0), m_stopProc(false)
: m_indexPredicate(0), m_stopProc(false)
{}
inline XPathPredicateList(const XPathPredicateList& other)
: m_predicates(other.m_predicates), m_indexPredicate(0), m_stopProc(other.m_stopProc)
{
if (other.m_indexPredicate) {
const XPathPredicate* p = other.m_predicates.data();
for (unsigned int i = 0; i < other.m_predicates.length(); ++i, ++p)
if (p == other.m_indexPredicate) {
m_indexPredicate = m_predicates.data(i,1);
break;
}
}
}
inline int check(XPathNodeCheck& data, const XmlElement* xml = 0,
inline bool valid() const
{ return m_predicates[0].valid(); }
inline XPathPredicate* first()
{ return m_predicates; }
inline const XPathPredicate* first() const
{ return m_predicates; }
inline int check(unsigned int& index, const XmlElement* xml = 0,
const NamedString* attr = 0) const {
const XPathPredicate* f = m_predicates.first();
if (!f)
if (!valid())
return XPathProcHandleCont;
data.advanceIndex();
index++;
int rProc = XPathProcHandleCont;
if (!m_stopProc) {
// Always evalute predicates with position first. May lead to fast return
if (m_indexPredicate)
check(rProc,true,*m_indexPredicate,data,xml,attr);
for (unsigned int i = 0; rProc > 0 && i < m_predicates.length(); ++i, ++f) {
if (f != m_indexPredicate)
check(rProc,!(m_indexPredicate || i),*f,data,xml,attr);
check(rProc,true,*m_indexPredicate,index,xml,attr);
const XPathPredicate* f = first();
for (unsigned int i = 0; rProc > 0 && i < XPATH_MAX_PREDICATES && f->valid(); ++i, ++f) {
if (!f->isPosition())
check(rProc,!(m_indexPredicate || i),*f,index,xml,attr);
}
}
else
@ -3059,13 +2911,36 @@ public:
"Checked %s '%s' idx=%u. Predicate(s) not matched proc=%s",
(xml ? "xml" : (attr ? "attribute" : "???")),
(xml ? xml->tag() : ((attr ? attr->name().c_str() : ""))),
data.index(),lookup(rProc,s_xpathProcAct));
index,lookup(rProc,s_xpathProcAct));
#endif
return rProc;
}
inline bool check(int& rProc, bool first, const XPathPredicate& pred,
unsigned int index, const XmlElement* xml, const NamedString* attr) const {
#ifdef XPATH_XDEBUG_FIND
String tmp;
pred.dump(tmp) << " index=" << index;
#endif
if (first) {
rProc = pred.check(index,xml,attr);
#ifdef XPATH_XDEBUG_FIND
Debug("XPath",DebugAll,"Predicate %s check returned %s",
tmp.safe(),lookup(rProc,s_xpathProcAct));
#endif
}
else {
int proc = pred.check(index,xml,attr);
rProc = filterProc(rProc,proc);
#ifdef XPATH_XDEBUG_FIND
Debug("XPath",DebugAll,"Predicate %s check returned %s. Filtered: %s",
tmp.safe(),lookup(proc,s_xpathProcAct),lookup(rProc,s_xpathProcAct));
#endif
}
return rProc > 0;
}
inline String& dump(String& buf, bool escape = false) const {
const XPathPredicate* f = m_predicates.first();
for (unsigned int i = 0; i < m_predicates.length(); ++i, ++f)
const XPathPredicate* f = first();
for (unsigned int i = 0; i < XPATH_MAX_PREDICATES && f->valid(); ++i, ++f)
f->dump(buf,escape);
return buf;
}
@ -3090,34 +2965,9 @@ public:
return XPathProcCont;
}
XPathPredicateVector m_predicates; // Predicate expression(s)
XPathPredicate m_predicates[XPATH_MAX_PREDICATES]; // Predicate expression(s)
XPathPredicate* m_indexPredicate;
bool m_stopProc;
protected:
inline bool check(int& rProc, bool first, const XPathPredicate& pred,
XPathNodeCheck& data, const XmlElement* xml, const NamedString* attr) const {
#ifdef XPATH_XDEBUG_FIND
String tmp;
pred.dump(tmp) << " index=" << data.index();
#endif
if (first) {
rProc = pred.check(data,xml,attr);
#ifdef XPATH_XDEBUG_FIND
Debug("XPath",DebugAll,"Predicate %s check returned %s",
tmp.safe(),lookup(rProc,s_xpathProcAct));
#endif
}
else {
int proc = pred.check(data,xml,attr);
rProc = filterProc(rProc,proc);
#ifdef XPATH_XDEBUG_FIND
Debug("XPath",DebugAll,"Predicate %s check returned %s. Filtered: %s",
tmp.safe(),lookup(proc,s_xpathProcAct),lookup(rProc,s_xpathProcAct));
#endif
}
return rProc > 0;
}
};
namespace TelEngine {
@ -3145,7 +2995,7 @@ public:
{}
inline XPathStep(const XPathStep& other)
: String(other.c_str()),
m_nodeType(other.m_nodeType), m_predicates(other.m_predicates)
m_nodeType(other.m_nodeType)
{}
inline int nodeType() const
{ return m_nodeType; }
@ -3158,7 +3008,7 @@ public:
inline const String* valueMatch() const
{ return valueMatchAny() ? 0 : (const String*)this; }
inline const XPathPredicateList* predicates() const
{ return m_predicates.m_predicates.length() ? &m_predicates : 0; }
{ return m_predicates.valid() ? &m_predicates : 0; }
inline String& dump(String& buf, bool escape = false) {
switch (m_nodeType) {
case Xml:
@ -3176,6 +3026,17 @@ public:
}
return m_predicates.dump(buf,escape);
}
// Check if a given item should be added to result set
inline int checkHandle(const XPath* path, unsigned int& resultIdx,
const XmlElement* xml = 0, const NamedString* attr = 0,
const String& name = String::empty(), const String* nameCheck = 0) const {
if (nameCheck && name != *nameCheck) {
XPathDebugFind("XPath",DebugAll,"Checked %s '%s': not matched [%p]",
(xml ? "xml" : "attribute"),name.c_str(),path);
return XPathProcCont;
}
return m_predicates.check(resultIdx,xml,attr);
}
static inline bool matchAny(const char* buf, unsigned int len)
{ return 1 == len && '*' == *buf; }
@ -3228,17 +3089,20 @@ XPath::XPath(const char* value, unsigned int flags)
}
XPath::XPath(const XPath& other)
: m_flags(0),
m_status(NotParsed),
m_errorItem(0)
: String(other.c_str()),
m_flags(other.m_flags),
m_status(other.m_status),
m_errorItem(other.m_errorItem),
m_error(other.m_error)
{
XDebug(DebugAll,"XPath(%p) [%p]",&other,this);
copy(other,true);
XDebug(DebugAll,"XPath(%s,0x%x) [%p]",c_str(),m_flags,this);
ObjList* itAppend = &m_items;
for (ObjList* o = other.m_items.skipNull(); o; o = o->skipNext())
itAppend->append(new XPathStep(*static_cast<XPathStep*>(o->get())));
}
XPath::~XPath()
{
XDebug(DebugAll,"~XPath [%p]",this);
reset();
}
@ -3343,21 +3207,26 @@ int XPath::find(unsigned int& total, const XmlElement& src, const GenObject*& re
ObjList* lstAppend = list;
unsigned int n = 0;
bool stop = false;
XPathNodeCheck info(&it,list);
unsigned int resultIdx = 0;
while (true) {
if (it.isElementNode()) {
ObjList* o = 0;
XmlElement* x = 0;
if (absolute)
x = (XmlElement*)&src;
else {
o = src.getChildren().skipNull();
x = XmlFragment::getElement(o);
}
bool xmlReq = 0 != (what & FindXml);
// Last item but no XML/TEXT requested ?
if (!nextItem && !xmlReq && 0 == (what & FindText)) {
stop = true;
break;
}
info.setType(XPathNodeCheck::Xml);
info.m_nameCheck = it.valueMatch();
XPathNodeCheck infoText(0,list);
infoText.setType(XPathNodeCheck::Text);
for (XmlElement* x = info.startXml(src,absolute); x; x = info.advanceXml()) {
int proc = it.m_predicates.check(info,x);
const String* tag = it.valueMatch();
for ( ; x; x = XmlFragment::getElement(o)) {
int proc = it.checkHandle(this,resultIdx,x,0,x->getTag(),tag);
if (proc > 0) {
if (nextItem)
proc = XPathStep::filterProc(proc,find(n,*x,res,list,what,nextItem,step + 1));
@ -3368,7 +3237,7 @@ int XPath::find(unsigned int& total, const XmlElement& src, const GenObject*& re
}
else
// Last item pointing to an XML but XML was not requested
proc = XPathStep::filterProc(proc,getText(n,*x,res,infoText));
proc = XPathStep::filterProc(proc,getText(n,*x,0,resultIdx,res,list));
}
if (proc < 0 || XPathProcHandleStop == proc)
break;
@ -3376,7 +3245,7 @@ int XPath::find(unsigned int& total, const XmlElement& src, const GenObject*& re
break;
}
if (XPathStep::Text == it.m_nodeType || XPathStep::ChildText == it.m_nodeType) {
if (XPathStep::Text == it.m_nodeType || XPathStep::Text == it.m_nodeType) {
// No need to check anything if the requested result set contains other data
// type (non XML Text) or we have a next item
// If next item is present there is nothing there to match (XmlText has no attributes, children ...)
@ -3386,14 +3255,12 @@ int XPath::find(unsigned int& total, const XmlElement& src, const GenObject*& re
stop = true;
break;
}
if (XPathStep::Text == it.m_nodeType) {
info.setType(XPathNodeCheck::Text);
getText(n,src,res,info);
}
if (XPathStep::Text == it.m_nodeType)
getText(n,src,&it,resultIdx,res,list);
else {
info.setType(XPathNodeCheck::ChildText);
for (XmlElement* x = info.startXml(src); x; x = info.advanceXml()) {
int proc = getText(n,*x,res,info);
ObjList* o = src.getChildren().skipNull();
for (XmlElement* x = XmlFragment::getElement(o); x; x = XmlFragment::getElement(o)) {
int proc = getText(n,*x,&it,resultIdx,res,list);
if (proc < 0 || XPathProcHandleStop == proc)
break;
}
@ -3408,10 +3275,10 @@ int XPath::find(unsigned int& total, const XmlElement& src, const GenObject*& re
stop = true;
break;
}
info.setType(XPathNodeCheck::Attribute);
info.m_nameCheck = it.valueMatch();
for (NamedString* ns = info.startAttr(src); ns; ns = info.advanceAttr()) {
int proc = it.m_predicates.check(info,0,ns);
const String* name = it.valueMatch();
for (const ObjList* o = src.attributes().paramList()->skipNull(); o; o = o->skipNext()) {
NamedString* ns = static_cast<NamedString*>(o->get());
int proc = it.checkHandle(this,resultIdx,0,ns,ns->name(),name);
if (proc > 0) {
n++;
if (!xpathAddResult(this,ns,res,lstAppend))
@ -3438,19 +3305,20 @@ int XPath::find(unsigned int& total, const XmlElement& src, const GenObject*& re
return rProc;
}
int XPath::getText(unsigned int& total, const XmlElement& src, const GenObject*& res,
XPathNodeCheck& data) const
int XPath::getText(unsigned int& total, const XmlElement& src, const XPathStep* step,
unsigned int& resultIdx, const GenObject*& res, ObjList* list) const
{
XPathDebugFind("XPath",DebugAll,"Get text xml '%s' multi=%s step=(%p) [%p]",
src.getTag().c_str(),String::boolText(data.m_resList),data.m_step,this);
src.getTag().c_str(),String::boolText(list),step,this);
unsigned int n = 0;
int proc = XPathProcHandleCont;
for (XmlText* t = data.startText(src); t; t = data.advanceText()) {
if (data.m_step)
proc = data.m_step->m_predicates.check(data);
ObjList* o = src.getChildren().skipNull();
for (XmlText* t = XmlFragment::getText(o); t; t = XmlFragment::getText(o)) {
if (step)
proc = step->checkHandle(this,resultIdx);
if (proc > 0) {
n++;
if (!xpathAddResult(this,&t->getText(),res,data.m_resList))
if (!xpathAddResult(this,&t->getText(),res,list))
proc = XPathProcStop;
}
if (proc < 0 || XPathProcHandleStop == proc)
@ -3464,8 +3332,7 @@ int XPath::getText(unsigned int& total, const XmlElement& src, const GenObject*&
void XPath::changed()
{
if (FCopying != m_flags)
parsePath();
parsePath();
}
#define XPATH_SET_STATUS_BREAK(code,str) { setStatus(code,data.step(),str); break; }
@ -3598,7 +3465,8 @@ void XPath::parsePath()
prevStep = step;
}
for (unsigned int i = 0; ; ++i) {
XPathPredicate* p = step->m_predicates.first();
for (unsigned int i = 0; ; ++p, ++i) {
if (!data.strictParse)
data.skipBlanks();
if (data.isStepEnd())
@ -3610,14 +3478,10 @@ void XPath::parsePath()
}
if (i == XPATH_MAX_PREDICATES)
XPATH_SET_STATUS_BREAK(ERange,"Too many predicates");
XPathPredicateVector& predicates = step->m_predicates.m_predicates;
if (!predicates.resize(1 + predicates.length()))
XPATH_SET_STATUS_BREAK(ERange,"Memory allocation failure");
XPathPredicate* p = predicates.last();
if (!(parseStepPredicate(data,p) && checkStepPredicate(data,step,p))) {
predicates.removeLast(n);
if (!parseStepPredicate(data,p))
break;
if (!checkStepPredicate(data,step,p))
break;
}
}
if (m_status)
break;
@ -3687,6 +3551,7 @@ bool XPath::parseStepPredicate(XPathParseData& data, XPathPredicate* pred)
XPATH_SET_SYNTAX_RET("Predicate index value invalid or out of range");
pred->m_type = XPathPredicate::Index;
pred->m_opc = (unsigned int)val;
XPathDebugParse("XPath",DebugInfo,"Parsed predicate %u '%s' value=%u [%p]",
pred->type(),pred->typeName(),pred->opc(),this);
return true;
@ -3847,33 +3712,22 @@ bool XPath::parseStepPredicate(XPathParseData& data, XPathPredicate* pred)
case 0:
// Function not found. Check for selector type function
func = lookup(fn,XPathPredicate::s_typeName);
#define XPATH_PARSE_END_FUNC_DONE \
if (data.ended() || data != ')') \
XPATH_SET_SYNTAX_RET(tmp.printf("Expecting ')' after '%s' start",fn.c_str())); \
func = 0; \
selector.advance(); \
data.advance();
switch (func) {
case XPathPredicate::Text:
XPATH_PARSE_END_FUNC_DONE;
if (data.ended() || data != ')')
XPATH_SET_SYNTAX_RET("Expecting ')' after predicate input selector");
pred->m_type = XPathPredicate::Text;
break;
case XPathPredicate::PosLast:
XPATH_PARSE_END_FUNC_DONE;
// Skip now until predicate end: we don't expect anything else
XPATH_PARSE_STRICT_BLANK_PREDICATE;
if (!data.isPredicatedEnd())
tmp.printf("Expecting predicate end after position selector");
pred->m_type = XPathPredicate::PosLast;
func = 0;
selector.advance();
data.advance();
break;
default:
if (!func)
tmp.printf("Unknown function '%s' in predicate",fn.c_str());
else
if (func)
tmp.printf("Predicate function '%s' not implemented",fn.c_str());
else
tmp.printf("Unknown function '%s' in predicate",fn.c_str());
XPATH_SET_SYNTAX_RET(tmp);
}
#undef XPATH_PARSE_END_FUNC_DONE
break;
default:
tmp.printf("Predicate function '%s' not implemented",fn.c_str());
@ -4002,11 +3856,10 @@ bool XPath::checkStepPredicate(XPathParseData& data, XPathStep* step, XPathPredi
else {
if (data.strictParse)
XPATH_SET_STATUS_RET(ESemantic,"Repeated index predicate in step");
if (!pred->sameIndex(*(lst.m_indexPredicate))) {
if (pred->opc() != lst.m_indexPredicate->opc())
if (data.checkEmptyRes)
XPATH_SET_STATUS_RET(EEmptyResult,"Path step with different index value in predicate");
lst.m_stopProc = true;
}
}
}
else {
@ -4025,8 +3878,6 @@ bool XPath::checkStepPredicate(XPathParseData& data, XPathStep* step, XPathPredi
}
break;
case XPathPredicate::Index:
case XPathPredicate::Position:
case XPathPredicate::PosLast:
break;
default:
Debug("XPath",DebugStub,
@ -4107,22 +3958,4 @@ bool XPath::setStatus(unsigned int code, unsigned int itemIdx, const char* error
return false;
}
XPath& XPath::copy(const XPath& other, bool constr)
{
if (&other == this)
return *this;
if (!constr)
reset();
m_flags = FCopying;
String::assign(other.c_str()),
m_flags = other.m_flags;
m_status = other.m_status;
m_errorItem = other.m_errorItem;
m_error = other.m_error;
ObjList* itAppend = &m_items;
for (ObjList* o = other.m_items.skipNull(); o; o = o->skipNext())
itAppend->append(new XPathStep(*static_cast<XPathStep*>(o->get())));
return *this;
}
/* vi: set ts=8 sw=4 sts=4 noet: */

View File

@ -6,7 +6,7 @@
* Adapted for YATE by Paul Chitescu
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -9,7 +9,7 @@
* Adapted for YATE by Paul Chitescu
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -7,7 +7,7 @@
* Adapted for YATE by Paul Chitescu
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2013-2023 Null Team
* Copyright (C) 2013-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -1,8 +0,0 @@
Makefile
YateLocal*
core*
*.o
*.a
*.orig
*~
.*.swp

View File

@ -5,7 +5,7 @@
* Classes for interfacing with Mac OS X API
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -3,7 +3,7 @@
* This file is part of the YATE Project http://YATE.null.ro
*
* Yet Another Telephony Engine - a fully featured software PBX and IVR
* Copyright (C) 2004-2023 Null Team
* Copyright (C) 2004-2014 Null Team
*
* This software is distributed under multiple licenses;
* see the COPYING file in the main directory for licensing

View File

@ -1,7 +0,0 @@
Makefile
core*
*.o
*.a
*.orig
*~
.*.swp

View File

@ -1,4 +0,0 @@
core*
*.orig
*~
.*.swp

View File

@ -1,7 +0,0 @@
Makefile
core*
*.o
*.a
*.orig
*~
.*.swp

View File

@ -1,7 +0,0 @@
Makefile
core*
*.o
*.a
*.orig
*~
.*.swp

View File

@ -1,6 +0,0 @@
core*
*.o
*.a
*.orig
*~
.*.swp

View File

@ -1,6 +0,0 @@
core*
*.o
*.a
*.orig
*~
.*.swp

View File

@ -1,6 +0,0 @@
core*
*.o
*.a
*.orig
*~
.*.swp

View File

@ -1,6 +0,0 @@
core*
*.o
*.a
*.orig
*~
.*.swp

View File

@ -1,6 +0,0 @@
core*
*.o
*.a
*.orig
*~
.*.swp

View File

@ -1,6 +0,0 @@
core*
*.o
*.a
*.orig
*~
.*.swp

View File

@ -1,6 +0,0 @@
core*
*.o
*.a
*.orig
*~
.*.swp

View File

@ -1,6 +0,0 @@
core*
*.o
*.a
*.orig
*~
.*.swp

View File

@ -1,6 +0,0 @@
core*
*.o
*.a
*.orig
*~
.*.swp

View File

@ -1,6 +0,0 @@
core*
*.o
*.a
*.orig
*~
.*.swp

View File

@ -1,6 +0,0 @@
core*
*.o
*.a
*.orig
*~
.*.swp

Some files were not shown because too many files have changed in this diff Show More