<?xml version="1.0" encoding="ISO-8859-1"?>
<!DOCTYPE book PUBLIC "-//OASIS//DTD DocBook V3.1//EN"
     [
<!ENTITY figtype "#FIGTYPE#">
<!ENTITY timestamp "#DATE#">
<!ENTITY version "#VERSION#">
<!ENTITY % draft "#DRAFTS#">
]>

<!-- Embbeb your block with these to set it to "draft"
<![%draft;[ <your block> ]]>
-->

<book>

<bookinfo>
	<title>Kannel &version; User's Guide</title>
	<subtitle>Open Source WAP and SMS gateway</subtitle>

<authorgroup>
	<author>
		<firstname>Andreas</firstname>
		<surname>Fink</surname>
		<affiliation>
			<jobtitle>Chairman &amp; CTO</jobtitle>
			<orgname>Global Networks Inc.</orgname>
			<address> <email>andreas@fink.org</email>
				<otheraddr>http://www.smsrelay.com</otheraddr>
				<otheraddr>http://www.gni.ch</otheraddr>
			</address>
		</affiliation>
	</author>
	<author>
		<firstname>Bruno</firstname>
		<surname>Rodrigues</surname>
		<affiliation>
			<address> 
				<email>bruno.rodrigues@litux.org</email>
				<otheraddr>http://litux.org/bruno</otheraddr>
			</address>
		</affiliation>
	</author>
	<author>
		<firstname>Stipe</firstname>
		<surname>Tolj</surname>
		<affiliation>
			<jobtitle>Chief Technology Scientist</jobtitle>
			<orgname>Wapme Systems AG</orgname>
			<address> 
				<email>stolj@wapme.de</email>
				<otheraddr>http://www.wapme.de</otheraddr>
			</address>
		</affiliation>
	</author>
	<author>
		<firstname>Aarno</firstname>
		<surname>Syv&auml;nen</surname>
		<affiliation>
			<jobtitle>Chief MMS Developer</jobtitle>
			<orgname>Global Networks Inc.</orgname>
			<address> 
				<email>as@gni.ch</email>
				<otheraddr>http://www.gni.ch</otheraddr>
			</address>
		</affiliation>
	</author>
	<author>
		<firstname>Alexander</firstname>
		<surname>Malysh</surname>
		<affiliation>
			<!-- <jobtitle>Chief Kannel Developer</jobtitle>
			<orgname>Centrium GmbH</orgname> -->
			<address> 
				<email>amalysh at kannel.org</email>
				<!-- <otheraddr>http://www.centrium.de</otheraddr> -->
			</address>
		</affiliation>
	</author>
	<author>
		<firstname>Lars</firstname>
		<surname>Wirzenius</surname>
		<affiliation>
			<jobtitle>Gateway architect</jobtitle>
			<orgname>former Wapit Ltd</orgname>
			<!--<address> <email>liw@wapit.com</email>
			<otheraddr>http://www.wapit.com</otheraddr>
			</address>-->
		</affiliation>
	</author>
	<author>
		<firstname>Kalle</firstname>
		<surname>Marjola</surname>
		<affiliation>
			<jobtitle>Senior Software Engineer</jobtitle>
			<orgname>Enpocket</orgname>
			<address> 
				<email>marjola@enpocket.com</email>
				<otheraddr>http://www.enpocket.com</otheraddr>
			</address>
		</affiliation>
	</author>

</authorgroup>

	<abstract>
		<title>Abstract</title> 
		<para>
		This document describes how
		to install and use Kannel, the Open Source WAP and SMS Gateway
		originally developed by Wapit Ltd (now out of business) and now
		being developed further by the open source community, namely the 
		Kannel Group.
		</para>
	</abstract>

  <revhistory>
    <revision>
      <revnumber>&version;</revnumber>
      <date>&timestamp;</date>
    </revision>
  </revhistory>

</bookinfo>


<chapter>
<title>Introduction</title>

	<highlights>
	<para>This chapter introduces WAP and SMS in general terms, and explains the
	role of the gateway in WAP and SMS, outlining their duties and features. It
	also explains why the Kannel project was started in the first place,
	and why it is open source.</para>
	</highlights>
	
	<para>With hundreds of millions of mobile phones in use all over the
	world, the market for services targeted at mobile users
	is mind-bogglingly immense.  Even simple services find plenty of users,
	as long as they're useful or fun. Being able to get news, send e-mail
	or just be entertained wherever you are is extremely attractive to
	many.</para>

	<para>The hottest technology for implementing mobile services is WAP,
	short for Wireless Application Protocol. It lets the phone act
	as a simple web browser, but optimizes the markup language,
	scripting language, and the transmission protocols for wireless
	use. The optimized protocols are translated to plain old HTTP by
	a <emphasis>WAP gateway</emphasis>.</para>

	<para>Kannel is an open source WAP gateway. It attempts to
	provide this essential part of the WAP infrastructure freely
	to everyone so that the market potential for WAP services,
	both from wireless operators and specialized service providers,
	will be realized as efficiently as possible.</para>

	<para>Kannel also works as an SMS gateway for GSM networks. Almost
	all GSM phones can send and receive SMS messages, so this is
	a way to serve many more clients than just those using a new
	WAP phone.</para>

        <para>In addition, Kannel operates as <emphasis>Push Proxy Gateway 
        </emphasis>, or <emphasis>PPG</emphasis>, making possible for content 
        servers to send data to the phones. This is a new type of WAP service,
        and have many interesting applications. Usually servers know whether
        some data is new, not the users. </para>

	<para>Kannel's quality has been recognized on March 7, 2001 when it
	was <ulink url="http://www.kannel.org/oldnews.shtml#wapcert">certified</ulink> 
	by <ulink url="http://www.wapforum.org">Wap Forum</ulink>
	as the first WAP 1.1 gateway in the world.</para>

	<para>Greater quality recognition are the quantity of companies 
	using Kannel to successful connect to a variety of SMSC protocols 
	in lots of countries.</para>

	<para><ulink url="http://www.opensource.org">Open Source</ulink>
	is a way to formalize the principle of openness by placing the
	source code of a product under a Open Source compliant software
	license. The BSD license was chosen over other Open Source
	licenses by the merit of placing the least amount of limitations
	on what a third party is able to do with the source code. In
	practice this means that Kannel is going to be a fully-featured
	WAP implementation and compatible with the maximum number of
	bearers with special emphasis on SMSC compatibility.
	The Kannel project was founded by Wapit Ltd in June, 1999.</para>
	
	
<sect1>
<title>Overview of WAP</title>

	<para>WAP, short for Wireless Application Protocol, is a
	collection of various languages and tools and an infrastructure for
	implementing services for mobile phones. Traditionally such
	services have worked via normal phone calls or short textual
	messages (e.g., SMS messages in GSM networks). Neither are very
	efficient to use, nor very user friendly.  WAP makes it possible
	to implement services similar to the World Wide Web.</para>
	
	<para>Unlike marketers claim, WAP does not bring the existing
	content of the Internet directly to the phone. There are too many
	technical and other problems for this to ever work properly. The
	main problem is that Internet content is mainly in the form of
	HTML pages, and they are written in such way that they require
	fast connections, fast processors, large memories, big screens,
	audio output and often also fairly efficient input mechanisms.
	That's OK, since they hopefully work better for traditional
	computers and networks that way. However, portable phones have
	very slow processors, very little memory, abysmal and intermittent
	bandwidth, and extremely awkward input mechanisms. Most existing
	HTML pages do not work on mobiles phones, and never will.</para>
	
	<para>WAP defines a completely new markup language, the Wireless
	Markup Language (WML), which is simpler and much more strictly
	defined than HTML.  It also defines a scripting language,
	WMLScript, which all browsers are required to support. To make
	things even simpler for the phones, it even defines its own
	bitmap format (Wireless Bitmap, or WBMP).</para>
	
	<para>HTTP is also too inefficient for wireless use. However, by using
	a semantically similar binary and compressed format it
	is possible to reduce the protocol overhead to a few bytes per
	request, instead of the usual hundreds of bytes. Thus, WAP defines a
	new protocol stack to be used. However, to make things simpler
	also for the people actually implementing the services, WAP
	introduces a gateway between the phones and the servers providing
	content to the phones.</para>

        <figure>
        <title>Logical position of WAP gateway (and PPG)between a phone and a 
        content server.</title>
        <graphic fileref="wap-gateway&figtype;"></graphic>
        </figure>

	<para>The WAP gateway talks to the phone using the WAP protocol
	stack, and translates the requests it receives to normal
	HTTP. Thus content providers can use any HTTP servers and
	utilize existing know-how about HTTP service implementation
	and administration.</para>
	
	<para>In addition to protocol translations, the gateway
	also compresses the WML pages into a more compact form, to
	save on-the-air bandwidth and to further reduce the phone's
	processing requirements. It also compiles WMLScript programs
	into a byte-code format. Latest WAP specifications defines some 
	additional conversions that Kannel is starting to implement, like
	multipart/form-data, multipart/mixed or MMS content conversion.</para>
	
	<para>Kannel is not just a WAP gateway. It also works as an
	SMS gateway.  Although WAP is the hot and technically superior
	technology, SMS phones exist in huge numbers and SMS services are
	thus quite useful. Therefore, Kannel functions simultaneously
	as both a WAP and an SMS gateway.</para>

</sect1>

<sect1>
<title>Overview of WAP Push</title>
       <para>Previous chapter explained pull mode of operation: the phone
       initiates the transaction. There is, however, situations when the
       server (called in this context a push initiator) should be the 
       initiator, for instance, when it must send a mail notification or a
       stock quote. For this purpose WAP Forum defined WAP Push.</para>

       <para>Push is an application level service, sitting on the top of
       existing WAP stack. It defines two protocols, OTA and PAP. OTA is
       a ligthweigth protocol speaking with WAP stack (to be more specific,
       with WSP), PAP speaks with the push initiator. It defines three kind
       of XML documents, one for the push data itself and another for 
       protocol purposes (these are called pap document or push control 
       documents). </para>

       <para>The server does not simply send push content to the phone, the
       user would surely not accept, for instance, interrupting of a voice 
       call. Instead it sends a specific XML document, either Service 
       Indication or Service Loading. These inform the user about the content 
       become available, and it is displayed only when it is not interrupting 
       anything. It contains an URL specifying the service and a text for user 
       describing the content. Then the user can decide does he accept push or not.
       </para>

       <para>The push content is send ed to the phones over SMS, but the 
       content is fetched by the phone over IP bearer, for instance CSD
       or GPRS. Because Push Proxy Gateway tokenises SI and SL documents, it 
       may fit one SMS message (if not, it is segmented for transfer). </para>

       <para>Using two bearers seems to be an unnecessary complication. But
       quite simply, phones currently operate this way. Push over GPRS can 
       only simplify matters.</para>
</sect1>
	
<sect1>
<title>Overview of SMS</title>

      <para>SMS, short messaging service, is a way to send short (160
      character) messages from one GSM phone to another. It can also
      be used to send regular text as well as advanced content like 
      operator logos, ringing tones, business cards
      and phone configurations.</para>

      <para><emphasis>SMS services</emphasis> are content services
      initiated by SMS message to certain (usually short) phone
      number, which then answers with requested content, if available.</para>

      <para>When SMS services are used, the client (mobile terminal) 
      sends an SMS
      message to certain number, usually a very short specialized
      number, which points to specific SMS center responsible
      for that number (plus possibly many others). This SMS center
      then sends the message onward to specified receiver in intra- or
      Internet, using an SMS center specific protocol. For example, a
      Nokia SMS center uses CIMD protocol.</para>

      <para>As practically every different kind of SMS center uses different
      protocol, an <emphasis>SMS gateway</emphasis> is used to handle
      connections with SMS centers and to relay them onward in an
      unified form. Kannel's biggest feature is to abstract each SMSC protocol
      to a well-known HTTP protocol, simplifying services deployment.</para>

        <figure>
        <title>Logical position of SMS gateway between a phone and a content server.</title>
        <graphic fileref="sms-gateway&figtype;"></graphic>
        </figure>

      <para>An SMS gateway can also be used to relay SMS messages from
      one GSM network to another, if the networks do not roam messages
      normally.</para>

      <para>Kannel works as an SMS gateway, talking with many
      different kind of SMS centers, and relaying the messages onward
      to content providers, as HTTP queries. Content providers then
      answer to this HTTP query and the answer is sent back to mobile
      terminal, with appropriate SMS center connection using SMS center
      specific protocol.</para>

      <para>In addition to serving mobile originated (MO) SMS messages
      Kannel also works as an SMS push gateway - content providers can
      request Kannel to send SMS messages to terminals. Kannel then
      determines the correct SMS center to relay the SMS message and
      sends the SMS message to that SMS center, again using SMS center
      specific protocol. This way the content provider does not need
      to know any SMS center specific protocol, just unified Kannel
      SMS sending interface.</para>

</sect1>

	
<sect1>
<title>Features</title>

	<sect2>
	<title>WAP</title>
		<para>
			<itemizedlist>
			<listitem><para>Fully compliant with WAP 1.1 specification</para></listitem>
			<listitem><para>Already implements some WAP 1.2 and even WAP 2.0 features.</para></listitem>
			</itemizedlist>
		</para>
	</sect2>
	<sect2>
	<title>WAP Push</title>
		<para>
			<itemizedlist>
			<listitem><para>Supports WAP Push SI and SL</para></listitem>
			<listitem><para>...</para></listitem>
			</itemizedlist>
		</para>
	</sect2>
	<sect2>
	<title>SMS</title>
		<para>
			<itemizedlist>
			<listitem><para>Supports a variety of SMSC protocols, namely:</para>
				<itemizedlist>
				<listitem><para>CMG's UCP/EMI 4.0 and 3.5</para></listitem>
				<listitem><para>...</para></listitem>
				</itemizedlist>
			</listitem>
			<listitem><para>Full support for MO and MT messages</para></listitem>
			</itemizedlist>
		</para>
	</sect2>
</sect1>

<sect1>
<title>Requirements</title>

	<para>Kannel is being developed on Linux systems,
	and should be fairly easy to export to other Unix-like
	systems. However, we don't yet support other platforms, due to lack
	of time, although it should be working without major problems on 
	Windows (through Cygwin), Solaris and FreeBSD.
	</para>
	
	<para>Kannel requires the following software environment:
	
	<itemizedlist>

	<listitem><para>C compiler and libraries for ANSI C, with normal
		Unix extensions such as BSD sockets and related tools. 
		(GNU's GCC tool-chain is recommended)</para></listitem>

	<listitem><para>The Gnome XML library (known as
		gnome-xml and libxml), version 2.2.5 or newer. See <ulink
		url="http://xmlsoft.org/xml.html">http://xmlsoft.org/xml.html</ulink>.
		</para>
		<para>If you are installing it from your distribution's packages, you'll need
		<literal>libxml2-dev</literal> in addition to run-time <literal>libxml2</literal> package
		libraries.</para></listitem>
	
	<listitem><para>GNU Make.</para></listitem>

	<listitem><para>An implementation of POSIX threads
		(<filename>pthread.h</filename>).</para></listitem>

	<listitem><para>GNU Bison 1.28, if you want to modify the WMLScript
		compiler (a pre-generated parser is included for those who just
		want to compile Kannel).</para></listitem>

	<listitem><para>DocBook processing tools: DocBook style-sheets,
		jade, jadetex, etc; see <filename>README</filename>, section
                `Documentation', for more information (pre-formatted versions
                of the documentation are available, and you can compile Kannel
                itself even without the documentation tools).</para></listitem>
	
	<listitem><para>GNU autoconf, if you want to modify the
		configuration script.</para></listitem>

	</itemizedlist>
	</para>
	
	<para>Hardware requirements are fluffier. Some informal benchmarkings 
	have shown that with a reasonably fast PC architecture (e.g. 400MHz 
	Pentium II with 128MB RAM), SMS performance's bottleneck is always on the
	SMSC side, even for example with multiple connections summing a pipeline with 
	400 msg/sec.  We haven't benchmarked Kannel yet on WAP side, so there are 
	no hard numbers.</para>

</sect1>

</chapter>

<chapter>
<title>Installing the gateway</title>

	<para>This chapter explains how the gateway can be installed,
	either from a source code package or by using a pre-compiled
	binary version. The goal of this chapter is to get the gateway
	compiled and all the files in the correct places; the next
	chapter will explain how the gateway is configured.</para>

	<note><para>If you are upgrading from a previous version, please look at
	<xref linkend="upgrading-notes"> for any important information.</para></note>

<sect1>
<title>Getting the source code</title>

	<para>The source code to
	Kannel is available for download at <ulink
	url="http://www.kannel.org/download.shtml">http://www.kannel.org/download.shtml</ulink>.
	It is available in various formats and you can choose to download
	either the latest release version or the daily snapshot of the
	development source tree for the next release version, depending
	on whether you want to use Kannel for production use or to
	participate in the development.</para>
	
	<para>If you're serious about development, you probably want to
	use CVS, the version control system used by the Kannel project.
	This allows you to participate in Kannel development much
	more easily than by downloading the current daily snapshot and
	integrating any changes you've made every day. CVS does that
	for you. (See the Kannel web site for more information on how
	to use CVS.)</para>

</sect1>


<sect1>
<title>Finding the documentation</title>

	<para>The documentation for Kannel consists of three parts:
	
	<orderedlist>
	<listitem><para><citetitle>User's Guide</citetitle>, i.e., the one
		you're reading at the moment.</para></listitem>
	<listitem><para><citetitle>Architecture and
		Design</citetitle>, in <filename>doc/arch</filename> or
		at <ulink url="http://www.kannel.org/arch.shtml">
		http://www.kannel.org/arch.shtml</ulink></para></listitem>
	<listitem><para>The <filename>README</filename> and various other
		text files in the source tree.</para></listitem>
		
	</orderedlist>
	</para>
	
	<para>You can also find general information on Kannel's 
		<ulink url="http://www.kannel.org">website</ulink> and
		information about existing problems at 
		<ulink url="http://bugs.kannel.org">our bugtracker</ulink>.
	</para>

	<para>
	We intend to cover everything you need to install and use Kannel
	is in <citetitle>User's Guide</citetitle>, but the guide is still 
	incomplete in this respect. Similarly, the <citetitle>Architecture and
	Design</citetitle> document should tell you everything you need
	to know to dive into the sources and quickly make your own modifications. 
	It's not a replacement for actually
	reading the source code, but it should work as a map to the
	source code.  The <filename>README</filename> is not supposed
	to be very important, nor contain much information. Instead,
	it will just point at the other documentation.
	</para>
	
</sect1>

<sect1>
<title>Compiling the gateway</title>

	<para>If you are using Kannel on a supported platform, or one
	that is similar enough to one, compiling Kannel should be trivial.
	After you have unpacked the source package of your choose,
	or after you have checked out the source code from CVS, enter
	the following commands:
	
	<screen><userinput>
        ./configure
        make
	</userinput></screen>
	
	The <filename>configure</filename> script investigates various
	things on your computer for the Kannel compilation needs, and
	writes out the <filename>Makefile</filename> used to compile
	Kannel. <command>make</command> then runs the commands to actually
	compile Kannel.</para>
	
	<para>If either command writes out an error message and stops
	before it finishes its job, you have a problem, and you either
	need to fix it yourself, if you can, or report the
	problem to the Kannel project. See <xref linkend="bug-reporting">
	for details.</para>
	
	<para>For detailed instruction on using the configuration
	script, see file <filename>INSTALL</filename>. That file is
	a generic documentation for <command>configure</command>. Kannel
	defines a few additional options:
	
    	<itemizedlist>

        <listitem><para><literal>--with-defaults=</literal><replaceable>type</replaceable>

	    Set defaults for the other options.
	    <replaceable>type</replaceable> is either <literal>speed</literal>
	    or <literal>debug</literal>.  The default is
            <literal>speed</literal>. <literal>speed</literal> options is equivalent to 
	    <literal>--with-malloc=native --disable-assertions</literal>, while 
	    <literal>debug</literal> is <literal>--with-malloc=checking --enable-assertions</literal>.

	    </para></listitem>

	<listitem><para><literal>--disable-docs (default is --enable-docs)</literal>

	    Use this option if you don't have DocBook installed and/or 
	    you want to save some time and CPU cycles. 
	    Pre-generated documentation is available on Kannel's site.
	    Default behavior is to build documentation, b.e., converting the User Guide and
	    the Architecture Guide from the DocBook markup language to
	    PostScript and HTML if DocBook is available.
	    </para></listitem>

	<listitem><para><literal>--enable-drafts (default is --disable-drafts)</literal>

	    When building documentation, include the sections marked as
	    <literal>draft</literal>.</para></listitem>

	<listitem><para><literal>--enable-debug (default is --disable-debug)</literal>

	    Enable non-reentrant development time
	    debugging of WMLScript compiler.</para></listitem>

	<listitem><para><literal>--disable-localtime (default is --enable-localtime)</literal>

	    Write log file time stamps in GMT, not in local time.
	    </para></listitem>

	<listitem><para><literal>--enable-assertions / --disable-assertions</literal>

	    Turn on or off runtime assertion checking.  <literal>enable</literal> makes
	    Kannel faster, but gives less information if it crashes.
	    Default value is dependent on <literal>--with-defaults</literal>.
	    </para></listitem>

	<listitem><para><literal>--with-malloc=</literal><replaceable>type</replaceable>

	    Select memory allocation module to use:
	    <replaceable>type</replaceable> is <literal>native</literal>,
            <literal>checking</literal>, or
            <literal>slow</literal>.  For production use you probably
	    want <literal>native</literal>.  The <literal>slow</literal>
            module is more thorough than <literal>checking</literal>,
	    but much slower. 
	    Default value is dependent on <literal>--with-defaults</literal>.
	    </para></listitem>

	<listitem><para><literal>--enable-mutex-stats</literal>

	    Produce information about lock contention.</para></listitem>

	<listitem><para><literal>--enable-start-stop-daemon</literal>

	    Compile the start-stop-daemon program.</para></listitem>

	<listitem><para><literal>--enable-pam</literal>

	    Enable using PAM for authentication of sendsms users for
	    smsbox.</para></listitem>

        <listitem><para><literal>--with-mysql</literal>

            Enable using MySQL libraries for DBPool and
            DLR support.</para></listitem>

        <listitem><para><literal>--with-mysql-dir=</literal><replaceable>DIR</replaceable>

            Where to look for MySQL libs and header files.
            DIR points to the installation of MySQL.</para></listitem>

        <listitem><para><literal>--with-sdb</literal>

            Enable using LibSDB libraries for dlr support.
            </para></listitem>

        <listitem><para><literal>--with-oracle</literal>

            Enable using Oracle OCI-Libraries for Oracle 8i/9i DBPool and
            DLR support.</para></listitem>

        <listitem><para><literal>--with-oracle-includes=</literal><replaceable>DIR</replaceable>

            Where to look for Oracle OCI-Header files.</para></listitem>

        <listitem><para><literal>--with-oracle-libs=</literal><replaceable>DIR</replaceable>

            Where to look for Oracle OCI-Library files.</para></listitem>

	<!-- XXX DAVI add openssl and others in here -->

	</itemizedlist>
	</para>
	
	<para>You may need to add compilations flags to configure:

	<screen><userinput>
	CFLAGS='-pthread' ./configure
	</userinput></screen>

	The above, for instance, seems to be required on FreeBSD. If you
	want to develop Kannel, you probably want to add CFLAGS that make
	your compiler use warning messages. For example, for GCC:
	
	<screen><userinput>
	CFLAGS='-Wall -O2 -g' ./configure
	</userinput></screen>
	
	(You may, at your preference, use even stricter checking options.)
	</para>

</sect1>

<sect1>
<title>Installing the gateway</title>

	<para>After you have compiled Kannel, you need to install
	certain programs in a suitable place. This is most easily
	done by using <command>make</command> again:
	
	<screen><userinput>
	make bindir=<replaceable>/path/to/directory</replaceable> install
	</userinput></screen>

	Replace <replaceable>/path/to/directory</replaceable> with the
	pathname of the actual directory where the programs should be
	installed. The programs that are installed are (as filenames
	from the root of the source directory):
	
	<simplelist>
	<member><filename>gw/bearerbox</filename></member>
	<member><filename>gw/smsbox</filename></member>
	<member><filename>gw/wapbox</filename></member>
	</simplelist>
	
	The version number of the gateway is added to the file names
	during installation. This makes it easier to have several
	versions installed, and makes it easy to go back to an older
	version if the new version proves problematic.</para>
	
	<para>Kannel consists of three programs called boxes: the
	bearer box is the interface towards the phones. It accepts
	WAP and SMS messages from the phones and sends them to the
	other boxes. The SMS box handles SMS gateway functionality,
	and the WAP box handles WAP gateway functionality. There can
	be several SMS boxes and several WAP boxes running and they
	don't have to run on the same host. This makes it possible
	to handle much larger loads.</para>

</sect1>

<sect1>
<title>Using pre-compiled binary packages</title>

<sect2>
<title>Installing Kannel from RPM packages</title>

	<para>This chapter explains how to install, upgrade and remove
	Kannel binary RPM packages.</para>
		
	<para>Before you install Kannel, check that you have libxml2
	installed on your system:</para>

	<screen><userinput>
	rpm -q libxml2
	</userinput></screen>
	
	<para>Installing Kannel</para>

	<para>1. Download the binary RPM packet from the Kannel
	web site.</para>
	
	<para>2. Install the RPM package:

	<screen><userinput>
	rpm -ivh kannel-<replaceable>VERSION</replaceable>.<replaceable>i386</replaceable>.rpm
	</userinput></screen>
	</para>

	<para>Upgrading Kannel</para>

	<para>1. Download the binary RPM packet from the Kannel
        web site.</para>

	<para>2. Upgrade the RPM package:

        <screen><userinput>
	rpm -Uvh kannel-<replaceable>VERSION</replaceable>.<replaceable>i386</replaceable>.rpm
	</userinput></screen>
        </para>
	
	<para>Removing Kannel</para>

	<para>1. Remove the RPM package:
	
	<screen><userinput>
	rpm -e kannel
	</userinput></screen>
	</para>

	<para>After you have installed Kannel from the RPM packages you
	should now be able to run the Kannel init.d script that will
	start Kannel as a WAP gateway. Run the script as root.</para>

	<screen><userinput>
	/etc/rc.d/init.d/kannel start
	</userinput></screen>

	<para>To stop the gateway just run the same script with the
	stop parameter.</para>

	<screen><userinput>
	/etc/rc.d/init.d/kannel stop
	</userinput></screen>
	
	<para>If Kannel is already running and you just want to quickly
	stop and start the gateway,e.g.to set a new configuration option,
	run the script with the restart parameter.</para>

	<screen><userinput>
	/etc/rc.d/init.d/kannel restart
	</userinput></screen>
	
	<para>If you want Kannel to run as a daemon, you need to add a
	symbolic link to the Kannel script from the runlevel you want
	Kannel to run in. E.g. to run Kannel in runlevel 5 add symbolic
	links to /etc/rc.d/rc5.d/.</para>

	<screen><userinput>
	cd /etc/rc.d/rc5.d/
	ln -s ../init.d/kannel S91kannel
	ln -s ../init.d/kannel K91kannel
	</userinput></screen>

	<para>To run Kannel as a SMS gateway you need to edit the
	configuration file which is at /etc/kannel/kannel.conf.
	In kannel's documentation directory 
	(<filename>/usr/share/doc/kannel</filename>) 
	there is an example file called examples/smskannel.conf. 
	It has some basic examples of the configuration groups needed 
	to run Kannel as a SMS gateway. For more detailed information 
	please see <filename>examples/kannel.conf</filename> in the
	same directory for a commented complete example, and read the 
	section "SMS gateway configuration" later in this same 
	document.</para>

	<para>The logging is disabled by default and you can enable
	it from the kannel.conf file. Just add the log-file option
	to the group of which box you want to log.</para>  
	
	<para>The documentation will be installed at 
	/usr/doc/kannel-VERSION/ or /usr/share/doc/kannel-VERSION/
	depending on if you used the RedHat 6.x or a 7.x or newer 
	package.</para>

	<para>In the Kannel documentation directory there is a HTML
	file called control.html. It is an example file that shows
	how to use the Kannel HTTP administration interface. It
	also has a template for sending SMS messages.</para>

</sect2>

<sect2>
<title>Installing Kannel from DEB packages</title>

	<para>This chapter explains how to install, upgrade and remove
	Kannel binary DEB packages.</para>

	<para>Kannel's packages are available on main Debian repository 
	(<ulink url="http://packages.debian.org/kannel">http://packages.debian.org/kannel</ulink>)
	although that version may be out-of-sync with latest Kannel version.
	</para>
	<!-- XXX DAVI add kannel packages and my repository here -->
		
	<para>Before you install Kannel, check that you have libxml2
	installed on your system:</para>

	<screen><userinput>
	dpkg -l libxml2
	</userinput></screen>
	
	<para>Installing or upgrading Kannel from Debian or Kannel repository</para>

	<para>1. Install or upgrade the package:

	<screen><userinput>
	apt-get install kannel
	</userinput></screen>
	</para>

	<para>See http://kannel.org/download.shtml#debian_repository for 
	informations about kannel repository sources.list</para>

	<para>Installing or upgrading Kannel from a file</para>

	<para>1. Download the binary DEB packet from the Kannel
	web site.</para>
	
	<para>2. Log in as root:</para>

	<screen><userinput>
	su -
	</userinput></screen>

	<para>3. Install or upgrade the DEB package:</para>
	<screen><userinput>
	dpkg -i kannel-<replaceable>VERSION</replaceable>.deb
	</userinput></screen>

	<para>Removing Kannel</para>
	
	<para>1. Log in as root:</para>

	<para>2. Remove the package keeping configuration files:</para>
	<screen><userinput>
	dpkg --remove kannel
	</userinput></screen>

	<para>3. Remove the package completely:</para>
	<screen><userinput>
	dpkg --purge kannel
	</userinput></screen>

	<para>After you have installed Kannel from the DEB packages you
	should now be able to run the Kannel init.d script that will
	start Kannel as a WAP gateway. Run the script as root.</para>

	<screen><userinput>
	/etc/init.d/kannel start
	</userinput></screen>

	<para>To stop the gateway just run the same script with the
	stop parameter.</para>

	<screen><userinput>
	/etc/init.d/kannel stop
	</userinput></screen>
	
	<para>If Kannel is already running and you just want to quickly
	stop and start the gateway,e.g.to set a new configuration option,
	run the script with the restart parameter.</para>

	<screen><userinput>
	/etc/init.d/kannel restart
	</userinput></screen>
	
	<para>If you don't want Kannel to run as a daemon, 
	run: </para>
	
	<screen><userinput>
	update-rc.d -f kannel remove
	</userinput></screen>

	<para>If you want to restore Kannel running as a daemon, you 
	need to add a
	symbolic link to the Kannel script from the runlevel you want
	Kannel to run in. E.g. to run Kannel in default runlevel, 
	just run: </para>
	
	<screen><userinput>
	update-rc.d kannel defaults
	</userinput></screen>
	
	<para>Kannel package starts by default with a wapbox daemon.
	To activate smsbox or select which box you want to start, 
	edit /etc/default/kannel and comment/uncomment START_xxxBOX.
	</para>

	<para>To run Kannel as a SMS gateway you need to edit the
	configuration file which is at /etc/kannel/kannel.conf.
	In /usr/share/docs/kannel/examples/ there are example files. 
	They have some basic examples of the configuration groups 
	needed to run Kannel as a SMS gateway. For
	more detailed information please read the section "SMS gateway
	configuration" later in this same document.</para>

	<para>The documentation will be installed at 
	/usr/share/doc/kannel/.</para>

	<para>In the Kannel documentation directory there is a html
	file called control.html. It is an example file that shows
	how to use the Kannel HTTP administration interface. It
	also has a template for sending SMS messages.</para>

	<para>Additionally to kannel-VERSION.deb, there's now an optional
	kannel-docs-VERSION.deb with documentation (userguide et al) and
	a kannel-extras-VERSION.deb with contrib and test stuff.</para>

	<para>If you want to test development version, use the packages
	called kannel-devel-*.deb.</para>

</sect2>

</sect1>

</chapter>


<chapter>
<title>Using the gateway</title>

	<para>This chapter explains how the gateway core, bearerbox,
        is configured and used.
	It covers the configuration file, keeping an eye on the gateway
	while it is running, and using the HTTP interface to control
	the gateway.</para>

        <para>After this chapter there is distinct chapter for each
        kind of gateway use: WAP gateway, SMS gateway and WAP Push
        proxy. These chapters explain the configuration and other
        aspects of gateway of that type.</para>
	
	<para>You can configure your Kannel to be only a WAP or a SMS
	gateway, or to be both at the same time. You just need to read
	each chapter and combine all configurations.</para>

	<para>There is only one configuration file for all parts of
	Kannel, although when Kannel is distributed to several hosts
	some lines from the configuration file can be removed in some
	hosts.</para>

<sect1>
<title>Configuring the gateway</title>

	<para>The configuration file can be divided into three parts:
	bearerbox configurations, smsbox configurations and
	wapbox configurations. Bearerbox part has one 'core' group
	and any used SMS center groups, while wapbox part has only
	one wapbox group. In smsbox part there is one smsbox group and
	then number of sms-service and sendsms-user groups.</para>

	<para>Details of each part are in an appropriate section of this
        documentation. The 'core' group used by the bearerbox is
        explained in this chapter, while 'wapbox' part is in the next
        chapter and 'smsbox', 'smsc' (SMS center), 'sms-service' and
        'sendsms-user' groups are in the SMS Kannel chapter.</para>

  

<sect2>
<title>Configuration file syntax</title>

	<para>A configuration file consists of groups of configuration variables. Groups are
	separated by empty lines, and each variable is defined on its
	own line. Each group in Kannel configuration is distinguished
	with a group variable. Comments are lines that begin with a number sign
	(<literal>#</literal>) and are ignored (they don't, for example,
	separate groups of variables).</para>
	
	<para>A variable definition line has the name of the variable,
	and equals sign (<literal>=</literal>) and the value of the
	variable. The name of the variable can contain any characters
	except whitespace and equals. The value of the variable is a
	string, with or without quotation marks (<literal></literal>)
	around it. Quotation marks are needed if the variable needs to
	begin or end with whitespace or contain special
	characters. Normal C 	escape character syntax works inside 
	quotation marks.</para>

	<para>Perhaps an example will make things easier to comprehend:

<programlisting>
1    # A do-nothing service.
2    group = sms-service
3    keyword = nop
4    text = "You asked nothing and I did it!"
5
6    # Default service.
7    group = sms-service
8    keyword = default
9    text = "No services defined"
</programlisting>

	The above snippet defines the keyword <literal>nop</literal>
	for an SMS service, and a default action for situation when
	the keyword in the SMS message does not match any defined
	service.</para>
	
	<para>Lines 1 and 6 are comment lines. Line 5 separates the
	two groups. The remaining lines define variables. The
	group type is defined by the group variable value.</para>
	
	<para>The various variables that are understood in each type
	of configuration group are explained below.</para>

	<para>Some variable values are marked as
	<literal>'bool'</literal>. The value for variable can be like
	true, false, yes, no, on, off, 0 or 1. Other values are
	treated as 'true' while if the variable is not present at all,
	it is treated as being 'false'.</para>

	<para>In order to make some configuration lines more readable
	you may use the delimiter '\' at the end of a line to wrap
	and concatenate the next line up to the current line. Here is 
	an example:

<programlisting>
1    # A group with a wrapped alias line
2    group = sms-service
3    keyword = hello
4    aliases = hallo;haalloo;\
5      heelloo;haelloo;healloo
5    text = "Hello world!"
</programlisting>
 
     The above example shows how a list for various alias keywords
     is wrapped to two lines using the line wrap delimiter. In order
     to use the delimiter '\' itself, you need to escape it via a
     prefixed '\' itself. So this is '\\' to escape the wrapping
     function and use the character in the string.</para>
     
</sect2>

<sect2 id="includes">
<title id="includes.title">Inclusion of configuration files</title>

	<para>A configuration file may contain a special directive 
	called <literal>include</literal> to include other 
	file or a directory with files to the configuration 
	processing.</para>
 
	<para>This allows to segment the specific configuration groups
	required for several services and boxes to different files and
	hence to have more control in larger setups.</para>

	<para>Here is an example that illustrates the <literal>include
	</literal> statement :

<programlisting>
group = core
admin-port = 13000
wapbox-port = 13002
admin-password = bar
wdp-interface-name = "*"
log-file = "/var/log/bearerbox.log"
log-level = 1
box-deny-ip = "*.*.*.*"
box-allow-ip = "127.0.0.1"

include = "wapbox.conf"

include = "configurations"
</programlisting>

	Above is the main <literal>kannel.conf</literal> configuration
	file that includes the following <literal>wapbox.conf</literal>
	file with all required directives for the specific box, and a 
	<literal>configurations</literal> directory which may include 
	more files to include.

<programlisting>
group = wapbox
bearerbox-host = localhost
log-file = "/var/log/wapbox.log"
log-level = 0
syslog-level = none
</programlisting>


	The above <literal>include</literal> statement may be defined
	at any point in the configuration file and at any inclusion 
	depth. Hence you can cascade numerous inclusions if necessary.
	</para>

	<para>At process start time inclusion of configuration files 
	breaks if either the included file can not be opened and 
	processed or the included file has been processed already in 
	the stack and a recursive cycling has been detected.</para>

</sect2>

<sect2>
<title>Core configuration</title>

  <para>Configuration for Kannel <emphasis>MUST</emphasis> always
  include a group for general bearerbox configuration. This group is
  named as 'core' in configuration file, and should be the first group
  in the configuration file.</para>

  <para>As its simplest form, 'core' group looks like this:

<programlisting>
group = core
admin-port = 13000
admin-password = f00bar
</programlisting>

   Naturally this is not sufficient for any real use, as you want to
   use Kannel as an SMS gateway, or WAP gateway, or both. Thus, one or
   more of the optional configuration variables are used. In following
   list (as in any other similar lists), all mandatory variables are
   marked with <literal>(m)</literal>, while conditionally mandatory
   (variables which must be set in certain cases) are marked with
   <literal>(c)</literal>.</para>


 <table frame="none">
  <title>Core Group Variables</title>
  <tgroup cols="3">
  <thead>
   <row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row>
  </thead>
  <tbody>
   <row><entry><literal>group (m)</literal></entry>
     <entry><literal>core</literal></entry>
     <entry valign="bottom">
       This is a mandatory variable
     </entry></row>

    <row><entry><literal>admin-port (m)</literal></entry>
     <entry>port-number</entry>
     <entry valign="bottom">
        The port number in which the bearerbox listens to HTTP
        administration commands. It is NOT the same as the HTTP
        port of the local HTTP server, just invent any port, but
        it must be over 1023 unless you are running Kannel as a
        root process (not recommended)
     </entry></row>

	 <row><entry><literal>admin-port-ssl (o)</literal></entry>
     <entry>bool</entry>
     <entry valign="bottom">
        If set to true a SSL-enabled administration HTTP server
		  will be used instead of the default insecure plain HTTP
		  server. To access the administration pages you will have
		  to use a HTTP client that is capable of talking to such
		  a server. Use the "https://" scheme to access the
		  secured HTTP server. Defaults to "no".
     </entry></row>

    <row><entry><literal>admin-password (m)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
         Password for HTTP administration commands (see below)
     </entry></row>

    <row><entry><literal>status-password</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
         Password to request Kannel status. If not set, no password is
	 required, and if set, either this or
	 <literal>admin-password</literal> can be used
     </entry></row>
   
    <row><entry><literal>admin-deny-ip</literal></entry>
     <entry morerows="1">IP-list</entry>
     <entry morerows="1" valign="bottom">
        These lists can be used to prevent connection from given IP 
  addresses. Each list can have several addresses, separated with    
  semicolons (';'). An asterisk ('*') can be used
        as a wild-card in a place of any ONE number, so *.*.*.*
        matches any IP.
     </entry></row>
    <row><entry><literal>admin-allow-ip</literal></entry></row>


    <row><entry><literal>smsbox-port (c)</literal></entry>
     <entry>port-number</entry>
     <entry valign="bottom">
        This is the port number to which the smsboxes, if any, connect.
        As with admin-port, this can be anything you want. Must be set
        if you want to handle any SMS traffic.
     </entry></row>
	  
	 <row><entry><literal>smsbox-port-ssl (o)</literal></entry>
     <entry>bool</entry>
     <entry valign="bottom">
	     If set to true, the smsbox connection module will be SSL-enabled.
		  Your smsboxes will have to connect using SSL to the bearerbox
		  then. This is used to secure communication between bearerbox
		  and smsboxes in case they are in separate networks operated and
		  the TCP communication is not secured on a lower network layer.
		  Defaults to "no".
     </entry></row>

    <row><entry><literal>wapbox-port (c)</literal></entry>
     <entry>port-number</entry>
     <entry valign="bottom">
        Like smsbox-port, but for wapbox-connections. If not set,
        Kannel cannot handle WAP traffic
     </entry></row>

	 <row><entry><literal>wapbox-port-ssl (o)</literal></entry>
     <entry>bool</entry>
     <entry valign="bottom">
	     If set to true, the wapbox connection module will be SSL-enabled.
		  Your wapboxes will have to connect using SSL to the bearerbox
		  then. This is used to secure communication between bearerbox
		  and wapboxes in case they are in separate networks operated and
		  the TCP communication is not secured on a lower network layer.
		  Defaults to "no".
     </entry></row>

    <row><entry><literal>box-deny-ip</literal></entry>
     <entry morerows="1">IP-list</entry>
     <entry morerows="1" valign="bottom">
        These lists can be used to prevent box connections from given IP 
        addresses. Each list can have several addresses, 
        separated with semicolons (';'). An asterisk ('*') can be used
        as a wild-card in place of any ONE number, so *.*.*.*
        matches any IP.
     </entry></row>
    <row><entry><literal>box-allow-ip</literal></entry></row>

    <row><entry><literal>udp-deny-ip</literal></entry>
     <entry morerows="1">IP-list</entry>
     <entry morerows="1" valign="bottom">
        These lists can be used to prevent UDP packets from given IP 
        addresses, thus preventing unwanted use of the WAP gateway.
	Used the same way as <literal>box-deny-ip</literal> and
	<literal>box-allow-ip</literal>.
     </entry></row>
    <row><entry><literal>udp-allow-ip</literal></entry></row>

    <row><entry><literal>wdp-interface-name (c)</literal></entry>
     <entry>IP or '*'</entry>
     <entry valign="bottom">
        If this is set, Kannel listens to WAP UDP packets incoming to
        ports 9200-9208, bound to given IP. If no specific IP is
        needed, use just an asterisk ('*'). If UDP messages are
        listened to, wapbox-port variable MUST be set.
     </entry></row>

    <row><entry><literal>log-file</literal></entry>
     <entry>filename</entry>
     <entry valign="bottom">
        A file in which to write a log. This in addition to <literal>stdout</literal>
        and any log file defined in command line. Log-file in 'core'
        group is only used by the bearerbox.
     </entry></row>

    <row><entry><literal>log-level</literal></entry>
     <entry>number 0..5</entry>
     <entry valign="bottom">
        Minimum level of log-file events logged. 0 is for 'debug', 1
        'info', 2 'warning, 3 'error' and 4 'panic' (see Command Line
        Options)
     </entry></row>

    <row><entry><literal>access-log</literal></entry>
     <entry>filename</entry>
     <entry valign="bottom">
        A file in which information about received/sent SMS messages 
        is stored. Access-log in 'core' group is only used by the
        bearerbox.
     </entry></row>

    <row><entry><literal>access-log-clean</literal></entry>
     <entry>boolean</entry>
     <entry valign="bottom">
        Indicates if <literal>access-log</literal> will contain standard 'markers', 
		  which means the 'Log begins', 'Log ends' markers and the prefixed
		  timestamp. This config directive should be set to 'true' if a custom 
		  logging format is desired without a prefixed default timestamp. 
     </entry></row>

    <row><entry><literal>access-log-format</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
		  String defining a custom log file line format. May use escape codes as defined
		  later on to substitute values of the messages into the log entry. If no
		  custom log format is used the standard format will be:
		  <literal>"%t %l [SMSC:%i] [SVC:%n] [ACT:%A] [BINF:%B] [from:%p] [to:%P] 
		           [flags:%m:%c:%M:%C:%d] [msg:%L:%b] [udh:%U:%u]"</literal>
     </entry></row>

    <row><entry><literal>unified-prefix</literal></entry>
     <entry>prefix-list</entry>
     <entry valign="bottom">
        String to unify received phone numbers, for SMSC routing and
        to ensure that SMS centers can handle them properly. 
        This is applied to 'sender' number when receiving SMS
        messages from SMS Center and for 'receiver' number when
        receiving messages from smsbox (either sendsms message or
         reply to original message). Format is that first comes the
        unified prefix, then all prefixes which are replaced by the
        unified prefix, separated with comma (','). For example,
        for Finland an unified-prefix "+358,00358,0;+,00" should do the trick. 
        If there are several unified prefixes, separate their rules with
        semicolon (';'), like "+35850,050;+35840,040". <emphasis>Note
        that prefix routing is next to useless now that there are
        SMSC ID entries. To remove prefixes, use like 
	"-,+35850,050;-,+35840,040".
	</emphasis>

     </entry></row>

    <row><entry><literal>white-list</literal></entry>
     <entry>URL</entry>
     <entry valign="bottom">
        Load a list of accepted senders of SMS messages. If a sender
        of an SMS message is not in this list, any message received
        from the SMS Center is discarded. See notes of phone number
        format from numhash.h header file. NOTE: the system has only
        a precision of last 9 or 18 digits of phone numbers, so
        beware!
     </entry></row>

    <row><entry><literal>black-list</literal></entry>
     <entry>URL</entry>
     <entry valign="bottom">
        As white-list, but SMS messages to these numbers are
        automatically discarded
     </entry></row>

    <row><entry><literal>store-file</literal></entry>
     <entry>filename</entry>
     <entry valign="bottom">
        A file in which any received SMS messages are stored until
        they are successfully handled. By using this variable, no SMS
        messages are lost in Kannel, but theoretically some messages
        can duplicate when system is taken down violently. 
     </entry></row>

    <row><entry><literal>store-dump-freq</literal></entry>
     <entry>seconds</entry>
     <entry valign="bottom">
        Approximated frequency how often the memory dump of current
        pending messages are stored to store-file, providing something
        has happened. Defaults to 10 seconds if not set.
     </entry></row>

    <row><entry><literal>http-proxy-host</literal></entry>
     <entry>hostname</entry>
     <entry morerows="1" valign="bottom">
        Enable the use of an HTTP proxy for all HTTP requests.
     </entry></row>
    <row><entry><literal>http-proxy-port</literal></entry>
     <entry>port-number</entry></row>

    <row><entry><literal>http-proxy-exceptions</literal></entry>
     <entry>URL-list</entry>
     <entry valign="bottom">
         A list of excluded hosts from being used via a
         proxy. Separate each entry with space.
     </entry></row>

    <row><entry><literal>http-proxy-exceptions-regex</literal></entry>
     <entry>UNIX regular expression</entry>
     <entry valign="bottom">
         Same as http-proxy-exceptions but match against UNIX regular expression.
     </entry></row>
    
    <row><entry><literal>http-proxy-username</literal></entry>
     <entry>username</entry>
     <entry valign="bottom">
         Username for authenticating proxy use, for proxies that
	 require this.
     </entry></row>
    
    <row><entry><literal>http-proxy-password</literal></entry>
     <entry>URL-list</entry>
     <entry valign="bottom">
         Password for authenticating proxy use, for proxies that
	 require this.
     </entry></row>
    
    <row><entry><literal>ssl-client-certkey-file (c)</literal></entry>
     <entry>filename</entry>
     <entry valign="bottom">
      A PEM encoded SSL certificate and private key file to be used
      with SSL client connections. This certificate is used for
  	   the HTTPS client side only, i.e. for SMS service requests to 
		SSL-enabled HTTP servers. 
     </entry>
    </row>
  
	 <row><entry><literal>ssl-server-cert-file (c)</literal></entry>
     <entry>filename</entry>
     <entry valign="bottom">
      A PEM encoded SSL certificate file to be used with SSL server
		connections. This certificate is used for the HTTPS server
		side only, i.e. for the administration HTTP server and the
		HTTP interface to send SMS messages.
	  </entry>
    </row>

	 <row><entry><literal>ssl-server-key-file (c)</literal></entry>
     <entry>filename</entry>
     <entry valign="bottom">
      A PEM encoded SSL private key file to be used with SSL server
		connections. This key is associated to the specified 
		certificate and is used for the HTTPS server side only.
	  </entry>
    </row>
	 <row><entry><literal>ssl-trusted-ca-file</literal></entry>
     <entry>filename</entry>
     <entry valign="bottom">
     This file contains the certificates Kannel is willing to trust when
     working as a HTTPS client. If this option is not set, certificates
     are not validated and those the identity of the server is not proven.
	  </entry>
    </row>

    <row><entry><literal>dlr-storage</literal></entry>
     <entry>type</entry>
     <entry valign="bottom">
        Defines the way DLRs are stored. If you have build-in external 
		  DLR storage support, i.e. using MySQL you may define here the
		  alternative storage type like 'mysql'. Supported types are:
		  internal, mysql, oracle. By default this is set to 'internal'.
     </entry></row>

     <row><entry><literal>maximum-queue-length</literal></entry>
	  <entry>number of messages</entry>
     <entry valign="bottom">
   	 (deprecated, see <literal>sms-incoming-queue-limit</literal>).
     </entry></row>

     <row><entry><literal>sms-incoming-queue-limit</literal></entry>
     <entry>number of messages</entry>
     <entry valign="bottom">
        Set maximum size of incoming message queue. After number of messages
        has hit this value, Kannel began to discard them.
        Value 0 means giving strict priority to outgoing messages. -1,
        default, means that the queue of infinite length is accepted. (This
        works with any normal input, use this variable only when Kannel message
        queues grow very long).
     </entry></row>

     <row><entry><literal>white-list-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        A regular expression defining the set of accepted senders. See section on regular 
        expressions for details.
        </entry>   
     </row>
     <row><entry><literal>black-list-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        A regular expression defining the set of rejected senders. See section on regular 
        expressions for details.
        </entry>   
     </row>

     <row><entry><literal>smsbox-max-pending</literal></entry>
        <entry>number of messages</entry>
        <entry valign="bottom">
        Maximum number of pending messages on the line to smsbox compatible boxes.
        </entry>   
     </row>
  
     <row><entry><literal>sms-resend-freq</literal></entry>
        <entry>seconds</entry>
        <entry valign="bottom">
        Frequency for the SMS resend thread in which temporarily failed or queued messages will be resent.
        Defaults to 60 seconds.
        </entry>   
     </row>

     <row><entry><literal>sms-resend-retry</literal></entry>
        <entry>number</entry>
        <entry valign="bottom">
        Maximum retry attempts for the temporarily failed messages.
        Defaults to -1, means: unlimited.
        </entry>   
     </row>

  </tbody>
  </tgroup>
 </table>

  <para>A sample more complex 'core' group could be something like
  this:

<programlisting>
group = core
admin-port = 13000
admin-password = f00bar
status-password = sTat
admin-deny-ip = "*.*.*.*"
admin-allow-ip = "127.0.0.1;200.100.0.*"
smsbox-port = 13003
wapbox-port = 13004
box-deny-ip = "*.*.*.*"
box-allow-ip = "127.0.0.1;200.100.0.*"
wdp-interface-name = "*"
log-file = "kannel.log"
log-level = 1
access-log = "kannel.access"
unified-prefix = "+358,00358,0;+,00"
white-list = "http://localhost/whitelist.txt"
</programlisting>
  
    </para>

</sect2>

</sect1>

<sect1>
<title>Running Kannel</title>

	<para>To start the gateway, you need to start each box you need.
	You always need the bearer box, and depending on whether you want
	WAP and SMS gateways you need to start the WAP and SMS boxes. If
	you want, you can run several of them, but we'll explain the
	simple case of only running one each.</para>


<sect2>
<title>Starting the gateway</title>

  <para>After you have compiled Kannel and edited configuration file
  for your taste, you can either run Kannel from command line or use
  supplied <literal>start-stop-daemon</literal> and
  <literal>run_kannel_box</literal> programs to use it as a daemon
  service (more documentation about that later).</para>

  <para>If you cannot or do not know how to set up daemon systems or
  just want to test Kannel, you probably want to start it from
  command line. This means that you probably want to have one terminal
  window for each box you want to start (xterm or screen will do
  fine). To start the bearerbox, give the following command:

	<screen><userinput>
	./bearerbox -v 1 [config-file]
	</userinput></screen>

  The <option>-v 1</option> sets the logging level to
  <literal>INFO</literal>. This way, you won't see a large amount of
  debugging output (the default is <literal>DEBUG</literal>). Full
  explanation of Kannel command line arguments is below.</para>

  <para><emphasis>[config-file]</emphasis> is the name of the
  configuration file you are using with Kannel. The basic distribution
  packet comes with two sample configuration files,
  <literal>smskannel.conf</literal> and
  <literal>wapkannel.conf</literal> (in <literal>gw</literal>
  subdirectory), of which the first one is for
  testing out SMS Kannel and the second one for setting up a WAP
  Kannel. Feel free to edit those configuration files to set up your
  own specialized system.</para>

  <para>After the bearer box, you can start the WAP box:

	<screen><userinput>
	./wapbox -v 1 [config-file]
	</userinput></screen>

  or the SMS box:

	<screen><userinput>
	./smsbox -v 1 [config-file]
	</userinput></screen>

  or both, of course. The order does not matter, except that you need
  to start the bearer box before the other boxes. Without the bearer
  box, the other boxes won't even start.</para>

</sect2>

<sect2 id="arguments">
<title id="arguments.title">Command line options</title>

 <para>Bearerbox, smsbox and wapbox each accept certain command line options
   and arguments when they are launched. These arguments are:</para>

 <table frame="none">
  <title>Kannel Command Line Options</title>
  <tgroup cols="2">
  <tbody>
   <row><entry><literal>-v &lt;level&gt;</literal></entry>
        <entry morerows="1" valign="bottom">
             Set verbosity level for stdout (screen) logging. Default is 0,
             which means 'debug'. 1 is 'info, 2 'warning', 3
             'error' and 4 'panic'
        </entry></row>
   <row><entry><literal>--verbosity &lt;level&gt;</literal></entry></row>

   <row><entry><literal>-D &lt;places&gt;</literal></entry>
        <entry morerows="1" valign="bottom">
             Set debug-places for 'debug' level output.
        </entry></row>
   <row><entry><literal>--debug &lt;places&gt;</literal></entry></row>

   <row><entry><literal>-F &lt;file-name&gt;</literal></entry>
        <entry morerows="1" valign="bottom">
              Log to file named file-name, too. Does not overrun or
              affect any log-file defined in configuration file.
        </entry></row>
   <row><entry><literal>--logfile &lt;file-name&gt;</literal></entry></row>

   <row><entry><literal>-V &lt;level&gt;</literal></entry>
        <entry morerows="1" valign="bottom">
            Set verbosity level for that extra log-file (default 0,
            which means 'debug'). Does not affect verbosity level of
            the log-file defined in configuration file, not verbosity
            level of the <literal>stdout</literal> output.
        </entry></row>
   <row><entry><literal>--fileverbosity &lt;level&gt;</literal></entry></row>

   <row><entry><literal>-S</literal></entry>
        <entry morerows="1" valign="bottom">
             Start the system initially at SUSPENDED state (see below,
              bearerbox only)
        </entry></row>
   <row><entry><literal>--suspended</literal></entry></row>

   <row><entry><literal>-I</literal></entry>
        <entry morerows="1" valign="bottom">
             Start the system initially at ISOLATED state (see below,
              bearerbox only)
        </entry></row>
   <row><entry><literal>--isolated</literal></entry></row>

   <row><entry><literal>-H</literal></entry>
        <entry morerows="1" valign="bottom">
             Only try to open HTTP sendsms interface; if it
             fails, only warn about that, do not exit. (smsbox only)
        </entry></row>
   <row><entry><literal>--tryhttp</literal></entry></row>

   <row><entry><literal>-g</literal></entry>
        <entry morerows="1" valign="bottom">
             Dump all known config groups and config keys to stdout
             and exit.
        </entry></row>
   <row><entry><literal>--generate</literal></entry></row>

   <row><entry><literal>-u &lt;username&gt;</literal></entry>
        <entry morerows="1" valign="bottom">
             Change process user-id to the given.
        </entry></row>
   <row><entry><literal>--user &lt;username&gt;</literal></entry></row>

   <row><entry><literal>-p &lt;filename&gt;</literal></entry>
        <entry morerows="1" valign="bottom">
             Write process PID to the given file.
        </entry></row>
   <row><entry><literal>--pid-file &lt;filename&gt;</literal></entry></row>

   <row><entry><literal>-d</literal></entry>
        <entry morerows="1" valign="bottom">
             Start process as daemon (detached from a current shell session).
             Note: Process will change CWD (Current working directory) to <literal>/</literal>,
                   therefore you should ensure that all paths to binary/config/config-includes are
                   absolute instead of relative.
        </entry></row>
   <row><entry><literal>--daemonize</literal></entry></row>

   <row><entry><literal>-P</literal></entry>
        <entry morerows="1" valign="bottom">
             Start watcher process. This process watch a child process and if child process
             crashed will restart them automatically.
        </entry></row>
   <row><entry><literal>--parachute</literal></entry></row>

   <row><entry><literal>-X &lt;scriptname&gt;</literal></entry>
        <entry morerows="1" valign="bottom">
             Execute a given shell script or binary when child process crash detected. This option
             is usable only with <literal>--parachute/-P</literal>.
             Script will be executed with 2 arguments:
                 scriptname 'processname' 'respawn-count'.
        </entry></row>
   <row><entry><literal>--panic-script &lt;scriptname&gt;</literal></entry></row>

 </tbody>
 </tgroup>
 </table>

</sect2>

<sect2>
<title>Kannel statuses</title>

    <para>In Kannel, there are four states for the program (which
    currently directly only apply to bearerbox):</para>

    <orderedlist numeration="loweralpha">
     <listitem><para>
       Running. The gateway accepts, proceeds and relies 
       messages normally. This is the default state for the bearerbox.
     </para></listitem>
     <listitem><para>
 Suspended. The gateway does not accept any new messages from SMS
   centers nor from UDP ports. Neither does it accept new sms and wapbox
   connections nor sends any messages already in the system
   onward.

     </para></listitem>
     <listitem><para>
 Isolated. In this state, the gateway does not accept any messages
   from external message providers, which means SMS Centers and UDP
   ports. It still processes any messages in the system and can
   accept new messages from sendsms interface in smsbox.
     </para></listitem>

     <listitem><para>
   Full. Gateway does not accept any messages from SMS centers, because 
   <literal>maximum-queue-length</literal> is achieved.
     </para></listitem>

     <listitem><para>
   Shutdown. When the gateway is brought down, it does not accept any
   new messages from SMS centers and UDP ports, but processes all
   systems already in the system. As soon as any queues are emptied,
   the system exits

   </para></listitem>
    </orderedlist>
 
  <para>
The state can be changed via HTTP administration interface (see below),
and shutdown can also be initiated via TERM or INT signal from
terminal. In addition, the bearerbox can be started already in
suspended or isolated state with -S or -I command line option, see
above.
</para>

</sect2>

<sect2>
<title>HTTP administration</title>

<para>Kannel can be controlled via an HTTP administration interface. All
commands are done as normal HTTP queries, so they can be easily done
from command line like this:

	<screen><userinput>
	lynx -dump "http://localhost:12345/shutdown?password=bar"
	</userinput></screen>

...in which the '12345' is the configured admin-port in Kannel
configuration file (see above). For most commands, admin-password is required as a
argument as shown above. In addition, HTTP administration can
be denied from certain IP addresses, as explained in configuration
chapter.</para>

<para>Note that you can use these commands with WAP terminal, too, but
if you use it through the same Kannel, replies to various suspend
commands never arrive nor can you restart it via WAP anymore.</para>

 <table frame="none">
  <title>Kannel HTTP Administration Commands</title>
  <tgroup cols="2">
  <tbody>
   <row><entry><literal>status or status.txt</literal></entry>
   <entry valign="bottom">
        Get the current status of the gateway in a text version. Tells the current 
	state (see above) and total number of messages relied and queuing 
	in the system right now. Also lists the total number of smsbox
        and wapbox connections. No password required, unless
        <literal>status-password</literal> set, in which case either
        that or main admin password must be supplied.
   </entry></row>
   <row><entry><literal>status.html</literal></entry>
   <entry valign="bottom">
        HTML version of status
   </entry></row>
   <row><entry><literal>status.xml</literal></entry>
   <entry valign="bottom">
        XML version of status
   </entry></row>
   <row><entry><literal>status.wml</literal></entry>
   <entry valign="bottom">
        WML version of status
   </entry></row>

   <row><entry><literal>store-status or store-status.txt</literal></entry>
   <entry valign="bottom">
        Get the current content of the store queue of the gateway 
		  in a text version. No password required, unless
        <literal>status-password</literal> set, in which case either
        that or main admin password must be supplied.
   </entry></row>
   <row><entry><literal>store-status.html</literal></entry>
   <entry valign="bottom">
        HTML version of store-status
   </entry></row>
   <row><entry><literal>store-status.xml</literal></entry>
   <entry valign="bottom">
        XML version of store-status
   </entry></row>

   <row><entry><literal>suspend</literal></entry>
   <entry valign="bottom">
        Set Kannel state as 'suspended' (see above). Password
        required.
   </entry></row>

   <row><entry><literal>isolate</literal></entry>
   <entry valign="bottom">
        Set Kannel state as 'isolated' (see above). Password required.
   </entry></row>

   <row><entry><literal>resume</literal></entry>
   <entry valign="bottom">
        Set Kannel state as 'running' if it is suspended or isolated.
        Password required.
   </entry></row>

   <row><entry><literal>shutdown</literal></entry>
   <entry valign="bottom">
        Bring down the gateway, by setting state to 'shutdown'. After
        a shutdown is initiated, there is no other chance to resume
        normal operation. However, 'status' command still works.
        Password required. If shutdown is sent for a second time, the
        gateway is forced down, even if it has still messages in
        queue.
   </entry></row>

	<row><entry><literal>flush-dlr</literal></entry>
   <entry valign="bottom">
        If Kannel state is 'suspended' this will flush all queued DLR
		  messages in the current storage space. Password required.
   </entry></row>

	<row><entry><literal>start-smsc</literal></entry>
   <entry valign="bottom">
        Re-start a single SMSC link. Password required. Additionally
		  the <literal>smsc</literal> parameter must be given to identify
 		  which <literal>smsc-id</literal> should be re-started.
   </entry></row>

  	<row><entry><literal>stop-smsc</literal></entry>
   <entry valign="bottom">
        Shutdown a single SMSC link. Password required. Additionally
		  the <literal>smsc</literal> parameter must be given (see above).
   </entry></row>

	<row><entry><literal>restart</literal></entry>
   <entry valign="bottom">
        Re-start whole bearerbox, hence all SMSC links. Password required.
 		  Beware that you loose the smsbox connections in such a case.
   </entry></row>

	<row><entry><literal>loglevel</literal></entry>
   <entry valign="bottom">
        Set Kannel log-level of log-files while running. This allows
		  you to change the current log-level of the log-files on the fly.
   </entry></row>

  </tbody>
  </tgroup>
 </table>

</sect2>
  
</sect1>
</chapter>



<chapter id="wap-gateway">
<title>Setting up a WAP gateway</title>

    <para>This chapter tells you how to set Kannel up as a WAP
    gateway.</para>

<sect1>
<title>WAP gateway configuration</title>

  <para>To set up a WAP Kannel, you have to edit the 'core' group in the
  configuration file, and define the 'wapbox' group.</para>

  <para>You must set following variables for the 'core' group:  
    <literal>wapbox-port</literal> and
    <literal>wdp-interface-name</literal>. See previous chapter about
    details of these variables.</para>

  <para>With standard distribution, a sample configuration file
  <literal>wapkannel.conf</literal> is supplied. You may want to take
  a look at that when setting up a WAP Kannel.</para>

<sect2>
<title>Wapbox group</title>

  <para>If you have set <literal>wapbox-port</literal> variable in the
  'core' configuration group, you <emphasis>MUST</emphasis> supply
  a 'wapbox' group.</para>

  <para>The simplest working 'wapbox' group looks like this:
<programlisting>
group = wapbox
bearerbox-host = localhost
</programlisting>

   There is, however, multiple optional variables for the 'wapbox'
   group.</para>

 <table frame="none">
  <title>Wapbox Group Variables</title>
  <tgroup cols="3">
  <thead>
   <row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row>
  </thead>
  <tbody>
   <row><entry><literal>group (m)</literal></entry>
     <entry><literal>wapbox</literal></entry>
     <entry valign="bottom">
       This is mandatory variable
     </entry></row>

   <row><entry><literal>bearerbox-host (m)</literal></entry>
     <entry><literal>hostname</literal></entry>
     <entry valign="bottom">
        The machine in which the bearerbox is. 
     </entry></row>

    <row><entry><literal>timer-freq</literal></entry>
     <entry>value-in-seconds</entry>
     <entry valign="bottom">
         The frequency of how often timers are checked out. Default is 1 
     </entry></row>

    <row><entry><literal>http-interface-name</literal></entry>
     <entry>IP address</entry>
     <entry valign="bottom">
         If this is set then Kannel do outgoing HTTP requests
         using this interface.
     </entry></row>

    <row><entry><literal>map-url</literal></entry>
     <entry>URL-pair</entry>
     <entry valign="bottom">
        The pair is separated with space.
        Adds a single mapping for the left side URL to the given destination.
        If you append an asterisk `*' to the left side URL, its prefix
        Is matched against the incoming URL. Whenever the prefix matches,
        the URL will be replaced completely by the right side. In addition, if 	  if you append an asterisk to the right side URL, the part
        of the incoming URL coming after the prefix, will be appended
        to the right side URL. Thus, for a line:
                map-url = "http://source/* http://destination/*"
        and an incoming URL of "http://source/some/path", the result
        will be "http://destination/some/path"
     </entry></row>

    <row><entry><literal>map-url-max</literal></entry>
     <entry>number</entry>
     <entry valign="bottom">
        If you need more than one mapping, set this to the highest number
        mapping you need. The default gives you 10 mappings, numbered
        from 0 to 9. Default: 9
     </entry></row>

    <row><entry><literal>map-url-0</literal></entry>
     <entry>URL-pair</entry>
     <entry valign="bottom">
        Adds a mapping for the left side URL to the given destination URL.
        Repeat these lines, with 0 replaced by a number up to map-url-max,
        if you need several mappings.
     </entry></row>

    <row><entry><literal>device-home</literal></entry>
     <entry>URL</entry>
     <entry valign="bottom">
        Adds a mapping for the URL DEVICE:home (as sent by Phone.com browsers)
        to the given destination URL. There is no default mapping.
        NOTE: the mapping is added with both asterisks, as described above
        for the "map-url" setting. Thus, the above example line is
        equivalent to writing
                map-url = "DEVICE:home* http://some.where/*"

     </entry></row>

    <row><entry><literal>log-file</literal></entry>
     <entry>filename</entry>
     <entry morerows="1" valign="bottom">
       As with bearerbox 'core' group. 
     </entry></row>

    <row><entry><literal>log-level</literal></entry>
     <entry>number 0..5</entry></row>

    <row><entry><literal>syslog-level</literal></entry>
     <entry>number</entry>
     <entry valign="bottom">
	 Messages of this log level or higher will also be
	 sent to syslog, the UNIX system log daemon.  The wapbox
	 logs under the 'daemon' category.
	 The default is not to use syslog, and you can set that
	 explicitly by setting <literal>syslog-level</literal>
	 to 'none'.
     </entry></row>

    <row><entry><literal>access-log</literal></entry>
     <entry>filename</entry>
     <entry valign="bottom">
        A file containing all requested URLs from clients while wapbox operation,
        including client IP, HTTP server User-Agent string, HTTP reponse code, 
        size of reply.
     </entry></row>

    <row><entry><literal>access-log-clean</literal></entry>
     <entry>boolean</entry>
     <entry valign="bottom">
        Indicates if <literal>access-log</literal> will contain standard 'markers', 
		  which means the 'Log begins', 'Log ends' markers and the prefixed
		  timestamp. This config directive should be set to 'true' if a custom 
		  logging format is desired without a prefixed default timestamp. 
     </entry></row>

    <row><entry><literal>access-log-time</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
          Determine which timezone we use for access logging. Use 'gmt' for GMT time, 
          anything else will use local time. Default is local time.
     </entry></row>

	 <row><entry><literal>smart-errors</literal></entry>
     <entry>bool</entry>
     <entry valign="bottom">
	 If set wapbox will return a valid WML deck describing the 
	 error that occurred while processing an WSP request. This may
	 be used to have a smarter gateway and let the user know what
	 happened actually.
	 </entry></row>
	 
	 <row><entry><literal>wml-strict</literal></entry>
     <entry>bool</entry>
     <entry valign="bottom">
	 If set wapbox will use a strict policy in XML parsing the WML
	 deck. If not set it will be more relaxing and let the XML parser
	 recover from parsing errors. This has mainly impacts in how smart
	 the WML deck and it's character set encoding can be addopted, even
	 while you used an encoding that does not fit the XML preamble.
	 BEWARE: This may be a vulnerability in your wapbox for large bogus 
	 WML input. Therefore this defaults to 'yes', strict parsing.
	 is assimed.
	 </entry></row>

  </tbody>
  </tgroup>
 </table>


<programlisting>
</programlisting>
</sect2>
  
</sect1>

<sect1>
<title>Running WAP gateway</title>

 <para>WAP Gateway is ran as explained in previous chapter.</para>

</sect1>


<sect1>
<title>Checking whether the WAP gateway is alive</title>

    <para>You can check whether the WAP gateway (both the
    bearerbox and the wapbox) is alive by fetching the URL
    <literal>kannel:alive</literal>.</para>

</sect1>

</chapter>



<chapter id="msisdn-provisioning">
<title>Setting up MSISDN provisioning for WAP gateway</title>

    <para>This chapter tells you how to set Kannel up to deliver the MSISDN
	 number of the WAP device using the WAP gateway.</para>

	 <para>Mostly this feature is interested because the WAP protocol stack
	 itself does not provide such a protocol layer bridging of information.
	 In case you want to know which unique MSISDN is used by the WAP device
	 your HTTP application is currently interacting, then you can pick this
	 information from a RADIUS server that is used by a NAS (network access
	 server) for authentication and accounting purposes.
	 </para>

	 <para>Kannel provides a RADIUS accounting proxy thread inside wapbox
	 which holds a mapping table for the dynamically assigned (DHCP) IP 
	 addresses of the WAP clients and their MSISDN numbers provided to the
	 NAS device.
	 </para>

	 <para>Beware that you <emphasis>HAVE TO</emphasis> to be in control of 
	 the NAS to configure it to use Kannel's wapbox as RADIUS accounting 
	 server. You can not use
	 MSISDN provisioning via Kannel's RADIUS accounting proxy if you can
	 not forward the accounting packets to Kannel's accounting proxy thread.
	 So obviously this feature is for operators and people who have dedicated
	 dial-in servers (NAS).
	 </para>

<sect1>
<title>RADIUS accounting proxy configuration</title>

  <para>To set up the RADIUS accounting proxy thread inside Kannel you 
  have to define a 'radius-acct' group.</para>

<sect2>
<title>RADIUS-Acct configuration</title>

  <para>The simplest working 'radius-acct' group looks like this:
<programlisting>
group = radius-acct
our-port = 1646
secret-nas = radius
</programlisting>

   This example does not forward any accounting packets to a remote 
	RADIUS server. There is, however, multiple optional variables for 
	the 'radius-acct' group.</para>

 <table frame="none">
  <title>RADIUS-Acct Group Variables</title>
  <tgroup cols="3">
  <thead>
   <row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row>
  </thead>
  <tbody>
   <row><entry><literal>group (m)</literal></entry>
     <entry><literal>radius-acct</literal></entry>
     <entry valign="bottom">
       This is mandatory variable if you want to have Kannel's 
		 RADIUS accounting proxy thread to be active inside wapbox.
     </entry></row>

   <row><entry><literal>secret-nas (m)</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
	    Specifies the shared secret between NAS and our RADIUS accounting proxy.
     </entry></row>

   <row><entry><literal>secret-radius</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
	    Specifies the shared secret between our RADIUS accounting proxy and the
		 remote RADIUS server itself in case we are forwarding packets.
     </entry></row>

   <row><entry><literal>our-host</literal></entry>
     <entry><literal>IP address</literal></entry>
     <entry valign="bottom">
	    Specifies the local interface where our-port value will bind
		 to. (defaults to 0.0.0.0)
     </entry></row>

   <row><entry><literal>remote-host</literal></entry>
     <entry><literal>FQDN or IP address</literal></entry>
     <entry valign="bottom">
	    Specifies the remote RADIUS server to which we forward the 
		 accounting packets. If none is given, then no forwarding of
		 accounting packets is performed.
     </entry></row>

   <row><entry><literal>our-port</literal></entry>
     <entry><literal>number</literal></entry>
     <entry valign="bottom">
	    Specifies the port to which our RADIUS accounting proxy thread
		 will listen to. (defaults according to RFC2866 to 1813)
     </entry></row>

   <row><entry><literal>remote-port</literal></entry>
     <entry><literal>number</literal></entry>
     <entry valign="bottom">
	    Specifies the port to which our RADIUS accounting proxy thread
		 will forward any packets to the remote-host. 
		 (defaults according to RFC2866 to 1813)
     </entry></row>
     
   <row><entry><literal>remote-timeout</literal></entry>
     <entry><literal>number</literal></entry>
     <entry valign="bottom">
	    Specifies the timeout value in milliseconds for waiting on a 
	    response from the remote RADIUS server.
		 (defaults to 40 msecs.)
     </entry></row>

   <row><entry><literal>nas-ports</literal></entry>
     <entry><literal>number</literal></entry>
     <entry valign="bottom">
	    Specifies how many possible clients can connect simultaneously 
		 to the NAS. This value is used to initialize the mapping hash table.
		 If does not require to be exact, because the table grows automatically
		 if required. (defaults to 30)
     </entry></row>

    <row><entry><literal>unified-prefix</literal></entry>
     <entry>prefix-list</entry>
     <entry valign="bottom">
        String to unify provided phone numbers from NAS.
		  Format is that first comes the
        unified prefix, then all prefixes which are replaced by the
        unified prefix, separated with comma (','). For example,
        for Finland an unified-prefix "+358,00358,0;+,00" should do the trick. 
        If there are several unified prefixes, separate their rules with
        semicolon (';'), like "+35850,050;+35840,040".
	  </entry></row>

  </tbody>
  </tgroup>
 </table>
<programlisting>
</programlisting>

</sect2>
<sect2>
<title>Using the MSISDN provisioning on HTTP server side</title>

  <para>Kannel's wapbox will include a specific HTTP header in the HTTP
  request issued to the URL provided by the WAP client. That HTTP header 
  is <literal>X-WAP-Network-Client-MSISDN</literal>. It will carry as value
  the MSISDN of the WAP client if the RADIUS accounting proxy has received
  a valid accounting packet from the NAS that provided the client IP.
  </para>

</sect2>
</sect1>
</chapter>



<chapter id="sms-gateway">
<title>Setting up a SMS Gateway</title>

    <para>This chapter is a more detailed guide on how to set up Kannel as an
    SMS gateway.</para>

<sect1>
<title>Required components</title>

    <para>To set up an SMS gateway, you need, in addition to a machine
    running Kannel, access to (an operator's) SMS center, or possibly
    to multiple ones. The list of supported SMS centers and their
    configuration variables is below.</para>

    <para>If you do not have such access, you can still
    use Kannel as an SMS gateway via <emphasis>phone-as-SMSC</emphasis> 
    feature, by using a GSM phone as a virtual SMS center.</para>

    <para>In addition to an SMS center (real or virtual), you need some
    server to handle any SMS requests received. This server then has
    simple or more complex cgi-bins, programs or scripts to serve HTTP
    requests generated by Kannel in response to received SMS
    messages. These services can also initiate SMS push via Kannel
    smsbox HTTP sendsms interface.</para>

</sect1>

<sect1>
<title>SMS gateway configuration</title>

  <para>To set up a SMS Kannel, you have to edit the 'core' group in the
  configuration file, and define an 'smsbox' group plus one or more
  'sms-service' groups, plus possibly one or more 'sendsms-user' groups.</para>

  <para>For the 'core' group, you must set the following variable:  
    <literal>smsbox-port</literal>. In addition, you may be interested
    to set <literal>unified-prefix</literal>,
    <literal>white-list</literal> and/or <literal>black-list</literal>
    variables. See above for details of these variables.</para>

  <para> A sample configuration file <literal>smskannel.conf</literal> 
  is supplied with the standard distribution. You may want to take
  a look at that when setting up an SMS Kannel.</para>
</sect1>

<sect1>
<title>SMS centers</title>

    <para>To set up the SMS center at Kannel, you have to add a 'smsc'
    group into configuration file. 
    This group must include all the data needed to connect
    that SMS center. You may also want to define an ID
    (identification) name for the SMSC, for logging and routing
    purposes.</para>

    <para>SMSC ID is an abstract name for the connection. It can be
    anything you like, but you should avoid any special
    characters. You do not need to use ID, but rely on SMS center IP
    address and other information. However, if you use the ID, you do
    not need to re-define sms-services nor routing systems if the IP
    of the SMS Center is changed, for example.</para>

    <para>Common 'smsc' group variables are defined in the following
    table. The first two (<literal>group</literal> and
    <literal>smsc</literal>) are mandatory, but rest can be used if
    needed.</para>

 <table frame="none">
  <title>SMSC Group Variables</title>
  <tgroup cols="3">
  <thead>
   <row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row>
  </thead>
  <tbody>
   <row><entry><literal>group (m)</literal></entry>
     <entry><literal>smsc</literal></entry>
     <entry valign="bottom">
       This is a mandatory variable
     </entry></row>

   <row><entry><literal>smsc (m)</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       Identifies the SMS center type. See below
       for a complete list.
     </entry></row>


   <row><entry><literal>smsc-id</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
        An optional name or id for the smsc. Any string is
        acceptable, but semicolon ';' may cause problems, so avoid
        it and any other special non-alphabet characters. 
        This 'id' is written into log files and can be used to
        route SMS messages, and to specify the used SMS-service. 
        Several SMSCs can have the same id. The name is
        case-insensitive. Note that if SMS Center connection has an
	assigned SMSC ID, it does NOT automatically mean that messages
	with identical SMSC ID are routed to it; instead configuration
	variables <literal>denied-smsc-id</literal>, 
	<literal>allowed-smsc-id</literal> and
	<literal>preferred-smsc-id</literal> is used for that.
	If you want to use Delivery Reports, you must define this.

     </entry></row>

    <row><entry><literal>throughput</literal></entry>
      <entry><literal>number (messages/sec)</literal></entry>
      <entry valign="bottom">
        If SMSC requires that Kannel limits the number of messages per second, 
        use this variable. This is considered as active throttling. (optional)
     </entry></row>

   <row><entry><literal>denied-smsc-id</literal></entry>
     <entry><literal>id-list</literal></entry>
     <entry valign="bottom">
        SMS messages with SMSC ID equal to any of the IDs in this list
        are never routed to this SMSC. Multiple entries are separated 
        with semicolons (';')
     </entry></row>

   <row><entry><literal>allowed-smsc-id</literal></entry>
     <entry><literal>id-list</literal></entry>
     <entry valign="bottom">
        This list is opposite to previous: only SMS messages with SMSC
        ID in this list are ever routed to this SMSC.
        Multiple entries are separated with semicolons (';')
     </entry></row>

   <row><entry><literal>preferred-smsc-id</literal></entry>
     <entry><literal>id-list</literal></entry>
     <entry valign="bottom">
        SMS messages with SMSC ID from this list are sent to this SMSC
        instead than to SMSC without that ID as preferred. Multiple
        entries are separated with semicolons (';')
     </entry></row>

   <row><entry><literal>allowed-prefix</literal></entry>
     <entry><literal>prefix-list</literal></entry>
     <entry valign="bottom">
        A list of phone number prefixes which are accepted to be
        sent through this SMSC. Multiple entries are separated with 
        semicolon (';'). For example, "040;050" prevents sending of
        any SMS message with prefix of 040 or 050 through this SMSC.
	If denied-prefix is unset, only these numbers are allowed. If
	set, number are allowed if present in allowed or not in 
	denied list.
     </entry></row>

   <row><entry><literal>denied-prefix</literal></entry>
     <entry><literal>prefix-list</literal></entry>
     <entry valign="bottom">
        A list of phone number prefixes which are NOT accepted to be
        sent through this SMSC.
     </entry></row>

   <row><entry><literal>preferred-prefix</literal></entry>
     <entry><literal>prefix-list</literal></entry>
     <entry valign="bottom">
        As <literal>denied-prefix</literal>, but SMS messages with receiver starting
        with any of these prefixes are preferably sent through this
        SMSC. In a case of multiple preferences, one is selected at random
        (also if there are preferences, SMSC is selected randomly)

     </entry></row>

   <row><entry><literal>unified-prefix</literal></entry>
     <entry>prefix-list</entry>
     <entry valign="bottom">
        String to unify received phone numbers, for SMSC routing and
        to ensure that SMS centers can handle them properly. 
        This is applied to 'sender' number when receiving SMS
        messages from SMS Center and for 'receiver' number when
        receiving messages from smsbox (either sendsms message or
        reply to original message). Format is that first comes the
        unified prefix, then all prefixes which are replaced by the
        unified prefix, separated with comma (','). For example,
        for Finland an unified-prefix "+358,00358,0;+,00" should do the trick. 
        If there are several unified prefixes, separate their rules with
        semicolon (';'), like "+35850,050;+35840,040". <emphasis>Note
        that prefix routing is next to useless now that there are
        SMSC ID entries. To remove prefixes, use like 
	     "-,+35850,050;-,+35840,040".
	</emphasis>
     </entry></row>

   <row><entry><literal>alt-charset</literal></entry>
     <entry><literal>number</literal></entry>
     <entry valign="bottom">
        As some SMS Centers do not follow the standards in character
        coding, an <literal>alt-charset</literal> character conversion is
        presented. This directive acts different for specific SMSC types.
		  Please see your SMSC module type you want to use for more details.
     </entry></row>

   <row><entry><literal>our-host</literal></entry>
     <entry><literal>hostname</literal></entry>
     <entry valign="bottom">
       Optional hostname or IP address in which to bind the connection in our
     end. TCP/IP connection only.
     </entry></row>

    <row><entry><literal>log-file</literal></entry>
     <entry>filename</entry>
     <entry valign="bottom">
        A file in which to write a log of the given smsc output. Hence
 		  this allows to log smsc specific entries to a separate file.
     </entry></row>

    <row><entry><literal>log-level</literal></entry>
     <entry>number 0..5</entry>
     <entry valign="bottom">
        Minimum level of log-file events logged. 0 is for 'debug', 1
        'info', 2 'warning, 3 'error' and 4 'panic' (see Command Line
        Options)
     </entry></row>

    <row><entry><literal>reconnect-delay</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
			Number of seconds to wait between single re-connection attempts.
			Hence all SMSC modules should use this value for their 
			re-connect behavior. (Defaults to '10' seconds).
     </entry></row>

    <row><entry><literal>reroute</literal></entry>
      <entry><literal>boolean</literal></entry>
      <entry valign="bottom">
			If set for a smsc group, all inbound messages coming from this smsc
			connection are passed internally	to the outbound routing functions. 
			Hence this messages is not delivered to any connected box for 
			processing. It is passed to the bearerbox routing as if it would
 		   have originated from an externally connected smsbox.
			(Defaults to 'no').
     </entry></row>

    <row><entry><literal>reroute-smsc-id</literal></entry>
      <entry><literal>string</literal></entry>
      <entry valign="bottom">
			Similar to 'reroute'. Defines the explicit smsc-id 
			the MO message should be passed to for MT traffic. Hence all 
			messages coming from the the configuration group smsc are passed
			to the outbound queue of the specified smsc-id. This allows 
			direct proxying of messages between 2 smsc connections without 
			injecting them to the general	routing procedure in bearerbox.
     </entry></row>

    <row><entry><literal>reroute-receiver</literal></entry>
      <entry><literal>string</literal></entry>
      <entry valign="bottom">
			Similar to 'reroute'. Defines the explicit smsc-id routes 
 		   for specific receiver numbers of messages that are coming from this
			smsc connection.
			Format is that first comes the smsc-id to route the message to, then 
			all receiver numbers that should be routed, separated with comma (','). 
			For example, route receivers 111 and 222 to smsc-id A and 333 and 444
			to smsc-id B would look like: "A,111,222; B,333,444".
     </entry></row>

    <row><entry><literal>reroute-dlr</literal></entry>
      <entry><literal>boolean</literal></entry>
      <entry valign="bottom">
                       Indicate whether DLR's should be re-routed too, if one of above reroute
                       rules are enabled. Please note, that SMSC-Module should support DLR sending.
                       At time of writing none of SMSC-Module supports DLR sending.
      </entry></row>

     <row><entry><literal>allowed-smsc-id-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        SMS messages with SMSC ID equal to any of the IDs in this set of SMSC IDs
        are always routed to this SMSC. 
        See section on regular 
        expressions for details.
        </entry>   
     </row>

     <row><entry><literal>denied-smsc-id-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        SMS messages with SMSC ID equal to any of the IDs in this set of SMSC IDs
        are never routed to this SMSC. 
        See section on regular 
        expressions for details.
        </entry>   
     </row>

     <row><entry><literal>preferred-smsc-id-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        SMS messages with SMSC ID in this set of SMSC IDs are sent to this SMSC
        as preferred.
        See section on regular 
        expressions for details.
        </entry>   
     </row>

     <row><entry><literal>allowed-prefix-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        A set of phone number prefixes which are accepted to be
        sent through this SMSC. 
        See section on regular 
        expressions for details.
        </entry>   
     </row>

     <row><entry><literal>denied-prefix-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        A set of phone number prefixes which may not be
        sent through this SMSC. 
        See section on regular 
        expressions for details.
        </entry>   
     </row>

     <row><entry><literal>preferred-prefix-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        As <literal>denied-prefix-regex</literal>, but SMS messages with receiver matching 
        any of these prefixes are preferably sent through this
        SMSC. In a case of multiple preferences, one is selected at random.
        See section on regular 
        expressions for details.
        </entry>   
     </row>

  </tbody>
  </tgroup>
 </table>

   <para>In addition to these common variables there are several
   variables used by certain SMS center connections. Each currently
   supported SMS center type is explained below, with configuration
   group for each. Note that many of them use variables with same
   name, but most also have some specific variables.</para>

   <para><emphasis>NOTE: SMS center configuration variables are a bit 
   incomplete, and will be updated as soon as people responsible for
   the protocols are contacted. Meanwhile, please have
   patience.</emphasis></para>


<sect2>
<title>Nokia CIMD 1.37 and 2.0</title>

<para>Support for CIMD 1.37 is quite old and will be removed in a
future version of Kannel.  Please let us know if you still need it.</para>

<programlisting>
group = smsc
smsc = cimd
host = 100.101.102.103
port = 600
smsc-username = foo
smsc-password = bar
</programlisting>

<para>The driver for CIMD2 is a "receiving SME" and expects the SMSC
to be configured for that.  It also expects the SMSC to automatically
send stored messages as soon as Kannel logs in (this is the normal
configuration).</para>

<programlisting>
group = smsc
smsc = cimd2
host = 100.101.102.103
port = 600
smsc-username = foo
smsc-password = bar
keepalive = 5 
my-number = "12345"
</programlisting>

 <informaltable frame="none">
  <tgroup cols="3"><thead><row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row></thead><tbody>

   <row><entry><literal>host (m)</literal></entry>
     <entry><literal>hostname</literal></entry>
     <entry valign="bottom">
        Machine that runs the SMSC. As IP (100.100.100.100) 
        or hostname (their.machine.here)
     </entry></row>

   <row><entry><literal>port (m)</literal></entry>
     <entry><literal>port-number</literal></entry>
     <entry valign="bottom">
       Port number in the smsc host machine
     </entry></row>

   <row><entry><literal>smsc-username (m)</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       Username in the SMSC machine/connection account
     </entry></row>

   <row><entry><literal>smsc-password (m)</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
        Password in the SMSC machine needed to contact SMSC
     </entry></row>

   <row><entry><literal>keepalive</literal></entry>
     <entry><literal>number</literal></entry>
     <entry valign="bottom">
       SMSC connection will not be left idle for longer than this many
       seconds.  The right value to use depends on how eager the SMSC
       is to close idle connections. If you see many unexplained 
       reconnects, try lowering this value.
       Set it to 0 to disable this feature.
     </entry></row>

   <row><entry><literal>no-dlr</literal></entry>
     <entry><literal>boolean</literal></entry>
     <entry valign="bottom">
       Optional. If defined, status delivery report requests (DLR) won't be
       requested at all. Some CIMD2 SMSC have prohibited these reports so
       if you are getting error like "Incorrect status report request parameter
       usage", this option is for you. Defaults to "false".
     </entry></row>

   <row><entry><literal>my-number</literal></entry>
      <entry><literal>string</literal></entry>
      <entry valign="bottom">
        The number that the SMSC will add in front of the sender number
        of all messages sent from Kannel.  If Kannel is asked to send
        a message, it will remove this prefix from the sender number
        so that the SMSC will add it again.  If the prefix was not present,
        Kannel will log a warning and will not send the sender number.
        If <literal>my-number</literal> is not set, or is set
        to <literal>"never"</literal>, then Kannel will not send the
        sender number to the SMSC at all.
        If you want Kannel to pass all sender numbers to the SMSC
        unchanged, then just set <literal>sender-prefix</literal> to the
        empty string <literal>""</literal>.
      </entry></row>

   <row><entry><literal>our-port</literal></entry>
     <entry><literal>port-number</literal></entry>
     <entry valign="bottom">
       Optional port number in which to bind the connection in our
       end.
     </entry></row>

   </tbody></tgroup></informaltable>
   
</sect2>

<sect2>
<title>CMG UCP/EMI 4.0 and 3.5</title>

  <warning><para>See <xref linkend="upgrading-notes"> for changes.</para></warning>
  <para>Kannel supports two types of connections with CMG SMS centers:
  direct TCP/IP connections ( <literal>emi</literal>) and ISDN/modem 
  (X.25) connection (<literal>emi_x25</literal>).</para>
  <note><para><literal>emi_x25</literal> is an old implementation and supports less 
  features than it's IP counterpart. If you still need this module, please tell
  us to <literal>devel@kannel.org</literal> so we can fix it.</para></note> 
  <para>Sample configurations for these are:</para>
  
<programlisting>
group = smsc
smsc = emi
host = 103.102.101.100
port = 6000
smsc-username = foo
smsc-password = bar
keepalive = 55
our-port = 600 (optional bind in our end)
receive-port = 700 (the port in which the SMSC will contact)
idle-timeout = 30

group = smsc
smsc = emi_x25
phone = ...
device = /dev/tty0
smsc-username = foo
smsc-password = bar
</programlisting>

 <informaltable frame="none">
  <tgroup cols="3"><thead><row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row></thead><tbody>

   <row><entry><literal>host (c)</literal></entry>
     <entry><literal>hostname</literal></entry>
     <entry valign="bottom">
        Machine that runs SMSC. As IP (100.100.100.100) 
        or hostname (their.machine.here)
     </entry></row>

   <row><entry><literal>port (c)</literal></entry>
     <entry><literal>port-number</literal></entry>
     <entry valign="bottom">
       Port number in the SMSC host machine
     </entry></row>

   <row><entry><literal>alt-host</literal></entry>
     <entry><literal>hostname</literal></entry>
     <entry valign="bottom">
        Optional alternate Machine that runs SMSC. 
	As IP (100.100.100.100) or hostname (their.machine.here)
	(If undef but exists alt-port, emi2 would try host:alt-port)
     </entry></row>

   <row><entry><literal>alt-port</literal></entry>
     <entry><literal>port-number</literal></entry>
     <entry valign="bottom">
       Optional alternate Port number in the SMSC host machine
	(If undef but exists alt-host, emi2 would try alt-host:port)
     </entry></row>

   <row><entry><literal>smsc-username</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       Username in the SMSC machine/connection account
     </entry></row>

   <row><entry><literal>smsc-password</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
        Password in the SMSC machine needed to contact SMSC
     </entry></row>

   <row><entry><literal>device (c)</literal></entry>
     <entry><literal>device-name</literal></entry>
     <entry valign="bottom">
          The device the modem is connected to, like <literal>/dev/ttyS0</literal>.
          ISDN connection only.
     </entry></row>

   <row><entry><literal>phone (c)</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       Phone number to dial to, when connecting over a modem to an
       SMS center.
     </entry></row>

   <row><entry><literal>our-port</literal></entry>
     <entry><literal>port-number</literal></entry>
     <entry valign="bottom">
       Optional port number in which to bind the connection in our
     end. TCP/IP connection only.
     </entry></row>

   <row><entry><literal>receive-port</literal></entry>
     <entry><literal>port-number</literal></entry>
     <entry valign="bottom">
        Optional port number we listen to and to which the SMS center
        connects when it has messages to send. Required if SMS center
	needs one connection to send and other to receive.
	TCP/IP connection only.
     </entry></row>

   <row><entry><literal>appname</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
	    Name of a "Send only" service. Defaults to <literal>send</literal>.
		 All outgoing messages are routed through this service.
     </entry></row>

   <row><entry><literal>connect-allow-ip</literal></entry>
     <entry><literal>IP-list</literal></entry>
     <entry valign="bottom">
       If set, only connections from these IP addresses are accepted
       to receive-port. TCP/IP connection only.
     </entry></row>

    <row><entry><literal>idle-timeout</literal></entry>
      <entry><literal>number (seconds)</literal></entry>
      <entry valign="bottom">
      If this option is set to a value larger than 0, then the connection will
      be closed after the configured amount of seconds without activity. This 
      option interacts with the <literal>keepalive</literal> configuration option.
      If <literal>keepalive</literal> is smaller than <literal>idle-timeout</literal>,
      then the connection will never be idle and those this option has no effect.
      If <literal>keepalive</literal> is larger than <literal>idle-timeout</literal>,
      than <literal>keepalive</literal> reopens the connection. This allows one to poll
      for pending mobile originated Short Messages at the SMSC.
     </entry></row>

    <row><entry><literal>keepalive</literal></entry>
      <entry><literal>number (seconds)</literal></entry>
      <entry valign="bottom">
        A keepalive command will be
        sent to the SMSC connection this many seconds after the last
        message. The right value to use depends on how eager the SMSC is
        to close idle connections.  50 seconds is a good guess. If you
        see many unexplained reconnects, try lowering this value. Set it
        to 0 to disable this feature.
	Requires username or my-number to be set.
     </entry></row>

    <row><entry><literal>wait-ack</literal></entry>
      <entry><literal>number (seconds)</literal></entry>
      <entry valign="bottom">
        A message is resent if the acknowledge from SMSC takes more than 
	this time.  Defaults to 60 seconds.
     </entry></row>

    <row><entry><literal>wait-ack-expire</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
        Defines what kind of action should be taken if the the ack of 
		  a message expires. The options for this value are:
		  0x00 - disconnect/reconnect, (default) 0x01 - as is now, re-queue, 
		  but this could potentially result in the msg arriving twice
		  0x02 - just carry on waiting (given that the wait-ack should never 
		  expire this is the mst accurate)
     </entry></row>

    <row><entry><literal>flow-control</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
	This SMSC can support two types of flow control. The first type 
	of flow control is a <literal>stop-and-wait</literal> protocol, 
	when this parameter equals to '1'. During the handling of commands, 
	no other commands shall be sent before the a response is received. 
	Any command that is sent before the reception of the response will 
	be discarded.
	The second type of flow control is <literal>windowing</literal>,
	when this parameter is unset or equals '0'. In this case a maximum 
	of n commands can be sent before a response is received. 
     </entry></row>

    <row><entry><literal>window</literal></entry>
      <entry><literal>number (messages)</literal></entry>
      <entry valign="bottom">
        When using <literal>flow-control=0</literal>, emi works in windowed
        flow control mode. This variable defines the size of the window used
        to send messages. (optional, defaults to the maximum - 100)
     </entry></row>

    <row><entry><literal>my-number</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
        If the large account number is different from the short number, assign
	it with this variable. For example, if short number is 12345 and large account
	is 0100100100101234 (IP+port), set my-number to 12345 and 
	every message received will have that receiver. In addition, if you are bound
	to the SMSC without an explicit login, use this configuration directive to 
	enable keep-alive (OP/31) operations. 
     </entry></row>

   <row><entry><literal>alt-charset</literal></entry>
     <entry><literal>number</literal></entry>
     <entry valign="bottom">
        Defines which character conversion kludge may be used for this 
		  specific link. Currently implemented alternative charsets are 
		  defined in "alt_charsets.h" and new ones can be added.
     </entry></row>

   <row><entry><literal>notification-pid</literal></entry>
     <entry><literal>4 num char.</literal></entry>
     <entry valign="bottom">
        Notification PID value. See below for a complete list and other notes.
	Example: 0539
       <footnote id="notification-pid-note"><para>If you set 
       <literal>notification-pid</literal>, you should also set 
       <literal>notification-addr</literal>.</para></footnote>
     </entry></row>

   <row><entry><literal>notification-addr</literal></entry>
     <entry><literal>string (max 16)</literal></entry>
     <entry valign="bottom">
        Notification Address. Example: 0100110120131234.
       <footnote id="notification-addr-note"><para>If you set 
       <literal>notification-addr</literal>, you should also set 
       <literal>notification-pid</literal>.</para></footnote>
     </entry></row>

 </tbody></tgroup></informaltable>

 <para>
   You should use <literal>notification-pid</literal> and 
   <literal>notification-addr</literal> if you need to inform
   your exact "address" to your smsc. For example, if you have a
   <literal>Multiple-Address (MA)</literal> account with several
   connections to the same <literal>short number</literal>, you may 
   need to tell your smsc to send delivery reports to the exact instance
   that sent the message. This is required because if you send a message
   with instance 1, your instance 2 wouldn't know about it, unless you
   use a shared DB store for delivery reports.
 </para>

 <informaltable frame="none">
  <tgroup cols="2"><thead><row>
     <entry>Notification PID Value</entry>
     <entry>Description</entry>
   </row></thead><tbody>

   <row><entry>0100</entry><entry>Mobile Station</entry></row>
   <row><entry>0122</entry><entry>Fax Group 3</entry></row>
   <row><entry>0131</entry><entry>X.400</entry></row>
   <row><entry>0138</entry><entry>Menu over PSTN</entry></row>
   <row><entry>0139</entry><entry>PC appl. over PSTN (E.164)</entry></row>
   <row><entry>0339</entry><entry>PC appl. over X.25 (X.121)</entry></row>
   <row><entry>0439</entry><entry>PC appl. over ISDN (E.164)</entry></row>
   <row><entry>0539</entry><entry>PC appl. over TCP/IP</entry></row>

 </tbody></tgroup></informaltable>


   

</sect2>

<sect2>
<title>SMPP 3.4</title>

   <para>This implements Short Message Peer to Peer (SMPP) Protocol
   3.4 in a manner that should also be compatible with 3.3. Sample
   configuration:</para>

<programlisting>
group = smsc
smsc = smpp
host = 123.123.123.123
port = 600
receive-port = 700 
smsc-username = "STT"
smsc-password = foo
system-type = "VMA"
address-range = ""
</programlisting>

<informaltable frame="none">
  <tgroup cols="3"><thead><row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row></thead><tbody>

   <row><entry><literal>host (m)</literal></entry>
     <entry><literal>hostname</literal></entry>
     <entry valign="bottom">
        Machine that runs SMSC. As IP (100.100.100.100) 
        or hostname (their.machine.here)
     </entry></row>

   <row><entry><literal>port (m)</literal></entry>
     <entry><literal>port-number</literal></entry>
     <entry valign="bottom">
       The port number for the TRANSMITTER connection to the SMSC. 
       May be the same as receive-port. 
		 Use value 0 to disable this I/O thread.
     </entry></row>

   <row><entry><literal>transceiver-mode</literal></entry>
     <entry>bool</entry>
     <entry valign="bottom">
       Attempt to use a TRANSCEIVER mode connection
       to the SM-SC. It uses the standard transmit 'port',
       there is no need to set 'receive-port'.
       This is a SMPP 3.4 only feature and will not work
       on an earlier SM-SC.
       This will try a bind_transceiver only and will not attempt
       to fall back to doing transmit and receive on the same connection.
      </entry></row>

   <row><entry><literal>receive-port</literal></entry>
     <entry><literal>port-number</literal></entry>
     <entry valign="bottom">
       The port number for the RECEIVER connection to the SMSC. 
       May be the same as port.
		 Use value 0 to disable this I/O thread.
     </entry></row>

   <row><entry><literal>smsc-username (m)</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       The 'username' of the Messaging Entity connecting to the
       SM-SC. If the SM-SC operator reports that the "TELEPATH
       SYSTEM MANAGER TERMINAL" view "Control.Apps.View" value 
       "Name:" is "SMPP_ZAPVMA_T" for the transmitter and 
       "SMPP_ZAPVMA_R" for the receiver the smsc-username value 
       is accordingly "SMPP_ZAP". Note that this used to be called
       system-id (the name in SMPP documentation) and has been
       changed to smsc-username to make all Kannel SMS center
       drivers use the same name.
     </entry></row>

   <row><entry><literal>smsc-password (m)</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       The password matching the "smsc-username" your teleoperator
       provided you with.
     </entry></row>


   <row><entry><literal>system-type (m)</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       Usually you can get away with "VMA" which stands for
       Voice Mail Activation.
     </entry></row>

   <row><entry><literal>service-type</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       Optional; if specified, sets the service type for the SMSC. If
       unset, the default service type is used. This may be used to
       influence SMS routing (for example). The SMSC operator may
       also refer to this as the "profile ID". The maximum length of the
       service type is 6, according to the SMPP specification v3.4.
     </entry></row>

   <row><entry><literal>interface-version</literal></entry>
     <entry><literal>number</literal></entry>
     <entry valign="bottom">
       Change the "interface version" parameter sent from Kannel to
       a value other then 0x34 (for SMPP v3.4). the value entered here
       should be the hexadecimal representation of the interface version
       parameter. for example, the default (if not set) is "34" which stands
       for 0x34. for SMPP v3.3 set to "33".
     </entry></row>

   <row><entry><literal>address-range (m)</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       According to the SMPP 3.4 spec this is supposed to
       affect which MS's can send messages to this account.
       Doesn't seem to work, though.
     </entry></row>

    <row><entry><literal>my-number</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      	Optional smsc short number. Should be set if smsc sends
	a different one.
     </entry></row>

    <row><entry><literal>enquire-link-interval</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      Optional the time lapse allowed between operations after which 
      an SMPP entity should interrogate whether it's peer still has an 
      active session. The default is 30 seconds.  
     </entry></row>

    <row><entry><literal>max-pending-submits</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      	Optional the maximum number of outstanding (i.e. acknowledged)
        SMPP operations between an ESME and SMSC. This number
        is not specified explicitly in the SMPP Protocol Specification
        and will be governed by the SMPP implementation on the SMSC.
        As a guideline it is recommended that no more than 10 (default)
        SMPP messages are outstanding at any time.
     </entry></row>

    <row><entry><literal>reconnect-delay</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      Optional the time between attempts to connect an ESME to an SMSC 
      having failed to connect initiating or during an SMPP session. 
		The default is 10 seconds.
     </entry></row>

    <row><entry><literal>source-addr-ton</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      Optional, source address TON setting for the link.
		(Defaults to 0).
     </entry></row>

    <row><entry><literal>source-addr-npi</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      Optional, source address NPI setting for the link.
		(Defaults to 1).
     </entry></row>

    <row><entry><literal>source-addr-autodetect</literal></entry>
      <entry><literal>boolean</literal></entry>
      <entry valign="bottom">
      Optional, if defined tries to scan the source address and 
		set TON and NPI settings accordingly. If you don't want to autodetect
		the source address, turn this off, by setting it to no.
		(Defaults to yes).
     </entry></row>

    <row><entry><literal>dest-addr-ton</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      Optional, destination address TON setting for the link.
		(Defaults to 0).
     </entry></row>

    <row><entry><literal>dest-addr-npi</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      Optional, destination address NPI setting for the link.
		(Defaults to 1).
     </entry></row>

    <row><entry><literal>bind-addr-ton</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      Optional, bind address TON setting for the link.
		(Defaults to 0).
     </entry></row>

    <row><entry><literal>bind-addr-npi</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      Optional, bind address NPI setting for the link.
		(Defaults to 0).
     </entry></row>

   <row><entry><literal>msg-id-type</literal></entry>
     <entry><literal>number</literal></entry>
     <entry valign="bottom">
       Optional, specifies which number base the SMSC is using for the
		 message ID numbers in the corresponding <literal>submit_sm_resp</literal> 
		 and <literal>deliver_sm</literal> PDUs. This is required to make
		 delivery reports (DLR) work on SMSC that behave differently. The number
		 is a combined set of bit 1 and bit 2 that indicate as follows:
		 bit 1: type for <literal>submit_sm_resp</literal>, bit 2: type for 
		 <literal>deliver_sm</literal>. If the bit is set then the  value is 
		 in hex otherwise in decimal number base. Which means the following
		 combinations are possible and valid: 
		 0x00 <literal>deliver_sm</literal> decimal, 
		 <literal>submit_sm_resp</literal> decimal;
		 0x01 <literal>deliver_sm</literal> decimal, 
		 <literal>submit_sm_resp</literal> hex;
		 0x02 <literal>deliver_sm</literal> hex, 
		 <literal>submit_sm_resp</literal> decimal;
		 0x03 <literal>deliver_sm</literal> hex, 
		 <literal>submit_sm_resp</literal> hex. 
		 In accordance to the SMPP v3.4 specs the default will be a C string 
		 literal if no of the above values is explicitly indicated using the 
		 config directive.
     </entry></row>

   <row><entry><literal>alt-charset</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
        Defines which character encoding is used for this specific smsc link. 
		  Uses <literal>iconv()</literal> routines to convert from and to that
		  specific character set encoding. See your local iconv_open(3) manual 
		  page for the supported character encodings and the type strings that
		  should be presented for this directive.
     </entry></row>

     <row><entry><literal>alt-addr-charset</literal></entry>
        <entry><literal>string</literal></entry>
        <entry valign="bottom">
            Defines which character encoding is used for alphanumeric addresses.
            When set to <literal>GSM</literal>, addresses are converted into the
            GSM 03.38 charset (Since @ is translated into 0x00 which will break
			the SMPP PDU, @ replaced with ?). If set to another value,
            <literal>iconv()</literal> is used.
            (Defaults to windows-1252)
        </entry></row>

    <row><entry><literal>connection-timeout</literal></entry>
      <entry><literal>number (seconds)</literal></entry>
      <entry valign="bottom">
        This timer specifies the maximum time lapse allowed 
        between transactions , after which period of inactivity, an SMPP driver may 
        assume that the session is no longer active and does reconnect.
	Defaults to 300 seconds, to disable set it to 0.
     </entry></row>

    <row><entry><literal>wait-ack</literal></entry>
      <entry><literal>number (seconds)</literal></entry>
      <entry valign="bottom">
        A message is resent if the acknowledge from SMSC takes more than 
	this time.  Defaults to 60 seconds.
     </entry></row>

    <row><entry><literal>wait-ack-expire</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
        Defines what kind of action should be taken if the ack of 
		  a message expires. The options for this value are:
		  0x00 - disconnect/reconnect, (default) 0x01 - as is now, re-queue, 
		  but this could potentially result in the msg arriving twice
		  0x02 - just carry on waiting (given that the wait-ack should never 
		  expire this is the mst accurate)
     </entry></row>

   <row><entry><literal>validityperiod</literal></entry>
     <entry><literal>integer</literal></entry>
     <entry valign="bottom">
     	 How long the message will be valid, i.e., how long the SMSC will try
     	 try to send the message to the recipient. Defined in minutes.
     </entry></row>

   </tbody></tgroup></informaltable>

</sect2>

<sect2>
<title>Sema Group SMS2000 OIS 4.0, 5.0 and 5.8</title>
 
   <para>The 4.0 implementation is over Radio PAD (X.28). Following
   configuration variables are needed, and if you find out the more
   exact meaning, please send a report.</para>

   <para>The 5.0 implementation uses X.25 access gateway.</para>
  
   <para>The 5.8 implementation uses direct TCP/IP access interface.</para>

<programlisting>
group = smsc
smsc = sema
device = /dev/tty0
smsc_nua = (X121 smsc address)
home_nua = (x121 radio pad address)
wait_report = 0/1 (0 means false, 1 means true)
</programlisting>

<informaltable frame="none">
  <tgroup cols="3"><thead><row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row></thead><tbody>

   <row><entry><literal>device (m)</literal></entry>
     <entry><literal>device</literal></entry>
     <entry valign="bottom">
        ex: /dev/tty0
     </entry></row>

   <row><entry><literal>smsc_nua (m)</literal></entry>
     <entry><literal>X121 smsc address</literal></entry>
     <entry valign="bottom">
       The address of an SMSC for SEMA SMS2000 protocols using an
       X.28 connection.
     </entry></row>

   <row><entry><literal>home_nua (m)</literal></entry>
     <entry><literal>X121 radio pad address</literal></entry>
     <entry valign="bottom">
       The address of a radio PAD implementing Sema SMS2000 using
       X.28 connection.
     </entry></row>

   <row><entry><literal>wait_report</literal></entry>
     <entry><literal>0 (false)/1 (true)</literal></entry>
     <entry valign="bottom">
       Report indicator used by the Sema SMS2000 protocol. Optional.
     </entry></row>
   </tbody></tgroup></informaltable>

<programlisting>
group = smsc
smsc = ois
host = 103.102.101.100
port = 10000
receive-port = 10000
ois-debug-level = 0
</programlisting>

<informaltable frame="none">
  <tgroup cols="3"><thead><row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row></thead><tbody>

   <row><entry><literal>host (m)</literal></entry>
     <entry><literal>ip</literal></entry>
     <entry valign="bottom">
        SMSC Host name or IP
     </entry></row>

   <row><entry><literal>port (m)</literal></entry>
     <entry><literal>port number</literal></entry>
     <entry valign="bottom">
       SMSC Port number
     </entry></row>

   <row><entry><literal>receive-port (m)</literal></entry>
     <entry><literal>port number</literal></entry>
     <entry valign="bottom">
       The port in which the SMSC will contact
     </entry></row>

   <row><entry><literal>ois-debug-level</literal></entry>
     <entry><literal>number 0 to 8</literal></entry>
     <entry valign="bottom">
       extra debug, optional, see smsc_ois.c
     </entry></row>

   </tbody></tgroup></informaltable>

<programlisting>
group = smsc
smsc = oisd
host = 103.102.101.100
port = 10000
keepalive = 25
my-number = 12345
validityperiod = 30
</programlisting>

<informaltable frame="none">
  <tgroup cols="3"><thead><row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row></thead><tbody>

   <row><entry><literal>host (m)</literal></entry>
     <entry><literal>ip</literal></entry>
     <entry valign="bottom">
        SMSC Host name or IP
     </entry></row>

   <row><entry><literal>port (m)</literal></entry>
     <entry><literal>port number</literal></entry>
     <entry valign="bottom">
       SMSC Port number
     </entry></row>

   <row><entry><literal>keepalive</literal></entry>
     <entry><literal>number</literal></entry>
     <entry valign="bottom">
       SMSC connection will not be left idle for longer than this many
       seconds.  The right value to use depends on how eager the SMSC
       is to close idle connections. If you see many unexplained 
       reconnects, try lowering this value.
       Set it to 0 to disable this feature.
     </entry></row>

   <row><entry><literal>my-number</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       Any valid SME number acceptable by SMSC. This number is used only in keepalive request. 
     </entry></row>

   <row><entry><literal>validityperiod</literal></entry>
     <entry><literal>integer</literal></entry>
     <entry valign="bottom">
     	 How long the message will be valid, i.e., how long the SMS
	 center (the real one, not the phone acting as one for Kannel)
	 will try to send the message to the recipient. Defined in minutes.
     </entry></row>

   </tbody></tgroup></informaltable>
</sect2>


<sect2>
<title>SM/ASI (for CriticalPath InVoke SMS Center 4.x)</title>

   <para>This implements Short Message/Advanced Service Interface 
	(SM/ASI) Protocol for the use of connecting to a CriticalPath
	InVoke SMS Center. Sample
   configuration:</para>

<programlisting>
group = smsc
smsc = smasi
host = 10.11.12.13
port = 23456
smsc-username = foo
smsc-password = foo
</programlisting>

<informaltable frame="none">
  <tgroup cols="3"><thead><row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row></thead><tbody>

   <row><entry><literal>host (m)</literal></entry>
     <entry><literal>hostname</literal></entry>
     <entry valign="bottom">
        Machine that runs SMSC. As IP (10.11.12.13) 
        or hostname (host.foobar.com)
     </entry></row>

   <row><entry><literal>port (m)</literal></entry>
     <entry><literal>port-number</literal></entry>
     <entry valign="bottom">
       The port number for the connection to the SMSC. 
     </entry></row>

   <row><entry><literal>smsc-username (m)</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       The 'username' of the Messaging Entity connecting to the
       SMSC. 
     </entry></row>

   <row><entry><literal>smsc-password (m)</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       The password matching the "smsc-username" your teleoperator
       provided you with.
     </entry></row>

    <row><entry><literal>reconnect-delay</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      Optional, the time between attempts to connect to an SMSC 
      having failed to connect initiating or during an session. 
		The default is 10 seconds.
     </entry></row>

    <row><entry><literal>source-addr-ton</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      Optional, source address TON setting for the link.
		(Defaults to 1).
     </entry></row>

    <row><entry><literal>source-addr-npi</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      Optional, source address NPI setting for the link.
		(Defaults to 1).
     </entry></row>

    <row><entry><literal>dest-addr-ton</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      Optional, destination address TON setting for the link.
		(Defaults to 1).
     </entry></row>

    <row><entry><literal>dest-addr-npi</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      Optional, destination address NPI setting for the link.
		(Defaults to 1).
     </entry></row>

    <row><entry><literal>priority</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      Optional, sets the default priority of messages transmitted 
		over this smsc link. (Defaults to 0, which is the highest
		priority)
     </entry></row>

   </tbody></tgroup></informaltable>
</sect2>


<sect2>
<title>GSM modem</title>

  <warning><para>See <xref linkend="upgrading-notes"> for changes.</para></warning>

  <para>This driver allows a GSM Modem or Phone to be connected to Kannel 
  and work as a virtual SMSC</para>

<programlisting>
group = smsc
smsc = at
modemtype = auto
device = /dev/ttyS0
speed = 9600
pin = 2345
</programlisting>

 <informaltable frame="none">
  <tgroup cols="3"><thead><row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row></thead><tbody>

   <row><entry><literal>modemtype</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
        Modems from different manufacturers have slightly different
        behavior. We need to know what type of modem is used. Use "auto"
        or omit parameter to have Kannel detect the modem type automatically.
        (some types should not be auto-detected like the Nokia Premicell).
     </entry></row>

   <row><entry><literal>device (m)</literal></entry>
     <entry><literal>device-name</literal></entry>
     <entry valign="bottom">
          The device the modem is connected to, like <literal>/dev/ttyS0</literal>.
          When the device name is set to <literal>rawtcp</literal>, two other
          variables are required in the configuration: <literal>host</literal>
          and <literal>port</literal>. See the note below.
      </entry></row>

   <row><entry><literal>speed</literal></entry>
     <entry><literal>serial speed in bps</literal></entry>
     <entry valign="bottom">
          The speed in bits per second. Default value 0 means to try to use
	  speed from modem definition, or if it fails, try to autodetect.
     </entry></row>

   <row><entry><literal>pin</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
         This is the PIN number of the SIM card in the GSM modem. You can specify
         this option if your SIM has never been used before and needs to have
         the PIN number entered. The PIN is usually a four digit number.
     </entry></row>

   <row><entry><literal>validityperiod</literal></entry>
     <entry><literal>integer</literal></entry>
     <entry valign="bottom">
     	 How long the message will be valid, i.e., how long the SMS
	 center (the real one, not the phone acting as one for Kannel)
	 will try to send the message to the recipient. Encoded as per
	 the GSM 03.40 standard, section 9.2.3.12. Default is
	 167, meaning 24 hours.
     </entry></row>

    <row><entry><literal>keepalive</literal></entry>
      <entry><literal>seconds</literal></entry>
      <entry valign="bottom">
        Kannel would "ping" the modem for this many seconds. If the probe fails, 
	try to reconnect to it.
     </entry></row>

    <row><entry><literal>my-number</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      	Optional phone number.
     </entry></row>

    <row><entry><literal>sms-center</literal></entry>
      <entry><literal>number</literal></entry>
      <entry valign="bottom">
      	SMS Center to send messages.
     </entry></row>

    <row><entry><literal>sim-buffering</literal></entry>
      <entry><literal>boolean</literal></entry>
      <entry valign="bottom">
        Whether to enable the so-called "SIM buffering behavior" of the GSM module.
                if assigned a true value, the module will query the message storage memory
                of the modem and will process and delete any messages found there. this does
                not alter normal behavior, but only add the capability of reading messages that
                were stored in the memory for some reason. The type of memory to use can be
                selected using the 'message-storage' parameter of the modem configuration.
                Polling the memory is done at the same interval as keepalive (if set) or 60 seconds
                (if not set).
                NOTE: This behavior is known to cause minor or major hiccups for a few buggy modems.
                Modems known to work with this setting are Wavecom WM02/M1200 and the Siemens M20.
     </entry></row>

     <row><entry><literal>max-error-count</literal></entry>
       <entry><literal>integer</literal></entry>
       <entry valign="bottom">
          Maximal error count for opening modem device or initializing of the modem before
          <literal>reset-string</literal> will be executed. This is useful when modem crashed and needs
          hard reset. Default disabled.
       </entry></row>
       
     <row><entry><literal>host</literal></entry>
       <entry><literal>IP address</literal></entry>
       <entry valign="bottom">
          Hostname or IP address to connect in <literal>rawtcp</literal> mode. 
          Required if <literal>device</literal> is set to <literal>rawtcp</literal>.
       </entry></row>

     <row><entry><literal>port</literal></entry>
       <entry><literal>integer</literal></entry>
       <entry valign="bottom">
          TCP port to connect to on <literal>rawtcp-host</literal>.
          Required if <literal>device</literal> is set to <literal>rawtcp</literal>.
       </entry></row>

   </tbody></tgroup></informaltable>

   <para>Modem definitions are now multiple groups present in kannel.conf,
   either directly or, for example, by including the example
   modems.conf. (See <xref linkend="includes" endterm="includes.title">)
   </para>

 <informaltable frame="none">
  <tgroup cols="3"><thead><row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row></thead><tbody>

   <row><entry><literal>group</literal></entry>
     <entry><literal>modems</literal></entry>
     <entry valign="bottom">
     	This is a mandatory variable
     </entry></row>

   <row><entry><literal>id</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
     	This is the the id that should be used in
	<literal>modemtype</literal> variable from AT2
     </entry></row>

   <row><entry><literal>name</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
     	The name of this modem configuration. Used in
	logs
     </entry></row>

   <row><entry><literal>detect-string</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
     	String to use when trying to detect the modem.
	See <literal>detect-string2</literal>
     </entry></row>

   <row><entry><literal>detect-string2</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
     	Second string to use to detect the modem. For example,
	if the modem replies with "SIEMENS MODEM M20", 
	<literal>detect-string</literal> could be "SIEMENS" 
	and <literal>detect-string2</literal> "M20"
     </entry></row>

   <row><entry><literal>init-string</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
     	Optional initialization string. Defaults to
	"AT+CNMI=1,2,0,1,0"
     </entry></row>

   <row><entry><literal>speed</literal></entry>
     <entry><literal>number</literal></entry>
     <entry valign="bottom">
     	Serial port hint speed to use. Optional. 
	Defaults to smsc group speed or autodetect
     </entry></row>

   <row><entry><literal>enable-hwhs</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
     	Optional AT command to enable hardware handshake.
	Defaults to "AT+IFC=2,2"
     </entry></row>

   <row><entry><literal>need-sleep</literal></entry>
     <entry><literal>boolean</literal></entry>
     <entry valign="bottom">
     	Optional. Defaults to false. Some modems needs
	to sleep after opening the serial port and before
	first command
     </entry></row>

   <row><entry><literal>no-pin</literal></entry>
     <entry><literal>boolean</literal></entry>
     <entry valign="bottom">
     	Optional. Defaults to false. If the modem doesn't
	support the PIN command, enable this
     </entry></row>

   <row><entry><literal>no-smsc</literal></entry>
     <entry><literal>boolean</literal></entry>
     <entry valign="bottom">
     	Optional. Defaults to false. If the modem doesn't
	support setting the SMSC directly on the PDU, enable
	this. (Default is to include a "00" at the beginning
	of the PDU to say it's the default smsc, and remove
	the "00" when receiving)
     </entry></row>

   <row><entry><literal>sendline-sleep</literal></entry>
     <entry><literal>number (milliseconds)</literal></entry>
     <entry valign="bottom">
     	Optional, defaults to 100 milliseconds. The sleep time
	after sending a AT command.
     </entry></row>

   <row><entry><literal>keepalive-cmd</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
     	Optional, defaults to "AT". If keepalive is activated
	in AT2 group, this is the command to be sent. If your
	modem supports it, for example, use "AT+CBC;+CSQ", and
	see in logs the reply "+CBC: 0,64" (0=On battery, 64% 
	full) and "+CSQ: 14,99" (0-31, 0-7: signal strength and
	channel bit error rate; 99 for unknown). See 3GPP 27007.
     </entry></row>

   <row><entry><literal>message-storage</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
        Message storage memory type to enable for "SIM buffering".
                Possible values are: "SM" - SIM card memory or "ME" -
                Mobile equipment memory (may not be supported by your
                modem). check your modem's manual for more types.
                By default, if the option is not set, no message storage command
                will be sent to the modem and the modem's default message
                storage will be used (usually "SM").
     </entry></row>

   <row><entry><literal>enable-mms</literal></entry>
     <entry><literal>boolean</literal></entry>
     <entry valign="bottom">
     	Optional, defaults to false. If enabled, Kannel
	would send an AT+CMMS=2 if it have more than one
	message on queue and hopefully will be quicker
	sending the messages.
     </entry></row>

   <row><entry><literal>reset-string</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
        Which reset string to execute when <literal>max-error-count</literal> reached.
        Example for Falcom: AT+CFUN=1
     </entry></row>


   </tbody></tgroup></informaltable>

   <para><emphasis>A note about delivery reports and GSM modems:</emphasis>
   while it is possible (and supported) to receive delivery reports on GSM 
   modems, it may not work for you. if you encounter problems, check that your 
   modem's init string (if not the default) is set to correctly allow the modem 
   to send delivery reports using unsolicited notification (check your modem's 
   manual). If the init-string is not set as si, some modems will store delivery 
   reports to SIM memory, to get at which you will need to enable sim-buffering. 
   finally your GSM network provider may not support delivery reports to mobile 
   units.</para>

   <para><emphasis>About <literal>rawtcp</literal> mode:</emphasis>
   This mode allows you to use a GSM modem connected to a remote terminal server,
   such as Perle IOLAN DS1 or a Cisco router with reverse telnet. The teminal
   server should support raw TCP mode. The driver is not tested in telnet mode.
   It is recommended to use <literal>keepalive</literal> variable, in order to 
   automatically reconnect in case of network connectivity problems.</para>


</sect2>


<sect2>
<title>Fake SMSC</title>

  <para>Fake SMSC is a simple protocol to test out Kannel. It is not
  a real SMS center, and cannot be used to send or receive SMS
  messages from real phones. So, it is ONLY used for testing purposes.
  </para>

<programlisting>
group = smsc
smsc = fake
port = 10000
connect-allow-ip = 127.0.0.1
</programlisting>

 <informaltable frame="none">
  <tgroup cols="3"><thead><row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row></thead><tbody>

   <row><entry><literal>host (m)</literal></entry>
     <entry><literal>hostname</literal></entry>
     <entry valign="bottom">
        Machine that runs the SMSC. As IP (100.100.100.100) 
        or hostname (their.machine.here)
     </entry></row>

   <row><entry><literal>port (m)</literal></entry>
     <entry><literal>port-number</literal></entry>
     <entry valign="bottom">
       Port number in smsc host machine
     </entry></row>

   <row><entry><literal>connect-allow-ip</literal></entry>
     <entry><literal>IP-list</literal></entry>
     <entry valign="bottom">
       If set, only connections from these IP addresses are accepted.
     </entry></row>

   </tbody></tgroup></informaltable>

</sect2>


<sect2>
<title>HTTP-based relay and content gateways</title>
 
   <para>This special "SMSC" is used for HTTP based connections with
   other gateways and various other relay services, when direct SMSC
   is not available.</para>
  
<programlisting>
group = smsc
smsc = http
system-type = kannel
smsc-username = nork
smsc-password = z0rK
port = 13015
send-url = "http://localhost:20022"
</programlisting>


 <informaltable frame="none">
  <tgroup cols="3"><thead><row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row></thead><tbody>

   <row><entry><literal>system-type (m)</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
        Type of HTTP connection. Currently supported are: 'kannel', 
		  'brunet', 'xidris', 'wapme'.
     </entry></row>

   <row><entry><literal>send-url (m)</literal></entry>
     <entry><literal>url</literal></entry>
     <entry valign="bottom">
       Location to send MT messages. This URL is expanded by used
       system, if need to.
     </entry></row>

   <row><entry><literal>no-sender</literal></entry>
   <entry><literal>boolean</literal></entry>
   <entry valign="bottom">
      Do not add variable sender to the send-url.
   </entry></row>

   <row><entry><literal>no-coding</literal></entry>
   <entry><literal>boolean</literal></entry>
   <entry valign="bottom">
      Do not add variable coding to the send-url.
   </entry></row>

   <row><entry><literal>no-sep</literal></entry>
   <entry><literal>boolean</literal></entry>
   <entry valign="bottom">
      Represent udh and text as a numeric string containing the hex-dump. For
      instance, text=%2b123 is represented as text=2b313233. 
   </entry></row>

   <row><entry><literal>port (m)</literal></entry>
     <entry><literal>port-number</literal></entry>
     <entry valign="bottom">
       Port number in which Kannel listens to (MO) messages from other
       gateway
     </entry></row>

   <row><entry><literal>connect-allow-ip</literal></entry>
     <entry><literal>IP-list</literal></entry>
     <entry valign="bottom">
       IPs allowed to use this interface. If not set, "127.0.0.1"
     (localhost) is the only host allowed to connect.
     </entry></row>

   <row><entry><literal>smsc-username</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       Username associated to connection, if needed. Kannel requires
       this, and it is the same as send-sms username at other end.
     </entry></row>

   <row><entry><literal>smsc-password</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       Password for username, if needed.
     </entry></row>

   </tbody></tgroup></informaltable>

   <para>This module can be easily adopted to other HTTP-based interfaces.
   </para>
 
</sect2>

<sect2>
<title>MT to MO direction switching</title>

    <para>In case you want to route MT messages coming from 
	 <literal>smsbox</literal> to 
	 <literal>bearerbox</literal> back into the system again as MO messages, 
	 you can use the HTTP SMSC to address it's own MO interface like this:
	 </para>
  
<programlisting>
group = smsc
smsc = http
smsc-id = MT2MO
system-type = kannel
smsc-username = tester
smsc-password = foobar
port = 14000
send-url = "http://localhost:14000/cgi-bin/sendsms"
</programlisting>

    <para>This smsc group will allow you to send MT messages to 
	 <literal>smsc-id MT2MO</literal>, which addresses the configured HTTP SMSC 
	 module. Now the module will use the <literal>send-url</literal> to pass the 
	 MT messages. As you see, the send-url loops back to it's own MO interface 
	 listening on <literal>port</literal> 14000, which will lead into an MO message 
	 and passed to smsbox again. 
	 </para>

	 <para>This can be used to generate cycles or allow to connect smsbox users
	 that pass messages and make them look like they originated from an SMSC.
	 </para>
</sect2>

<sect2>
<title>Using multiple SMS centers</title>

    <para>If you have several SMS center connections (multiple
    operators or a number of GSM modems) you need to configure one smsc
    group per SMS center (or GSM modem). When doing this, you might
    want to use routing systems to rout messages to specific centers -
    for example, you have 2 operator SMS centers, and the other is
    much faster and cheaper to use.</para>

    <para>To set up routing systems, first give an unique ID for each
    SMS center - or if you want to treat multiple ones completely
    identical, give them identical ID. Then use 
    <literal>preferred-smsc-id</literal> and
    <literal>denied-smsc-id</literal> to set up the routing to your
    taste. See also SMS PUSH settings ('sendsms-user' groups), below.</para>
</sect2>

<sect2>
<title>Feature checklist</title>

<para>Not all of Kannel's SMSC drivers support the same set of features.
This is because they were written at different times, and new features
are often only added to drivers that the feature author can test.</para>

<para>The table in this section is an attempt to show exactly what
features to expect from a driver, and to help identify areas where
drivers need to be updated.  Currently most of the entries are
marked as "not tested" because the table is still new.</para>

<table frame="ALL">
 <title>SMSC driver features</title>
 <tgroup cols="13" align="center">
  <colspec colname="first" colnum="1" align="center">
  <colspec colname="last" colnum="13">
  <spanspec spanname="feature" namest="first" nameend="last">
  <thead>
   <row>
     <entry>Feature</entry>
     <entry>cimd</entry>
     <entry>cimd2</entry>
     <entry>emi</entry>
     <entry>emi_x25</entry>
     <entry>smpp</entry>
     <entry>sema</entry>
     <entry>ois</entry>
     <entry>oisd</entry>
     <entry>at</entry>
     <entry>http</entry>
     <entry>fake</entry>
     <entry>smasi</entry>
   </row>
  </thead>
  <tbody>
   <row>
    <entry spanname="feature">Can use DLR</entry>
   </row>
   <row>
    <entry></entry>
    <entry>n</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>y?</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>y</entry>
   </row>
   <row>
    <entry spanname="feature">Can set DCS<footnote id="fields-to-dcs"><para>To use 
      <literal>mclass</literal>, <literal>mwi</literal>, <literal>coding</literal>
      and <literal>compress</literal> fields.</para></footnote></entry>
   </row>
   <row>
    <entry></entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
   </row>
   <row>
    <entry spanname="feature">Can set Alt-DCS</entry>
   </row>
   <row>
    <entry></entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can set Validity</entry>
   </row>
   <row>
    <entry></entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can set Deferred</entry>
   </row>
   <row>
    <entry></entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can set PID</entry>
   </row>
   <row>
    <entry></entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>?</entry>
   </row>

	<row>
    <entry spanname="feature">Can set RPI</entry>
   </row>
   <row>
    <entry></entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can send Unicode</entry>
   </row>
   <row>
    <entry></entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can send 8 bits</entry>
   </row>
   <row>
    <entry></entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>y</entry>
   </row>

   <row>
    <entry spanname="feature">Correctly send GSM alphabet</entry>
   </row>
   <row>
    <entry></entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can set binfo / tariff class</entry>
   </row>
   <row>
    <entry></entry>
    <entry>?</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>n</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can use throttling</entry>
   </row>
   <row>
    <entry></entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>y</entry>
   </row>
   
  </tbody>
 </tgroup>
</table>

<table frame="ALL">
 <title>SMSC driver internal features</title>
 <tgroup cols="13" align="center">
  <colspec colname="first" colnum="1" align="center">
  <colspec colname="last" colnum="13">
  <spanspec spanname="feature" namest="first" nameend="last">
  <thead>
   <row>
     <entry>Feature</entry>
     <entry>cimd</entry>
     <entry>cimd2</entry>
     <entry>emi2</entry>
     <entry>emi_x25</entry>
     <entry>smpp</entry>
     <entry>sema</entry>
     <entry>ois</entry>
     <entry>oisd</entry>
     <entry>at</entry>
     <entry>http</entry>
     <entry>fake</entry>
     <entry>smasi</entry>
   </row>
  </thead>
  <tbody>

   <row>
    <entry spanname="feature">Can keep idle connections alive</entry>
   </row>
   <row>
    <entry></entry>
    <entry>n</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>y?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>y</entry>
   </row>

   <!-- Lets clean the rest of the table -->

   <row>
    <entry spanname="feature">Can send octet data without UDH</entry>
   </row>
   <row>
    <entry></entry>
    <entry>n</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>y?</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>y?<footnote id="nomarkod"><para>Does not mark it as octet data</para></footnote></entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can send octet data with UDH</entry>
   </row>
   <row>
    <entry></entry>
    <entry>N</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>y?</entry>
    <entry>y?</entry>
    <entry>n</entry>
    <entry>?</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>y?</entry>
    <entry>y?<footnoteref linkend="nomarkod"></entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can send text messages with UDH</entry>
   </row>
   <row>
    <entry></entry>
    <entry>n</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>y?</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>?</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>y?</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can receive octet data without UDH</entry>
   </row>
   <row>
    <entry></entry>
    <entry>n</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>y?<footnote><para>However, it looks like the <literal>sema</literal> driver can't receive <emphasis>text</emphasis> data.</para></footnote></entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can receive Unicode messages</entry>
   </row>
   <row>
    <entry></entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can receive octet data with UDH</entry>
   </row>
   <row>
    <entry></entry>
    <entry>n</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>N</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>y?</entry>
    <entry>y?</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can receive text messages with UDH</entry>
   </row>
   <row>
    <entry></entry>
    <entry>n</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>N</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Correctly encodes <literal>@</literal> when sending</entry>
   </row>
   <row>
    <entry></entry>
    <entry>y?</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>y?</entry>
    <entry>?</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>y?</entry>
    <entry>y?</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Correctly encodes <literal>&auml;</literal> when sending</entry>
   </row>
   <row>
    <entry></entry>
    <entry>y?</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>y?</entry>
    <entry>?</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>y?</entry>
    <entry>y?</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Correctly encodes <literal>{</literal> when sending</entry>
   </row>
   <row>
    <entry></entry>
    <entry>n</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>y?</entry>
    <entry>?</entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>N<footnote><para>Miscalculates message length</para></footnote></entry>
    <entry>y?</entry>
    <entry>y?</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can receive <literal>@</literal> in text messages</entry>
   </row>
   <row>
    <entry></entry>
    <entry>y?</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>y?</entry>
    <entry>?</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>y</entry>
    <entry>y?</entry>
    <entry>y?</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can receive <literal>&auml;</literal> in text messages</entry>
   </row>
   <row>
    <entry></entry>
    <entry>y?</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>y?</entry>
    <entry>?</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>y?</entry>
    <entry>y?</entry>
    <entry>y?</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can receive <literal>{</literal> in text messages</entry>
   </row>
   <row>
    <entry></entry>
    <entry>n</entry>
    <entry>y?</entry>
    <entry>y</entry>
    <entry>?</entry>
    <entry>y?</entry>
    <entry>?</entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>y?</entry>
    <entry>y?</entry>
    <entry>y?</entry>
    <entry>?</entry>
   </row>

   <row>
    <entry spanname="feature">Can shut down idle connections</entry>
   </row>
   <row>
    <entry></entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>y</entry>
    <entry>n</entry>
    <entry>n</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>n</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
    <entry>?</entry>
   </row>

  </tbody>
 </tgroup>
</table>

<informaltable frame="none">
 <tgroup cols="2">
  <colspec colnum="1" align="left">
  <thead>
   <row><entry>Symbol</entry><entry>Meaning</entry></row>
  </thead>

  <tbody>

   <row>
    <entry>?</entry>
    <entry>not yet investigated</entry>
   </row>
 
   <row>
    <entry>y</entry>
    <entry>driver has this feature, and it has been tested</entry>
   </row>
  
   <row>
    <entry>y?</entry>
    <entry>driver probably has this feature, has not been tested</entry>
   </row>
  
   <row>
    <entry>n</entry>
    <entry>driver does not have this feature</entry>
   </row>
  
   <row>
    <entry>N</entry>
    <entry>driver claims to have this feature but it doesn't work</entry>
   </row>

   <row>
    <entry>-</entry>
    <entry>feature is not applicable for this driver</entry>
   </row>

  </tbody>

 </tgroup>
</informaltable>

</sect2>
</sect1>


<sect1>
<title>External delivery report (DLR) storage</title>

   <para>Delivery reports are supported by default internally, which
	means all DLRs are stored in the memory of the bearerbox process.
	This is problematic if bearerbox crashes or you take the process
	down in a controlled way, but there are still DLRs open. Therefore
	you may use external DLR storage places, i.e. a MySQL database.
	</para>
	<para>Following are the supported DLR storage types and how to use
	them:</para>

	<sect2>
	<title>Internal DLR storage</title>

   <para>This is the default way in handling DLRs and does not
	require any special configuration. In order to configure bearerbox
	to use internal DLR storage use <literal>dlr-storage = internal</literal>
	in the <literal>core</literal> group.
	</para>

   </sect2>

	<sect2>
	<title>MySQL DLR storage</title>
	<para>To store DLR information into a MySQL database you may use the
	<literal>dlr-storage = mysql</literal> configuration directive in the
	<literal>core</literal> group.
	</para>
	<para>In addition to that you must have a <literal>dlr-db</literal>
	group defined that specifies the table field names that are used to the
	DLR attributes and a <literal>mysql-connection</literal> group that
	defines the connection to the MySQL server itself.
	</para>
	<para>Here is the example configuration from
	<literal>doc/examples/dlr-mysql.conf</literal>:

<programlisting>
group = mysql-connection
id = mydlr
host = localhost
username = foo
password = bar
database = dlr
max-connections = 1

group = dlr-db
id = mydlr
table = dlr
field-smsc = smsc
field-timestamp = ts
field-destination = destination
field-source = source
field-service = service
field-url = url
field-mask = mask
field-status = status
field-boxc-id = boxc
</programlisting>

	</para>

<sect3>
<title>MySQL connection configuration</title>

   <para>For several reasons external storage may be required to 
	handle dynamical issues, i.e. DLRs, sms-service, sendsms-user, 
	ota-setting, ota-bookmark definitions and so on. To define a 
	MySQL database connection you simple need to specify a
	<literal>mysql-connection</literal> group as follows:
	</para>
	
 <table frame="none">
  <title>MySQL Connection Group Variables</title>
  <tgroup cols="3">
  <thead>
   <row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row>
  </thead>
  <tbody>
   <row><entry><literal>group</literal></entry>
     <entry><literal>mysql-connection</literal></entry>
     <entry valign="bottom">
       This is a mandatory variable
     </entry></row>

   <row><entry><literal>id (m)</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
	     An optional name or id to identify this MySQL connection
		  for internal reference with other MySQL related configuration
		  groups. Any string is acceptable, but semicolon ';' may cause
		  problems, so avoid it and any other special non-alphabet characters.
     </entry></row>

   <row><entry><literal>host (m)</literal></entry>
     <entry>hostname or IP</entry>
     <entry valign="bottom">
        Hostname or IP of a server running a MySQL database to connect to.
     </entry></row>

    <row><entry><literal>username (m)</literal></entry>
     <entry>username</entry>
     <entry valign="bottom">
        User name for connecting to MySQL database.
     </entry></row>

    <row><entry><literal>password (m)</literal></entry>
     <entry>password</entry>
     <entry valign="bottom">
        Password for connecting to MySQL database.
     </entry></row>

    <row><entry><literal>database (m)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        Name of database in MySQL database server to connect to.
     </entry></row>

    <row><entry><literal>max-connections</literal></entry>
     <entry>integer</entry>
     <entry valign="bottom">
        How many connections should be opened to the given database.
        This is used for database pool.
     </entry></row>

  </tbody>
  </tgroup>
 </table>

  <para>A sample 'mysql-connection' group:

<programlisting>
group = mysql-connection
id = dlr-db
host = localhost
username = foo
password = bar
database = dlr
max-connections = 1
</programlisting>

  </para>
  <para>In case you use different MySQL connections for several storage
  issues, i.e. one for DLR and another different one for sms-service you
  may use the <literal>include</literal> configuration statement to extract
  the MySQL related configuration groups to a separate <literal>mysql.conf
  </literal> file.
  </para>

</sect3>
	</sect2>

	<sect2>
	<title>LibSDB DLR storage</title>
	<para>To store DLR information into a LibSDB resource (which is an
	abstraction	of a real database) you may use the
	<literal>dlr-storage = sdb</literal> configuration directive in the
	<literal>core</literal> group.
	</para>
	<para>In addition to that you must have a <literal>dlr-db</literal>
	group defined that specifies the table field names that are used to the
	DLR attributes and a <literal>sdb-connection</literal> group that
	defines the LibSDB resource itself.
	</para>
	<para>Here is the example configuration from
	<literal>doc/examples/dlr-sdb.conf</literal> using a PostgreSQL resource:

<programlisting>
group = sdb-connection
id = pgdlr
url = "postgres:host=localhost:db=myapp:port=1234"
max-connections = 1

group = dlr-db
id = pgdlr
table = dlr
field-smsc = smsc
field-timestamp = ts
field-destination = destination
field-source = source
field-service = service
field-url = url
field-mask = mask
field-status = status
field-boxc-id = boxc
</programlisting>

	</para>
  <para>Beware that you have the DB support build in your LibSDB
  installation when trying to use a specific DB type within the URL.
  </para>

	</sect2>

	<sect2>
	<title>Oracle 8i/9i DLR storage</title>
	<para>To store DLR information into a Oracle database you may use the
	<literal>dlr-storage = oracle</literal> configuration directive in the
	<literal>core</literal> group.
	</para>
	<para>In addition to that you must have a <literal>dlr-db</literal>
	group defined that specifies the table field names that are used to the
	DLR attributes and a <literal>oracle-connection</literal> group that
	defines the connection to the Oracle server itself.
	</para>
	<para>Here is the example configuration from
	<literal>doc/examples/dlr-oracle.conf</literal>:

<programlisting>
group = oracle-connection
id = mydlr
username = foo
password = bar
tnsname = dlr
max-connections = 1

group = dlr-db
id = mydlr
table = dlr
field-smsc = smsc
field-timestamp = ts
field-destination = destination
field-source = source
field-service = service
field-url = url
field-mask = mask
field-status = status
field-boxc-id = boxc
</programlisting>

	</para>

	</sect2>

	<sect2>
	<title>PostgreSQL DLR storage</title>
	<para>To store DLR information into a PostgreSQL database you may use the
	<literal>dlr-storage = pgsql</literal> configuration directive in the
	<literal>core</literal> group.
	</para>
	<para>In addition to that you must have a <literal>dlr-db</literal>
	group defined that specifies the table field names that are used to the
	DLR attributes and a <literal>pgsql-connection</literal> group that
	defines the connection to the PostgreSQL server itself.
	</para>
	<para>Here is the example configuration:

<programlisting>
group = pgsql-connection
id = mydlr
host = myhost.com
username = foo
password = bar
database = dlr
max-connections = 1

group = dlr-db
id = mydlr
table = dlr
field-smsc = smsc
field-timestamp = ts
field-destination = destination
field-source = source
field-service = service
field-url = url
field-mask = mask
field-status = status
field-boxc-id = boxc
</programlisting>

	</para>

	</sect2>

        <sect2>
	<title>DLR database field configuration</title>
	<para>For external database storage of DLR information in relational
	database management systems (RDBMS) you will have to specify which table
	field are used to represent the stored data. This is done via the
	<literal>dlr-db</literal> group as follows:
	</para>

 <table frame="none">
  <title>DLR Database Field Configuration Group Variables</title>
  <tgroup cols="3">
  <thead>
   <row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row>
  </thead>
  <tbody>
   <row><entry><literal>group</literal></entry>
     <entry><literal>dlr-db</literal></entry>
     <entry valign="bottom">
       This is a mandatory variable
     </entry></row>

   <row><entry><literal>id (m)</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
	     An id to identify which external connection should be used for
 		  DLR storage. Any string is acceptable, but semicolon ';' may cause
		  problems, so avoid it and any other special non-alphabet characters.
     </entry></row>

   <row><entry><literal>table (m)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        The name of the table that is used to store the DLR information.
     </entry></row>

   <row><entry><literal>field-smsc (m)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        The table field that is used for the smsc data.
     </entry></row>

   <row><entry><literal>field-timestamp (m)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        The table field that is used for the timestamp data.
     </entry></row>

   <row><entry><literal>field-destination (m)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        The table field that is used for the destination number data.
     </entry></row>

   <row><entry><literal>field-source (m)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        The table field that is used for the source number data.
     </entry></row>

   <row><entry><literal>field-service (m)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        The table field that is used for the service username data.
     </entry></row>

   <row><entry><literal>field-url (m)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        The table field that is used for the DLR URL which is triggered
		  when the DLR for this message arrives from the SMSC.
     </entry></row>

   <row><entry><literal>field-mask (m)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        The table field that is used for the DLR mask that has been set
		  for a message.
     </entry></row>

   <row><entry><literal>field-status (m)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        The table field that is used to reflect the status of the DLR
		  for a specific message.
     </entry></row>

   <row><entry><literal>field-boxc-id (m)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        The table field that is used to store the smsbox connection id
		  that has passed the message for delivery. This is required in 
		  cases you want to guarantee that DLR messages are routed back to
		  the same smsbox conn instance. This is done via the smsbox routing.
		  If you don't use smsbox routing simply add this field to your
		  database table and keep it empty.
     </entry></row>

  </tbody>
  </tgroup>
 </table>

  <para>A sample 'dlr-db' group:

<programlisting>
group = dlr-db
id = dlr-db
table = dlr
field-smsc = smsc
field-timestamp = ts
field-source = source
field-destination = destination
field-service = service
field-url = url
field-mask = mask
field-status = status
field-boxc-id = boxc
</programlisting>

  </para>
  <para>Beware that all variables in this group are mandatory, so you
  have to specify all fields to enable bearerbox to know how to store
  and retrieve the DLR information from the external storage spaces.
  </para>

	</sect2>

</sect1>	  



<sect1>
<title>SMSBox configuration</title>

<sect2>
<title>Smsbox group</title>

  <para>You must define an 'smsbox' group into the configuration file to be
  able to use SMS Kannel. The simplest working 'smsbox' group looks 
   like this:

<programlisting>
group = smsbox
bearerbox-host = localhost
</programlisting>

   ...but you would most probably want to define 'sendsms-port' to be
   able to use SMS push.</para>

   <para>SMSBox inherits from core the following fields:
<programlisting>
smsbox-port
http-proxy-port
http-proxy-host
http-proxy-username
http-proxy-password
http-proxy-exceptions
http-proxy-exceptions-regex
ssl-certkey-file
</programlisting>
   </para>

 <table frame="none">
  <title>Smsbox Group Variables</title>
  <tgroup cols="3">
  <thead>
   <row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row>
  </thead>
  <tbody>
   <row><entry><literal>group (m)</literal></entry>
     <entry><literal>smsbox</literal></entry>
     <entry valign="bottom">
       This is a mandatory variable
     </entry></row>

   <row><entry><literal>bearerbox-host (m)</literal></entry>
     <entry><literal>hostname</literal></entry>
     <entry valign="bottom">
        The machine in which the bearerbox is. 
     </entry></row>

   <row><entry><literal>bearerbox-port (o)</literal></entry>
     <entry>port-number</entry>
     <entry valign="bottom">
        This is the port number to which smsbox will connect bearerbox.
        If not given <literal>smsbox-port</literal> from core group used.
     </entry></row>
	  
   <row><entry><literal>bearerbox-port-ssl (o)</literal></entry>
     <entry>bool</entry>
     <entry valign="bottom">
         If set to true, the smsbox connection will be SSL-enabled.
	 Your smsbox will connect using SSL to the bearerbox
	 then. This is used to secure communication between bearerbox
	 and smsboxes in case they are in separate networks operated and
	 the TCP communication is not secured on a lower network layer.
         If not given <literal>smsbox-port-ssl</literal> from core group used.
     </entry></row>

   <row><entry><literal>smsbox-id (o)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        Optional smsbox instance identifier. This is used to 
 		  identify an smsbox connected to an bearerbox for the purpose
		  of having smsbox specific routing inside bearerbox. So if you
		  you own boxes that do pass messages into bearerbox for delivery
		  you may want that answers to those are routed back to your 
		  specific smsbox instance, i.e. SMPP or EMI proxying boxes.
     </entry></row>

    <row><entry><literal>sendsms-port (c)</literal></entry>
     <entry>port-number</entry>
     <entry valign="bottom">
        The port in which any sendsms HTTP requests are done. As with
        other ports in Kannel, can be set as anything desired.
     </entry></row>

	 <row><entry><literal>sendsms-port-ssl (o)</literal></entry>
     <entry>bool</entry>
     <entry valign="bottom">
        If set to true, the sendsms HTTP interface will use a
		  SSL-enabled HTTP server with the specified 
		  ssl-server-cert-file and ssl-server-key-file from the 
		  core group. Defaults to "no".
     </entry></row>

	 <row><entry><literal>sendsms-url (o)</literal></entry>
     <entry>url</entry>
     <entry valign="bottom">
	     URL locating the sendsms service. Defaults to <literal>
        /cgi-bin/sendsms</literal>.
     </entry></row>

	 <row><entry><literal>sendota-url (o)</literal></entry>
     <entry>url</entry>
     <entry valign="bottom">
	     URL locating the sendota service. Defaults to <literal>
        /cgi-bin/sendota</literal>.
     </entry></row>
	
    <row><entry><literal>immediate-sendsms-reply (o)</literal></entry>
     <entry>boolean</entry>
     <entry valign="bottom">
        This is a backward compatibility flag: when set, Kannel will 
        immediately answer to any sendsms requests, without knowing if
        the bearerbox will ever accept the message. If set to false
       (default), smsbox will not reply to HTTP request until the bearerbox
        has received the message.
     </entry></row>

    <row><entry><literal>sendsms-chars</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        Only these characters are allowed in 'to' field when send-SMS
        service is requested via HTTP. Naturally, you should allow 
        at least <literal>0123456789</literal>. The
        <emphasis>space</emphasis> character (' ') has special
        meaning: it is used to separate multiple phone numbers from
        each other in multi-send. To disable this feature, do not have
        it as an accepted character. If this variable is
        not set, the default set <literal>"0123456789&nbsp;+-"</literal> is used.
     </entry></row>

    <row><entry><literal>global-sender</literal></entry>
     <entry>phone-number</entry>
     <entry valign="bottom">
        If set, all sendsms originators are set as these before
        proceeding. Note that in a case of most SMS centers you
        cannot set the sender number, but it is automatically set
        as the number of SMSC
     </entry></row>

    <row><entry><literal>log-file</literal></entry>
     <entry>filename</entry>
     <entry morerows="2" valign="bottom">
       As with the bearerbox 'core' group. Access-log is used to store
       information about MO and send-sms requests. Can be named same as the 
       'main' access-log (in 'core' group).
     </entry></row>

    <row><entry><literal>log-level</literal></entry>
     <entry>number 0..5</entry></row>

    <row><entry><literal>access-log</literal></entry>
     <entry>filename</entry></row>

    <row><entry><literal>white-list</literal></entry>
     <entry>URL</entry>
     <entry valign="bottom">
        Load a list of accepted destinations of SMS messages. If a 
	destination of an SMS message is not in this list, any message 
	received from the HTTP interface is rejected. See notes of phone 
	number format from numhash.h header file. 
     </entry></row>

    <row><entry><literal>black-list</literal></entry>
     <entry>URL</entry>
     <entry valign="bottom">
        As white-list, but SMS messages to these numbers are
        automatically discarded
     </entry></row>

    <row><entry><literal>reply-couldnotfetch</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        If set, replaces the SMS message sent back to user when Kannel
	could not fetch content. 
	Defaults to <literal>Could not fetch content, sorry.</literal>.
     </entry></row>

    <row><entry><literal>reply-couldnotrepresent</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        If set, replaces the SMS message sent back when Kannel could not 
	represent the result as a SMS message. 
	Defaults to <literal>Result could not be represented as an 
	SMS message.</literal>.
     </entry></row>

    <row><entry><literal>reply-requestfailed</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        If set, replaces the SMS message sent back when Kannel could not 
	contact http service.
	Defaults to <literal>Request Failed</literal>.
     </entry></row>

    <row><entry><literal>reply-emptymessage</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        If set, replaces the SMS message sent back when message is
	empty. Set to "" to enable empty messages.
	Defaults to <literal>&lt;Empty reply from service provider&gt;</literal>.
     </entry></row>

    <row><entry><literal>mo-recode</literal></entry>
     <entry>boolean</entry>
     <entry valign="bottom">
        If enabled, Kannel will try to convert received messages with UCS-2 charset
	to WINDOWS-1252 or to UTF-8, simplifying external servers jobs. If Kannel is 
	able to recode message, it will also change <literal>coding</literal> to 
	<literal>7 bits</literal> and <literal>charset</literal> to 
	<literal>windows-1252</literal> or to <literal>utf-8</literal>. 
     </entry></row>

    <row><entry><literal>http-request-retry</literal></entry>
     <entry>integer</entry>
     <entry valign="bottom">
        If set, specifies how many retries should be performed for failing
        HTTP requests of sms-services. Defaults to 0, which means no retries
        should be performed and hence no HTTP request queuing is done.
     </entry></row>

	 <row><entry><literal>http-queue-delay</literal></entry>
     <entry>integer</entry>
     <entry valign="bottom">
        If set, specifies how many seconds should pass within the HTTP queuing
        thread for retrying a failed HTTP request. Defaults to 10 sec. and is
        only obeyed if <literal>http-request-retry</literal> is set to a 
        non-zero value.
     </entry></row>

     <row><entry><literal>white-list-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        Defines the set of accepted destinations of SMS messages. If a 
	destination of an SMS message is not in this set, any message 
	received from the HTTP interface is rejected. 
        See section on regular 
        expressions for details.
        </entry>   
     </row>
     <row><entry><literal>black-list-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        As white-list-regex, but SMS messages to numbers within in this set are
        automatically discarded.
        See section on regular 
        expressions for details.
        </entry>   
     </row>
     <row><entry><literal>max-pending-requests</literal></entry>   
        <entry>number of messages</entry>
        <entry valign="bottom">
        Maximum number of pending MO or DLR messages that are handled in parallel.
        (Default: 512)
        </entry>
     </row>

  </tbody>
  </tgroup>
 </table>

   <para>A typical 'smsbox' group could be something like this:

<programlisting>
group = smsbox
bearerbox-host = localhost
sendsms-port = 13131
sendsms-chars = "0123456789 "
global-sender = 123456
access-log = "kannel.access"
log-file = "smsbox.log"
log-level = 0
</programlisting>
 </para>


</sect2>

<sect2>
<title>Smsbox routing inside bearerbox</title>

  <para>The communication link between bearerbox and smsbox has been
  designed for the purpose of load-balancing via random assignment. 
  Which means, bearerbox holds all smsc connections and passes inbound
  message to one of the connected smsboxes. So you have a determined route
  for outbound messages, but no determined route for inbound messages.
  </para>

  <para>The smsbox routing solves this for the inbound direction. In
  certain scenarios you want that bearerbox to know to which smsbox
  instance it should pass messages. I.e. if you implement our own boxes
  that pass messages to bearerbox and expect to receive messages defined
  on certain rules, like receiver number or smsc-id. This is the case
  for EMI/UCP and SMPP proxies that can be written easily using smsbox
  routing facility.
  </para>

  <para>If you smppbox handles the SMPP specific communication to your
  EMSEs, and if an client send a submit_sm PDU, smppbox would transform
  the message into Kannel message representation and inject the message to
  bearerbox as if it would be an smsbox. As you want to assign your clients
  shortcuts for certain networks or route any inbound traffic from a certain
  smsc link connected to bearerbox, you need to separate in the scope of 
  bearerbox where the inbound message will be going to. An example may
  look like this:

<programlisting>
group = smsbox
...
smsbox-id = mysmsc
...

group = smsbox-route
smsbox-id = mysmsc
shortcuts = "1111;2222;3333"
</programlisting>

	which means and inbound message with receiver number 1111, 2222 or 3333
	will be delivered to the smsbox instance that has identified itself
	via the id "mysmsc" to bearerbox. Using this routing the smsbox instance
	(which may be an EMI/UCP or SMPP proxy) is able to send a deliver_sm PDU
	</para>

   <para>smsbox-route inherits from core the following fields:
   </para>

 <table frame="none">
  <title>Smsbox-route Group Variables</title>
  <tgroup cols="3">
  <thead>
   <row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row>
  </thead>
  <tbody>
   <row><entry><literal>group (m)</literal></entry>
     <entry><literal>smsbox-route</literal></entry>
     <entry valign="bottom">
       This is a mandatory variable
     </entry></row>

   <row><entry><literal>smsbox-id (m)</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
        Defines for which smsbox instance the routing rules do apply.
     </entry></row>

	 <row><entry><literal>smsc-ids</literal></entry>
     <entry>word-list</entry>
     <entry valign="bottom">
        If set, specifies from which smsc-ids all inbound messages should
		  be routed to this smsbox instance. List contains smsc-ids separated
		  by semicolon (";"). This rule may be used to pull any smsc specific
		  message stream to an smsbox instance.
     </entry></row>

	 <row><entry><literal>shortcuts</literal></entry>
     <entry>number-list</entry>
     <entry valign="bottom">
        If set, specifies which receiver numbers for inbound messages should
		  be routed to this smsbox instance. List contains numbers separated
		  by semicolon (";"). This rule may be used to pull receiver number
		  specific message streams to an smsbox instance.
     </entry></row>

  </tbody>
  </tgroup>
 </table>

</sect2>

<sect2>
<title>SMS-service configurations</title>

    <para>Now that you have an SMS center connection to send and
    receive SMS messages you need to define services for incoming
    messages. This is done via 'sms-service' configuration
    groups.</para>

    <para>These groups define SMS services in the smsbox, so they are only
    used by the smsbox. Each service is recognized from the first word
    in an SMS message and by the number of arguments accepted by the
    service configuration (unless <literal>catch-all</literal>
    configuration variable is used).  By adding a username and password in the URL
    in the following manner
    "http://luser:password@host.domain:port/path?query" we can perform
    HTTP Basic authentication.</para>

    <para>The simplest service group looks like this:

<programlisting>
group = sms-service
keyword = www
get-url = "http://%S"
</programlisting>
     
     This service grabs any SMS with two words and 'www' as the first
     word, and then does an HTTP request to an URL which is taken from
     the rest of the message. Any result is sent back to the phone
     (or requester), but is truncated to the 160 characters that will
     fit into an SMS message, naturally.</para>

     <para>Service group <literal>default</literal> has a special
     meaning: if the incoming message is not routed to any other
     service, <literal>default</literal> 'sms-service' group is used.
     You should always define <literal>default</literal> service.</para>

     <para>Service group <literal>black-list</literal> has a special
     meaning: if the incoming message is in service's black-list, this
     service is used to reply to user. If unset, message will be 
     discarded.</para>

 <table frame="none">
  <title>SMS-Service Group Variables</title>
  <tgroup cols="3">
  <thead>
   <row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row>
  </thead>
  <tbody>
   <row><entry><literal>group (m)</literal></entry>
     <entry><literal>sms-service</literal></entry>
     <entry valign="bottom">
       This is a mandatory variable
     </entry></row>

   <row><entry><literal>keyword (m)</literal></entry>
     <entry>word</entry>
     <entry valign="bottom">
        Services are identified by the first word in the SMS. Each
        `%s' in the URL corresponds to one word in the SMS message.
         Words are separated with spaces. A keyword is matched only if
         the number of words in the SMS message is the same as the
         number of `%s' fields in the URL. This allows you to
        configure the gateway to use different URLs for the same
        keyword depending on the number of words the SMS message
        contains. The keyword matches in non-case sensitive manner,
		  which means you don't have to use aliases to handle different
		  cased versions of your keyword.
     </entry></row>

   <row><entry><literal>keyword-regex</literal></entry>
     <entry>POSIX regular expression</entry>
     <entry valign="bottom">
     This field may be used to enable service-selection based on a regular expression.
     If this field is defined for a service, then the selection will rely on the regex only, never taking
     the literal <literal>keyword</literal> into account.
     See section on regular expressions for details.
   </entry></row>

   <row><entry><literal>aliases</literal></entry>
     <entry>word-list</entry>
     <entry valign="bottom">
        If the service has aliases, they are listed as a list with 
        each entry separated with a semicolon (';')

     </entry></row>

   <row><entry><literal>name</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        Optional name to identify the service in logs. If unset,
	<literal>keyword</literal> is used.
     </entry></row>

   <row><entry><literal>get-url (c)</literal></entry>
     <entry>URL</entry>
     <entry valign="bottom">
        Requested URL. The url can include a list of parameters, which are
        parsed before the url is fetched. See below for these
        parameters. Also works with plain 'url'

     </entry></row>

   <row><entry><literal>post-url (c)</literal></entry>
     <entry>URL</entry>
     <entry valign="bottom">
        Requested URL. As above, but request is done as POST, not GET.
	Always matches the keyword, regardless of pattern matching.
	See notes on POST other where.

     </entry></row>


   <row><entry><literal>post-xml (c)</literal></entry>
     <entry>URL</entry>
     <entry valign="bottom">
        Requested URL. As above, but request is done as XML POST.
	Always matches the keyword, regardless of pattern matching.
	See notes on POST other where and <xref
	    linkend="postxml" endterm="postxml.title">
     </entry></row>

   <row><entry><literal>file (c)</literal></entry>
     <entry>filename</entry>
     <entry valign="bottom">
        File read from a local disc. Use this variable only if no
        <literal>url</literal> is set. All escape codes (parameters)
        in <literal>url</literal> are supported in filename. 
        The last character of the file (usually linefeed) is removed.

     </entry></row>

   <row><entry><literal>text (c)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        Predefined text answer. Only if there is neither <literal>url</literal> nor 
        <literal>file</literal> set. Escape codes (parameters) are
        usable here, too.

     </entry></row>

   <row><entry><literal>exec (c)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        Executes the given shell command as the current UID of the
		  running smsbox user and returns the output to 
		  <literal>stdout</literal> as reply.
		  Escape codes (parameters) are
        usable here, too. BEWARE: You may harm your system if you use
		  this sms-service type without serious caution! Make sure anyone
		  who is allowed to use these kind of services is checked using 
		  white/black-list mechanisms for security reasons.
     </entry></row>

   <row><entry><literal>accepted-smsc</literal></entry>
     <entry>id-list</entry>
     <entry valign="bottom">
        Accept ONLY SMS messages arriving from SMSC with matching ID.
        <footnote><para>Even if this service is denied,
	Kannel still searches for other service which accepts the message,
	or default service.</para></footnote>
        Separate multiple entries with ';'. For example, if 
         <literal>accepted-smsc</literal>
        is "RL;SON", accept messages which originate from SMSC with
        ID set as 'RL' or 'SON'
     </entry></row>

   <row><entry><literal>allowed-prefix</literal></entry>
     <entry><literal>prefix-list</literal></entry>
     <entry valign="bottom">
        A list of phone number prefixes of the sender number which are 
		  accepted to be received by this service. 
        <footnote><para>Like in accepted-smsc, 
	Kannel still searches for other service which accepts the message.
	This way there could be several services with the same keyword and
	different results.</para></footnote>
	Multiple entries are separated with 
        semicolon (';'). For example, "91;93" selects this service for
	these prefixes. 
	If denied-prefix is unset, only this numbers are allowed. If 
	denied is set, number are allowed if present in allowed or not 
	in denied list.
     </entry></row>

   <row><entry><literal>denied-prefix</literal></entry>
     <entry><literal>prefix-list</literal></entry>
     <entry valign="bottom">
        A list of phone number prefixes of the sender number which are 
		  NOT accepted to be sent through this SMSC.
     </entry></row>

   <row><entry><literal>allowed-receiver-prefix</literal></entry>
     <entry><literal>prefix-list</literal></entry>
     <entry valign="bottom">
        A list of phone number prefixes of the receiver number which are 
		  accepted to be received by this service. This may be used to
 		  allow only inbound SMS to certain shortcut numbers to be allowed
		  to this service.
     </entry></row>

   <row><entry><literal>denied-receiver-prefix</literal></entry>
     <entry><literal>prefix-list</literal></entry>
     <entry valign="bottom">
        A list of phone number prefixes of the receiver number which are 
		  NOT accepted to be sent through this SMSC.
     </entry></row>


   <row><entry><literal>catch-all</literal></entry>
     <entry>bool</entry>
     <entry valign="bottom">
        Catch keyword regardless of '%s' parameters in pattern.

     </entry></row>

   <row><entry><literal>send-sender</literal></entry>
     <entry>bool</entry>
     <entry valign="bottom">
        Used only with POST. If set to true, number of the handset is
        set, otherwise not.
     </entry></row>

   <row><entry><literal>strip-keyword</literal></entry>
     <entry>bool</entry>
     <entry valign="bottom">
     Used only with POST. Remove matched keyword from message text
        before sending it onward.
     </entry></row>

   <row><entry><literal>faked-sender</literal></entry>
     <entry>phone-number</entry>
     <entry valign="bottom">
        This number is set as sender. Most SMS centers ignore this,
        and use their fixed number instead. This option
        overrides all other sender setting methods.
     </entry></row>

   <row><entry><literal>max-messages</literal></entry>
     <entry>number</entry>
     <entry valign="bottom">
        If the message to be sent is longer than maximum length of an SMS
        it will be split into several parts. <literal>max-messages</literal>
        lets you specify a maximum number of individual SMS messages that
        can be used. If
        <literal>max-messages</literal> is set to 0, no reply is sent, 
        except for error messages. 
     </entry></row>

   <row><entry><literal>accept-x-kannel-headers</literal></entry>
     <entry>bool</entry>
     <entry valign="bottom">
        Request reply can include special X-Kannel headers but these
        are only accepted if this variable is set to true. See
	<xref linkend="xkannel" endterm="xkannel.title">.
     </entry></row>

   <row><entry><literal>assume-plain-text</literal></entry>
     <entry>bool</entry>
     <entry valign="bottom">
        If client does not set Content-Type for reply, it is normally
        application/octet-stream which is then handled as data in
        Kannel. This can be forced to be plain/text to allow backward
        compatibility, when data was not expected.
     </entry></row>

   <row><entry><literal>concatenation</literal></entry>
     <entry>bool</entry>
     <entry valign="bottom">
        Long messages can be sent as independent SMS messages with
        <literal>concatenation = false</literal> or as concatenated messages
        with <literal>concatenation = true</literal>. Concatenated messages
        are reassembled into one long message by the receiving device.
     </entry></row>

   <row><entry><literal>split-chars</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        Allowed characters to split the message into several messages.
        So, with "#!" the message is split from last '#' or '!', which is 
        included in the previous part.

     </entry></row>

   <row><entry><literal>split-suffix</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        If the message is split into several ones, this string is appended to 
        each message except the last one.
     </entry></row>

   <row><entry><literal>omit-empty</literal></entry>
     <entry>bool</entry>
     <entry valign="bottom">
	Normally, Kannel sends a warning to the user if there was an
	empty reply from the service provider.  If
	<literal>omit-empty</literal> is set to 'true', Kannel will send
	nothing at all in such a case.

     </entry></row>

   <row><entry><literal>header</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        If specified, this string is automatically added to each SMS sent with
        this service. If the message is split, it is added to each part.

     </entry></row>

   <row><entry><literal>footer</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        As header, but not inserted into head but appended to end.

     </entry></row>

   <row><entry><literal>prefix</literal></entry>
     <entry>string</entry>
     <entry morerows="1" valign="bottom">
        Stuff in answer that is cut away, only things between prefix
        and suffix is left. Not case sensitive. Matches the first prefix
        and then the first suffix. These are only used for 
        <literal>url</literal> type services, and only if both are
	specified.
     </entry></row>

   <row><entry><literal>suffix</literal></entry>
     <entry>string</entry></row>

    <row><entry><literal>white-list</literal></entry>
     <entry>URL</entry>
     <entry valign="bottom">
        Load a list of accepted senders of SMS messages. If a 
	sender of an SMS message is not in this list, any message 
	received from the SMSC is rejected, unless a <literal>
	black-list</literal> service is defined. See notes of phone 
	number format from numhash.h header file. 
     </entry></row>

    <row><entry><literal>black-list</literal></entry>
     <entry>URL</entry>
     <entry valign="bottom">
        As white-list, but SMS messages from these numbers are
        automatically discarded
     </entry></row>

     <row><entry><literal>accepted-smsc-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        Accept only SMS messages arriving from SMSCs with a matching ID.
        <footnote><para>Even if this service is denied,
	Kannel still searches for other service which accepts the message,
	or default service.</para></footnote>
        See section on regular 
        expressions for details.
        </entry>   
     </row>

     <row><entry><literal>allowed-prefix-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        A set of phone number prefixes of sender-numbers accepted by this service.
        <footnote><para>Like in accepted-smsc-regex, 
	Kannel still searches for another service which accepts the message.
	This way there could be several services with the same keyword and
	different results.</para></footnote>
        See section on regular 
        expressions for details.
        </entry>   
     </row>

     <row><entry><literal>denied-prefix-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        A set of phone number prefixes of sender-numbers which may
        not use this service.
        See section on regular 
        expressions for details.
        </entry>   
     </row>

     <row><entry><literal>allowed-receiver-prefix-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        A set of phone number prefixes of receiver-numbers which 
        may receive data sent by this service. This can be used to
        allow only inbound SMS to certain shortcut numbers to be allowed
	to this service.
        See section on regular 
        expressions for details.
        </entry>   
     </row>

     <row><entry><literal>denied-receiver-prefix-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        A set of phone number prefixes of receiver-numbers which may not
        receive data sent by this service.
        See section on regular 
        expressions for details.
        </entry>   
     </row>

     <row><entry><literal>white-list-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        Defines a set of accepted senders of SMS messages. If a 
	sender of an SMS message is not in this list, the message is rejected.
        See section on regular 
        expressions for details.
        </entry>   
     </row>

     <row><entry><literal>black-list-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        As white-list-regex, but SMS messages from these numbers are
        automatically discarded.
        See section on regular 
        expressions for details.
        </entry>   
     </row>

  </tbody>
  </tgroup>
 </table>






 <table frame="none">
  <title>Parameters (Escape Codes)</title>
  <tgroup cols="2">
  <tbody>

<row><entry><literal>%k</literal></entry><entry>
the keyword in the SMS request (i.e., the first word in the SMS message)
                 
</entry></row>

<row><entry><literal>%s</literal></entry><entry>
next word from the SMS message, starting with
                         the second one (i.e., the first word, the
                         keyword, is not included); problematic characters
                         for URLs are encoded (e.g., '+' becomes '%2B')
                 
</entry></row>

<row><entry><literal>%S</literal></entry><entry>
same as %s, but '*' is converted to '~' (useful
                         when user enters a URL) and URL encoding isn't done
                         (all others do URL encode)
</entry></row>

<row><entry><literal>%r</literal></entry><entry>
words not yet used by %s; e.g., if the message
                         is "FOO BAR FOOBAR BAZ", and the has been one %s,
                         %r will mean "FOOBAR BAZ"
</entry></row>

<row><entry><literal>%a</literal></entry><entry>
all words of the SMS message, including the first one, with spaces
squeezed to one
</entry></row>

<row><entry><literal>%b</literal></entry><entry>
the original SMS message, in a binary form
</entry></row>

<row><entry><literal>%t</literal></entry><entry>
the time the message was sent, formatted as
                         "YYYY-MM-DD HH:MM", e.g., "1999-09-21 14:18"
</entry></row>

<row><entry><literal>%T</literal></entry><entry>
the time the message was sent, in UNIX epoch timestamp format
</entry></row>

<row><entry><literal>%p</literal></entry><entry>
the phone number of the sender of the SMS message
</entry></row>

<row><entry><literal>%P</literal></entry><entry>
the phone number of the receiver of the SMS message
</entry></row>

<row><entry><literal>%q</literal></entry><entry>
like %p, but a leading `00' is replaced with `+'
</entry></row>

<row><entry><literal>%Q</literal></entry><entry>
like %P, but a leading `00' is replaced with `+'
</entry></row>

<row><entry><literal>%i</literal></entry><entry>
the smsc-id of the connection that received the message
</entry></row>

<row><entry><literal>%I</literal></entry><entry>
the SMS ID of the internal message structure
</entry></row>

<row><entry><literal>%d</literal></entry><entry>
the delivery report value
</entry></row>

<row><entry><literal>%A</literal></entry><entry>
the delivery report SMSC reply, if any
</entry></row>

<row><entry><literal>%n</literal></entry><entry>
the sendsms-user or sms-service name
</entry></row>

<row><entry><literal>%c</literal></entry><entry>
message coding: 0 (default, 7 bits), 1 (8 bits) or 2 (Unicode)
</entry></row>

<row><entry><literal>%m</literal></entry><entry>
message class bits of DCS: 0 (directly to display, flash),
1 (to mobile), 2 (to SIM) or 3 (to SIM toolkit).
</entry></row>

<row><entry><literal>%M</literal></entry><entry>
mwi (message waiting indicator) bits of DCS:
0 (voice), 1, (fax), 2 (email) or 3 (other) for activation
and 4, 5, 6, 7 for deactivation respectively.
</entry></row>

<row><entry><literal>%C</literal></entry><entry>
message charset: for a "normal" message, it will 
be "GSM" (coding=0), "binary" (coding=1) or 
"UTF-16BE" (coding=2). If the message was successfully
recoded from Unicode, it will be "WINDOWS-1252"
</entry></row>

<row><entry><literal>%u</literal></entry><entry>
<literal>udh</literal> of incoming message
</entry></row>

<row><entry><literal>%B</literal></entry><entry>
billing identifier/information of incoming message. The value
depends on the SMSC module and the associated billing semantics
of the specific SMSC providing the information. For EMI2 the value
is the XSer 0c field, for SMPP it is the service_type of the 
deliver_sm PDU. (Note: This is used for proxying billing 
information to external applications. There is no semantics 
associated while processing these.)
</entry></row>

<row><entry><literal>%o</literal></entry><entry>
account identifier/information of incoming message. The value
depends on the SMSC module and has been introduced to allow the
forwarding of an operator ID from aggregator SMSCs to the application
layer, hence the smsbox HTTP calling instance.
</entry></row>

<row><entry><literal>%f</literal></entry><entry>
Originating SMSC of incoming message. The value is set if
the AT driver is used to receive a SMS on a gsm modem.
The value of %f will contain the number of the SMSC sending
the SMS to the SIM card. Other SMSC types than AT do not
set this field so it will be empty.
</entry></row>

</tbody>
</tgroup>
</table>



 <para>Some sample 'sms-service' groups:

<programlisting>
group = sms-service
keyword = nop
text = "You asked nothing and I did it!"
catch-all = true

group = sms-service
keyword = complex
get-url = "http://host/service?sender=%p&amp;text=%r"
accept-x-kannel-headers = true
max-messages = 3
concatenation = true

group = sms-service
keyword = default
text = "No action specified"
</programlisting>
</para>


</sect2>


<sect2>
<title>How sms-service interprets the HTTP response</title>

    <para>When an <literal>sms-service</literal> requests a document
    via HTTP, it will accept one of four types of content types:

    	<informaltable frame="none">
	<tgroup cols="2">
	<tbody>
	
	<row>
	<entry><literal>text/plain</literal></entry>
	<entry>Blanks are squeezed into one, rest is chopped to fit an
	SMS message.</entry>
	</row>
	
	<row>
	<entry><literal>text/html</literal></entry>
	<entry>Tags are removed, rest is chopped to fit an
	SMS message.</entry>
	</row>
	
	<row>
	<entry><literal>text/vnd.wap.wml</literal></entry>
	<entry>Processed like HTML.</entry>
	</row>
	
	<row>
	<entry><literal>text/xml</literal></entry>
	<entry>Processed as a POST-XML. See <xref
	    linkend="postxml" endterm="postxml.title"></entry>
	</row>
	
	<row>
	<entry><literal>application/octet-stream</literal></entry>
	<entry>The body will be transmitted as the SMS message, as
	8-bit data. This can be avoided by setting
	<literal>assume-plain-text</literal> variable on for the
	SMS-service.</entry>
	</row>
	
	</tbody>
	</tgroup>
	</informaltable>

        </para>


<sect3 id="xkannel">
<title id="xkannel.title">Extended headers</title>
	
	<para>Kannel uses and accepts several X-Kannel headers to be
	used with SMS-services, if option
        <literal>accept-x-kannel-headers</literal> was provided in the
        relevant 'sms-service' group.</para>

 <table frame="none">
  <title>X-Kannel Headers</title>
  <tgroup cols="2">
  <thead>
   <row>
     <entry>SMSPush equivalent</entry>
     <entry>X-Kannel Header</entry>
   </row>
  </thead>
  <tbody>
   <row><entry><literal>username</literal></entry>
   <entry><literal>X-Kannel-Username</literal></entry></row>

   <row><entry><literal>password</literal></entry>
   <entry><literal>X-Kannel-Password</literal></entry></row>

   <row><entry><literal>from</literal></entry>
   <entry><literal>X-Kannel-From</literal></entry></row>

   <row><entry><literal>to</literal></entry>
   <entry><literal>X-Kannel-To</literal></entry></row>

   <row><entry><literal>text</literal></entry>
   <entry>request body</entry></row>

   <row><entry><literal>charset</literal></entry>
   <entry>charset as in <literal>Content-Type: text/html; charset=ISO-8859-1</literal></entry></row>

   <row><entry><literal>udh</literal></entry>
   <entry><literal>X-Kannel-UDH</literal></entry></row>

   <row><entry><literal>smsc</literal></entry>
   <entry><literal>X-Kannel-SMSC</literal></entry></row>

   <row><entry><literal>flash</literal></entry>
   <entry><literal>X-Kannel-Flash</literal> (deprecated, see <literal>X-Kannel-MClass</literal></entry></row>

   <row><entry><literal>mclass</literal></entry>
   <entry><literal>X-Kannel-MClass</literal></entry></row>

   <row><entry><literal>mwi</literal></entry>
   <entry><literal>X-Kannel-MWI</literal></entry></row>

   <row><entry><literal>compress</literal></entry>
   <entry><literal>X-Kannel-Compress</literal></entry></row>

   <row><entry><literal>coding</literal></entry>
   <entry><literal>X-Kannel-Coding</literal>. If unset, defaults to 0 
   (7 bits) if <literal>Content-Type</literal> is <literal>text/plain
   </literal>, <literal>text/html</literal> or 
   <literal>text/vnd.wap.wml</literal>. On 
   <literal>application/octet-stream</literal>, defaults to
   8 bits (1). All other <literal>Content-Type</literal> values 
   are rejected.</entry></row>

   <row><entry><literal>validity</literal></entry>
   <entry><literal>X-Kannel-Validity</literal></entry></row>

   <row><entry><literal>deferred</literal></entry>
   <entry><literal>X-Kannel-Deferred</literal></entry></row>

   <row><entry><literal>dlr-mask</literal></entry>
   <entry><literal>X-Kannel-DLR-Mask</literal></entry></row>

   <row><entry><literal>dlr-url</literal></entry>
   <entry><literal>X-Kannel-DLR-Url</literal></entry></row>

   <row><entry><literal>account</literal></entry>
   <entry><literal>X-Kannel-Account</literal></entry></row>

   <row><entry><literal>pid</literal></entry>
   <entry><literal>X-Kannel-PID</literal></entry></row>

   <row><entry><literal>alt-dcs</literal></entry>
   <entry><literal>X-Kannel-Alt-DCS</literal></entry></row>

   <row><entry><literal>binfo</literal></entry>
   <entry><literal>X-Kannel-BInfo</literal></entry></row>

   <row><entry><literal>rpi</literal></entry>
   <entry><literal>X-Kannel-RPI</literal></entry></row>

   <row><entry><literal>priority</literal></entry>
   <entry><literal>X-Kannel-Priority</literal></entry></row>

  </tbody>
  </tgroup>
 </table>

</sect3>


<sect3 id="kannelpost">
<title id="kannelpost.title">Kannel POST</title>

	<para>Kannel can do POST if <literal>service</literal> is
	contains a <literal>post-url="..."</literal>.</para>

<table frame="none">
  <title>X-Kannel Post Headers</title>
  <tgroup cols="2">
  <thead>
   <row>
     <entry>Parameter (escape code) equivalent</entry>
     <entry>X-Kannel Header</entry>
     <entry>Notes</entry>
   </row>
  </thead>
  <tbody>
   <row><entry><literal>%p (from)</literal></entry>
   <entry><literal>X-Kannel-From</literal></entry>
   <entry>Only sent if <literal>send-sender</literal> is true</entry> </row>

   <row><entry><literal>%P (to)</literal></entry>
   <entry><literal>X-Kannel-To</literal></entry>
   <entry></entry></row>

   <row><entry><literal>%t (time)</literal></entry>
   <entry><literal>X-Kannel-Time</literal></entry>
   <entry></entry></row>

   <row><entry><literal>%u (udh)</literal></entry>
   <entry><literal>X-Kannel-UDH</literal></entry>
   <entry>in hex format: <literal>06050415820000</literal></entry></row>

   <row><entry><literal>%i (smsc)</literal></entry>
   <entry><literal>X-Kannel-SMSC</literal></entry>
   <entry></entry></row>

   <row><entry><literal>- (mclass)</literal></entry>
   <entry><literal>X-Kannel-MClass</literal></entry>
   <entry></entry></row>

   <row><entry><literal>- (pid)</literal></entry>
   <entry><literal>X-Kannel-PID</literal></entry>
   <entry></entry></row>

   <row><entry><literal>- (alt-dcs)</literal></entry>
   <entry><literal>X-Kannel-Alt-DCS</literal></entry>
   <entry></entry></row>

   <row><entry><literal>- (mwi)</literal></entry>
   <entry><literal>X-Kannel-MWI</literal></entry>
   <entry></entry></row>

   <row><entry><literal>%c (coding)</literal></entry>
   <entry><literal>X-Kannel-Coding</literal></entry>
   <entry>0=7 Bits, 1=8 Bits, 2=UCS-2</entry></row>

   <row><entry><literal>- (compress)</literal></entry>
   <entry><literal>X-Kannel-Compress</literal></entry>
   <entry></entry></row>

   <row><entry><literal>- (validity)</literal></entry>
   <entry><literal>X-Kannel-Validity</literal></entry>
   <entry></entry></row>

   <row><entry><literal>- (deferred)</literal></entry>
   <entry><literal>X-Kannel-Deferred</literal></entry>
   <entry></entry></row>

   <row><entry><literal>%n (service name)</literal></entry>
   <entry><literal>X-Kannel-Service</literal></entry>
   <entry></entry></row>

   <row><entry><literal>%a or %r (text)</literal></entry>
   <entry>request body</entry>
   <entry>Kannel send all words (%a) unless <literal>strip-keyword</literal> is true</entry></row>

   <row><entry><literal>%C (charset)</literal></entry>
   <entry>present in <literal>Content-Type</literal> <literal>HTTP</literal></entry>
   <entry>Example: <literal>Content-Type: text/plain; charset=ISO-8859-1</literal></entry></row>

  </tbody>
  </tgroup>
</table>
 
</sect3>
	
<sect3 id="postxml">
<title id="postxml.title">XML Post</title>
	
	<para>Kannel can send and receive XML POST with the following
	format:</para>

<programlisting>
&#60;?xml version="1.0"?&#62;
&#60;!DOCTYPE ...&#62;
&#60;message&#62;
  &#60;submit&#62;
    &#60;da&#62;&#60;number&#62;destination number (to)&#60;/number&#62;&#60;/da&#62;
    &#60;oa&#62;&#60;number&#62;originating number (from)&#60;/number&#62;&#60;/oa&#62;
    &#60;ud&#62;user data (text)&#60;/ud&#62;
    &#60;udh&#62;user data header (udh)&#60;/udh&#62;
    &#60;dcs&#62;
      &#60;mclass&#62;mclass&#60;/mclass&#62;
      &#60;coding&#62;coding&#60;/coding&#62;
      &#60;mwi&#62;mwi&#60;/mwi&#62;
      &#60;compress&#62;compress&#60;/compress&#62;
      &#60;alt-dcs&#62;alt-dcs&#60;/alt-dcs&#62;
    &#60;/dcs&#62;
    &#60;pid&#62;pid&#60;/pid&#62;
    &#60;rpi&#62;rpi&#60;/rpi&#62;
    &#60;vp&#62;
      &#60;delay&#62;validity time in minutes&#60;/delay&#62;
    &#60;/vp&#62;
    &#60;timing&#62;
      &#60;delay&#62;deferred time in minutes&#60;/delay&#62;
    &#60;/timing&#62;
    &#60;statusrequest&#62;
      &#60;dlr-mask&#62;dlr-mask&#60;/dlr-mask&#62;
      &#60;dlr-url&#62;dlr-url&#60;/dlr-url&#62;
    &#60;/statusrequest&#62;

    &#60;!-- request from Kannel to application --&#62;
    &#60;from&#62;
      &#60;user&#62;username&#60;/user&#62;
      &#60;username&#62;username&#60;/username&#62; 
      &#60;pass&#62;password&#60;/pass&#62;
      &#60;password&#62;password&#60;/password&#62;
      &#60;account&#62;account&#60;/account&#62;
    &#60;/from&#62;
    &#60;to&#62;smsc-id&#60;/to&#62;

    &#60;!-- request from application to Kannel --&#62;
    &#60;from&#62;smsc-id&#60;/from&#62;
    &#60;to&#62;service-name&#60;/to&#62;

  &#60;/submit&#62;
&#60;/message&#62;
</programlisting>

	<note><para>Don't forget to set POST Content-Type to 
	<literal>text/xml</literal>!</para></note>

	<para>There could be several <literal>da</literal> entries for <literal>sendsms-user
	</literal> to enable multi-recipient messages. <literal>da</literal> doesn't make
	sense in <literal>sms-service</literal>.</para>

	<!--
	<para><literal>ud</literal><note><para>DAVI: I still have to test binary and Unicode
	&#60;ud&#62; content</para></note></para>
	-->
	
	<para><literal>udh</literal> is the same format as <literal>X-Kannel-UDH</literal>.
	Example: &#60;udh&#62;06050415820000&#60;/udh&#62;.</para>
	
	<para>On Kannel->application, <literal>from</literal> is the <literal>smsc-id</literal>
	that message arrives and <literal>to</literal> is the service name.</para>
	<para>On application->Kannel, <literal>from</literal> contains the credentials (
	<literal>user/username</literal>, <literal>pass/password</literal> and <literal>
	account</literal> and <literal>to</literal> corresponds to the <literal>smsc-id
	</literal> to submit the message.</para>
	
	<para><literal>user</literal> and <literal>username</literal> are equivalent and 
	only one of them should be used. (same for <literal>pass</literal> and <literal>
	password</literal>.</para>

	<para>When application POST in Kannel, as in GET, only <literal>user</literal>, <literal>
	pass</literal> and <literal>da</literal> are required. Everything else is optional. 
	(<literal>oa</literal> could be needed too is there's no <literal>default-sender</literal>
	or <literal>forced-sender</literal>.</para>

	<warning><para>This is experimental code. XML format could and should change to fully
	met IETF's sms-xml standard (yet in draft) and additional tags needed by Kannel should be
	pondered.</para></warning>
</sect3>

</sect2>


<sect2>
<title>SendSMS-user configurations</title>

   <para>To enable an SMS push, you must set
   <literal>sendsms-port</literal> into the 'smsbox' group and define one or
   more 'sendsms-user' groups. Each of these groups define one
   account, which can be used for the SMS push, via HTTP interface (see
   below)</para>

 <table frame="none">
  <title>SendSMS-User Group Variables</title>
  <tgroup cols="3">
  <thead>
   <row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row>
  </thead>
  <tbody>
   <row><entry><literal>group (m)</literal></entry>
     <entry><literal>sendsms-user</literal></entry>
     <entry valign="bottom">
       This is a mandatory variable
     </entry></row>

   <row><entry><literal>username (m)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
       Name for the user/account. 
     </entry></row>

   <row><entry><literal>password (m)</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
       Password for the user (see HTTP interface, below)
     </entry></row>

   <row><entry><literal>name</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
       As in 'sms-service' groups.
     </entry></row>

   <row><entry><literal>user-deny-ip</literal></entry>
     <entry>IP-list</entry>
     <entry morerows="1" valign="bottom">
        As other deny/allow IP lists, but for this user (i.e. this
         user is not allowed to do the SMS push HTTP request from
         other IPs than allowed ones). If not set, there is no
         limitations.
     </entry></row>
   <row><entry><literal>user-allow-IP</literal></entry>
     <entry>IP-list</entry></row>

   <row><entry><literal>forced-smsc</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
         Force SMSC ID as a 'string' (linked to SMS routing, see 'smsc' groups)
     </entry></row>

   <row><entry><literal>default-smsc</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
        If no SMSC ID is given with the send-sms request (see below), use
        this one. No idea to use with forced-smsc.
     </entry></row>


   <row><entry><literal>default-sender</literal></entry>
     <entry>phone-number</entry>
     <entry valign="bottom">
        This number is set as sender if not set by <literal>from</literal>
	get/post parameter 
     </entry></row>

   <row><entry><literal>faked-sender</literal></entry>
     <entry>phone-number</entry>
     <entry valign="bottom">
        As in 'sms-service' groups
     </entry></row>

   <row><entry><literal>max-messages</literal></entry>
     <entry>number</entry></row>

   <row><entry><literal>concatenation</literal></entry>
     <entry>bool</entry></row>

   <row><entry><literal>split-chars</literal></entry>
     <entry>string</entry></row>

   <row><entry><literal>split-suffix</literal></entry>
     <entry>string</entry></row>

   <row><entry><literal>omit-empty</literal></entry>
     <entry>bool</entry></row>

   <row><entry><literal>header</literal></entry>
     <entry>string</entry></row>

   <row><entry><literal>footer</literal></entry>
     <entry>string</entry></row>

   <row><entry><literal>allowed-prefix</literal></entry>
     <entry><literal>prefix-list</literal></entry>
     <entry valign="bottom">
        A list of phone number prefixes which are accepted to be
        sent using this username. Multiple entries are separated with 
        semicolon (';'). For example, "040;050" prevents sending of
        any SMS message with prefix of 040 or 050 through this SMSC.
	If denied-prefix is unset, only this numbers are allowed. If
	set, number are allowed if present in allowed or not in 
	denied list.
     </entry></row>

   <row><entry><literal>denied-prefix</literal></entry>
     <entry><literal>prefix-list</literal></entry>
     <entry valign="bottom">
        A list of phone number prefixes which are NOT accepted to be
        sent using this username.
     </entry></row>

    <row><entry><literal>white-list</literal></entry>
     <entry>URL</entry>
     <entry valign="bottom">
        Load a list of accepted destinations of SMS messages. If a 
	destination of an SMS message is not in this list, any message 
	received from the HTTP interface is rejected. See notes of phone 
	number format from numhash.h header file. 
     </entry></row>

    <row><entry><literal>black-list</literal></entry>
     <entry>URL</entry>
     <entry valign="bottom">
        As white-list, but SMS messages from these numbers are
        automatically rejected.
     </entry></row>

    <row><entry><literal>dlr-url</literal></entry>
     <entry>URL</entry>
     <entry valign="bottom">
	URL to be fetched if a <literal>dlr-mask</literal> CGI 
	parameter is present.
     </entry></row>

     <row><entry><literal>allowed-prefix-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        A set of phone numbers which are accepted to be
        sent using this username. 
        See section on regular expressions for details.
        </entry>
     </row>

     <row><entry><literal>denied-prefix-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        A set of phone numbers which may not
        send using this username. 
        See section on regular expressions for details.
        </entry>
     </row>

     <row><entry><literal>white-list-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        Defines a set of accepted destinations of SMS messages. If a 
	destination of an SMS message is not in this list, any message 
	received from the HTTP interface is rejected. 
        See section on regular expressions for details.
        </entry>
     </row>

     <row><entry><literal>black-list-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
        As <literal>white-list-regex</literal>, but SMS messages originating from 
        a number matching the pattern are discarded.
        See section on regular expressions for details.
        </entry>
     </row>

  </tbody>
  </tgroup>
 </table>

  <para>Some sample 'sendsms-user' groups:

<programlisting>
group = sendsms-user
username = simple
password = elpmis

group = sendsms-user
username = complex
password = 76ftY
user-deny-ip = "*.*.*.*"
user-allow-ip = "123.234.123.234"
max-messages = 3
concatenation = true
forced-smsc = SOL
</programlisting>

   The second one is very limited and only allows a user from IP
   "123.234.123.234". On the other hand, the user can send a longer
   message, up to 3 SMSes long, which is sent as concatenated
   SMS.</para>

</sect2>

<sect2>
<title>Over-The-Air configurations</title>

   <para>To enable Over-The-Air configuration of phones or other client
   devices that support the protocol you need to configure a <literal>
   sendsms-user</literal>.<literal>ota-setting</literal> group is not 
   necessary, you can send settings to the phone as a XML document, but
   this method is perhaps more suitable for continuous provisioning.
   </para>

   <para>If you want to send multiple OTA configurations through the smsbox
   and you do not want to send XML documents, you will have to declare a 
   <literal>ota-id</literal> string to the different <literal>ota-setting
   </literal> groups.
   </para>

 <table frame="none">
  <title>OTA Setting Group Variables</title>
  <tgroup cols="3">
  <thead>
   <row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row>
  </thead>
  <tbody>
   <row><entry><literal>group</literal></entry>
     <entry><literal>ota-setting</literal></entry>
     <entry valign="bottom">
       This is a mandatory variable
     </entry></row>

   <row><entry><literal>ota-id</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
	     An optional name or id for the ota-setting. Any string is
        acceptable, but semicolon ';' may cause problems, so avoid
        it and any other special non-alphabet characters. 
     </entry></row>

   <row><entry><literal>location</literal></entry>
     <entry><literal>URL</literal></entry>
     <entry valign="bottom">
       The address of the HTTP server for your WAP services, i.e. 
		 <literal>http://wap.company.com</literal>
     </entry></row>

   <row><entry><literal>service</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       Description of the service
     </entry></row>

   <row><entry><literal>ipaddress</literal></entry>
     <entry><literal>IP</literal></entry>
     <entry valign="bottom">
      IP address of your WAP gateway 
     </entry></row>

   <row><entry><literal>phonenumber</literal></entry>
     <entry><literal>phone-number</literal></entry>
     <entry valign="bottom">
       Phone number used to establish the PPP connection
     </entry></row>

   <row><entry><literal>speed</literal></entry>
     <entry><literal>number</literal></entry>
     <entry valign="bottom">
       Connection speed: 9600 or 14400. Defaults to 9600.
     </entry></row>

   <row><entry><literal>bearer</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       Bearer type: data or sms. Defaults to data.
     </entry></row>

   <row><entry><literal>calltype</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       Call type: isdn or analog. Defaults to isdn.
     </entry></row>

   <row><entry><literal>connection</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       Connection type: cont or temp. Cont uses TCP port 9201
		 and Temp uses UDP port 9200. Defaults to cont.
     </entry></row>

   <row><entry><literal>pppsecurity</literal></entry>
     <entry><literal>on or off</literal></entry>
     <entry valign="bottom">
       Enable CHAP authentication if set to on, PAP otherwise
     </entry></row>

   <row><entry><literal>authentication</literal></entry>
     <entry><literal></literal></entry>
     <entry valign="bottom">
       normal or secure. Indicates whether WTLS should be used 
		 or not. Defaults to normal.
     </entry></row>

   <row><entry><literal>login</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       Login name.
     </entry></row>

   <row><entry><literal>secret</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       Login password
     </entry></row>

  </tbody>
  </tgroup>
 </table>

  <para>A sample 'ota-setting' group:

<programlisting>
group = ota-setting
location = http://wap.company.com
service = "Our company's WAP site"
ipaddress = 10.11.12.13
phonenumber = 013456789
bearer = data
calltype = analog
connection = cont
pppsecurity = off
authentication = normal
login = wapusr
secret = thepasswd
</programlisting>

And a 'sendsms-user' to use with it. With concatenation enabled:

<programlisting>
group = sendsms-user
username = otauser
password = foo
max-messages = 2
concatenation = 1
</programlisting>

  </para>

 <table frame="none">
  <title>OTA Bookmark Group Variables</title>
  <tgroup cols="3">
  <thead>
   <row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row>
  </thead>
  <tbody>
   <row><entry><literal>group</literal></entry>
     <entry><literal>ota-bookmark</literal></entry>
     <entry valign="bottom">
       This is a mandatory variable
     </entry></row>

   <row><entry><literal>ota-id</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
	     An optional name or id for the ota-bookmark. Any string is
        acceptable, but semicolon ';' may cause problems, so avoid
        it and any other special non-alphabet characters. 
     </entry></row>

   <row><entry><literal>url</literal></entry>
     <entry><literal>URL</literal></entry>
     <entry valign="bottom">
       The address of the HTTP server for your WAP services, i.e. 
		 <literal>http://wap.company.com</literal>
     </entry></row>

   <row><entry><literal>name</literal></entry>
     <entry><literal>string</literal></entry>
     <entry valign="bottom">
       Description of the service
     </entry></row>

  </tbody>
  </tgroup>
 </table>

  <para>A sample 'ota-bookmark' group:

<programlisting>
group = ota-bookmark
ota-id = wap-link
url = "http://wap.company.com"
service = "Our company's WAP site"
</programlisting>

And a 'sendsms-user' to use with it, with the same conditions as for the
'ota-setting' group.

  </para>


</sect2>

<sect2>
<title>Setting up more complex services</title>

    <para>The basic service system is very limited - it can only
    answer to original requester and it cannot send UDH data, for
    example. This chapter explains some more sophisticated and complex
    SMS service setups.</para>

<sect3>
<title>Redirected replies</title>

    <para>The basic service system always sends the answer back to
    original requester, but sometimes the content server needs to send
    something to other terminals or delay the answer. To create 
    such systems, an SMS push is used.</para>

    <para>The idea is to get the initial request, but then send no
    reply. Instead, the reply (if any) is sent via HTTP
    sendsms-interface as SMS Push. This way the service
    application has full control of the return content, and can do all
    needed formatting beforehand.</para>

    <para>Note that when no reply is wanted, remember to set the variable
    <literal>max-messages</literal> to zero (0) so that no reply is sent, unless an
    error occurs. Simple sample:</para>

<programlisting>
group = sms-service
keyword = talk
get-url = "http://my.applet.machine/Servlet/talk?sender=%p&amp;text=%r"
max-messages = 0
</programlisting>


</sect3>
<sect3>
<title>Setting up operator specific services</title>

   <para>Those running Kannel with several SMS centers might need to
   define services according to the relying SMS center. To achieve this,
   first you need to give an ID name for SMS center connections (see
   above). Then use the <literal>accepted-smsc</literal> variable to 
   define which messages can use that service.</para>

<programlisting>
group = sms-service
keyword = weather
accepted-smsc = SOL
get-url = "http://my.applet.machine/Servlet/weather?sender=%p&amp;operator=SOL&amp;text=%r"
</programlisting>

</sect3>
<sect3>
<title>Setting up multi-operator Kannel</title>

   <para>Sometimes there is a need for Kannel to listen to two (or
   more) distinct SMS centers, and messages must be routed to services
   according to where they came from, and replies likewise must return
   to same SMSC. This is done via <literal>smsc-id</literal>
   magic. Here is a shortened sample configuration, which handles to
   distinct SMS servers and services:</para>

<programlisting>
group = smsc
smsc-id = A
denied-smsc-id = B
...

group = smsc
smsc-id = B
denied-smsc-id = A
...

group = sms-service
accepted-smsc = A
get-url = "..."

group = sms-service
accepted-smsc = B
get-url = "..."
</programlisting>
 
    <para>As can be seen, the <literal>smsc-id</literal> is used to
    identify the SMS center from which the message came. Then, the
    <literal>denied-smsc-id</literal> variable is used to prevent
    messages originally from the other SMS center from being sent
    through the other one. Finally 'sms-service' groups are defined
    with <literal>accepted-smsc</literal> so that they only accept
    messages from certain SMS center.</para>

    <para>If you want to use SMS push services, requesters 
    should then set the <literal>smsc</literal> request parameter, or
    'sendsms-user' groups should be defined like this:</para>

<programlisting>
group = sendsms-user
username = operator_A
password = foo
forced-smsc = A

group = sendsms-user
username = operator_B
password = bar
forced-smsc = B
</programlisting> 

    <para>Note that if your SMS centers do not set the sender phone
    number but rely on number transmitted, you should set
    <literal>faked-sender</literal> to all 'sendsms-user'
    groups.</para>

</sect3>

</sect2>

</sect1>

<sect1>
<title>Running SMS gateway</title>

<sect2>
<title>Using the HTTP interface to send SMS messages</title>

	<para>After you have configured Kannel to allow the sendsms
	service, you can send SMS messages via HTTP, e.g., using a
	WWW browser. The URL looks something like this:
	
<programlisting>
http://smsbox.host.name:13013/cgi-bin/sendsms?
username=foo&amp;password=bar&amp;to=0123456&amp;text=Hello+world
</programlisting>

         Thus, technically,
	you make an HTTP GET request. This means that all the information
	is stuffed into the URL. If you want to use this often via a
	browser, you probably want to make an HTML form for this.</para>

  <para>
     Kannel will answer to sendsms request with following codes and
     body texts:</para>
  
 <table frame="none">
  <title>SMS Push reply codes</title>
      <tgroup cols="3"><thead><row>
             <entry>Status</entry>
             <entry>Body</entry>
             <entry>Meaning</entry>
             </row></thead>
  <tbody>
   <row><entry><literal>202</literal></entry>
   <entry><literal>0: Accepted for delivery</literal></entry>
   <entry valign="bottom">
        The message has been accepted and is delivered onward to a SMSC
        driver. Note that this status does not ensure that the
        intended recipient receives the message.
   </entry></row>
   <row><entry><literal>202</literal></entry>
   <entry><literal>3: Queued for later delivery</literal></entry>
   <entry valign="bottom">
        The bearerbox accepted and stored the message, but there was
        temporarily no SMSC driver to accept the message so it was
        queued. However, it should be delivered later on.
   </entry></row>
   <row><entry><literal>4xx</literal></entry>
   <entry>(varies)</entry>
   <entry valign="bottom">
        There was something wrong in the request or Kannel was so
      configured that the message cannot be in any circumstances
      delivered. Check the request and Kannel configuration.
   </entry></row>
   <row><entry><literal>503</literal></entry>
   <entry><literal>Temporal failure, try again later.</literal></entry>
   <entry valign="bottom">
        There was temporal failure in Kannel. Try again later.
   </entry></row>

  </tbody>
  </tgroup>
 </table>


 <table frame="none">
  <title>SMS Push (send-sms) CGI Variables</title>
  <tgroup cols="3">
  <tbody>
   <row><entry><literal>username</literal> (or <literal>user</literal>)</entry>
   <entry><literal>string</literal></entry>
   <entry valign="bottom">
        Username or account name. Must be <literal>username</literal> of the one
        'sendsms-user' group in the Kannel configuration,
        or results in 'Authorization failed' reply.
   </entry></row>

   <row><entry><literal>password</literal> (or <literal>pass</literal>)</entry>
   <entry><literal>string</literal></entry>
   <entry valign="bottom">
       Password associated with given <literal>username</literal>. Must match
 corresponding field in the 'sendsms-user' group of
the Kannel configuration, or 'Authorization failed' is returned.
   </entry></row>

   <row><entry><literal>from</literal></entry>
   <entry><literal>string</literal></entry>
   <entry valign="bottom">
        Phone number of the sender. This field is usually overridden
        by the SMS Center, or it can be overridden by
        <literal>faked-sender</literal> variable in the
        <literal>sendsms-user</literal> group. If this variable is not
        set, smsbox <literal>global-sender</literal> is used.
   </entry></row>

   <row><entry><literal>to</literal></entry>
   <entry><literal>phone number list</literal></entry>
   <entry valign="bottom">
        Phone number of the receiver. To send to multiple receivers,
   separate each entry with <emphasis>space</emphasis> (' ', '+'
   url-encoded) - but note that this can be deactivated via
   <literal>sendsms-chars</literal> in the 'smsbox' group.
   </entry></row>

   <row><entry><literal>text</literal></entry>
   <entry><literal>string</literal></entry>
   <entry valign="bottom">
        Contents of the message, URL encoded as necessary. The content
        can be more than 160 characters, but then
        <literal>sendsms-user</literal> group must have
        <literal>max-messages</literal> set more than 1.
   </entry></row>

   <row><entry><literal>charset</literal></entry>
   <entry><literal>string</literal></entry>
   <entry valign="bottom">
        Charset of text message. Used to convert to a format suitable for
	7 bits or to UCS-2. Defaults to WINDOWS-1252 if coding is 7bits and
	UTF-16BE if coding is UCS-2.
   </entry></row>

   <row><entry><literal>udh</literal></entry>
   <entry><literal>string</literal></entry>
   <entry valign="bottom">
         Optional User Data Header (UDH) part of the message. Must be
         URL encoded.
   </entry></row>

   <row><entry><literal>smsc</literal></entry>
   <entry><literal>string</literal></entry>
   <entry valign="bottom">
        Optional virtual smsc-id from which the message is supposed to 
	have arrived. This is used for routing purposes, if any denied
	or preferred SMS centers are set up in SMS center
	configuration. This variable can be overridden with a
        <literal>forced-smsc</literal> configuration
        variable. Likewise, the <literal>default-smsc</literal> variable
        can be used to set the SMSC if it is not set otherwise.
   </entry></row>

   <row><entry><literal>flash</literal></entry>
   <entry><literal>number</literal></entry>
   <entry valign="bottom">
         Deprecated. See <literal>mclass</literal>.
   </entry></row>

   <row><entry><literal>mclass</literal></entry>
   <entry><literal>number</literal></entry>
   <entry valign="bottom">
         Optional. Sets the Message Class in DCS field.
	 Accepts values between 0 and 3, for Message Class 0 to 3, 
	 A value of 0 sends the message directly to display, 1 sends
	 to mobile, 2 to SIM and 3 to SIM toolkit.
   </entry></row>

   <row><entry><literal>mwi</literal></entry>
   <entry><literal>number</literal></entry>
   <entry valign="bottom">
         Optional. Sets Message Waiting Indicator bits in DCS field.
	 If given, the message will be encoded as a Message Waiting
	 Indicator. The accepted values are 0,1,2 and 3 for activating the
	 voice, fax, email and other indicator, or 4,5,6,7 for deactivating,
	 respectively.
	 This option excludes the <literal>flash</literal> option.
     <footnote id="mwi-messages"><para>To set number of messages, use
	 <literal>mwi=[0-3]&amp;coding=0&amp;udh=%04%01%02%&lt;XX&gt;%&lt;YY&gt;</literal>,
	 where YY are the number of messages, in HEX, and XX are <literal>mwi</literal>
	 plus 0xC0 if <literal>text</literal> field is not empty.</para> </footnote>
   </entry></row>

   <row><entry><literal>compress</literal></entry>
   <entry><literal>number</literal></entry>
   <entry valign="bottom">
         Optional. Sets the Compression bit in DCS Field.
   </entry></row>

   <row><entry><literal>coding</literal></entry>
   <entry><literal>number</literal></entry>
   <entry valign="bottom">
         Optional. Sets the coding scheme bits in DCS field.
	 Accepts values 0 to 2, for 7bit, 8bit or UCS-2.
	 If unset, defaults to 7 bits unless a udh is defined, which sets
	 coding to 8bits.
   </entry></row>

   <row><entry><literal>validity</literal></entry>
   <entry><literal>number (minutes)</literal></entry>
   <entry valign="bottom">
         Optional. If given, Kannel will inform SMS Center that it should only
	 try to send the message for this many minutes. If the destination
	 mobile is off other situation that it cannot receive the sms, the
	 smsc discards the message.
	 Note: you must have your Kannel box time synchronized with the SMS Center.
   </entry></row>

   <row><entry><literal>deferred</literal></entry>
   <entry><literal>number (minutes)</literal></entry>
   <entry valign="bottom">
         Optional. If given, the SMS center will postpone the message to be
	 delivered at now plus this many minutes.
	 Note: you must have your Kannel box time synchronized with the SMS Center.
   </entry></row>

   <row><entry><literal>dlrmask</literal></entry>
   <entry><literal>number (bit mask)</literal></entry>
   <entry valign="bottom">
	   Deprecated. See <literal>dlr-mask</literal>.
   </entry></row>

   <row><entry><literal>dlr-mask</literal></entry>
   <entry><literal>number (bit mask)</literal></entry>
   <entry valign="bottom">
	   Optional. Request for delivery reports with the state of the sent 
	   message. The value is a bit mask composed of: 1: Delivered to phone, 
	   2: Non-Delivered to Phone, 4: Queued on SMSC, 8: Delivered to SMSC, 
	   16: Non-Delivered to SMSC. Must set <literal>dlr-url</literal> on 
	   <literal>sendsms-user</literal> group or use the 
	   <literal>dlr-url</literal> CGI variable. 
   </entry></row>

   <row><entry><literal>dlrurl</literal></entry>
   <entry><literal>string (url)</literal></entry>
   <entry valign="bottom">
	   Deprecated. See <literal>dlr-url</literal>.
   </entry></row>

   <row><entry><literal>dlr-url</literal></entry>
   <entry><literal>string (url)</literal></entry>
   <entry valign="bottom">
	   Optional. If <literal>dlr-mask</literal> is given, this is the url to
	   be fetched. (Must be url-encoded)
   </entry></row>

   <row><entry><literal>pid</literal></entry>
   <entry><literal>byte</literal></entry>
   <entry valign="bottom">
	   Optional. Sets the PID value. (See ETSI Documentation).
	   Ex: SIM Toolkit messages would use something like 
	   <literal>&amp;pid=127&amp;coding=1&amp;alt-dcs=1&amp;mclass=3</literal>
   </entry></row>

   <row><entry><literal>alt-dcs</literal></entry>
   <entry><literal>number</literal></entry>
   <entry valign="bottom">
	   Optional. If unset, Kannel uses the alt-dcs defined on smsc configuration,
	   or 0X per default. If equals to 1, uses FX. If equals to 0, force 0X.
   </entry></row>

   <row><entry><literal>rpi</literal></entry>
   <entry><literal>number</literal></entry>
   <entry valign="bottom">
	   Optional. Sets the Return Path Indicator (RPI) value. (See ETSI Documentation).
   </entry></row>

   <row><entry><literal>account</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
	Optional. Account name or number to carry forward for billing purposes.
	This field is logged as ACT in the log file so it allows you to do some
	accounting on it if your front end uses the same username for all services
	but wants to distinguish them in the log. In the case of a HTTP SMSC
	type the account name is prepended with the service-name (username) and a colon (:)
	and forwarded to the next instance of Kannel. This allows hierarchical accounting.
   </entry></row>

   <row><entry><literal>binfo</literal></entry>
     <entry>string</entry>
     <entry valign="bottom">
	Optional. Billing identifier/information proxy field used to pass arbitrary
	billing transaction IDs or information to the specific SMSC modules. For EMI2 this
	is encapsulated into the XSer 0c field, for SMPP this is encapsulated into the 
	service_type of the submit_sm PDU.
   </entry></row>

   <row><entry><literal>priority</literal></entry>
   <entry>number</entry>
   <entry valign="bottom">
     Optional. Sets the Priority value (range 0-3 is allowed).
   </entry></row>

  </tbody>
  </tgroup>
 </table>

	
</sect2>

<sect2>
<title>Using the HTTP interface to send OTA configuration messages</title>

       <para>OTA messages can be sent to mobile phones or devices to auto-configure the  
       settings for WAP. They are actually complex SMS messages with UDH and sent as
       concatenated messages if too long (and compiled if necessary).</para>
		 
		 <para>You may either pass an HTTP request as GET method or POST method to the 
		 HTTP interface.</para>

		 <para>If you want to send a configuration that is defined within Kannel's 
		 configuration file itself you have to pass a valid 
		 <literal>ota-id</literal> value otherwise the content of the request will 
		 be compiled to as OTA message.</para>

<sect3>
<title>OTA settings and bookmark documents</title>

       <para>
       Here is an example XML document (this one contains CSD settings for logging
       in to a mobile service; note that you must store DTD locally):

<programlisting>
&#60;?xml version="1.0"?&#62;
&#60;!DOCTYPE CHARACTERISTIC-LIST SYSTEM "file:///gw/settings.dtd"&#62;
&#60;CHARACTERISTIC-LIST&#62;

  &#60;CHARACTERISTIC TYPE="ADDRESS"&#62;
    &#60;PARM NAME="BEARER" VALUE="GSM/CSD"/&#62;
    &#60;PARM NAME="PROXY" VALUE="10.11.12.13"/&#62;
    &#60;PARM NAME="PORT" VALUE="9201"/&#62;
    &#60;PARM NAME="CSD_DIALSTRING" VALUE="+12345678"/&#62;
    &#60;PARM NAME="PPP_AUTHTYPE" VALUE="PAP"/&#62;
    &#60;PARM NAME="PPP_AUTHNAME" VALUE="yourusername"/&#62;
    &#60;PARM NAME="PPP_AUTHSECRET" VALUE="yourauthsecret"/&#62;
    &#60;PARM NAME="CSD_CALLTYPE" VALUE="ISDN"/&#62;
    &#60;PARM NAME="CSD_CALLSPEED" VALUE="9600"/&#62;
  &#60;/CHARACTERISTIC&#62;

  &#60;CHARACTERISTIC TYPE="URL" 
                  VALUE="http://wap.company.com/"/&#62;

  &#60;CHARACTERISTIC TYPE="NAME"&#62;
    &#60;PARM NAME="NAME" VALUE="Your WAP Company"/&#62;
  &#60;/CHARACTERISTIC&#62;

&#60;/CHARACTERISTIC-LIST&#62;
</programlisting>

       A bookmark document looks like this:

<programlisting>
&#60;?xml version="1.0"?&#62;
&#60;!DOCTYPE CHARACTERISTIC_LIST SYSTEM "file:///gw/settings.dtd"&#62;
&#60;CHARACTERISTIC-LIST&#62;
  &#60;CHARACTERISTIC TYPE="BOOKMARK"&#62;
    &#60;PARM NAME="NAME" VALUE="WAP Company"/&#62;
    &#60;PARM NAME="URL" VALUE="http://wap.company.com/"/&#62;
  &#60;/CHARACTERISTIC&#62;
&#60;/CHARACTERISTIC-LIST&#62;
</programlisting>

       Document type definition (DTD) for these documents is not
       available from Internet, you must supply it as a file. Kannel
       gw directory contains an
       example, <literal>settings.dtd</literal>.

       </para>
</sect3>

<sect3>
<title>OTA syncsettings documents</title>

	<para>Used for the provisioning of sync configuration to
	  SyncMl enabled handsets. Best supported by sonyericcsson
	  terminals.
	</para>

	<para>Sample syncsettings documents to set contacts, connection data
	  and authentication:

<programlisting>
&#60;SyncSettings&#62;
&#60;Version&#62;1.0&#60;/Version&#62;
&#60;HostAddr&#62;http://syncml.server.com&#60;/HostAddr&#62;
&#60;RemoteDB&#62;
  &#60;CTType&#62;text/x-vcard&#60;/CTType&#62;
  &#60;CTVer&#62;2.1&#60;/CTVer&#62;
  &#60;URI&#62;contact&#60;/URI&#62;
  &#60;Name&#62;Address Book&#60;/Name&#62;
&#60;/RemoteDB&#62;
&#60;Name&#62;Synchonization&#60;/Name&#62;
&#60;Auth&#62;
  &#60;AuthLevel&#62;1&#60;/AuthLevel&#62;
  &#60;AuthScheme&#62;1&#60;/AuthScheme&#62;
  &#60;Username&#62;yourusername&#60;/Username&#62;
  &#60;Cred&#62;passwordbase64encoded&#60;/Cred&#62;
&#60;/Auth&#62;
&#60;/SyncSettings&#62;
</programlisting>

</para>

</sect3>

<sect3>
<title>OMA provisioning content</title>

	<para>OMA provisioning allows the configuration of a wider
	  range of settings than previously available in OTA
	  terminals. Refer to OMA-WAP-ProvCont-v1_1-20021112-C (at
	  http://www.openmobilealliance.org/tech/docs/) for details.
	</para>

	<para>A shared secret (i.e. a pin or the phone IMSI) can be
	  used to authenticate the settings. Defaults are 'userpin'
	  and '1234' a. See the cgi variables 'sec' and 'pin' for
	  available authentication options.
	</para>

</sect3>
<sect3>
<title>GET method for the OTA HTTP interface</title>
														  
		 <para>An example URL (OTA configuration defined in the Kannel 
		 configuration file):
	
	<screen><userinput>
	http://smsbox.host.name:13013/cgi-bin/sendota?
	    otaid=myconfig&amp;username=foo&amp;password=bar&amp;to=0123456
	</userinput></screen>

       URL containing XML document looks like this (you must URL encode it before sending
       it over HTTP): 

	<screen><userinput>
	http://smsbox.host.name:13013/cgi-bin/sendota?
	    username=foo&amp;password=bar&amp;to=0123456&amp;
	    text=MyURLEncodedXMLdocument&amp;type=settings
	</userinput></screen>
       
       You can send either settings, bookmark, syncsettings, or
       oma-settings, set CGI variable type accordingly.  Default for
       this variable is settings.
       </para>

 <table frame="none">
  <title>OTA CGI Variables</title>
  <tgroup cols="3">
  <tbody>
   <row><entry><literal>otaid</literal></entry>
   <entry><literal>string</literal></entry>
   <entry valign="bottom">
        Name or ID of the 'ota-setting' group in Kannel configuration
        that should be sent to the phone. This variable is optional.
        If it is not given the first 'ota-setting' group is sent. This
        is unnecessary when a XML document is send to the phone.
   </entry></row>

   <row><entry><literal>username</literal></entry>
   <entry><literal>string</literal></entry>
   <entry valign="bottom">
        Username of the 'sendsms-user' group in Kannel configuration, that has
        been configured to send OTA messages.
   </entry></row>

   <row><entry><literal>password</literal></entry>
   <entry><literal>string</literal></entry>
   <entry valign="bottom">
       Password associated with given <literal>username</literal>. Must match
       corresponding field in 'sendsms-user' group in Kannel configuration, or
       'Authorization failed' is returned.
   </entry></row>

   <row><entry><literal>to</literal></entry>
   <entry><literal>number</literal></entry>
   <entry valign="bottom">
       Number of the phone that is to receive the OTA configuration message.
   </entry></row>

   <row><entry><literal>from</literal></entry>
   <entry><literal>string</literal></entry>
   <entry valign="bottom">
       Phone number of the sender. This field is usually overridden by
       the SMS Center, or it can be overridden by faked-sender
       variable in the sendsms-user group. If this variable is not
       set, smsbox global-sender is used.
   </entry></row>

	<row><entry><literal>smsc</literal></entry>
   <entry><literal>string</literal></entry>
   <entry valign="bottom">
        Optional virtual smsc-id from which the message is supposed to 
	have arrived. This is used for routing purposes, if any denied
	or preferred SMS centers are set up in SMS center
	configuration. This variable can be overridden with a
        <literal>forced-smsc</literal> configuration
        variable. Likewise, the <literal>default-smsc</literal> variable
        can be used to set the SMSC if it is not set otherwise.
   </entry></row>

   <row><entry><literal>text</literal></entry>
   <entry><literal>XML document</literal></entry>
   <entry valign="bottom">
       An URL encoded XML document, containing either settings or bookmarks.
   </entry></row>

   <row><entry><literal>type</literal></entry>
   <entry><literal>string</literal></entry>
   <entry valign="bottom">
       Type of the XML document, supported values are "settings",
       "bookmarks", "syncsettings", and "oma-settings". Default is "settings".
   </entry></row>

   <row><entry><literal>sec</literal></entry>
   <entry><literal>string</literal></entry>
   <entry valign="bottom">
       Security model used to authenticate oma-settings. One of:
       "userpin", "netwpin", "usernetwpin", or "userpinmac".
   </entry></row>

   <row><entry><literal>pin</literal></entry>
   <entry><literal>number</literal></entry>
   <entry valign="bottom">
     Authentication token.
   </entry></row>

  </tbody>
  </tgroup>
 </table>

</sect3>

</sect2>

</sect1>

</chapter>




<chapter id="ppg">
<title>Setting up Push Proxy Gateway</title>
      <para>This chapter explains how to set up a push proxy gateway (PPG). 
       An example configuration file are given. A working push proxy gateway
      is described. Routing wap pushes to a certain smsc and asking for
      <emphasis>SMS level</emphasis> delivery reports are described.</para>
<sect1>
<title>Configuring ppg core group, for push initiator (PI) interface</title>
     <para>PPG configuration group defines gateway's service interface.
     Configuring a PPG working with a trusted PI is easiest. Actually,
     you need no configuration at all: in this case a PPG with default 
     values will be set up. Do not rely on this, default values may change.
     For PPG core configuration variables, see table 7.1.
     </para>

     <para>An example of a core configuration for PPG working only with 
     specific addresses follows. Note that ppg-deny-ip-list is not actually 
     necessary, but does make configuring simpler: IPs here are always denied,
     even when they are mentioned in the allowed IPs list.</para>

     <para>Ppg-url is a simple stamp, used for routing requests to the right 
     service. You can change this stamp by setting <literal>push-url</literal> 
     configuration variable.
     </para>
<programlisting>
group = ppg
ppg-url = /wappush
ppg-port = 8080
concurrent-pushes = 100
users = 1024
ppg-allow-ip = 194.100.32.125;127.0.0.1
ppg-deny-ip = 194.100.32.89;194.100.32.103
trusted-pi = false
</programlisting>
     <table frame="none">
     <title>PPG core group configuration variables</title>
             <tgroup cols="3"><thead><row>
             <entry>Variable</entry>
             <entry>Value</entry>
             <entry>Description</entry>
             </row></thead>
             <tbody>
             <row><entry><literal>group</literal></entry>
             <entry><emphasis>ppg</emphasis></entry>
             <entry valign="bottom">
             Mandatory value. Tells that we are configuring the PPG group.
             </entry></row>
             <row><entry><literal>ppg-port</literal></entry>
             <entry><emphasis>number</emphasis></entry>
             <entry valign="bottom">
             The port PPG is listening at. Default 8080.
             </entry></row>
             <row><entry><literal>ppg-ssl-port (o)</literal></entry>
             <entry><emphasis>number</emphasis></entry>
             <entry valign="bottom">
             Mandatory value for PPG HTTPS support. The port at which PPG listens
             for HTTPS requests. There are no defaults; you must set the value 
             separately.
             </entry></row>
             <row><entry><literal>ssl-server-cert-file</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             Mandatory value for PPG HTTPS support. The file containing server's ssl
             certificate.
             </entry></row>
             <row><entry><literal>ssl-server-key-file</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             Mandatory value for PPG HTTPS support. The file containing server's ssl
             private key.
             </entry></row>
             <row><entry><literal>ppg-url</literal></entry>
             <entry><emphasis>url</emphasis></entry>
             <entry valign="bottom">
             URL locating PPG services. Default <literal>/wappush
             </literal>.
             </entry></row>
             <row><entry><literal>global-sender</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             Sender phone number required by some protocols.
             </entry></row>
             <row><entry><literal>concurrent-pushes</literal></entry>
             <entry><emphasis>number</emphasis></entry>
             <entry valign="bottom">
             Number of concurrent pushes expected. Note that PPG <emphasis>
             does</emphasis> work even value is too low; it will only be 
             slower. Default 100.
             </entry></row>
             <row><entry><literal>users</literal></entry>
             <entry><emphasis>number</emphasis></entry>
             <entry valign="bottom">
             Number of actually configured user accounts. Note that PPG 
             <emphasis>does</emphasis> work even value is too low; it will 
             only be slower. Default 1024.
             </entry></row>
             <row><entry><literal>trusted-pi</literal></entry>
             <entry><emphasis>boolean</emphasis></entry>
             <entry valign="bottom">
             If true, PI does authentication for PPG. Obviously, both of them
             must reside inside same firewall. Default true. If this variable
             is true, all security variables are ignored (even though they
             may be present).
             </entry></row>
             <row><entry><literal>ppg-deny-ip</literal></entry>
             <entry><emphasis>ip-list</emphasis></entry>
             <entry valign="bottom">
             PPG will not accept pushes from these IPs. Wild-cards are allowed.
             If this attribute is missing, no IP is denied <emphasis> by this
             list </emphasis>.
             </entry></row>
             <row><entry><literal>ppg-allow-ip</literal></entry>
             <entry><emphasis>ip-list</emphasis></entry>
             <entry valign="bottom">
             PPG will accept pushes from these, and only these, IPs. Wild-cards
             are allowed. Adding this list means that IPs not mentioned are 
             denied, too.
             </entry></row>
             <row><entry><literal>default-smsc</literal></entry>
     	     <entry><emphasis>string</emphasis></entry>
     	     <entry valign="bottom">
             If no SMSC ID is given with the wappush HTTP request (see below), use
             this one as default route for all push messages.
     	     </entry></row>
             <row><entry><literal>default-dlr</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             If no dlr url is given with the wappush HTTP request (see below), use
             this one as default route for all push messages.
             </entry></row>
             <row><entry><literal>ppg-smsbox-id</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             All ppg delivery reports are handled by this smsbox. This routes all
				 DLR messages inside beaerbox to the specified smsbox for processing
				 the HTTP requests to the DLR-URL.
             </entry></row>
             <row><entry><literal>service-name</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             This is sms service name used by smsbox for wap push.
             </entry></row>
             <row><entry><literal>default-dlr</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             If no dlr url is given with the wappush HTTP request (see below), use
             this one as default route for all push messages.
             </entry></row>
             <row><entry><literal>service-name</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             This is sms service name used by smsbox for wap push..
             </entry></row>
             <row><entry><literal>concatenation</literal></entry>
             <entry><emphasis>boolean</emphasis></entry>
             <entry valign="bottom">
             Segment wap push binary sms. Default on. You need
             not normally set this value.
             </entry></row>
             <row><entry><literal>max-messages</literal></entry>
             <entry><emphasis>integer</emphasis></entry>
             <entry valign="bottom">
             Maximum number of sm messages generated. Default
             10. You need not set this variable, expect when 
             your push documents are <emphasis>very</emphasis>
             long.
             </entry></row>
             </tbody>
             </tgroup>
     </table>
</sect1>
<sect1>
<title>Configuring PPG user group variables</title>

      <para>In addition of pi lists similar to the core group, ppg 
      configuration specific to a certain user contains variables used for
      authentication and enforcing restrictions to phone numbers pi may 
      contact. All variables are elaborated in table 7.2.</para>

      <para>As an example, let us see how to configure a ppg user (a pi, 
      named here 'picom') allowed to send pushes only from a specified ip.
      </para>

<programlisting>
group = wap-push-user
wap-push-user = picom
ppg-username = foo
ppg-password = bar
allow-ip = 62.254.217.163
</programlisting>

      <para>It goes without saying that in real systems you must use more
            complex passwords than bar.</para>

      <table frame="none">
      <title>PPG user group configuration variables</title>
      <tgroup cols="3"><thead><row>
             <entry>Variable</entry>
             <entry>Value</entry>
             <entry>Description</entry>
             </row></thead>
             <tbody>
             <row><entry><literal>group</literal></entry>
             <entry><emphasis>wap-push-user</emphasis></entry>
             <entry valign="bottom">
             Mandatory value. Tells that we are configuring the users group.
             </entry></row>
             <row><entry><literal>wap-push-user</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             (More) human readable name of an user.
             </entry></row>
             <row><entry><literal>ppg-username</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             Username for this user.
             </entry></row>
             <row><entry><literal>ppg-password</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             Password for this user.
             </entry></row>
             <row><entry><literal>allowed-prefix</literal></entry>
             <entry><emphasis>number-list</emphasis></entry>
             <entry valign="bottom">
             Phone number prefixes allowed in pushes coming from this pi. These
             prefixes must conform international phone number format.
             </entry></row>
             <row><entry><literal>denied-prefix</literal></entry>
             <entry><emphasis>number-list</emphasis></entry>
             <entry valign="bottom">
             Phone number prefixes denied in pushes coming from this pi. These
             prefixes must conform international phone number format.
             </entry></row>
             <row><entry><literal>white-list</literal></entry>
             <entry><emphasis>url</emphasis></entry>
             <entry valign="bottom">
             Defines an url where from the white-list can be fetched. White list
             itself contains list of phone numbers accepting pushes from this 
             pi.
             </entry></row>
             <row><entry><literal>black-list</literal></entry>
             <entry><emphasis>url</emphasis></entry>
             <entry valign="bottom">
             Defines an url where from the blacklist can be fetched. Blacklist 
             itself contains list of phone number not accepting pushes from 
             this pi.
             </entry></row>
             <row><entry><literal>allow-ip</literal></entry>
             <entry><emphasis>ip-list</emphasis></entry>
             <entry valign="bottom">
             Defines IPs where from this pi can do pushes. Adding this list 
             means that IPs not mentioned are denied.
             </entry></row>
             <row><entry><literal>deny-ip</literal></entry>
             <entry><emphasis>ip-list</emphasis></entry>
             <entry valign="bottom">
             Defines IPs where from this pi cannot do pushes. IPs not mentioned
             in either list are denied, too.
             </entry></row>
	     <row><entry><literal>default-smsc</literal></entry>
     	     <entry><emphasis>string</emphasis></entry>
     	     <entry valign="bottom">
             If no SMSC ID is given with the wappush HTTP request (see below), use
             this one as default route for this specific push user.
     	     </entry></row>
	     <row><entry><literal>forced-smsc</literal></entry>
     	     <entry><emphasis>string</emphasis></entry>
     	     <entry valign="bottom">
             Allow only routing to a defined SMSC ID for this specific push user.
     	     </entry></row>
             <row><entry><literal>dlr-url</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             If no dlr  is given with the wappush HTTP request (see below), use
             this one as default route for this specific push user.
             </entry></row>
             <row><entry><literal>smsbox-id</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             Smsbox handling delivery reports fro this user.
             </entry></row>
	     <row><entry><literal>forced-smsc</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             Allow only routing to a defined SMSC ID for this specific push user.
     	     </entry></row>

     <row><entry><literal>white-list-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
             Defines the set of phone-numbers accepting pushes from this 
             pi.
        See section on regular 
        expressions for details.
        </entry>   
     </row>

     <row><entry><literal>black-list-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
             Defines the set of phone-numbers rejecting pushes from this 
             pi.
        See section on regular 
        expressions for details.
        </entry>   
     </row>

     <row><entry><literal>allowed-prefix-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
             Set of phone number prefixes allowed in pushes coming from this pi. 
        See section on regular 
        expressions for details.
        </entry>   
     </row>
     <row><entry><literal>denied-list-regex</literal></entry>
        <entry>POSIX regular expression</entry>
        <entry valign="bottom">
             Set of phone number prefixes denied in pushes coming from this pi. 
        See section on regular 
        expressions for details.
        </entry>   
     </row>

             </tbody>
             </tgroup>
      </table>
</sect1>
<sect1>
<title>Finishing ppg configuration</title>
     <para>PPG uses SMS for sending SI to the phone and an IP bearer to
     fetch content specified by it (see chapter Overview of WAP Push). This
     means both wapbox and bearer smsc connections are in use. So your push 
     proxy gateway configuration file must contain groups core, wapbox, smsc 
     and smsbox. These are configured normal way, only smsc group may have 
     push-specific variables. Note that following configurations are only an 
     example, you may need more complex ones.
     </para>
     <para>Bearerbox setup does not require any new variables:</para>
<programlisting>
group = core
admin-port = 13000
smsbox-port = 13001
wapbox-port = 13002
admin-password = b
wdp-interface-name = "*"
log-file = "filename"
log-level = 1
box-deny-ip = "*.*.*.*"
box-allow-ip = "127.0.0.1"
unified-prefix = "00358,0"
</programlisting>
      <para>You must set up wapbox, for pulling (fetching) the wap data, and
      of course starting the push itself. No new variables here, either.
      </para> 
<programlisting>
group = wapbox
bearerbox-host = localhost
log-file = "filename"
log-level = 0
syslog-level = none
</programlisting>
      <para>To set up smsc connections, for pushing SI or SL over SMS. Here
      HTTP SMSC is used as an example. Variables no-sender and no-coding 
      simplify HTTP request generated by Kannel. Send-url specifies content 
      gateway, or sendsms service.
      </para>
<programlisting>
group = smsc
smsc = http
smsc-id = HTTP
port = 10000
system-type = kannel
smsc-username = foo
smsc-password = bar
no-sender = true
no-coding = true
send-url = http://host:port/path
</programlisting>
     <para>To set up smsbox. This is used for ppg delivery reports,
     see later.</para>
<programlisting>
group = smsbox
bearerbox-host = localhost
smsbox-id = dlrbox
</programlisting>
      <para>Kannel sources contain a sample push configuration file 
      <literal>gw/pushkannel.conf</literal>.</para>
</sect1>
<sect1>
<title>Running a push proxy gateway</title>
     <para>Push proxy gateway is started by simply typing, using separate 
     windows:
	<screen><userinput>
	gw/bearerbox [config-file]
	gw/wapbox [config-file]
	</userinput></screen>
     You can, of course, use more complex command line options.</para>
</sect1>
<sect1>
<title>An example using HTTP SMSC</title>
     <para>An easy way to test and implement push services is to put ppg
     in the front of an existing sendsms service capable to send SMS data
     messages and to understand HTTP requests generated by HTTP SMSC.
     (See next chapter.) Then you need only configure SMSC configuration 
     send-url to point to sendsms service.</para>
</sect1>
<sect1>
<title>An example of minimum SI document</title>
     <para> Service indication (SI) should work with all types of
     phones, service loading does not. URL to be loaded is the
     main content of the document in both cases, however. Here an 
     example (this is a minimum si document, not usable for testing,
     probably, but you want PPG to generate only one one SM per 
     SI, if at all possible):</para>
<programlisting>
&#60;?xml version="1.0"?&#62;
&#60;!DOCTYPE si PUBLIC "-//WAPFORUM//DTD SI 1.0//EN"
"http://www.wapforum.org/DTD/si.dtd"&#62;
&#60;si&#62;
    &#60;indication href="http://www.gni.ch"
        si-id="1@gni.ch"&#62;
            You have 4 new emails
    &#60;/indication&#62;
&#60;/si&#62;
</programlisting>
      <para>Note following points:
            a) Every SI must have different si-id. If there are none,
               href is used as an (very unsatisfactory) id.
            b) this si should not interrupt the phone's current action.
      </para>
</sect1>
<sect1>
<title>An example push (tokenized SI) document</title>
       <para>HTTP SMSC generates a HTTP get request when it get a send-message 
       event, expressed in Unicode. The content gateway, or the sendsms 
       service must, of course, understand this URL. So here is an example,
       cgi variable text contains the url escaped form of a SI document. It is
       usable for testing prototype phones.
       </para>
	<screen><userinput>
	http://matrix:8080/phplib/kannelgw.php?user=*deleted*&amp;
	pass=*deleted*=to=%2B358408676001&amp;text=3D%02%06%17%AE%96localhost
	%3A8080%00%AF%80%8D%CF%B4%80%02%05j%00E%C6%0C%03wap.iobox.fi%00%11%03
	1%40wiral.com%00%07%0A%C3%07%19%99%06%25%15%23%15%10%C3%04+%02%060%01
	%03Want+to+test+a+fetch%3F%00%01%01&amp;udh=%06%05%04%0B%84%23%F0
	</userinput></screen>
</sect1>

<sect1>
<title>Default network and bearer used by push proxy gateway</title>
       <para> If network and bearer attributes of the pap control document are
       missing or set any, Kannel uses address type for routing purposes: if
       the address type is a phone number (TYPE=PLMN), network defaults to GSM
       and bearer to SMS; if it is a IP-address (TYPE=IPv4), network defaults
       to GSM and bearer to CSD. So following minimal pap document works:
<programlisting>
&#60;?xml version="1.0"?&#62;
&#60;!DOCTYPE pap PUBLIC "-//WAPFORUM//DTD PAP//EN"
          "http://www.wapforum.org/DTD/pap_1.0.dtd"&#62;
&#60;pap&#62;
  &#60;push-message push-id="9fjeo39jf084@pi.com"&#62;
    &#60;address address-value="WAPPUSH=+358408676001/TYPE=PLMN@ppg.carrier.com"/&#62;
  &#60;/push-message&#62;
&#60;/pap&#62;
</programlisting>
       </para>
</sect1>

<sect1>
<title>Push related Kannel headers</title>
       <para>This chapter recapitulates Kannel headers used by ppg.</para>

       <para>PPG uses many Kannel headers. These are very similar as ones
       used by smsbox. (Both send sms to to the phone, after all.)</para>

       <table frame="none">
       <title>Kannel headers used by PPG</title>
       <tgroup cols="3">
       <thead><row><entry>Variable</entry>
       <entry>Value</entry>
       <entry>Description</entry></row></thead>
       <tbody>
       <row><entry><literal>X-Kannel-SMSC</literal></entry>
       <entry><emphasis>string</emphasis></entry>
       <entry valign="bottom">Name of smsc used to deliver this push.
       Smsc configuration must contain some of corresponding variables, 
       see </entry></row>
       <row><entry><literal>X-Kannel-DLR-URL</literal></entry>
       <entry><emphasis>url</emphasis></entry>
       <entry valign="bottom">Url smsbox would call this url when doing 
       the delivery report. Note that it can contain all Kannel escapes.
       See table 6.7 for details.</entry></row>
       <row><entry><literal>X-Kannel-DLR-Mask</literal></entry>
       <entry><emphasis>number</emphasis></entry>
       <entry valign="bottom">Mask telling smsbox when it should do
       the delivery reports. Values are same as used by smsbox, see
       chapter Delivery Reports for details.</entry></row>
       <row><entry><literal>X-Kannel-Smsbox-Id</literal></entry>
       <entry><emphasis>string</emphasis></entry>
       <entry valign="bottom">Tells which smsbox does the delivery
       report. Smsbox configuration must contain corresponding 
       variable.</entry></row>
       </tbody>
       </tgroup>
       </table>
</sect1>

<sect1>
<title>Requesting SMS level delivery reports for WAP pushes</title>
       <para>Push content is a normal binary SM, so you can ask delivery 
       reports for them. These are useful for testing purposes (did the
       phone get the content at all, or did it just reject it.) Another
       use is create fall-back services for phones not supporting displaying
       a specific push content. (MMS one being perhaps currently most
       obvious.) Generally speaking, this service is very similar to 
       smsbox one. See chapter Delivery Reports for details.</para>

       <para> For ppg sms delivery reports you will need a fully working 
       smsbox. Add configuration variable <literal>smsbox-id</literal> to
       <literal>smsbox</literal> group (it is necessary, because there
       is no MT from any smsbox corresponding the delivery report 
       bearerbox is receiving):</para>

<programlisting>
       group = smsbox
       smsbox-id = dlrbox
       bearerbox-host = localhost
       log-file = "/var/log/kannel/smsbox-core.log"
       log-level = 0
       access-log = "/var/log/kannel/smsbox-access.log"
</programlisting>

       <para> Start smsbox normal way after updating the configuration
       file. </para>

       <para> You must add to PPG configuration file two less obvious
       variables: <literal>ppg-smsbox-id</literal> and <literal>
       service-name</literal>. <literal>Ppg-smsbox-id</literal> 
       defines smsbox through which you want to route delivery reports,
       <literal>service-name</literal> makes possible for smsbox to
       handle wap pushes as a separate sms service.</para>

       <para>Setting <literal>ppg-smsbox-id</literal> will route all
       ppg messages through same smsbox. You can route delivery 
       reports of separate user through separate smsboxes, by using
       configuration variable <literal>smsbox-id</literal> in group
       wap push user. Or you can use <literal>X-Kannel-Smsbox-Id
      </literal>. This means routing every message separately. </para>

       <para> You can supply dlr url and dlr mask as kannel header, or
       as a configuration variable in ppg user or ppg core group. (This
       is order of precedence, too.) First one is valid for only one
       message, second for a specific user, and third for every ppg
       user. </para>

       <para> So following is a minimum ppg core group for sms delivery
       reports:</para>

<programlisting>
group = ppg
ppg-url = /wappush
ppg-port = 8080
concurrent-pushes = 100
trusted-pi = true
users = 1024
service-name = ppg
ppg-smsbox-id = dlrbox
</programlisting>

       <para>And you can add Kannel headers to http post request. Here
       an example code snippet (C using Kannel gwlib; this example asks
       for all possible delivery reports).</para>

<programlisting>
http_header_add(push_headers, "X-Kannel-SMSC", "link0");
http_header_add(push_headers, "X-Kannel-DLR-Url",
                "http://193.53.0.56:8001/notification-dlr?smsc-id=%i"
                "&amp;status=%d&amp;answer=%A&amp;to=%P&amp;from=%p&amp;ts=%t");
http_header_add(push_headers, "X-Kannel-DLR-Mask",
                octstr_get_cstr(dos = octstr_format("%d", 31)));
http_header_add(push_headers, "X-Kannel-Smsbox-Id", "dlrbox"));
</programlisting>

       <para>Here status=%d tells the type of the delivery report and
       answer=%A the delivery report itself (sms content of it).
       Other ones are needed to map delivery report to original wap
       push.</para>

       <para>With these  you can use with following http post request</para>

<screen><userinput>
       http://193.53.0.56:8080/phplib/kannelgw.php?user=*deleted*&amp;
       pass=*deleted*=to=%2B358408676001&amp;text=3D%02%06%17%AE%96localhost
       %3A8080%00%AF%80%8D%CF%B4%80%02%05j%00E%C6%0C%03wap.iobox.fi%00%11%03
       1%40wiral.com%00%07%0A%C3%07%19%99%06%25%15%23%15%10%C3%04+%02%060%01
       %03Want+to+test+a+fetch%3F%00%01%01&amp;udh=%06%05%04%0B%84%23%F0
</userinput></screen>

       <para>Note that you can use all sms service escapes in dlrurl, see
       Parameters (Escape Codes) for details.</para>

       <para> If you want to set dlr url for a specific user, you must set
       configuration variable <literal>dlr-url</literal>in <literal>
       wap-push-user</literal>, if for entire ppg, <literal>default-dlr-url
       </literal> in group <literal>ppg</literal>. Value must naturally match
       with one used in group smsc.</para>
</sect1>

<sect1>
<title>Routing WAP pushes to a specific smsc</title>
       <para> This chapter explains how to route wap push to a specific
       smsc. </para>

       <para> Smsc routing for wap pushes is similar to sms pushes. So,
       firstly you must define configuration variable <literal>smsc-id
       </literal> in smsc group (or groups) in question. Say you used
       value <literal>link0</literal>. You can send this as a Kannel
       header:</para>

<programlisting>
http_header_add(push_headers, "X-Kannel-SMSC", "link0");
</programlisting> 

       <para>Then you can issue a request:</para>

<screen><userinput>
       http://193.53.0.56:8080/phplib/kannelgw.php?user=*deleted*&amp;
       pass=*deleted*=to=%2B358408676001&amp;text=3D%02%06%17%AE%96localhost
       %3A8080%00%AF%80%8D%CF%B4%80%02%05j%00E%C6%0C%03wap.iobox.fi%00%11%03
       1%40wiral.com%00%07%0A%C3%07%19%99%06%25%15%23%15%10%C3%04+%02%060%01
       %03Want+to+test+a+fetch%3F%00%01%01&amp;udh=%06%05%04%0B%84%23%F0
</userinput></screen>

      <para> You can use configuration variables to route all messages of a
      specific user or all ppg messages. Set <literal>default-smsc</literal>
      in group wap-push-user or in group ppg.</para>

      <para>Again precedence of various methods of setting the smsc is 
      kannel header, then configuration variable in group wap push user and
      then in group ppg.</para>

</sect1>
     
</chapter>


<chapter id="ssl-enabling">
<title>Using SSL for HTTP</title>

	<para>This chapter explains how you can use SSL to ensure
	secure HTTP communication on both, client and server side.
	</para>

	<para>Beware that the gateway, is acting in both roles of
	the HTTP model:

	<orderedlist>
	 <listitem><para>as HTTP client, i.e. for requesting URLs 
	   while acting as WAP gateway and while fetching information
		for the SMS services.</para></listitem>
	 <listitem><para>as HTTP server, i.e. for the administration HTTP
	   interface, the PPG and for the sendsms HTTP interface.
		</para></listitem>
   </orderedlist>

	That is why you can specify separate certification files within
	the core group to be used for the HTTP sides.</para>

	<para>You can use one or both sides of the SSL support. There 
	is no mandatory to use both if only one is desired.</para>

	<sect1>
	 <title>Using SSL client support</title>
     <para>To use the client support please use the following
	    configuration directive within the core group</para>
<programlisting>
group = core
...
ssl-client-certkey-file = "filename"
</programlisting>
	  <para>Now you are able to use https:// scheme URLs within 
 	    your WML decks and SMS services.</para>
	</sect1>	

	<sect1>
	 <title>Using SSL server support for the administration HTTP
	   interface</title>
     <para>To use the SSL-enabled HTTP server please use the 
	    following configuration directive within the core group
		 </para>
<programlisting>
group = core
...
admin-port-ssl = true
...
ssl-server-cert-file = "filename"
ssl-server-key-file = "filename"
</programlisting>
	</sect1>	

	<sect1>
	 <title>Using SSL server support for the sendsms HTTP
	   interface</title>
     <para>To use the SSL-enabled HTTP server please use the 
	    following configuration directive within the core and 
		 smsbox groups
		 </para>
<programlisting>
group = core
...
ssl-server-cert-file = "filename"
ssl-server-key-file = "filename"

group = smsbox
...
sendsms-port-ssl = true
</programlisting>
	</sect1>

        <sect1>
        <title>Using SSL server support for PPG HTTPS interface</title>
        <para>
        If you want use PAP over HTTPS, (it is, a https scheme) add following 
        directives to the ppg core group:
<programlisting>
group = ppg
...
ppg-ssl-port = 8090
ssl-server-cert-file = "/etc/kannel/cert1.pem"
ssl-server-key-file = "/etc/kannel/key1.pem"
</programlisting>
        </para>
        <para>
        PPG uses a separate port for HTTPS traffic, so so you must define it. This
        means that you can use both HTTP and HTTPS, when needed.
        </para>
        </sect1>
							  
</chapter>

<chapter id="delivery-reports">
<title>SMS Delivery Reports</title>

	<para>This chapter explains how to set up Kannel to deliver delivery reports.
	</para>
	
	<para>Delivery reports are a method to tell your system if the message
	has arrived on the destination phone. There are different things which can happen
	to a message on the way to the phone which are:
	</para>
	<para>
	<itemizedlist>
	<listitem><para>Message gets rejected by the SMSC (unknown subscriber, invalid destination number etc).</para></listitem>
	<listitem><para>Message gets accepted by the SMSC but the phone rejects the message.</para></listitem>
	<listitem><para>Message gets accepted by the SMSC but the phone is off or out of reach.
	 The message gets buffered.</para></listitem>
	<listitem><para>Message gets successfully delivered.</para></listitem>
	</itemizedlist>
	</para>
	
	<note>
	    <para>If you want to use delivery reports, you must define a <literal>smsc-id</literal> for each smsc group.</para>
	</note>

	<para>When you deliver SMS to Kannel you have to indicate what kind of delivery report messages you
	would like to receive back from the system. The delivery report types currently implemented are:
	<itemizedlist>
	<listitem><para>1: delivery success</para></listitem>
	<listitem><para>2: delivery failure</para></listitem>
	<listitem><para>4: message buffered</para></listitem>
	<listitem><para>8: smsc submit</para></listitem>
	<listitem><para>16: smsc reject</para></listitem>
	</itemizedlist>
	If you want multiple report types, you simply add the values together. For example if you want to get delivery success and/or failure
	you set the <literal>dlr-mask</literal> value to 1+2. and so on. If you specify <literal>dlr-mask</literal> on the URL you pass on to
	Kannel you also need to specify <literal>dlr-url</literal>. <literal>dlr-url</literal> should contain the URL to which
	Kannel should place a HTTP requests once the delivery report is ready to be delivered back to your system.
	</para>
	<para>
	An example transaction would work as following.
	<itemizedlist>
	<listitem><para>1. you send a message using dlr-mask=7 and dlr-url=http://www.xyz.com/cgi/dlr.php?type=%d</para></listitem>
	<listitem><para>2. Kannel forwards the message to the SMSC and keeps track of the message</para></listitem>
	<listitem><para>3. The SMSC can not reach the phone and thus returns a buffered message</para></listitem>
	<listitem><para>4. Kannel calls http://www.xyz.com/cgi/dlr.php?type=4 to indicate the message being buffered</para></listitem>
	<listitem><para>5. The phone is switched on and the SMS gets delivered from the SMSC. The SMSC reports this to Kannel</para></listitem>
	<listitem><para>6. Kannel calls http://www.xyz.com/cgi/dlr.php?type=1 to indicate the final success</para></listitem>
	</itemizedlist>
	Depending on the SMSC type not all type of messages are supported. For example a CIMD SMSC does
	not support buffered messages. Also some SMSC drivers have not implemented all DLR types.
	</para>
</chapter>


<chapter id="bug-reporting">
<title>Getting help and reporting bugs</title>

	<para>This chapter explains where to find help with problems
	related to the gateway, and the preferred procedure for reporting
	bugs and sending corrections to them.</para>
	
	<para>The Kannel development mailing list is devel@kannel.org.  To subscribe, send mail to <ulink url="mailto:devel-subscribe@kannel.org">devel-subscribe@kannel.org</ulink>.
	This is currently the best location for asking help and reporting
	bugs. Please include configuration file and version number.</para>
	
</chapter>

<appendix id="upgrading-notes">
<title>Upgrading notes</title>

	<para>This appendix includes pertinent information about required
	changes on upgrades.
	</para>

<sect1>
	<title>From 1.2.x or 1.3.1 to 1.3.2 and later</title>
	<para>
		<itemizedlist>
		<listitem><para>1. <literal>at</literal> module was dropped and <literal>at2</literal> module is now called <literal>at</literal></para></listitem>
		<listitem><para>2. <literal>emi</literal> module was renamed to <literal>emi_x25</literal>, <literal>emi_ip</literal> sub-module was dropped and <literal>emi2</literal> is now called <literal>emi</literal>.</para></listitem>
		</itemizedlist>
	</para>
</sect1>

</appendix>

<appendix>
<title>Using the fake WAP sender</title>

	<para>This appendix explains how to use the fake WAP sender
	to test the gateway.</para>

</appendix>


<appendix>
<title>Using the fake SMS center</title>

	<para>Fakesmsc is a simple testing tool to test out Kannel and
	its SMS services. It <emphasis>cannot</emphasis> be used to
	send messages to mobile terminals, it is just a simulated SMS
	center with no connection to real terminals.</para>

<sect1>
<title>Setting up fakesmsc</title>

    <para>This section sums up needed steps to set up system for
    fakesmsc use.</para>


<sect2>
<title>Compiling fakesmsc</title>

     <para>The fake SMS center should compile at the same time as main
     Kannel compiles. The outcome binary,
     <literal>fakesmsc</literal>, is in <literal>test</literal>
     directory. The source code is quite simple and trivial, and is
     easily edited.</para>

</sect2>
<sect2>
<title>Configuring Kannel</title>

     <para>To use <literal>fakesmsc</literal> to test out Kannel, you
     have to add it to main configuration file (see above). The
     simplest form for this configuration group is like this:</para>

<programlisting>
group = smsc
smsc = fake
port = 10000
</programlisting>

      <para>The fakesmsc configuration group accepts all common 'smsc' 
      configuration group variables, like <literal>smsc-id</literal>,
      <literal>preferred-smsc-id</literal> or
      <literal>denied-smsc-id</literal>, which can be used to test out
      routing systems and diverted services, before setting up real
      SMS center connections. If you include a fakesmsc group when
      bearerbox is connected to real SMS centers, you should add
      the <literal>connect-allow-ip</literal> variable to prevent
      unauthorized use.</para>

      <para>To set up multiple fakesmsc'es, just add new
      groups. Remember to put a different port number to each one.</para>

</sect2>

</sect1>
<sect1>
<title>Running Kannel with fakesmsc connections</title>

      <para>After configuring Kannel, you can start testing
      it. The bearerbox will listen for fakesmsc client connections
      to the port(s) specified in the configuration file.</para>

<sect2>
<title>Starting fake SMS center</title>

    <para>Each fakesmsc is started from command line, with all sent
    messages after command name. If any options are used (see below),
    they are put between the command and the messages. The usage is as
    follows:</para>

<programlisting>
test/fakesmsc [options] &lt;message1&gt; [message2 ...]
</programlisting>

    <para>Options and messages are explained below, but as a quick
    example, a typical startup can go like this:</para>

<programlisting>
test/fakesmsc -i 0.1 -m 100 "100 200 text nop" "100 300 text echo this"
</programlisting>

    <para>This tells fakesmsc to connect to bearerbox at localhost:10000
    (default) and send a hundred messages with an interval of 0.1 seconds.
    Each message is from number 100, and is either to number 200 with
    message 'nop' or to 300 with message 'echo this'.</para>

    <para>Messages received from bearerbox are shown in the same format
    (described below).</para>

<sect3>
<title>Fake messages</title>

    <para>Each message consists of four or five parts: sender number,
    receiver number, type, udh (if present) and main message itself.
    Sender and receiver numbers do not mean anything except for log files
    and number-based routing in Kannel.</para>

    <para>The parts of a message are separated with spaces. As each message is
    taken as one argument, it must be put in quotation marks.</para>

    <para>Message type must be one of the following: "text", "data" and "udh".
    Here's an example of using each:</para>

<programlisting>
test/fakesmsc -i 0.01 -v 1 -m 1000 "100 300 text echo this message"
test/fakesmsc -i 0.01 -m 1000 "100 300 data echo+these+chars%03%04%7f"
test/fakesmsc -m 1 "100 500 udh %0eudh+stuff+here main+message"
</programlisting>

    <para>For "text", the rest of the argument is taken as the literal
    message. For "data", the next part must be the url-encoded version of
    the message. Space is coded as '+'. For "udh", the next 2 parts
    are the UDH and main message. Both must be in url-encoded form.</para>

    <para>If multiple messages are given, fakesmsc randomly chooses
    one for each sending.</para>

</sect3>
<sect3>
<title>Fakesmsc command line options</title>

   <para>Fake SMS center can be started with various optional command
   line arguments.</para>

 <table frame="none">
  <title>Fakesmsc command line options</title>
  <tgroup cols="3">
  <thead>
   <row>
     <entry>Switch</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row>
  </thead>
  <tbody>
   <row><entry><literal>-H</literal></entry>
     <entry><emphasis>host</emphasis></entry>
     <entry valign="bottom">
       Use host <emphasis>host</emphasis> instead of default
       <literal>localhost</literal>.
     </entry></row>

   <row><entry><literal>-r</literal></entry>
     <entry><emphasis>port</emphasis></entry>
     <entry valign="bottom">
       Use port number <emphasis>port</emphasis> instead of default
       10000.
     </entry></row>

   <row><entry><literal>-i</literal></entry>
     <entry><emphasis>interval</emphasis></entry>
     <entry valign="bottom">
       Use message interval <emphasis>interval</emphasis> (in seconds,
       fractions accepted) instead of default interval 1.0 seconds.
     </entry></row>

   <row><entry><literal>-m</literal></entry>
     <entry><emphasis>max</emphasis></entry>
     <entry valign="bottom">
       Send a maximum of <emphasis>max</emphasis> messages. Value -1
       means that an unlimited number of messages is sent. Default -1.
       Using 0 can be useful to listen for messages sent via other
       channels.
     </entry></row>
  </tbody>
  </tgroup>
 </table>

    <para>In addition, fakesmsc accepts all common Kannel <xref
    linkend="arguments" endterm="arguments.title"> like 
    <literal>--verbosity</literal>.</para>

</sect3>

</sect2>
</sect1>

</appendix>

<appendix>
<title>Setting up a test environment for Push Proxy Gateway</title>

       <para>This appendix explains how to set a test environment for PPG. 
       This contains a simulated SMSC, for instance a http server simulation
       (this is used as example, because it is simplest) and a simulated
       push initiator. Between them, there is the push proxy gateway to be
       tested. This means that you must configure HTTP SMSC.
       </para>
<sect1>
<title>Creating push content and control document for testing</title>
      <para>
      Here is an example of a push control document, which gives PPG 
      instructions how to do the pushing.
      <programlisting>
&#60;?xml version="1.0"?&#62;
&#60;!DOCTYPE pap PUBLIC "-//WAPFORUM//DTD PAP//EN"
          "http://www.wapforum.org/DTD/pap_1.0.dtd"&#62;
&#60;pap&#62;
  &#60;push-message push-id="9fjeo39jf084@pi.com"
                deliver-before-timestamp="2001-09-28T06:45:00Z"
                deliver-after-timestamp="2001-02-28T06:45:00Z"
                progress-notes-requested="false"&#62;
    &#60;address address-value="WAPPUSH=+358408676001/TYPE=PLMN@ppg.carrier.com"/&#62;
    &#60;quality-of-service priority="low"
                        delivery-method="unconfirmed"
                        network-required="true"
                        network="GSM"
                        bearer-required="true"
                        bearer="SMS"/&#62;
  &#60;/push-message&#62;
&#60;/pap&#62;
      </programlisting>
      Because the push content is send to the phone over SMS, right value for
      <literal>network-required</literal> and <literal>bearer-required
      </literal> is true, for <literal>network</literal> GSM and for <literal>bearer
      </literal> SMS. However, you can omit these values altogether, if you use
      a phone number as an address. Address value is international phone number and
      it must start with plus. It is used here as an unique identifier, SMSC, or 
      sendsms script must transform it to an usable phone number.
      </para>
      <para>
      Here is an example of Service Indication, a type of push content. 
      Essentially, the phone displays, when it receives this SI, the text 
      "Want to test a fetch" and if the user wants, fetches the content 
      located by URL <literal>http://wap.iobox.fi</literal>.
      <programlisting>
&#60;?xml version="1.0"?&#62;
&#60;!DOCTYPE si PUBLIC "-//WAPFORUM//DTD SI 1.0//EN"
          "http://www.wapforum.org/DTD/si.dtd"&#62;
&#60;si&#62;
  &#60;indication href="http://wap.iobox.fi"
              si-id="1@wiral.com"
              action="signal-high"
              created="1999-06-25T15:23:15Z"
              si-expires="2002-06-30T00:00:00Z"&#62;
    Want to test a fetch?
  &#60;/indication&#62;
&#60;/si&#62;
      </programlisting>
      Note that the date value of the si-expires attribute contains trailing
      zeroes. They are OK here, because SI tokenizer removes them. But phones
      does not accept them in the final SMS data message. You should probably
      use <literal>action="signal-high"</literal> for testing purposes, for
      it causes an immediate presentation of the push message. Production
      usage is a quite another matter.
      </para>

      <para>
      Another example of push content is Service Loading. In principle, the phone
      should fetch immediately content from URL <literal>http://wap.iobox.fi
      </literal> when it receives this document. This sounds quite insecure, and
      indeed, user invention is probably required before fetching.

      <programlisting>
&#60;?xml version="1.0"?&#62;
&#60;!DOCTYPE sl PUBLIC "-//WAPFORUM//DTD SL 1.0//EN"
          "http://www.wapforum.org/DTD/sl.dtd"&#62;
&#60;sl href="http://wap.iobox.fi"
    action="execute-high"&#62;
&#60;/sl&#62;
      </programlisting>
      </para>

</sect1>
<sect1>
<title>Starting necessary programs</title>
       <para>PPG test environment contains, in addition of wapbox and 
       bearerbox, two test programs, <literal>test_ppg</literal> (simulating
       push initiator) and <literal>test_http_server</literal> (simulating 
       a SMSC center accepting pushed content send over SMS. You can find 
       both of these programs in <literal>test</literal> directory, and they 
       both are short and easily editable. </para>

       <para>To set up a test environment, you must first configure a push
       proxy gateway (setting flag trusted-pi true makes testing easier). 
       This explained in Chapter "Setting up push proxy gateway". Then issue 
       following commands, in Kannel's root directory and in separate windows:
	<screen><userinput>
	gw/bearerbox [config-file]
	gw/wapbox [config-file]
	</userinput></screen>
       Of course you can use more complicated wapbox and bearerbox command
       line options, if necessary.</para>

       <para>To run a http smsc,  start http server simulation:
	<screen><userinput>
	test/test_http_server -p port
	</userinput></screen>
       You can, of course, select the port at will. Remember, though, that
       PPG listens at the port defined in the ppg configuration file. Other 
       <literal>test_http_server</literal> options are irrelevant here.</para>

       <para>Lastly, start making push requests, for instance with a test 
       program <literal> test_ppg</literal>. Its first argument is a URL 
       specifying location of push services. Other arguments are two file 
       names, first one push content and second one pap control document. 
       (For command line options, see Table C.1.). For example doing one 
       push(you can simplify push url by setting a ppg configuration variable,
       see "Setting up push proxy gateway"; q flag here prevents dumping of 
       test_ppg program debugging information):
       </para>
	<screen><userinput>
	test/test_ppg -q http://ppg-host-name:ppg-port/ppg-url [content_file] 
	[control_file]
	</userinput></screen>

       <para> This presumes that you have set trusted-pi true.
       </para>

       <para>If you want use authentication in a test environment, you can pass
       username and password either using headers (setting flag -b) or url (you
       must have set trusted-pi false and added wap-push-user configuration group):
       </para>

	<screen><userinput>
	test/test_ppg -q http://ppg-host-name:ppg-port?username=ppg-username'&'
	password=ppg-password [content_file] [control_file]
	</userinput></screen>
   
       <table frame="none">
             <title>Test_ppg's command line options</title>
             <tgroup cols="3"><thead><row>
             <entry>Switch</entry>
             <entry>Value</entry>
             <entry>Description</entry>
             </row></thead>
             <tbody>
             <row><entry><literal>-c</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             Use content qualifier <emphasis>string</emphasis> instead of 
             default <literal>si</literal> (service indication). Allowed 
             values are wml, si, sl, sia, multipart, nil and scrap. Nil and 
             scrap are used for debugging purposes. Wml does work with some 
             older phone simulators.
             </entry></row>
             <row><entry><literal>-a</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             Use application id <emphasis>string</emphasis> instead of default
             <literal>any</literal>. Application identifies the application in
             the phone that should handle the push request. Sia, ua, mms, nil
             and scrap are accepted. Nil and scrap are used for debugging 
             purposes.
             </entry></row>
             <row><entry><literal>-e</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             Use transfer encoding when sending a push content. Only base64 is
             currently supported.
             </entry></row>
             <row><entry><literal>-b</literal></entry>
             <entry><emphasis>boolean</emphasis></entry>
             <entry valign="bottom">
             Use headers for authentication, instead of url. Default off.
             </entry></row>
             <row><entry><literal>-i</literal></entry>
             <entry><emphasis>number</emphasis></entry>
             <entry valign="bottom">
             Wait interval <emphasis>number</emphasis> instead of default
             <literal>0</literal> between pushes.
             </entry></row>
             <row><entry><literal>-r</literal></entry>
             <entry><emphasis>number</emphasis></entry>
             <entry valign="bottom">
             Do <emphasis>number</emphasis> requests instead of default
             <literal>1</literal>.
             </entry></row>
             <row><entry><literal>-t</literal></entry>
             <entry><emphasis>number</emphasis></entry>
             <entry valign="bottom">
             Use <emphasis>number</emphasis> threads instead of default
             <literal>1</literal>.
             </entry></row>
             <row><entry><literal>-s</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             Use <literal>string</literal> as a X-WAP-Application-Id
             header (You must supply whole header).
             </entry></row>

             <row><entry><literal>-I</literal></entry>
             <entry><emphasis>string</emphasis></entry>
             <entry valign="bottom">
             Use <literal>string</literal> as a X-WAP-Initiator-URI
             header (You must supply whole header).
             </entry></row>

             <row><entry><literal>-B</literal></entry>
             <entry><emphasis>boolean</emphasis></entry>
             <entry valign="bottom">
             If set, accept binary content. Default is off.
             <literal>1</literal>.
             </entry></row>
             <row><entry><literal>-d</literal></entry>
             <entry><emphasis>enumerated string</emphasis></entry>
             <entry valign="bottom">
             Set delimiter to be used. Acceptable values are crlf and
             lf. Default is <literal>crlf</literal>.
             </entry></row>
             <row><entry><literal>-p</literal></entry>
             <entry><emphasis>boolean</emphasis></entry>
             <entry valign="bottom">
             If set, add an preamble (hard-coded one). Default
             is off.
             </entry></row>
             <row><entry><literal>-E</literal></entry>
             <entry><emphasis>boolean</emphasis></entry>
             <entry valign="bottom">
             if set, add an epilogue (hard-coded). Default is off.
             </entry></row>
             </tbody>
             </tgroup>
       </table>
</sect1>
<sect1>
<title>Using Nokia Toolkit as a part of a developing environment</title>
       <para>This chapter describes a developing environment using Nokia 
       Toolkit instead of <literal>test_http_server</literal> program.
       </para>
       <para>You cannot use a real phone for testing a push server. Sending
       random messages to a phone does not work, because its only feedback
       (if it works properly) in error situations is dropping the offending
       message.</para>
       <para>Nokia Toolkit, instead, displays push headers, decompiles
       tokenized documents and outputs debugging information. It is not,
       of course, a carbon copy of a real phone. But it is still useful
       for checking spec conformance of push servers.</para>
       <para>Toolkit runs on Windows, the first thing you must is to install
       a virtual machine (VMWare is one possibility) in the machine where
       Kannel runs. Then you must configure Toolkit for working with a push
       gateway.</para>
       <para>Then start <literal>bearerbox</literal> and <literal>wapbox
       </literal> similar way as told before. You must set the correct client
       address in the push document send by <literal>test_ppg</literal>
       program. Use IP address of our virtual machine (easiest way to get this
       is to ping your virtual machine name in the dos prompt window). Your
       bearer is in this case IP. An example pap document follows:</para> 
       
       <programlisting>
&#60;?xml version="1.0"?&#62;
&#60;!DOCTYPE pap PUBLIC "-//WAPFORUM//DTD PAP//EN"
          "http://www.wapforum.org/DTD/pap_1.0.dtd"&#62;
&#60;pap&#62;
  &#60;push-message push-id="9fjeo39jf084@pi.com"
                deliver-before-timestamp="2001-09-28T06:45:00Z"
                deliver-after-timestamp="2001-02-28T06:45:00Z"
                progress-notes-requested="false"&#62;
    &#60;address address-value="WAPPUSH=192.168.214.1/TYPE=IPV4@ppg.carrier.com"/&#62;
    &#60;quality-of-service priority="low"
                        delivery-method="unconfirmed"
    &#60;/quality-of-service&#62;
  &#60;/push-message&#62;
&#60;/pap&#62;
       </programlisting>
       <para>Note address-value format. It is contains type and value, 
       because PAP protocol supports different address formats.</para>
       <para>You must use <literal>test_ppg</literal>'s -a and -c flags
       when pushing messages to Toolkit. -A defines the client application
       handling pushes, right value for it is ua. -C defines the content 
       type of your push message. SI works with all Toolkits, wml only
       with some older versions. </para>
</sect1>

 <sect1>
 <title>Testing PAP protocol over HTTPS </title>
        <para>
        When testing HTTPS connection to PPG, you probably want use test_ppg's
        configuration file, because number of required parameters is quite 
        high. Here is a example test_ppg configuration file:
        </para>
 
<programlisting>
 group = test-ppg
 retries = 2
 pi-ssl = yes
 ssl-client-certkey-file = /etc/kannel/certkey.pem
 
 group = configuration
 push-url = https://localhost:8900/wappush
 pap-file = /etc/kannel/ipnoqos.txt
 content-file = /etc/kannel/si.txt
 username = foo
 password = bar
</programlisting>
 
        <para>
        With a configuration file, you can do a push by typing:
        </para>
 
	<screen><userinput>
        test/test_ppg -q [configuration_file]
	</userinput></screen>
 
        <table frame="none">
              <title>Test_ppg's configuration file directives</title>
              <tgroup cols="3"><thead><row>
              <entry>Directive</entry>
              <entry>Value</entry>
              <entry>Description</entry>
              </row></thead>
              <tbody>
              <row><entry><literal>group</literal></entry>
              <entry><emphasis>test_ppg</emphasis></entry>
              <entry valign="bottom">
              Mandatory parameter. Start of test_ppg's core group.
              </entry></row>
              <row><entry><literal>retries</literal></entry>
              <entry><emphasis>number</emphasis></entry>
              <entry valign="bottom">
              The client tries to log in to PPG <emphasis>number</emphasis> times
              before discarding the push request. Default is 2.
              </entry></row>
              <row><entry><literal>pi-ssl</literal></entry>
              <entry><emphasis>boolean</emphasis></entry>
              <entry valign="bottom">
              Mandatory parameter for HTTPS connection. Does the client use HTTPS
              connection. Default is no.
              </entry></row>
              <row><entry><literal>ssl-client-certkey-file</literal></entry>
              <entry><emphasis>filename</emphasis></entry>
              <entry valign="bottom">
               Mandatory parameter for HTTPS connection. File containing the client's 
               ssl certificate and private key. 
              </entry></row>
               <row><entry><literal>ssl-trusted-ca-file</literal></entry>
              <entry>filename</entry>
              <entry valign="bottom">
              Mandatory parameter for HTTPS connection.This file contains the 
              certificates test_ppg is willing to trust. If this directive is not set, 
              certificates are not validated and HTTPS would not be tested.
	      </entry></row>
              <row><entry><literal>group</literal></entry>
              <entry><emphasis>configuration</emphasis></entry>
              <entry valign="bottom">
              Mandatory parameter. Start of test_ppg's test group.
              </entry></row>
              <row><entry><literal>push-url</literal></entry>
              <entry><emphasis>url</emphasis></entry>
              <entry valign="bottom">
              Mandatory value. URL locating PPG's services.
              </entry></row>
              <row><entry><literal>pap-file</literal></entry>
              <entry><emphasis>filename</emphasis></entry>
              <entry valign="bottom">
              Mandatory value. File containing pap request's control document.
              </entry></row>
              <row><entry><literal>content-file</literal></entry>
              <entry><emphasis>filename</emphasis></entry>
              <entry valign="bottom">
              Mandatory value. File containing pap request's content document.
              </entry></row>
              <row><entry><literal>username</literal></entry>
              <entry><emphasis>string</emphasis></entry>
              <entry valign="bottom">
              Mandatory value. PPG service user's username.
              </entry></row>
              <row><entry><literal>password</literal></entry>
              <entry><emphasis>string</emphasis></entry>
              <entry valign="bottom">
              Mandatory value. PPG service user's password.
              </entry></row>
              </tbody>
              </tgroup>
        </table>
 </sect1>
</appendix>

<appendix>
<title>Setting up a dial-up line</title>

	<para>This appendix explains how to set up a dial-up line in Linux
	for use with the Kannel WAP gateway. In order for it to work you need
	a Linux kernel with PPP capabilities. Most distributions provides PPP
	kernel support by default. For more information how to compile PPP
	support into the kernel please read the "Linux Kernel HOWTO"
	at http://www.linuxdoc.org/.</para>

<sect1>
<title>Analog modem</title>

	<para>This section explains how to set up a dial-up line with an
	analog modem.</para>

	<para>Download and install the mgetty package.</para>

	<screen><userinput>
	rpm -ivh mgetty-VERSION-rpm
	</userinput></screen>	

	<para>To run mgetty as a daemon, add the following line to
	/etc/inittab.</para>

	<para>Read man inittab for more detailed information. In this
	example we assume your modem is connected to the serial port ttyS0
	(COM 1).</para>
	
	<screen><userinput>
	S0:2345:respawn:/sbin/mgetty ttyS0 -x 6 -D /dev/ttyS0
	</userinput></screen>

	<para>We need to start the pppd automatically when mgetty receives
	an AutoPPP request. Add the next line to /etc/mgetty+sendfax/login.config</para>

	<screen><userinput>
	/AutoPPP/ - - /usr/sbin/pppd file /etc/ppp/options.server
	</userinput></screen>

	<para>In /etc/mgetty+sendfax/mgetty.config you might need to change
	the connect speed between the computer and the modem. Note: this is
	not the connect speed between the WAP client and the server modem.
	If you are e.g. going to use a Nokia 7110 as the server side modem
	you need to change the speed to 19200. Usually you can just leave the
	speed to the default value (38400).</para>

	<screen><userinput>
	speed 38400
	</userinput></screen>

	<para>Add the following lines to /etc/ppp/options.server</para>
	
	<screen><userinput>
	refuse-chap
	require-pap
	lock
	modem
	crtscts
	passive
	192.168.1.10:192.168.1.20
	debug
	</userinput></screen>

	<para>In /etc/ppp/pap-secrets add the username and password for the
	ppp account. The IP address is the one assigned to the phone.</para>

	<screen><userinput>
	wapuser * wappswd 192.168.0.20
	</userinput></screen>

	<para>Configure your phone (this example is for Nokia 7110)</para>

	<screen><userinput>
	homepage http:/yourhost/hello.wml
	connection type continuous
	connection security off
	bearer data
	dial up number (your phone number)
	ip address (IP of host running bearerbox)
	auth type normal
	data call type analogue
	data call speed 9600
	username wapuser
	password wappswd
	</userinput></screen>
</sect1>

<sect1>
<title>ISDN terminal</title>

	<para>This section needs to be written</para>

</sect1>

</appendix>

<appendix>
    <title>Regular Expressions</title>
    <para>Note: this is not intended to be an introduction to regular expressions (short: regex) but a 
    description of their application within Kannel. For general information regarding regexes
    please refer to <xref linkend="Biblio-regexp"/>.
    </para>
    <sect1>
        <title>Syntax and semantics of the regex configuration parameter</title>
        <para>This section describes the regex-configuration parameters and their effects in combination with the
        respective non-regex-parameter, e.g. <literal>white-list</literal> and <literal>white-list-regex</literal>.</para>

        <sect2>
                <title>How-to setup the regex-parameters</title>
                <para>examples, short syntax, what happens on errors
                Regex-parameters are configured just as every other parameter is configured. Regular expressions are
                supported as defined by POSIX Extended Regular Expressions. Suppose a configuration where only SMS messages
                originating from a sender using a number with a prefix of "040", "050", "070" or "090" are accepted.
                Without regexes the configuration would read
                <programlisting>
                allowed-prefix="040;050;070;090"
                </programlisting>
                Using regular expressions yields a more concise configuration
                <programlisting>
                allowed-prefix-regex=^0[4579]0
                </programlisting>
                The following table gives an overview over some regex-operators and their meaning, the POSIX Regular
                Expressions manual page (regex(7)). Once again, the extended regex-syntax is used and the table is 
                just meant as a means to give a quick-start to regular expressions, the next section features some more
                complex examples.
                <informaltable>
                        <tgroup cols="2">
                                <thead>
                                        <row>
                                        <entry>Operator</entry>
                                        <entry>Meaning</entry>
                                        </row>
                                </thead>    
                                <tbody>
                                        <row>
                                        <entry><literal>|</literal></entry>
                                        <entry>or, for example "dog|hog" matches dog or hog.</entry>
                                        </row>
                                        <row>
                                        <entry><literal>{number,number}</literal></entry>
                                        <entry>repetition, for example "a{2,5}" matches - among others - 
                                        "aa", "aaa" and "baaaaad"</entry>
                                        </row>
                                        <row>
                                        <entry><literal>*</literal></entry>
                                        <entry>shorthand for {0,}</entry>
                                        </row>
                                        <row>
                                        <entry><literal>?</literal></entry>
                                        <entry>shorthand for {0,1}</entry>
                                        </row>
                                        <row>
                                        <entry><literal>+</literal></entry>
                                        <entry>shorthand for {1,}</entry>
                                        </row>
                                        <row>
                                        <entry><literal>[]</literal></entry>
                                        <entry>bracket expression, defines a class of possible single character matches.
                                        For example "[hb]og" matches "hog" and "bog". If the expression starts with
                                        <literal>^</literal> then the class is negated, e.g. "[^hb]og" does not match
                                        "hog" and "bog" but matches for example "dog".</entry>
                                        </row>
                                        <row>
                                        <entry><literal>()</literal></entry>
                                        <entry>groups patterns, e.g. "[hb]o(g|ld)" matches "hog", "hold", "bog", "bold"
                                        </entry>
                                        </row>
                                        <row>
                                        <entry><literal>[:class:]</literal></entry>
                                        <entry>A character class such as digit, space etc. See wctype(3) for details.
                                        </entry>
                                        </row>
                                        <row>
                                        <entry><literal>^</literal></entry>
                                        <entry>Start of line anchor.</entry>
                                        </row>
                                        <row>
                                        <entry><literal>$</literal></entry>
                                        <entry>End of line anchor.</entry>
                                        </row>
                                </tbody>
                        </tgroup>
                </informaltable>

                The advantages of regular expressions are at hand
		<itemizedlist>
		<listitem><para>Regexes are easier to understand, if one is fluent in POSIX Regular Expressions. 
                                Although simple expressions as shown above should be clear to everyone who has
                                ever used a standard UN*X shell.
                          </para></listitem>
                <listitem>
                        <para>Regexes are easier to maintain. Suppose the example above needed to cope with 
                        dozens of different prefixes each with subtle differences, in such cases using a - carefully
                        constructed - regular expression could help to keep things in apple pie order. 
                        Furthermore regexes help reducing redundancy within the configuration.
                        </para>
                </listitem>
                <listitem>
                        <para>Regexes more flexible than standard parameters.
                        </para>
                </listitem>
                </itemizedlist>
                Nevertheless, it must be mentioned that - in addition to the overhead involved - complexity is an issue, 
                too. Although the syntactic correctness of each used regular expression is ensured (see below)
                    the semantic correctness cannot be automatically proofed.
                </para>
                <para>
                Expressions that are not compilable, which means they are not valid POSIX regexes, force  Kannel
                to panic with a message like (note the missing "]")
	<screen><computeroutput>
                ERROR: gwlib/regex.c:106: gw_regex_comp_real: regex compilation `[hbo(g|ld)' failed: Invalid regular expression (Called from gw/urltrans.c:987:create_onetrans.)
                PANIC: Could not compile pattern '[hbo(g|ld)'
	</computeroutput></screen>
                As shown the erroneous pattern is reported in the error message. 
                </para>
        </sect2>
        
        <sect2>
                <title>Regex and non-regex-parameters</title>
                <para>
                Using the regex and non-regex version of a parameter at the same time should be done with caution.
                Both are combined in a boolean-or sense, for example
                <programlisting>
                white-list=01234
                white-list-regex=^5(23)?$
                </programlisting>
                implies that a number is accepted either if it is "01234", "5" or "523" - note the use of anchors!
                The same goes for all the other parameters, thus both mechanisms can be used without problems in parallel,
                but care should be taken that the implications are understood and wanted.
                </para>
        </sect2>
        
        <sect2>
                <title>Performance issues</title>
                <para>While there is some overhead involved, the actual performance degradation is negligible.
                At startup - e.g. when the configuration files are parsed - the regular expressions are pre-compiled
                and stored in the pre-compiled fashion, thus future comparisons involve executing the expression on 
                some string only. To be on the sure side, before using regexes extensively some benchmarking should be
                performed, to verify that the loss of performance is acceptable.
                </para>
        </sect2>
    </sect1>
    <sect1>
        <title>Examples</title>
        <para>This section discusses some simple scenarios and potential solutions based on regexes.
        The examples are not meant to be comprehensive but rather informative.</para>
        <sect2>
                <title>Example 1: core-configuration</title>
                <para>The bearerbox must only accept SMS messages from three costumers. The first costumer uses numbers
                that always start with "0824" the second one uses numbers that start with either "0123" and end in 
                "314" or start with "0882" and end in "666". The third costumer uses numbers starting with "0167"
                and ending in a number between "30" and "57".</para>
                <para>
                Important in this and in the following examples is the use of anchors, otherwise a "string contains"
                semantic instead of a "string is equal" semantic would be used.
                </para>
                <programlisting>
                group=core
                ...
                white-list-regex=^((0824[0-9]+)|(0123[0-9]+314)|(0882[0-9]+666)|(0167[0-9]+([34][0-9]|5[0-7])))$
                ...
                </programlisting>
        </sect2>
        <sect2>
                <title>Example 3: smsc-configuration</title>
                <para>Only SMS messages originating from certain SMSCs (<literal>smsc-id</literal> is either 
                        "foo", "bar" or "blah")
                are preferably forwarded to this smsc. 
                Furthermore all SMSCs with an id containing "vodafone" must never
                be forwarded to the smsc. Not the missing anchors around "vodafone".</para>
                <programlisting>
                group=smsc
                ...
                preferred-smsc-id-regex=^(foo|bar|blah)$
                denied-prefix-regex=vodafone
                ...
                </programlisting>
        </sect2>
        <sect2>
                <title>Example 4: sms-service-configuration</title>
                <para>Please note that there are a mandatory <literal>keyword</literal> and an optional
                <literal>keyword-regex</literal> fields.
                That means that service selection can be simplified as in the following example.
                Suppose that some Web-content should be delivered to the mobile. Different costumers use the 
                same service but they rely on different keywords. Whenever a sms-service is requested, Kannel
                first checks whether a regex has been defined, if not a literal match based on <literal>keyword</literal>
                is performed. If a regex is configured then the literal match is never tried.
                </para>
                <programlisting>
                group=sms-service
                ...
                keyword=web_service
                keyword-regex=^(data|www|text|net)$
                get-url=http://someserver.net/getContent.jsp
                ...
                </programlisting>
        </sect2>
    </sect1>
</appendix> 

<appendix>
<title>Log files</title>

	<para>This appendix describes the log file format.</para>

<sect1>
<title>Bearerbox Access Log</title>

	<screen><computeroutput>
	2001-01-01 12:00:00 Sent SMS [SMSC:smsc] [SVC:sms] [from:12345] 
	    [to:67890] [flags:0:1:0:0:0] [msg:11:Hello World] [udh:0]
	</computeroutput></screen>	

 <informaltable frame="none">
  <tgroup cols="3">
  <thead>
   <row>
     <entry>Variable</entry>
     <entry>Value</entry>
     <entry>Description</entry>
   </row>
  </thead>
  <tbody>
   <row><entry>Date</entry>
     <entry>2001-01-01 12:00:00</entry>
     <entry valign="bottom">
       Date
     </entry></row>

   <row><entry>Result</entry>
     <entry>Sent SMS</entry>
     <entry valign="bottom">
       Result: Send, failed, DLR (deliver report), Received, etc.
     </entry></row>

   <row><entry>SMSC</entry>
     <entry>smsc</entry>
     <entry valign="bottom">
	     Smsc id (<literal>smsc-id</literal>) defined in configuration 
	     group <literal>smsc</literal> 
     </entry></row>

     <row><entry>SVC</entry>
     <entry>sms</entry>
     <entry valign="bottom">
	     Service name (<literal>name</literal>) defined in configuration 
	     group <literal>sendsms-user</literal>
     </entry></row>

     <row><entry>from</entry>
     <entry>12345</entry>
     <entry valign="bottom">
	     Sender
     </entry></row>

     <row><entry>to</entry>
     <entry>67890</entry>
     <entry valign="bottom">
	     Recipient
     </entry></row>

     <row><entry>Flags</entry>
     <entry>0:1:0:0:0</entry>
     <entry valign="bottom">
	     Flags: MClass, Coding, MWI, Compress, DLRMask
     </entry></row>

     <row><entry>Message Text</entry>
     <entry>11:Hello World</entry>
     <entry valign="bottom">
	     Size of message and message dump (in text or hex if it's binary)
     </entry></row>

     <row><entry>User Data Header</entry>
     <entry>0:</entry>
     <entry valign="bottom">
	     Size of UDH and UDH Hex dump 
     </entry></row>

   </tbody>
   </tgroup>
  </informaltable>

</sect1>
<sect1>
<title>Log rotation</title>

	<para>If Kannel is configured so that the bearerbox, wapbox and/or smsbox 
        log to file each of these log files will continue to grow unless administered
        in some way (this is specially true if access logs are created and/or the 
        log level is set to debug). </para>

        <para>
        A typical way of administering log files is to 'rotate' the logs on a regular 
        basis using a tool such as logrotate.  A sample logrotate script (to be added 
        to /etc/logrotate.d) is shown below. In this example the Kannel log files found 
        in /var/log/kannel are rotated and compressed daily over 365 days.  See the 
        documentation for logrotate for more details.  Of particular note however is the 
        postrotate command, this killall -HUP issues a HUP command to each Kannel
        box running. The HUP signal has the effect of reopening the log file, without this 
        command Kannel will continue to write to the rotated log file.
        </para>

        <screen><userinput>
        /var/log/kannel/*.log {
              daily
              missingok
              rotate 365
              compress
              delaycompress
              notifempty
              create 640 kannel adm
              sharedscripts
              postrotate
                    killall -HUP bearerbox smsbox wapbox || true > /dev/null 2> /dev/null
              endscript
        }
        </userinput></screen>
</sect1>

</appendix>


<glossary>
        <title>Glossary</title>

        <glossdiv><title>M</title>
                <glossentry id="MO"><glossterm>MO</glossterm><glossdef>
                        <para>Mobile Originated - a SMS from mobile to application</para>
                </glossdef></glossentry>
                <glossentry id="MT"><glossterm>MT</glossterm><glossdef>
                        <para>Mobile Terminated - a SMS from application to mobile</para>
                </glossdef></glossentry>
                <glossentry id="MWI"><glossterm>MWI</glossterm><glossdef>
                        <para>Message Waiting Indicator (See <xref linkend="Biblio-3GPP-23038">)</para>
                </glossdef></glossentry>
                <glossentry id="MCLASS"><glossterm>MClass</glossterm><glossdef>
                        <para>Message Class (See <xref linkend="Biblio-3GPP-23038">)</para>
                </glossdef></glossentry>
                <glossentry id="CODING"><glossterm>Coding</glossterm><glossdef>
                        <para>Message Coding (See <xref linkend="Biblio-3GPP-23038">)</para>
                </glossdef></glossentry>
        </glossdiv>

</glossary>

<bibliography>
        <title>Bibliography</title>

        <biblioentry id="Biblio-RFC-2616">
                <title>RFC 2616 - Hypertext Transfer Protocol -- HTTP/1.1</title>
                <issn><ulink url="http://www.w3.org/Protocols/rfc2616/rfc2616.html">http://www.w3.org/Protocols/rfc2616/rfc2616.html</ulink></issn>
                <subtitle>Request for Comments: 2616</subtitle>
                <orgname>The Internet Society</orgname>
                <copyright><year>1999</year></copyright>
        </biblioentry>

        <biblioentry id="Biblio-3GPP-23038">
                <title>3GPP 23.038</title>
                <issn><ulink url="http://www.3gpp.org/ftp/Specs/latest/Rel-5/23_series/23038-500.zip">http://www.3gpp.org/ftp/Specs/latest/Rel-5/23_series/23038-500.zip</ulink></issn>
                <subtitle>...</subtitle>
                <orgname>3GPP</orgname>
                <copyright><year>?</year></copyright>
        </biblioentry>

        <biblioentry id="Biblio-3GPP-23040">
                <title>3GPP 23.040</title>
                <issn><ulink url="http://www.3gpp.org/ftp/Specs/latest/Rel-5/23_series/23040-530.zip">http://www.3gpp.org/ftp/Specs/latest/Rel-5/23_series/23040-530.zip</ulink></issn>
                <subtitle>...</subtitle>
                <orgname>3GPP</orgname>
                <copyright><year>?</year></copyright>
        </biblioentry>

        <biblioentry id="Biblio-regexp">
                <title>regex(7), GNU regex manual</title>
                <!-- <issn><ulink url="http://techpubs.sgi.com/library/tpl/cgi-bin/getdoc.cgi?coll=linux&db=man&fname=/usr/share/catman/man7/regex.7.html&srch=regex">http://techpubs.sgi.com/library/tpl/cgi-bin/getdoc.cgi?coll=linux&db=man&fname=/usr/share/catman/man7/regex.7.html&srch=regex</ulink></issn>-->
                <subtitle></subtitle>
                <orgname>GNU</orgname>
                <copyright><year>1998</year></copyright>
        </biblioentry>
        
</bibliography>

</book>


