summaryrefslogtreecommitdiff
path: root/doc
diff options
context:
space:
mode:
authorMatt Dew <matt@osource.org>2010-06-30 16:52:22 -0400
committerGaetan Nadon <memsize@videotron.ca>2010-06-30 17:02:20 -0400
commit5bb806a65bf23a507b135abe1e4a8b3cabc7b8aa (patch)
tree0c5b416db328110c0fbed23577b8018610218e72 /doc
parent9b54f509832c50c1fac0edc0cb78e1a3454a56dc (diff)
specs: convert ICE doc/specs from xorg-docs module to DocBook XML
Signed-off-by: Gaetan Nadon <memsize@videotron.ca>
Diffstat (limited to 'doc')
-rw-r--r--doc/.gitignore6
-rw-r--r--doc/ICElib.ms3400
-rw-r--r--doc/ICElib.xml4588
-rw-r--r--doc/Makefile.am65
-rw-r--r--doc/ice.ms1878
5 files changed, 4658 insertions, 5279 deletions
diff --git a/doc/.gitignore b/doc/.gitignore
new file mode 100644
index 0000000..12fe512
--- /dev/null
+++ b/doc/.gitignore
@@ -0,0 +1,6 @@
+# Add & Override for this directory and it's subdirectories
+*.html
+*.ps
+*.pdf
+*.txt
+*.css
diff --git a/doc/ICElib.ms b/doc/ICElib.ms
deleted file mode 100644
index 0c35d60..0000000
--- a/doc/ICElib.ms
+++ /dev/null
@@ -1,3400 +0,0 @@
-.\" $Xorg: ICElib.ms,v 1.3 2000/08/17 19:42:09 cpqbld Exp $
-.\" $XdotOrg: xc/doc/specs/ICE/ICElib.ms,v 1.2 2004/04/23 18:42:16 eich Exp $
-.\"
-.\" Use tbl, -ms, and macros.t
-.\"
-.\" macro: start marker
-.de sM
-.ne 4
-.sp 1
-\\h'-0.3i'\\L'-1v'\\v'3p'\\l'1v'\\v'1v-3p'
-.sp -1
-..
-.\" macro: end marker
-.de eM
-.sp -1
-\\h'-0.3i'\\L'-1v'\\v'1v+4p'\\l'1v'\\v'-4p'
-.sp 1
-..
-.EH ''''
-.OH ''''
-.EF ''''
-.OF ''''
-.ad b
-.sp 10
-.TL
-\s+2\fBInter-Client Exchange Library\fP\s-2
-.sp
-Version 1.0
-.sp
-X Consortium Standard
-.sp
-X Version 11, Release 6.8
-.AU
-Ralph Mor
-.AI
-X Consortium
-.LP
-.DS C
-Copyright \(co 1993, 1994, 1996 X Consortium
-.DE
-.LP
-.sp 5
-Permission is hereby granted, free of charge, to any person obtaining a copy
-of this software and associated documentation files (the ``Software''), to deal
-in the Software without restriction, including without limitation the rights
-to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
-copies of the Software, and to permit persons to whom the Software is
-furnished to do so, subject to the following conditions:
-.LP
-The above copyright notice and this permission notice shall be included in
-all copies or substantial portions of the Software.
-.LP
-THE SOFTWARE IS PROVIDED ``AS IS'', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
-AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
-CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-.LP
-Except as contained in this notice, the name of the X Consortium shall not be
-used in advertising or otherwise to promote the sale, use or other dealings
-in this Software without prior written authorization from the X Consortium.
-.sp 5
-X Window System is a trademark of The Open Group.
-.bp
-.EH '\fBInter-Client Exchange Library\fP''\fBX11, Release 6.8\fP'
-.OH '\fBInter-Client Exchange Library\fP''\fBX11, Release 6.8\fP'
-.bp 1
-.EF ''\- \\\\n(PN \-''
-.OF ''\- \\\\n(PN \-''
-.NH 1
-Overview of ICE
-.XS
-\*(SN Overview of ICE
-.XE
-.LP
-There are numerous possible inter-client protocols, with many similarities
-and common needs - authentication, version negotiation, byte
-order negotiation, and so on.
-The Inter-Client Exchange (ICE) protocol is intended to provide a framework
-for building such protocols, allowing them to make use of common negotiation
-mechanisms and to be multiplexed over a single transport connection.
-.NH 1
-The ICE Library - C Language Interface to ICE
-.XS
-\*(SN The ICE Library - C Language Interface to ICE
-.XE
-.LP
-A client that wishes to utilize ICE must first register the protocols it
-understands with the ICE library. Each protocol is dynamically assigned
-a major opcode ranging from 1-255 (two clients can use different
-major opcodes for the same protocol). The next step for the client is either
-to open a connection with another client or to wait for connections made
-by other clients. Authentication may be required. A client can both
-initiate connections with other clients and be
-waiting for clients to connect to itself (a nested session manager is an
-example). Once an ICE connection is established between the two clients, one
-of the clients needs to initiate a
-.PN ProtocolSetup
-in order to
-"activate" a given protocol. Once the other client accepts the
-.PN ProtocolSetup
-(once again, authentication may be required), the
-two clients are ready to start passing messages specific to that protocol to
-each other. Multiple protocols may be active on a single ICE connection.
-Clients are responsible for notifying the ICE library when a protocol is no
-longer active on an ICE connection, although ICE does not define how each
-subprotocol triggers a protocol shutdown.
-.LP
-The ICE library utilizes callbacks to process incoming messages. Using
-callbacks allows
-.PN ProtocolSetup
-messages and authentication to happen
-behind the scenes. An additional benefit is that messages never need
-to be buffered up by the library when the client blocks waiting for a
-particular message.
-.NH 1
-Intended Audience
-.XS
-\*(SN Intended Audience
-.XE
-.LP
-This document is intended primarily for implementors of protocol libraries
-layered on top of ICE. Typically, applications that wish to utilize ICE
-will make calls into individual protocol libraries rather than directly
-make calls into the ICE library. However, some applications will have to
-make some initial calls into the ICE library in order to accept ICE
-connections (for example, a session manager accepting connections from
-clients). But in general, protocol libraries should be designed to hide
-the inner details of ICE from applications.
-.NH 1
-Header Files and Library Name
-.XS
-\*(SN Header Files and Library Name
-.XE
-.LP
-The header file
-.Pn < X11/ICE/ICElib.h >
-defines all of the ICElib data structures and function prototypes.
-.PN ICElib.h
-includes the header file
-.Pn < X11/ICE/ICE.h >,
-which defines all of the ICElib constants.
-Protocol libraries that need to read and write messages should include
-the header file
-.Pn < X11/ICE/ICEmsg.h >.
-.LP
-Applications should link against ICElib using -lICE.
-.NH 1
-Note on Prefixes
-.XS
-\*(SN Note on Prefixes
-.XE
-.LP
-The following name prefixes are used in the library to distinguish between
-a client that initiates a
-.PN ProtocolSetup
-and a client that
-responds with a
-.PN ProtocolReply :
-.IP \(bu 5
-.PN IcePo
-\- Ice Protocol Originator
-.IP \(bu 5
-.PN IcePa
-\- Ice Protocol Acceptor
-.NH 1
-Protocol Registration
-.XS
-\*(SN Protocol Registration
-.XE
-.LP
-In order for two clients to exchange messages for a given protocol, each
-side must register the protocol with the ICE library. The purpose of
-registration is for each side to obtain a major opcode for the protocol
-and to provide callbacks for processing messages and handling authentication.
-There are two separate registration functions:
-.IP \(bu 5
-One to handle the side that does a
-.PN ProtocolSetup
-.IP \(bu 5
-One to handle the side that responds with a
-.PN ProtocolReply
-.LP
-It is recommended that protocol registration occur before the two clients
-establish an ICE connection. If protocol registration occurs after an
-ICE connection is created, there can be a brief interval of time in which
-a
-.PN ProtocolSetup
-is received, but the protocol is not registered.
-If it is not possible to register a protocol before the creation of an
-ICE connection, proper precautions should be taken to avoid the above race
-condition.
-.sp
-.LP
-The
-.PN IceRegisterForProtocolSetup
-function should be called for the client that initiates a
-.PN ProtocolSetup .
-.sM
-.FD 0
-int IceRegisterForProtocolSetup\^(\^\fIprotocol_name\fP, \fIvendor\fP\^, \
-\fIrelease\fP\^, \fIversion_count\fP\^, \fIversion_recs\fP\^,
-.br
- \fIauth_count\fP\^, \fIauth_names\fP\^, \fIauth_procs\fP\^, \
-\fIio_error_proc\fP\^)
-.br
- char *\fIprotocol_name\fP\^;
-.br
- char *\fIvendor\fP\^;
-.br
- char *\fIrelease\fP\^;
-.br
- int \fIversion_count\fP\^;
-.br
- IcePoVersionRec *\fIversion_recs\fP\^;
-.br
- int \fIauth_count\fP\^;
-.br
- char **\fIauth_names\fP\^;
-.br
- IcePoAuthProc *\fIauth_procs\fP\^;
-.br
- IceIOErrorProc \fIio_error_proc\fP\^;
-.FN
-.IP \fIprotocol_name\fP 1i
-A string specifying the name of the protocol to register.
-.IP \fIvendor\fP 1i
-A vendor string with semantics specified by the protocol.
-.IP \fIrelease\fP 1i
-A release string with semantics specified by the protocol.
-.IP \fIversion_count\fP 1i
-The number of different versions of the protocol supported.
-.IP \fIversion_recs\fP 1i
-List of versions and associated callbacks.
-.IP \fIauth_count\fP 1i
-The number of authentication methods supported.
-.IP \fIauth_names\fP 1i
-The list of authentication methods supported.
-.IP \fIauth_procs\fP 1i
-The list of authentication callbacks, one for each authentication method.
-.IP \fIio_error_proc\fP 1i
-IO error handler, or NULL.
-.LP
-.eM
-.PN IceRegisterForProtocolSetup
-returns the major opcode reserved or -1 if an error occurred. In order
-to actually activate the protocol, the
-.PN IceProtocolSetup
-function needs to be called with this major opcode. Once the protocol is
-activated, all messages for the protocol should be sent using this major
-opcode.
-.LP
-A protocol library may support multiple versions of the same protocol.
-The version_recs argument specifies a list of supported versions of the protocol,
-which are prioritized in decreasing order of preference.
-Each version record consists of a major and minor version of the protocol
-as well as a callback to be used for processing incoming messages.
-.LP
-.sM
-.Ds 0
-.TA .5i
-.ta .5i
-typedef struct {
- int major_version;
- int minor_version;
- IcePoProcessMsgProc process_msg_proc;
-} IcePoVersionRec;
-.De
-.LP
-.eM
-The
-.PN IcePoProcessMsgProc
-callback is responsible for processing the set of messages that can be
-received by the client that initiated the
-.PN ProtocolSetup .
-For further information,
-see section 6.1, ``Callbacks for Processing Messages.''
-.LP
-Authentication may be required before the protocol can become active.
-The protocol library must register the authentication methods that it
-supports with the ICE library.
-The auth_names and auth_procs arguments are a list of authentication names
-and callbacks that are prioritized in decreasing order of preference.
-For information on the
-.PN IcePoAuthProc
-callback, see section 6.2, ``Authentication Methods.''
-.LP
-The
-.PN IceIOErrorProc
-callback is invoked if the ICE connection unexpectedly breaks.
-You should pass NULL for io_error_proc if not interested in being notified.
-For further information,
-see section 13, ``Error Handling.''
-.sp
-.LP
-The
-.PN IceRegisterForProtocolReply
-function should be called for the client that responds to a
-.PN ProtocolSetup
-with a
-.PN ProtocolReply .
-.sM
-.FD 0
-int IceRegisterForProtocolReply\^(\^\fIprotocol_name\fP, \fIvendor\fP\^, \fIrelease\fP\^, \fIversion_count\fP\^, \fIversion_recs\fP\^,
-.br
- \fIauth_count\fP\^, \fIauth_names\fP\^, \fIauth_procs\fP\^, \fIhost_based_auth_proc\fP\^, \fIprotocol_setup_proc\fP\^,
-.br
- \fIprotocol_activate_proc\fP\^, \fIio_error_proc\fP\^)
-.br
- char *\fIprotocol_name\fP\^;
-.br
- char *\fIvendor\fP\^;
-.br
- char *\fIrelease\fP\^;
-.br
- int \fIversion_count\fP\^;
-.br
- IcePaVersionRec *\fIversion_recs\fP\^;
-.br
- int \fIauth_count\fP\^;
-.br
- char **\fIauth_names\fP\^;
-.br
- IcePaAuthProc *\fIauth_procs\fP\^;
-.br
- IceHostBasedAuthProc \fIhost_based_auth_proc\fP\^;
-.br
- IceProtocolSetupProc \fIprotocol_setup_proc\fP\^;
-.br
- IceProtocolActivateProc \fIprotocol_activate_proc\fP\^;
-.br
- IceIOErrorProc \fIio_error_proc\fP\^;
-.FN
-.IP \fIprotocol_name\fP 1i
-A string specifying the name of the protocol to register.
-.IP \fIvendor\fP 1i
-A vendor string with semantics specified by the protocol.
-.IP \fIrelease\fP 1i
-A release string with semantics specified by the protocol.
-.IP \fIversion_count\fP 1i
-The number of different versions of the protocol supported.
-.IP \fIversion_recs\fP 1i
-List of versions and associated callbacks.
-.IP \fIauth_count\fP 1i
-The number of authentication methods supported.
-.IP \fIauth_names\fP 1i
-The list of authentication methods supported.
-.IP \fIauth_procs\fP 1i
-The list of authentication callbacks, one for each authentication method.
-.IP \fIhost_based_auth_proc\fP 1i
-Host based authentication callback.
-.IP \fIprotocol_setup_proc\fP 1i
-A callback to be invoked when authentication has succeeded for a
-.PN ProtocolSetup
-but before the
-.PN ProtocolReply
-is sent.
-.IP \fIprotocol_activate_proc\fP 1i
-A callback to be invoked after the
-.PN ProtocolReply
-is sent.
-.IP \fIio_error_proc\fP 1i
-IO error handler, or NULL.
-.LP
-.eM
-.PN IceRegisterForProtocolReply
-returns the major opcode reserved or -1 if an error occurred. The major
-opcode should be used in all subsequent messages sent for this protocol.
-.LP
-A protocol library may support multiple versions of the same protocol.
-The version_recs argument specifies a list of supported versions of the protocol,
-which are prioritized in decreasing order of preference.
-Each version record consists of a major and minor version of the protocol
-as well as a callback to be used for processing incoming messages.
-.LP
-.sM
-.Ds 0
-.TA .5i
-.ta .5i
-typedef struct {
- int major_version;
- int minor_version;
- IcePaProcessMsgProc process_msg_proc;
-} IcePaVersionRec;
-.De
-.LP
-.eM
-The
-.PN IcePaProcessMsgProc
-callback is responsible for processing the set of messages that can be
-received by the client that accepted the
-.PN ProtocolSetup .
-For further information,
-see section 6.1, ``Callbacks for Processing Messages.''
-.LP
-Authentication may be required before the protocol can become active.
-The protocol library must register the authentication methods that it
-supports with the ICE library.
-The auth_names and auth_procs arguments are a list of authentication names
-and callbacks that are prioritized in decreasing order of preference.
-For information on the
-.PN IcePaAuthProc
-callback, see section 6.2, ``Authentication Methods.''
-.LP
-If authentication fails and the client attempting to initiate
-the
-.PN ProtocolSetup
-has not required authentication, the
-.PN IceHostBasedAuthProc
-callback is invoked with the host name of the originating client.
-If the callback returns
-.PN True ,
-the
-.PN ProtocolSetup
-will succeed, even though the original
-authentication failed.
-Note that authentication can effectively be disabled by registering an
-.PN IceHostBasedAuthProc ,
-which always returns
-.PN True .
-If no host based
-authentication is allowed, you should pass NULL for host_based_auth_proc.
-.LP
-.sM
-.FD 0
-typedef Bool (*IceHostBasedAuthProc) ();
-
-Bool HostBasedAuthProc\^(\^\fIhost_name\fP\^)
-.br
- char *\fIhost_name\fP\^;
-.FN
-.IP \fIhost_name\fP 1i
-The host name of the client that sent the
-.PN ProtocolSetup .
-.LP
-.eM
-The host_name argument is a string of the form \fIprotocol\fP\^/\^\fIhostname\fP,
-where \fIprotocol\fP\^ is one of {tcp, decnet, local}.
-.LP
-Because
-.PN ProtocolSetup
-messages and authentication happen behind the scenes
-via callbacks, the protocol library needs some way of being notified when the
-.PN ProtocolSetup
-has completed.
-This occurs in two phases.
-In the first phase, the
-.PN IceProtocolSetupProc
-callback is invoked after authentication has
-successfully completed but before the ICE library sends a
-.PN ProtocolReply .
-Any resources required for this protocol should be allocated at this time.
-If the
-.PN IceProtocolSetupProc
-returns a successful status, the ICE library will
-send the
-.PN ProtocolReply
-and then invoke the
-.PN IceProtocolActivateProc
-callback. Otherwise, an error will be sent to the
-other client in response to the
-.PN ProtocolSetup .
-.LP
-The
-.PN IceProtocolActivateProc
-is an optional callback and should be registered only if the protocol
-library intends to generate a message immediately following the
-.PN ProtocolReply .
-You should pass NULL for protocol_activate_proc if not interested
-in this callback.
-.if t .bp
-.sM
-.FD 0
-typedef Status (*IceProtocolSetupProc) ();
-
-Status ProtocolSetupProc\^(\^\fIice_conn\fP, \fImajor_version\fP\^, \
-\fIminor_version\fP\^, \fIvendor\fP\^, \fIrelease\fP\^,
-.br
- \fIclient_data_ret\fP\^, \fIfailure_reason_ret\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- int \fImajor_version\fP\^;
-.br
- int \fIminor_version\fP\^;
-.br
- char *\fIvendor\fP\^;
-.br
- char *\fIrelease\fP\^;
-.br
- IcePointer *\fIclient_data_ret\fP\^;
-.br
- char **\fIfailure_reason_ret\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-The ICE connection object.
-.IP \fImajor_version\fP 1i
-The major version of the protocol.
-.IP \fIminor_version\fP 1i
-The minor version of the protocol.
-.IP \fIvendor\fP 1i
-The vendor string registered by the protocol originator.
-.IP \fIrelease\fP 1i
-The release string registered by the protocol originator.
-.IP \fIclient_data_ret\fP 1i
-Client data to be set by callback.
-.IP \fIfailure_reason_ret\fP 1i
-Failure reason returned.
-.LP
-.eM
-The pointer stored in the client_data_ret argument will be passed
-to the
-.PN IcePaProcessMsgProc
-callback whenever a message has arrived for this protocol on the
-ICE connection.
-.LP
-The vendor and release strings should be freed with
-.PN free
-when they are no longer needed.
-.LP
-If a failure occurs, the
-.PN IceProtocolSetupProc
-should return a zero status as well as allocate and return a failure
-reason string in failure_reason_ret.
-The ICE library will be responsible for freeing this memory.
-.LP
-The
-.PN IceProtocolActivateProc
-callback is defined as follows:
-.sM
-.FD 0
-typedef void (*IceProtocolActivateProc)();
-
-void ProtocolActivateProc\^(\^\fIice_conn\fP, \fIclient_data\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- IcePointer \fIclient_data\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-The ICE connection object.
-.IP \fIclient_data\fP 1i
-The client data set in the
-.PN IceProtocolSetupProc
-callback.
-.LP
-.eM
-The
-.PN IceIOErrorProc
-callback is invoked if the ICE connection unexpectedly breaks.
-You should pass NULL for io_error_proc if not interested in being notified.
-For further information,
-see section 13, ``Error Handling.''
-.NH 2
-Callbacks for Processing Messages
-.XS
-\*(SN Callbacks for Processing Messages
-.XE
-.LP
-When an application detects that there is new data to read on an ICE
-connection (via
-.PN select ),
-it calls the
-.PN IceProcessMessages
-function (see section 9, ``Processing Messages'').
-When
-.PN IceProcessMessages
-reads an ICE message header with a major opcode other than
-zero (reserved for the ICE protocol), it needs to call a function that will
-read the rest of the message, unpack it, and process it accordingly.
-.LP
-If the message arrives at the client that initiated the
-.PN ProtocolSetup ,
-the
-.PN IcePoProcessMsgProc
-callback is invoked.
-.sM
-.FD 0
-typedef void (*IcePoProcessMsgProc)();
-
-void PoProcessMsgProc\^(\^\fIice_conn\fP, \fIclient_data\fP\^, \fIopcode\fP\^, \fIlength\fP\^, \fIswap\fP\^, \fIreply_wait\fP\^, \fIreply_ready_ret\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- IcePointer \fIclient_data\fP\^;
-.br
- int \fIopcode\fP\^;
-.br
- unsigned long \fIlength\fP\^;
-.br
- Bool \fIswap\fP\^;
-.br
- IceReplyWaitInfo *\fIreply_wait\fP\^;
-.br
- Bool *\fIreply_ready_ret\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-The ICE connection object.
-.IP \fIclient_data\fP 1i
-Client data associated with this protocol on the ICE connection.
-.IP \fIopcode\fP 1i
-The minor opcode of the message.
-.IP \fIlength\fP 1i
-The length (in 8-byte units) of the message beyond the ICE header.
-.IP \fIswap\fP 1i
-A flag that indicates if byte swapping is necessary.
-.IP \fIreply_wait\fP 1i
-Indicates if the invoking client is waiting for a reply.
-.IP \fIreply_ready_ret\fP 1i
-If set to
-.PN True ,
-a reply is ready.
-.LP
-.eM
-If the message arrives at the client that accepted the
-.PN ProtocolSetup ,
-the
-.PN IcePaProcessMsgProc
-callback is invoked.
-.sM
-.FD 0
-typedef void (*IcePaProcessMsgProc)();
-
-void PaProcessMsgProc\^(\^\fIice_conn\fP, \fIclient_data\fP\^, \fIopcode\fP\^, \fIlength\fP\^, \fIswap\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- IcePointer \fIclient_data\fP\^;
-.br
- int \fIopcode\fP\^;
-.br
- unsigned long \fIlength\fP\^;
-.br
- Bool \fIswap\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-The ICE connection object.
-.IP \fIclient_data\fP 1i
-Client data associated with this protocol on the ICE connection.
-.IP \fIopcode\fP 1i
-The minor opcode of the message.
-.IP \fIlength\fP 1i
-The length (in 8-byte units) of the message beyond the ICE header.
-.IP \fIswap\fP 1i
-A flag that indicates if byte swapping is necessary.
-.LP
-.eM
-In order to read the message, both of these callbacks should use the
-macros defined for this purpose (see section 12.2, ``Reading ICE Messages'').
-Note that byte swapping may be necessary.
-As a convenience, the length field in the ICE header will be swapped by ICElib
-if necessary.
-.LP
-In both of these callbacks, the client_data argument is a pointer to client
-data that was registered at
-.PN ProtocolSetup
-time.
-In the case of
-.PN IcePoProcessMsgProc ,
-the client data was set in the call to
-.PN IceProtocolSetup .
-In the case of
-.PN IcePaProcessMsgProc ,
-the client data was set in the
-.PN IceProtocolSetupProc
-callback.
-.LP
-The
-.PN IcePoProcessMsgProc
-callback needs to check the reply_wait argument.
-If reply_wait is NULL ,
-the ICE library expects the function to
-pass the message to the client via a callback.
-For example, if this is a Session Management ``Save Yourself'' message,
-this function should notify the client of the ``Save Yourself'' via a callback.
-The details of how such a callback would be defined
-are implementation-dependent.
-.LP
-However, if reply_wait is not NULL ,
-then the client is waiting for
-a reply or an error for a message it previously sent.
-The reply_wait is of type
-.PN IceReplyWaitInfo .
-.sM
-.Ds 0
-.TA .5i 2.5i
-.ta .5i 2.5i
-typedef struct {
- unsigned long sequence_of_request;
- int major_opcode_of_request;
- int minor_opcode_of_request;
- IcePointer reply;
-} IceReplyWaitInfo;
-.De
-.LP
-.eM
-.PN IceReplyWaitInfo
-contains the major/minor opcodes and sequence number of
-the message for which a reply is being awaited.
-It also contains a pointer to the reply message to be filled in
-(the protocol library should cast this
-.PN IcePointer
-to the appropriate reply type).
-In most cases, the reply will have some fixed-size part, and the client waiting
-for the reply will have provided a pointer to a structure to hold
-this fixed-size data. If there is variable-length data, it would be
-expected that the
-.PN IcePoProcessMsgProc
-callback will have to allocate additional
-memory and store pointer(s) to that memory in the fixed-size
-structure. If the entire data is variable length (for example., a single
-variable-length string), then the client waiting for the reply would probably
-just pass a pointer to fixed-size space to hold a pointer, and the
-.PN IcePoProcessMsgProc
-callback would allocate the storage and store the pointer.
-It is the responsibility of the client receiving the reply to
-free any memory allocated on its behalf.
-.LP
-If reply_wait is not NULL and
-.PN IcePoProcessMsgProc
-has a reply or error to return in response to this reply_wait
-(that is, no callback was generated), then the reply_ready_ret argument
-should be set to
-.PN True .
-Note that an error should only be returned
-if it corresponds to the reply being waited for. Otherwise, the
-.PN IcePoProcessMsgProc
-should either handle the error internally or invoke an error handler
-for its library.
-.LP
-If reply_wait is NULL,
-then care must be taken not to store any value in reply_ready_ret,
-because this pointer may also be NULL.
-.LP
-The
-.PN IcePaProcessMsgProc
-callback, on the other hand, should always pass
-the message to the client via a callback. For example, if this is a Session
-Management ``Interact Request'' message, this function should notify the
-client of the ``Interact Request'' via a callback.
-.LP
-The reason the
-.PN IcePaProcessMsgProc
-callback does not have a reply_wait, like
-.PN IcePoProcessMsgProc
-does, is because a process that is acting as
-a server should never block for a reply (infinite blocking can
-occur if the connecting client does not act properly, denying access
-to other clients).
-.NH 2
-Authentication Methods
-.XS
-\*(SN Authentication Methods
-.XE
-.LP
-As already stated, a protocol library must register the authentication
-methods that it supports with the ICE library. For each authentication
-method, there are two callbacks that may be registered:
-.IP \(bu 5
-One to handle the side that initiates a
-.PN ProtocolSetup
-.IP \(bu 5
-One to handle the side that accepts or rejects this request
-.LP
-.PN IcePoAuthProc
-is the callback invoked for the client that initiated the
-.PN ProtocolSetup .
-This callback must be able to respond
-to the initial ``Authentication Required'' message or subsequent
-``Authentication Next Phase'' messages sent by the other client.
-.if t .bp
-.sM
-.FD 0
-typedef IcePoAuthStatus (*IcePoAuthProc)();
-
-IcePoAuthStatus PoAuthProc\^(\^\fIice_conn\fP, \fIauth_state_ptr\fP\^, \fIclean_up\fP\^, \fIswap\fP\^, \fIauth_datalen\fP\^, \fIauth_data\fP\^,
-.br
- \fIreply_datalen_ret\fP\^, \fIreply_data_ret\fP\^, \fIerror_string_ret\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- IcePointer *\fIauth_state_ptr\fP\^;
-.br
- Bool \fIclean_up\fP\^;
-.br
- Bool \fIswap\fP\^;
-.br
- int \fIauth_datalen\fP\^;
-.br
- IcePointer \fIauth_data\fP\^;
-.br
- int *\fIreply_datalen_ret\fP\^;
-.br
- IcePointer *\fIreply_data_ret\fP\^;
-.br
- char **\fIerror_string_ret\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-The ICE connection object.
-.IP \fIauth_state_ptr\fP 1i
-A pointer to state for use by the authentication callback procedure.
-.IP \fIclean_up\fP 1i
-If
-.PN True ,
-authentication is over, and the function
-should clean up any state it was maintaining. The
-last 6 arguments should be ignored.
-.IP \fIswap\fP 1i
-If
-.PN True ,
-the auth_data may have to be byte swapped
-(depending on its contents).
-.IP \fIauth_datalen\fP 1i
-The length (in bytes) of the authenticator data.
-.IP \fIauth_data\fP 1i
-The data from the authenticator.
-.IP \fIreply_datalen_ret\fP 1i
-The length (in bytes) of the reply data returned.
-.IP \fIreply_data_ret\fP 1i
-The reply data returned.
-.IP \fIerror_string_ret\fP 1i
-If the authentication procedure encounters an error during
-authentication, it should allocate and return
-an error string.
-.LP
-.eM
-Authentication may require several phases, depending on the authentication
-method. As a result, the
-.PN IcePoAuthProc
-may be called more than once when authenticating a client, and
-some state will have to be maintained between each invocation.
-At the start of each
-.PN ProtocolSetup ,
-*auth_state_ptr is NULL,
-and the function should initialize its state and set
-this pointer. In subsequent invocations of the callback, the pointer
-should be used to get at any state previously stored by the callback.
-.LP
-If needed, the network ID of the client accepting the
-.PN ProtocolSetup
-can be obtained by calling the
-.PN IceConnectionString
-function.
-.LP
-ICElib will be responsible for freeing the reply_data_ret and
-error_string_ret pointers with
-.PN free .
-.LP
-The auth_data pointer may point to a volatile block of memory.
-If the data must be kept beyond this invocation of the callback, be sure
-to make a copy of it.
-.LP
-The
-.PN IcePoAuthProc
-should return one of four values:
-.IP \(bu 5
-.PN IcePoAuthHaveReply
-\- a reply is available.
-.IP \(bu 5
-.PN IcePoAuthRejected
-\- authentication rejected.
-.IP \(bu 5
-.PN IcePoAuthFailed
-\- authentication failed.
-.IP \(bu 5
-.PN IcePoAuthDoneCleanup
-\- done cleaning up.
-.LP
-.PN IcePaAuthProc
-is the callback invoked for the client that received the
-.PN ProtocolSetup .
-.if t .bp
-.sM
-.FD 0
-typedef IcePaAuthStatus (*IcePaAuthProc) ();
-
-IcePaAuthStatus PaAuthProc\^(\^\fIice_conn\fP, \fIauth_state_ptr\fP\^, \fIswap\fP\^, \fIauth_datalen\fP\^, \fIauth_data\fP\^,
-.br
- \fIreply_datalen_ret\fP\^, \fIreply_data_ret\fP\^, \fIerror_string_ret\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- IcePointer *\fIauth_state_ptr\fP\^;
-.br
- Bool \fIswap\fP\^;
-.br
- int \fIauth_datalen\fP\^;
-.br
- IcePointer \fIauth_data\fP\^;
-.br
- int *\fIreply_datalen_ret\fP\^;
-.br
- IcePointer *\fIreply_data_ret\fP\^;
-.br
- char **\fIerror_string_ret\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-The ICE connection object.
-.IP \fIauth_state_ptr\fP 1i
-A pointer to state for use by the authentication callback procedure.
-.IP \fIswap\fP 1i
-If
-.PN True ,
-auth_data may have to be byte swapped
-(depending on its contents).
-.IP \fIauth_datalen\fP 1i
-The length (in bytes) of the protocol originator authentication data.
-.IP \fIauth_data\fP 1i
-The authentication data from the protocol originator.
-.IP \fIreply_datalen_ret\fP 1i
-The length of the authentication data returned.
-.IP \fIreply_data_ret\fP 1i
-The authentication data returned.
-.IP \fIerror_string_ret\fP 1i
-If authentication is rejected or fails, an error
-string is returned.
-.LP
-.eM
-.LP
-Authentication may require several phases, depending on the authentication
-method. As a result, the
-.PN IcePaAuthProc
-may be called more than once when authenticating a client, and
-some state will have to be maintained between each invocation.
-At the start of each
-.PN ProtocolSetup ,
-auth_datalen is zero,
-*auth_state_ptr is NULL,
-and the function should initialize its state and set
-this pointer. In subsequent invocations of the callback, the pointer
-should be used to get at any state previously stored by the callback.
-.LP
-If needed, the network ID of the client accepting the
-.PN ProtocolSetup
-can be obtained by calling the
-.PN IceConnectionString
-function.
-.LP
-The auth_data pointer may point to a volatile block of memory.
-If the data must be kept beyond this invocation of the callback, be sure
-to make a copy of it.
-.LP
-ICElib will be responsible for transmitting and freeing the reply_data_ret and
-error_string_ret pointers with
-.PN free .
-.LP
-The
-.PN IcePaAuthProc
-should return one of four values:
-.IP \(bu 5
-.PN IcePaAuthContinue
-\- continue (or start) authentication.
-.IP \(bu 5
-.PN IcePaAuthAccepted
-\- authentication accepted.
-.IP \(bu 5
-.PN IcePaAuthRejected
-\- authentication rejected.
-.IP \(bu 5
-.PN IcePaAuthFailed
-\- authentication failed.
-.NH 1
-ICE Connections
-.XS
-\*(SN ICE Connections
-.XE
-.LP
-In order for two clients to establish an ICE connection, one client has
-to be waiting for connections, and the other client has to initiate the
-connection.
-Most clients will initiate connections, so we discuss that first.
-.NH 2
-Opening an ICE Connection
-.XS
-\*(SN Opening an ICE Connection
-.XE
-.LP
-To open an ICE connection with another client (that is, waiting
-for connections), use
-.PN IceOpenConnection .
-.sM
-.FD 0
-IceConn IceOpenConnection\^(\^\fInetwork_ids_list\fP, \fIcontext\fP\^, \fImust_authenticate\fP\^, \fImajor_opcode_check\fP\^,
-.br
- \fIerror_length\fP\^, \fIerror_string_ret\fP\^)
-.br
- char *\fInetwork_ids_list\fP\^;
-.br
- IcePointer \fIcontext\fP\^;
-.br
- Bool \fImust_authenticate\fP\^;
-.br
- int \fImajor_opcode_check\fP\^;
-.br
- int \fIerror_length\fP\^;
-.br
- char *\fIerror_string_ret\fP\^;
-.FN
-.IP \fInetwork_ids_list\fP 1i
-Specifies the network ID(s) of the other client.
-.IP \fIcontext\fP 1i
-A pointer to an opaque object or NULL. Used to determine if an
-ICE connection can be shared (see below).
-.IP \fImust_authenticate\fP 1i
-If
-.PN True ,
-the other client may not bypass authentication.
-.IP \fImajor_opcode_check\fP 1i
-Used to force a new ICE connection to be created (see below).
-.IP \fIerror_length\fP 1i
-Length of the error_string_ret argument passed in.
-.IP \fIerror_string_ret\fP 1i
-Returns a null-terminated error message, if any.
-The error_string_ret argument points to user supplied memory.
-No more than error_length bytes
-are used.
-.LP
-.eM
-.PN IceOpenConnection
-returns an opaque ICE connection object if it succeeds;
-otherwise, it returns NULL.
-.LP
-The network_ids_list argument contains a list of network IDs separated by commas.
-An attempt will be made to use the first network ID. If that fails,
-an attempt will be made using the second network ID, and so on.
-Each network ID has the following format:
-.TS
-lw(0.25i) lw(2.5i) lw(1i).
- tcp/<hostname>:<portnumber> or
- decnet/<hostname>::<objname> or
- local/<hostname>:<path>
-.TE
-.LP
-Most protocol libraries will have some sort of open function that should
-internally make a call into
-.PN IceOpenConnection .
-When
-.PN IceOpenConnection
-is called, it may be possible to use a previously opened ICE connection (if
-the target client is the same). However, there are cases in which shared
-ICE connections are not desired.
-.LP
-The context argument is used to determine if an ICE connection can
-be shared.
-If context is NULL,
-then the caller is always willing to share the connection.
-If context is not NULL,
-then the caller is not willing to use a previously opened ICE connection
-that has a different non-NULL context associated with it.
-.LP
-In addition, if major_opcode_check contains a nonzero major opcode value,
-a previously created ICE connection will be used only if the major opcode
-is not active on the connection. This can be used to force multiple ICE
-connections between two clients for the same protocol.
-.LP
-Any authentication requirements are handled internally by the ICE library.
-The method by which the authentication data is obtained
-is implementation-dependent.\(dg
-.FS \(dg
-The X Consortium's ICElib implementation uses an \&.ICEauthority file (see
-Appendix A).
-.FE
-.LP
-After
-.PN IceOpenConnection
-is called, the client is ready to send a
-.PN ProtocolSetup
-(provided that
-.PN IceRegisterForProtocolSetup
-was called) or receive a
-.PN ProtocolSetup
-(provided that
-.PN IceRegisterForProtocolReply
-was called).
-.NH 2
-Listening for ICE Connections
-.XS
-\*(SN Listening for ICE Connections
-.XE
-.LP
-Clients wishing to accept ICE connections must first call
-.PN IceListenForConnections
-or
-.PN IceListenForWellKnownConnections
-so that they can listen for connections. A list of opaque "listen" objects are
-returned, one for each type of transport method that is available
-(for example, Unix Domain, TCP, DECnet, and so on).
-.LP
-Normally clients will let ICElib allocate an available name in each
-transport and return listen objects. Such a client will then use
-.PN IceComposeNetworkIdList
-to extract the chosen names and make them
-available to other clients for opening the connection. In certain
-cases it may be necessary for a client to listen for connections
-on pre-arranged transport object names. Such a client may use
-.PN IceListenForWellKnownConnections
-to specify the names for the listen objects.
-.sM
-.FD 0
-Status IceListenForConnections\^(\^\fIcount_ret\fP, \fIlisten_objs_ret\fP\^, \fIerror_length\fP\^, \fIerror_string_ret\fP\^)
-.br
- int *\fIcount_ret\fP\^;
-.br
- IceListenObj **\fIlisten_objs_ret\fP\^;
-.br
- int \fIerror_length\fP\^;
-.br
- char *\fIerror_string_ret\fP\^;
-.FN
-.IP \fIcount_ret\fP 1i
-Returns the number of listen objects created.
-.IP \fIlisten_objs_ret\fP 1i
-Returns a list of pointers to opaque listen objects.
-.IP \fIerror_length\fP 1i
-The length of the error_string_ret argument passed in.
-.IP \fIerror_string_ret\fP 1i
-Returns a null-terminated error message, if any.
-The error_string_ret points to user supplied memory.
-No more than error_length bytes are used.
-.LP
-.eM
-The return value of
-.PN IceListenForConnections
-is zero for failure and a positive value for success.
-.sp
-.sM
-.FD 0
-Status IceListenForWellKnownConnections\^(\^\fIport_id\fP, \fIcount_ret\fP, \fIlisten_objs_ret\fP\^, \fIerror_length\fP\^, \fIerror_string_ret\fP\^)
-.br
- char *\fIport_id\fP\^;
-.br
- int *\fIcount_ret\fP\^;
-.br
- IceListenObj **\fIlisten_objs_ret\fP\^;
-.br
- int \fIerror_length\fP\^;
-.br
- char *\fIerror_string_ret\fP\^;
-.FN
-.IP \fIport_id\fP 1i
-Specifies the port identification for the address(es)
-to be opened. The value must not contain the slash
-(\^``/''\^) or comma (\^``,''\^) character;
-these are reserved for future use.
-.IP \fIcount_ret\fP 1i
-Returns the number of listen objects created.
-.IP \fIlisten_objs_ret\fP 1i
-Returns a list of pointers to opaque listen objects.
-.IP \fIerror_length\fP 1i
-The length of the error_string_ret argument passed in.
-.IP \fIerror_string_ret\fP 1i
-Returns a null-terminated error message, if any.
-The error_string_ret points to user supplied memory.
-No more than error_length bytes are used.
-.LP
-.eM
-.PN IceListenForWellKnownConnections
-constructs a list of network IDs
-by prepending each known transport to port_id and then attempts to
-create listen objects for the result. Port_id is the portnumber,
-objname, or path portion of the ICE network ID. If a listen object for
-a particular network ID cannot be created the network ID is ignored.
-If no listen objects are created
-.PN IceListenForWellKnownConnections
-returns failure.
-.LP
-The return value of
-.PN IceListenForWellKnownConnections
-is zero for failure and a positive value for success.
-.sp
-.LP
-To close and free the listen objects, use
-.PN IceFreeListenObjs .
-.LP
-.sM
-.FD 0
-void IceFreeListenObjs\^(\^\fIcount\fP, \fIlisten_objs\fP\^)
-.br
- int \fIcount\fP\^;
-.br
- IceListenObj *\fIlisten_objs\fP\^;
-.FN
-.IP \fIcount\fP 1i
-The number of listen objects.
-.IP \fIlisten_objs\fP 1i
-The listen objects.
-.LP
-.eM
-.LP
-To detect a new connection on a listen object, use
-.PN select
-on the descriptor associated with the listen object.
-.sp
-.LP
-To obtain the descriptor, use
-.PN IceGetListenConnectionNumber .
-.LP
-.sM
-.FD 0
-int IceGetListenConnectionNumber\^(\^\fIlisten_obj\fP\^)
-.br
- IceListenObj \fIlisten_obj\fP\^;
-.FN
-.IP \fIlisten_obj\fP 1i
-The listen object.
-.LP
-.eM
-.LP
-To obtain the network ID string associated with a listen object, use
-.PN IceGetListenConnectionString .
-.sM
-.FD 0
-char *IceGetListenConnectionString\^(\^\fIlisten_obj\fP\^)
-.br
- IceListenObj \fIlisten_obj\fP\^;
-.FN
-.IP \fIlisten_obj\fP 1i
-The listen object.
-.LP
-.eM
-.LP
-A network ID has the following format:
-.TS
-lw(0.25i) lw(2.5i) lw(1i).
- tcp/<hostname>:<portnumber> or
- decnet/<hostname>::<objname> or
- local/<hostname>:<path>
-.TE
-.LP
-To compose a string containing a list of network IDs separated by commas
-(the format recognized by
-.PN IceOpenConnection ),
-use
-.PN IceComposeNetworkIdList .
-.LP
-.sM
-.FD 0
-char *IceComposeNetworkIdList\^(\^\fIcount\fP, \fIlisten_objs\fP\^)
-.br
- int \fIcount\fP\^;
-.br
- IceListenObj *\fIlisten_objs\fP\^;
-.FN
-.IP \fIcount\fP 1i
-The number of listen objects.
-.IP \fIlisten_objs\fP 1i
-The listen objects.
-.LP
-.eM
-.NH 2
-Host Based Authentication for ICE Connections
-.XS
-\*(SN Host Based Authentication for ICE Connections
-.XE
-.LP
-If authentication fails when a client attempts to open an
-ICE connection and the initiating client has not required authentication,
-a host based authentication procedure may be invoked to provide
-a last chance for the client to connect. Each listen object has such a
-callback associated with it, and this callback is set using the
-.PN IceSetHostBasedAuthProc
-function.
-.sM
-.FD 0
-void IceSetHostBasedAuthProc\^(\^\fIlisten_obj\fP, \fIhost_based_auth_proc\fP\^)
-.br
- IceListenObj \fIlisten_obj\fP\^;
-.br
- IceHostBasedAuthProc \fIhost_based_auth_proc\fP\^;
-.FN
-.IP \fIlisten_obj\fP 1i
-The listen object.
-.IP \fIhost_based_auth_proc\fP 1i
-The host based authentication procedure.
-.LP
-.eM
-By default, each listen object has no host based authentication procedure
-associated with it.
-Passing NULL for host_based_auth_proc turns off host based authentication
-if it was previously set.
-.LP
-.sM
-.FD 0
-typedef Bool (*IceHostBasedAuthProc) ();
-
-Bool HostBasedAuthProc\^(\^\fIhost_name\fP\^)
-.br
- char *\fIhost_name\fP\^;
-.FN
-.IP \fIhost_name\fP 1i
-The host name of the client that tried to open an ICE connection.
-.LP
-.eM
-The host_name argument is a string in the form \fIprotocol\fP\^/\^\fIhostname\fP,
-where \fIprotocol\fP\^ is one of {tcp, decnet, local}.
-.LP
-If
-.PN IceHostBasedAuthProc
-returns
-.PN True ,
-access will be granted, even though the original
-authentication failed. Note that authentication can effectively be
-disabled by registering an
-.PN IceHostBasedAuthProc ,
-which always returns
-.PN True .
-.LP
-Host based authentication is also allowed at
-.PN ProtocolSetup
-time.
-The callback is specified in the
-.PN IceRegisterForProtocolReply
-function (see section 6, ``Protocol Registration'').
-.NH 2
-Accepting ICE Connections
-.XS
-\*(SN Accepting ICE Connections
-.XE
-.LP
-After a connection attempt is detected on a listen object returned by
-.PN IceListenForConnections ,
-you should call
-.PN IceAcceptConnection .
-This returns a new opaque ICE connection object.
-.sM
-.FD 0
-IceConn IceAcceptConnection\^(\^\fIlisten_obj\fP, \fI\^status_ret\fP\^)
-.br
- IceListenObj \fIlisten_obj\fP\^;
-.br
- IceAcceptStatus *\fIstatus_ret\fP\^;
-.FN
-.IP \fIlisten_obj\fP 1i
-The listen object on which a new connection was detected.
-.IP \fIstatus_ret\fP 1i
-Return status information.
-.LP
-.eM
-The status_ret argument is set to one of the following values:
-.IP \(bu 5
-.PN IceAcceptSuccess
-\- the accept operation succeeded,
-and the function returns a new connection object.
-.IP \(bu 5
-.PN IceAcceptFailure
-\- the accept operation failed, and the function returns NULL.
-.IP \(bu 5
-.PN IceAcceptBadMalloc
-\- a memory allocation failed, and the function returns NULL.
-.LP
-In general, to detect new connections, you should call
-.PN select
-on the file descriptors associated with the listen objects.
-When a new connection is detected, the
-.PN IceAcceptConnection
-function should be called.
-.PN IceAcceptConnection
-may return a new ICE connection that is in a pending state. This is because
-before the connection can become valid, authentication may be necessary.
-Because the ICE library cannot block and wait for the connection to
-become valid (infinite blocking can occur if the connecting client
-does not act properly), the application must wait for the connection status
-to become valid.
-.LP
-The following pseudo-code demonstrates how connections are accepted:
-.if t .bp
-.LP
-.Ds 0
-.TA .5i 1i 1.5i 2i
-.ta .5i 1i 1.5i 2i
-new_ice_conn = IceAcceptConnection (listen_obj, &accept_status);
-if (accept_status != IceAcceptSuccess)
-{
- close the file descriptor and return
-}
-
-status = IceConnectionStatus (new_ice_conn);
-time_start = time_now;
-
-while (status == IceConnectPending)
-{
- select() on {new_ice_conn, all open connections}
-
- for (each ice_conn in the list of open connections)
- if (data ready on ice_conn)
- {
- status = IceProcessMessages (ice_conn, NULL, NULL);
- if (status == IceProcessMessagesIOError)
- IceCloseConnection (ice_conn);
- }
-
- if (data ready on new_ice_conn)
- {
- /*
- * IceProcessMessages is called until the connection
- * is non-pending. Doing so handles the connection
- * setup request and any authentication requirements.
- */
-
- IceProcessMessages (new_ice_conn, NULL, NULL);
- status = IceConnectionStatus (new_ice_conn);
- }
- else
- {
- if (time_now - time_start > MAX_WAIT_TIME)
- status = IceConnectRejected;
- }
-}
-
-if (status == IceConnectAccepted)
-{
- Add new_ice_conn to the list of open connections
-}
-else
-{
- IceCloseConnection (new_ice_conn);
-}
-.De
-.LP
-After
-.PN IceAcceptConnection
-is called and the connection has been
-validated, the client is ready to receive a
-.PN ProtocolSetup
-(provided
-that
-.PN IceRegisterForProtocolReply
-was called) or send a
-.PN ProtocolSetup
-(provided that
-.PN IceRegisterForProtocolSetup
-was called).
-.NH 2
-Closing ICE Connections
-.XS
-\*(SN Closing ICE Connections
-.XE
-.LP
-To close an ICE connection created with
-.PN IceOpenConnection
-or
-.PN IceAcceptConnection ,
-use
-.PN IceCloseConnection .
-.sM
-.FD 0
-IceCloseStatus IceCloseConnection\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-The ICE connection to close.
-.LP
-.eM
-To actually close an ICE connection, the following conditions
-must be met:
-.IP \(bu 5
-The \fIopen reference count\fP must have reached zero on this ICE connection.
-When
-.PN IceOpenConnection
-is called, it tries to use a previously opened
-ICE connection. If it is able to use an existing connection, it increments
-the open reference count on the connection by one.
-So, to close an ICE connection, each call to
-.PN IceOpenConnection
-must be matched with a call to
-.PN IceCloseConnection .
-The connection can be closed only
-on the last call to
-.PN IceCloseConnection .
-.IP \(bu 5
-The \fIactive protocol count\fP\^ must have reached zero. Each time a
-.PN ProtocolSetup
-succeeds on the connection, the active protocol count
-is incremented by one. When the client no longer expects to use the
-protocol on the connection, the
-.PN IceProtocolShutdown
-function should be called, which decrements the active protocol count
-by one (see section 8, ``Protocol Setup and Shutdown'').
-.IP \(bu 5
-If shutdown negotiation is enabled on the connection, the client on the other
-side of the ICE connection must agree to have the connection closed.
-.LP
-.PN IceCloseConnection
-returns one of the following values:
-.IP \(bu 5
-.PN IceClosedNow
-\- the ICE connection was closed at this time. The watch procedures were
-invoked and the connection was freed.
-.IP \(bu 5
-.PN IceClosedASAP
-\- an IO error had occurred on the connection, but
-.PN IceCloseConnection
-is being called within a nested
-.PN IceProcessMessages .
-The watch procedures have been invoked at this time, but the connection
-will be freed as soon as possible (when the nesting level reaches zero and
-.PN IceProcessMessages
-returns a status of
-.PN IceProcessMessagesConnectionClosed ).
-.IP \(bu 5
-.PN IceConnectionInUse
-\- the connection was not closed at this time, because it is being used by
-other active protocols.
-.IP \(bu 5
-.PN IceStartedShutdownNegotiation
-\- the connection was not closed at this time and shutdown negotiation started
-with the client on the other side of the ICE connection. When the connection
-is actually closed,
-.PN IceProcessMessages
-will return a status of
-.PN IceProcessMessagesConnectionClosed .
-.sp
-.LP
-When it is known that the client on the other side of the ICE connection
-has terminated the connection without initiating shutdown negotiation, the
-.PN IceSetShutdownNegotiation
-function should be called to turn off shutdown negotiation. This will prevent
-.PN IceCloseConnection
-from writing to a broken connection.
-.sM
-.FD 0
-void IceSetShutdownNegotiation\^(\^\fIice_conn\fP, \fInegotiate\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- Bool \fInegotiate\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fInegotiate\fP 1i
-If
-.PN False ,
-shutdown negotiating will be turned off.
-.LP
-.eM
-.LP
-To check the shutdown negotiation status of an ICE connection, use
-.PN IceCheckShutdownNegotiation .
-.sM
-.FD 0
-Bool IceCheckShutdownNegotiation\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.LP
-.eM
-.PN IceCheckShutdownNegotiation
-returns
-.PN True
-if shutdown negotiation will take place on the connection;
-otherwise, it returns
-.PN False .
-Negotiation is on by default for a connection. It
-can only be changed with the
-.PN IceSetShutdownNegotiation
-function.
-.NH 2
-Connection Watch Procedures
-.XS
-\*(SN Connection Watch Procedures
-.XE
-.LP
-To add a watch procedure that will be called
-each time ICElib opens a new connection via
-.PN IceOpenConnection
-or
-.PN IceAcceptConnection
-or closes a connection via
-.PN IceCloseConnection ,
-use
-.PN IceAddConnectionWatch .
-.sM
-.FD 0
-Status IceAddConnectionWatch\^(\^\fIwatch_proc\fP, \fIclient_data\fP\^)
-.br
- IceWatchProc \fIwatch_proc\fP\^;
-.br
- IcePointer \fIclient_data\fP\^;
-.FN
-.IP \fIwatch_proc\fP 1i
-The watch procedure to invoke when ICElib opens or
-closes a connection.
-.IP \fIclient_data\fP 1i
-This pointer will be passed to the watch procedure.
-.LP
-.eM
-The return value of
-.PN IceAddConnectionWatch
-is zero for failure, and a positive value for success.
-.LP
-Note that several calls to
-.PN IceOpenConnection
-might share the same ICE connection. In such a case, the watch procedure
-is only invoked when the connection is first created (after authentication
-succeeds). Similarly, because
-connections might be shared, the watch procedure is called only if
-.PN IceCloseConnection
-actually closes the connection (right before the IceConn is freed).
-.LP
-The watch procedures are very useful for applications that
-need to add a file descriptor to a select mask when a new connection
-is created and remove the file descriptor when the connection is destroyed.
-Because connections are shared, knowing when to add and remove the file
-descriptor from the select mask would be difficult without the watch
-procedures.
-.LP
-Multiple watch procedures may be registered with the ICE library.
-No assumptions should be made about their order of invocation.
-.LP
-If one or more ICE connections were already created by the ICE library at the
-time the watch procedure is registered, the watch procedure will instantly
-be invoked for each of these ICE connections (with the opening argument
-set to
-.PN True ).
-.LP
-The watch procedure is of type
-.PN IceWatchProc .
-.sM
-.FD 0
-typedef void (*IceWatchProc)();
-
-void WatchProc\^(\^\fIice_conn\fP, \fIclient_data\fP\^, \fIopening\fP\^, \fIwatch_data\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- IcePointer \fIclient_data\fP\^;
-.br
- Bool \fIopening\fP\^;
-.br
- IcePointer *\fIwatch_data\fP\^;
-.FN
-.IP \fIice_conn\fP\^ 1i
-The opened or closed ICE connection. Call
-.PN IceConnectionNumber
-to get the file descriptor associated with this connection.
-.IP \fIclient_data\fP\^ 1i
-Client data specified in the call to
-.PN IceAddConnectionWatch .
-.IP \fIopening\fP\^ 1i
-If
-.PN True ,
-the connection is being opened. If
-.PN False ,
-the connection is being closed.
-.IP \fIwatch_data\fP\^ 1i
-Can be used to save a pointer to client data.
-.LP
-.eM
-If opening is
-.PN True ,
-the client should set the *watch_data
-pointer to any data it may need to save until the connection is closed
-and the watch procedure is
-invoked again with opening set to
-.PN False .
-.sp
-.LP
-To remove a watch procedure, use
-.PN IceRemoveConnectionWatch .
-.sM
-.FD 0
-void IceRemoveConnectionWatch\^(\^\fIwatch_proc\fP, \fIclient_data\fP\^)
-.br
- IceWatchProc \fIwatch_proc\fP\^;
-.br
- IcePointer \fIclient_data\fP\^;
-.LP
-.FN
-.IP \fIwatch_proc\fP 1i
-The watch procedure that was passed to
-.PN IceAddConnectionWatch .
-.IP \fIclient_data\fP 1i
-The client_data pointer that was passed to
-.PN IceAddConnectionWatch .
-.LP
-.eM
-.NH 1
-Protocol Setup and Shutdown
-.XS
-\*(SN Protocol Setup and Shutdown
-.XE
-.LP
-To activate a protocol on a given ICE connection, use
-.PN IceProtocolSetup .
-.LP
-.sM
-.FD 0
-IceProtocolSetupStatus IceProtocolSetup\^(\^\fIice_conn\fP, \fImy_opcode\fP\^, \fIclient_data\fP\^, \fImust_authenticate\fP\^,
-.br
- \fImajor_version_ret\fP\^, \fIminor_version_ret\fP\^, \fIvendor_ret\fP\^, \fIrelease_ret\fP\^, \fIerror_length\fP\^, \fIerror_string_ret\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- int \fImy_opcode\fP\^;
-.br
- IcePointer \fIclient_data\fP\^;
-.br
- Bool \fImust_authenticate\fP\^;
-.br
- int *\fImajor_version_ret\fP\^;
-.br
- int *\fIminor_version_ret\fP\^;
-.br
- char **\fIvendor_ret\fP\^;
-.br
- char **\fIrelease_ret\fP\^;
-.br
- int \fIerror_length\fP\^;
-.br
- char *\fIerror_string_ret\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fImy_opcode\fP 1i
-The major opcode of the protocol to be set up, as returned by
-.PN IceRegisterForProtocolSetup .
-.IP \fIclient_data\fP 1i
-The client data stored in this pointer will be passed to the
-.PN IcePoProcessMsgProc
-callback.
-.IP \fImust_authenticate\fP 1i
-If
-.PN True ,
-the other client may not bypass authentication.
-.IP \fImajor_version_ret\fP 1i
-The major version of the protocol to be used is returned.
-.IP \fIminor_version_ret\fP 1i
-The minor version of the protocol to be used is returned.
-.IP \fIvendor_ret\fP 1i
-The vendor string specified by the protocol acceptor.
-.IP \fIrelease_ret\fP 1i
-The release string specified by the protocol acceptor.
-.IP \fIerror_length\fP 1i
-Specifies the length of the error_string_ret argument passed in.
-.IP \fIerror_string_ret\fP 1i
-Returns a null-terminated error message, if any.
-The error_string_ret argument points to user supplied memory.
-No more than error_length bytes are used.
-.LP
-.eM
-The vendor_ret and release_ret strings should be freed with
-.PN free
-when no longer needed.
-.LP
-.PN IceProtocolSetup
-returns one of the following values:
-.IP \(bu 5
-.PN IceProtocolSetupSuccess
-\- the major_version_ret, minor_version_ret, vendor_ret, release_ret are set.
-.IP \(bu 5
-.PN IceProtocolSetupFailure
-or
-.PN IceProtocolSetupIOError
-\- check error_string_ret for failure reason.
-The major_version_ret, minor_version_ret, vendor_ret, release_ret are not set.
-.IP \(bu 5
-.PN IceProtocolAlreadyActive
-\- this protocol is already active on this connection.
-The major_version_ret, minor_version_ret, vendor_ret, release_ret are not set.
-.sp
-.LP
-To notify the ICE library when a given protocol
-will no longer be used on an ICE connection, use
-.PN IceProtocolShutdown .
-.LP
-.sM
-.FD 0
-Status IceProtocolShutdown\^(\^\fIice_conn\fP, \fImajor_opcode\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- int \fImajor_opcode\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fImajor_opcode\fP 1i
-The major opcode of the protocol to shut down.
-.LP
-.eM
-The return value of
-.PN IceProtocolShutdown
-is zero for failure and a positive value for success.
-.LP
-Failure will occur if the major opcode was never registered OR the protocol
-of the major opcode was never activated on the connection. By activated,
-we mean that a
-.PN ProtocolSetup
-succeeded on the connection.
-Note that ICE does not define how each sub-protocol triggers a
-protocol shutdown.
-.NH 1
-Processing Messages
-.XS
-\*(SN Processing Messages
-.XE
-.LP
-To process incoming messages on an ICE connection, use
-.PN IceProcessMessages .
-.sM
-.FD 0
-IceProcessMessagesStatus IceProcessMessages\^(\^\fIice_conn\fP, \fIreply_wait\fP\^, \fIreply_ready_ret\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- IceReplyWaitInfo *\fIreply_wait\fP\^;
-.br
- Bool *\fIreply_ready_ret\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fIreply_wait\fP 1i
-Indicates if a reply is being waited for.
-.IP \fIreply_ready_ret\fP 1i
-If set to
-.PN True
-on return, a reply is ready.
-.LP
-.eM
-.PN IceProcessMessages
-is used in two ways:
-.IP \(bu 5
-In the first, a client may
-generate a message and block by calling
-.PN IceProcessMessages
-repeatedly until it gets its reply.
-.IP \(bu 5
-In the second, a
-client calls
-.PN IceProcessMessages
-with reply_wait set to NULL in response to
-.PN select
-showing that there is data to read on the ICE connection.
-The ICE library may process zero or more complete messages.
-Note that messages that are not blocked for are always processed by
-invoking callbacks.
-.LP
-.PN IceReplyWaitInfo
-contains the major/minor opcodes and sequence number
-of the message for which a reply is being awaited. It also contains
-a pointer to the reply message to be filled in (the protocol library
-should cast this
-.PN IcePointer
-to the appropriate reply type). In most
-cases, the reply will have some fixed-size part, and the client waiting
-for the reply will have provided a pointer to a structure to hold
-this fixed-size data. If there is variable-length data, it would be
-expected that the
-.PN IcePoProcessMsgProc
-callback will have to allocate additional
-memory and store pointer(s) to that memory in the fixed-size
-structure. If the entire data is variable length (for example, a single
-variable-length string), then the client waiting for the reply would probably
-just pass a pointer to fixed-size space to hold a pointer, and the
-.PN IcePoProcessMsgProc
-callback would allocate the storage and store the pointer.
-It is the responsibility of the client receiving the reply to
-free up any memory allocated on its behalf.
-.LP
-.sM
-.Ds 0
-.TA .5i
-.ta .5i
-typedef struct {
- unsigned long sequence_of_request;
- int major_opcode_of_request;
- int minor_opcode_of_request;
- IcePointer reply;
-} IceReplyWaitInfo;
-.De
-.LP
-.eM
-If reply_wait is not NULL and
-.PN IceProcessMessages
-has a reply or error to return in response to this reply_wait
-(that is, no callback was generated), then the reply_ready_ret argument
-will be set to
-.PN True .
-.LP
-If reply_wait is NULL,
-then the caller may also pass NULL
-for reply_ready_ret and be guaranteed that no value will be stored
-in this pointer.
-.LP
-.PN IceProcessMessages
-returns one of the following values:
-.IP \(bu 5
-.PN IceProcessMessagesSuccess
-\- no error occurred.
-.IP \(bu 5
-.PN IceProcessMessagesIOError
-\- an IO error occurred,
-and the caller must explicitly close the connection by calling
-.PN IceCloseConnection .
-.IP \(bu 5
-.PN IceProcessMessagesConnectionClosed
-\- the ICE connection has been closed (closing of the connection was deferred
-because of shutdown negotiation, or because the
-.PN IceProcessMessages
-nesting level was not zero). Do not attempt
-to access the ICE connection at this point, since it has been freed.
-.NH 1
-Ping
-.XS
-\*(SN Ping
-.XE
-.LP
-To send a ``Ping'' message to the client on the other side of the
-ICE connection, use
-.PN IcePing .
-.sM
-.FD 0
-Status IcePing\^(\^\fIice_conn\fP, \fIping_reply_proc\fP\^, \fIclient_data\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- IcePingReplyProc \fIping_reply_proc\fP\^;
-.br
- IcePointer \fIclient_data\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fIping_reply_proc\fP 1i
-The callback to invoke when the Ping reply arrives.
-.IP \fIclient_data\fP 1i
-This pointer will be passed to the
-.PN IcePingReplyProc
-callback.
-.LP
-.eM
-.PN IcePing
-returns zero for failure and a positive value for success.
-.LP
-When
-.PN IceProcessMessages
-processes the Ping reply, it will invoke the
-.PN IcePingReplyProc
-callback.
-.sM
-.FD 0
-typedef void (*IcePingReplyProc)();
-
-void PingReplyProc\^(\^\fIice_conn\fP, \fIclient_data\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- IcePointer \fIclient_data\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-The ICE connection object.
-.IP \fIclient_data\fP 1i
-The client data specified in the call to
-.PN IcePing .
-.LP
-.eM
-.NH 1
-Using ICElib Informational Functions
-.XS
-\*(SN Using ICElib Informational Functions
-.XE
-.LP
-.sM
-.FD 0
-IceConnectStatus IceConnectionStatus\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.eM
-.PN IceConnectionStatus
-returns the status of an ICE connection. The possible return values are:
-.IP \(bu 5
-.PN IceConnectPending
-\- the connection is not valid yet (that is, authentication is taking place).
-This is only relevant to connections created by
-.PN IceAcceptConnection .
-.IP \(bu 5
-.PN IceConnectAccepted
-\- the connection has been accepted.
-This is only relevant to connections created by
-.PN IceAcceptConnection .
-.IP \(bu 5
-.PN IceConnectRejected
-\- the connection had been rejected (that is, authentication failed).
-This is only relevant to connections created by
-.PN IceAcceptConnection .
-.IP \(bu 5
-.PN IceConnectIOError
-\- an IO error has occurred on the connection.
-.LP
-.sM
-.FD 0
-char *IceVendor\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.eM
-.PN IceVendor
-returns the ICE library vendor identification
-for the other side of the connection.
-The string should be freed with a call to
-.PN free
-when no longer needed.
-.LP
-.sM
-.FD 0
-char *IceRelease\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.eM
-.PN IceRelease
-returns the release identification of the ICE library
-on the other side of the connection.
-The string should be freed with a call to
-.PN free
-when no longer needed.
-.LP
-.sM
-.FD 0
-int IceProtocolVersion\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.eM
-.PN IceProtocolVersion
-returns the major version of the ICE protocol on this connection.
-.LP
-.sM
-.FD 0
-int IceProtocolRevision\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.eM
-.PN IceProtocolRevision
-returns the minor version of the ICE protocol on this connection.
-.LP
-.sM
-.FD 0
-int IceConnectionNumber\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.eM
-.PN IceConnectionNumber
-returns the file descriptor of this ICE connection.
-.LP
-.sM
-.FD 0
-char *IceConnectionString\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.eM
-.PN IceConnectionString
-returns the network ID of the client that
-accepted this connection. The string should be freed with a call to
-.PN free
-when no longer needed.
-.LP
-.sM
-.FD 0
-unsigned long IceLastSentSequenceNumber\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.eM
-.PN IceLastSentSequenceNumber
-returns the sequence number of the last message sent on this ICE connection.
-.LP
-.sM
-.FD 0
-unsigned long IceLastReceivedSequenceNumber\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.eM
-.PN IceLastReceivedSequenceNumber
-returns the sequence number of the last message received on this
-ICE connection.
-.LP
-.sM
-.FD 0
-Bool IceSwapping\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.eM
-.PN IceSwapping
-returns
-.PN True
-if byte swapping is necessary when reading messages on the ICE connection.
-.LP
-.sM
-.FD 0
-IcePointer IceGetContext\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.eM
-.PN IceGetContext
-returns the context associated with a connection created by
-.PN IceOpenConnection .
-.NH 1
-ICE Messages
-.XS
-\*(SN ICE Messages
-.XE
-.LP
-All ICE messages have a standard 8-byte header. The ICElib macros that
-read and write messages rely on the following naming convention for message
-headers:
-.LP
-.Ds 0
-.TA .5i 1i
-.ta .5i 1i
- CARD8 major_opcode;
- CARD8 minor_opcode;
- CARD8 data[2];
- CARD32 length B32;
-.De
-.LP
-The 3rd and 4th bytes of the message header can be used as needed.
-The length field is specified in units of 8 bytes.
-.NH 2
-Sending ICE Messages
-.XS
-\*(SN Sending ICE Messages
-.XE
-.LP
-The ICE library maintains an output buffer used for generating messages.
-Protocol libraries layered on top of ICE may choose to batch messages
-together and flush the output buffer at appropriate times.
-.LP
-If an IO error has occurred on an ICE connection, all write operations
-will be ignored.
-For further information, see section 13, ``Error Handling.''
-.sp
-.LP
-To get the size of the ICE output buffer, use
-.PN IceGetOutBufSize .
-.sM
-.FD 0
-int IceGetOutBufSize\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.LP
-.eM
-.LP
-To flush the ICE output buffer, use
-.PN IceFlush .
-.sM
-.FD 0
-IceFlush\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.LP
-.eM
-Note that the output buffer may be implicitly flushed if there is insufficient
-space to generate a message.
-.LP
-The following macros can be used to generate ICE messages:
-.LP
-.sM
-.FD 0
-IceGetHeader\^(\^\fIice_conn\fP, \fImajor_opcode\fP\^, \fIminor_opcode\fP\^, \fIheader_size\fP\^, \fI<C_data_type>\fP\^, \fIpmsg\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- int \fImajor_opcode\fP\^;
-.br
- int \fIminor_opcode\fP\^;
-.br
- int \fIheader_size\fP\^;
-.br
- <C_data_type> *\fIpmsg\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fImajor_opcode\fP 1i
-The major opcode of the message.
-.IP \fIminor_opcode\fP 1i
-The minor opcode of the message.
-.IP \fIheader_size\fP 1i
-The size of the message header (in bytes).
-.IP \fI<C_data_type>\fP 1i
-The actual C data type of the message header.
-.IP \fIpmsg\fP 1i
-The message header pointer. After this macro is called, the
-library can store data in the message header.
-.LP
-.eM
-.PN IceGetHeader
-is used to set up a message header on an ICE connection.
-It sets the major and minor opcodes of the message, and initializes
-the message's length to the length of the header. If additional
-variable length data follows, the message's length field should be
-updated.
-.sp
-.LP
-.sM
-.FD 0
-IceGetHeaderExtra\^(\^\fIice_conn\fP, \fImajor_opcode\fP\^, \fIminor_opcode\fP\^, \fIheader_size\fP\^, \fIextra\fP\^, \fI<C_data_type>\fP\^, \fIpmsg\fP\^, \fIpdata\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- int \fImajor_opcode\fP\^;
-.br
- int \fIminor_opcode\fP\^;
-.br
- int \fIheader_size\fP\^;
-.br
- int \fIextra\fP\^;
-.br
- <C_data_type> *\fIpmsg\fP\^;
-.br
- char *\fIpdata\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fImajor_opcode\fP 1i
-The major opcode of the message.
-.IP \fIminor_opcode\fP 1i
-The minor opcode of the message.
-.IP \fIheader_size\fP 1i
-The size of the message header (in bytes).
-.IP \fIextra\fP 1i
-The size of the extra data beyond the header (in 8-byte units).
-.IP \fI<C_data_type>\fP 1i
-The actual C data type of the message header.
-.IP \fIpmsg\fP 1i
-The message header pointer. After this macro is called, the
-library can store data in the message header.
-.IP \fIpdata\fP 1i
-Returns a pointer to the ICE output buffer that points
-immediately after the message header. The variable length
-data should be stored here. If there was not enough room
-in the ICE output buffer, pdata is set to NULL.
-.LP
-.eM
-.PN IceGetHeaderExtra
-is used to generate a message with a fixed (and relatively small) amount
-of variable length data. The complete message must fit in the ICE output
-buffer.
-.sp
-.LP
-.sM
-.FD 0
-IceSimpleMessage\^(\^\fIice_conn\fP, \fImajor_opcode\fP\^, \fIminor_opcode\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- int \fImajor_opcode\fP\^;
-.br
- int \fIminor_opcode\fP\^;
-.FN
-.br
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fImajor_opcode\fP 1i
-The major opcode of the message.
-.IP \fIminor_opcode\fP 1i
-The minor opcode of the message.
-.LP
-.eM
-.PN IceSimpleMessage
-is used to generate a message that is identical
-in size to the ICE header message, and has no additional data.
-.sp
-.LP
-.sM
-.FD 0
-IceErrorHeader\^(\^\fIice_conn\fP, \fIoffending_major_opcode\fP\^, \fIoffending_minor_opcode\fP\^, \fIoffending_sequence_num\fP\^,
-.br
- \fIseverity\fP\^, \fIerror_class\fP\^, \fIdata_length\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- int \fIoffending_major_opcode\fP\^;
-.br
- int \fIoffending_minor_opcode\fP\^;
-.br
- int \fIoffending_sequence_num\fP\^;
-.br
- int \fIseverity\fP\^;
-.br
- int \fIerror_class\fP\^;
-.br
- int \fIdata_length\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fIoffending_major_opcode\fP 1i
-The major opcode of the protocol in which an error was detected.
-.IP \fIoffending_minor_opcode\fP 1i
-The minor opcode of the protocol in which an error was detected.
-.IP \fIoffending_sequence_num\fP 1i
-The sequence number of the message that caused the error.
-.IP \fIseverity\fP 1i
-.PN IceCanContinue ,
-.PN IceFatalToProtocol ,
-or
-.PN IceFatalToConnection .
-.IP \fIerror_class\fP 1i
-The error class.
-.IP \fIdata_length\fP 1i
-Length of data (in 8-byte units) to be written after the header.
-.LP
-.eM
-.PN IceErrorHeader
-sets up an error message header.
-.LP
-Note that the two clients connected by ICE may be using different
-major opcodes for a given protocol. The offending_major_opcode passed
-to this macro is the major opcode of the protocol for the client
-sending the error message.
-.LP
-Generic errors, which are common to all protocols, have classes
-in the range 0x8000..0xFFFF.
-See the \fIInter-Client Exchange Protocol\fP\^ standard for more details.
-.TS
-lw(1i) lw(1i).
-T{
-.PN IceBadMinor
-T} T{
-0x8000
-T}
-.sp 4p
-T{
-.PN IceBadState
-T} T{
-0x8001
-T}
-.sp 4p
-T{
-.PN IceBadLength
-T} T{
-0x8002
-T}
-.sp 4p
-T{
-.PN IceBadValue
-T} T{
-0x8003
-T}
-.TE
-.LP
-Per-protocol errors have classes in the range 0x0000-0x7fff.
-.sp
-.LP
-To write data to an ICE connection, use the
-.PN IceWriteData
-macro. If the data fits into the ICE output buffer, it is copied there.
-Otherwise, the ICE output buffer is flushed and the data is directly sent.
-.LP
-This macro is used in conjunction with
-.PN IceGetHeader
-and
-.PN IceErrorHeader .
-.sp
-.LP
-.sM
-.FD 0
-IceWriteData\^(\^\fIice_conn\fP, \fIbytes\fP\^, \fIdata\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- int \fIbytes\fP\^;
-.br
- char *\fIdata\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fIbytes\fP 1i
-The number of bytes to write.
-.IP \fIdata\fP 1i
-The data to write.
-.LP
-.eM
-.sp
-To write data as 16-bit quantities, use
-.PN IceWriteData16 .
-.sM
-.FD 0
-IceWriteData16\^(\^\fIice_conn\fP, \fIbytes\fP\^, \fIdata\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- int \fIbytes\fP\^;
-.br
- short *\fIdata\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fIbytes\fP 1i
-The number of bytes to write.
-.IP \fIdata\fP 1i
-The data to write.
-.LP
-.eM
-.sp
-To write data as 32-bit quantities, use
-.PN IceWriteData32 .
-.sM
-.FD 0
-IceWriteData32\^(\^\fIice_conn\fP, \fIbytes\fP\^, \fIdata\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- int \fIbytes\fP\^;
-.br
- long *\fIdata\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fIbytes\fP 1i
-The number of bytes to write.
-.IP \fIdata\fP 1i
-The data to write.
-.LP
-.eM
-.sp
-To bypass copying data to the ICE output buffer, use
-.PN IceSendData
-to directly send data over the network connection. If necessary, the
-ICE output buffer is first flushed.
-.sM
-.FD 0
-IceSendData\^(\^\fIice_conn\fP, \fIbytes\fP\^, \fI(char *) data\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- int \fIbytes\fP\^;
-.br
- char *\fIdata\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fIbytes\fP 1i
-The number of bytes to send.
-.IP \fIdata\fP 1i
-The data to send.
-.LP
-.eM
-.sp
-To force 32-bit or 64-bit alignment, use
-.PN IceWritePad .
-A maximum of 7 pad bytes can be specified.
-.sM
-.FD 0
-IceWritePad\^(\^\fIice_conn\fP, \fIbytes\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- int \fIbytes\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fIbytes\fP 1i
-The number of pad bytes.
-.LP
-.eM
-.NH 2
-Reading ICE Messages
-.XS
-\*(SN Reading ICE Messages
-.XE
-.LP
-The ICE library maintains an input buffer used for reading messages.
-If the ICE library chooses to perform nonblocking reads (this is
-implementation-dependent), then for every read operation that it makes,
-zero or more complete messages may be read into the input buffer. As
-a result, for all of the macros described in this section that read
-messages, an actual read operation will occur on the connection only if
-the data is not already present in the input buffer.
-.sp
-.LP
-To get the size of the ICE input buffer, use
-.PN IceGetInBufSize .
-.sM
-.FD 0
-int IceGetInBufSize\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.LP
-.eM
-.LP
-When reading messages, care must be taken to check for IO errors. If
-any IO error occurs in reading any part of a message, the message should
-be thrown out. After using any of the macros described below for reading
-messages, the
-.PN IceValidIO
-macro can be used to check if an IO error occurred on the
-connection. After an IO error has occurred on an ICE connection, all
-read operations will be ignored.
-For further information, see section 13, ``Error Handling.''
-.sp
-.LP
-.sM
-.FD 0
-Bool IceValidIO\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.LP
-.eM
-.LP
-The following macros can be used to read ICE messages.
-.sM
-.FD 0
-IceReadSimpleMessage\^(\^\fIice_conn\fP, \fI<C_data_type>\fP\^, \fIpmsg\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- <C_data_type> *\fIpmsg\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fI<C_data_type>\fP 1i
-The actual C data type of the message header.
-.IP \fIpmsg\fP 1i
-This pointer is set to the message header.
-.LP
-.eM
-.PN IceReadSimpleMessage
-is used for messages that are identical in size to the 8-byte ICE header, but
-use the spare 2 bytes in the header to encode additional data. Note that the
-ICE library always reads in these first 8 bytes, so it can obtain the major
-opcode of the message.
-.PN IceReadSimpleMessage
-simply returns a pointer to these 8 bytes; it does not actually read any data
-into the input buffer.
-.LP
-For a message with variable length data, there are two ways of reading
-the message. One method involves reading the complete message in one
-pass using
-.PN IceReadCompleteMessage .
-The second method involves reading the message header (note that this may
-be larger than the 8-byte ICE header), then reading
-the variable length data in chunks (see
-.PN IceReadMessageHeader
-and
-.PN IceReadData ).
-.sp
-.LP
-.sM
-.FD 0
-IceReadCompleteMessage\^(\^\fIice_conn\fP, \fIheader_size\fP\^, \fI<C_data_type>\fP\^, \fIpmsg\fP\^, \fIpdata\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- int \fIheader_size\fP\^;
-.br
- <C_data_type> *\fIpmsg\fP\^;
-.br
- char *\fIpdata\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fIheader_size\fP 1i
-The size of the message header (in bytes).
-.IP \fI<C_data_type>\fP 1i
-The actual C data type of the message header.
-.IP \fIpmsg\fP 1i
-This pointer is set to the message header.
-.IP \fIpdata\fP 1i
-This pointer is set to the variable length data of the message.
-.LP
-.eM
-If the ICE input buffer has sufficient space,
-.PN IceReadCompleteMessage
-will read the complete message into the
-ICE input buffer. Otherwise, a buffer will be allocated to hold the
-variable length data. After the call, the pdata argument should
-be checked against NULL to make sure that there was sufficient memory
-to allocate the buffer.
-.sp
-.LP
-After calling
-.PN IceReadCompleteMessage
-and processing the message,
-.PN IceDisposeCompleteMessage
-should be called.
-.LP
-.sM
-.FD 0
-IceDisposeCompleteMessage\^(\^\fIice_conn\fP, \fIpdata\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- char *\fIpdata\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fIpdata\fP 1i
-The pointer to the variable length data returned in
-.PN IceReadCompleteMessage .
-.LP
-.eM
-If a buffer had to be allocated to hold the variable length data (because
-it did not fit in the ICE input buffer), it is freed here by ICElib.
-.sp
-.LP
-.sM
-.FD 0
-IceReadMessageHeader\^(\^\fIice_conn\fP, \fIheader_size\fP\^, \fI<C_data_type>\fP\^, \fIpmsg\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- int \fIheader_size\fP\^;
-.br
- <C_data_type> *\fIpmsg\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fIheader_size\fP 1i
-The size of the message header (in bytes).
-.IP \fI<C_data_type>\fP 1i
-The actual C data type of the message header.
-.IP \fIpmsg\fP 1i
-This pointer is set to the message header.
-.LP
-.eM
-.PN IceReadMessageHeader
-reads just the message header. The rest
-of the data should be read with the
-.PN IceReadData
-family of macros. This method of reading a message should be used when the
-variable length data must be read in chunks.
-.sp
-.LP
-To read data directly into a user supplied buffer, use
-.PN IceReadData .
-.sM
-.FD 0
-IceReadData\^(\^\fIice_conn\fP, \fIbytes\fP\^, \fIpdata\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- int \fIbytes\fP\^;
-.br
- char *\fIpdata\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fIbytes\fP 1i
-The number of bytes to read.
-.IP \fIpdata\fP 1i
-The data is read into this user supplied buffer.
-.LP
-.eM
-.sp
-To read data as 16-bit quantities, use
-.PN IceReadData16 .
-.sM
-.FD 0
-IceReadData16\^(\^\fIice_conn\fP, \fIswap\fP\^, \fIbytes\fP\^, \fIpdata\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- Bool \fIswap\fP\^;
-.br
- int \fIbytes\fP\^;
-.br
- short *\fIpdata\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fIswap\fP 1i
-If
-.PN True,
-the values will be byte swapped.
-.IP \fIbytes\fP 1i
-The number of bytes to read.
-.IP \fIpdata\fP 1i
-The data is read into this user supplied buffer.
-.LP
-.eM
-.sp
-To read data as 32-bit quantities, use
-.PN IceReadData32 .
-.sM
-.FD 0
-IceReadData32\^(\^\fIice_conn\fP, \fIswap\fP\^, \fIbytes\fP\^, \fIpdata\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- Bool \fIswap\fP\^;
-.br
- int \fIbytes\fP\^;
-.br
- long *\fIpdata\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fIswap\fP 1i
-If
-.PN True,
-the values will be byte swapped.
-.IP \fIbytes\fP 1i
-The number of bytes to read.
-.IP \fIpdata\fP 1i
-The data is read into this user supplied buffer.
-.LP
-.eM
-.sp
-To force 32-bit or 64-bit alignment, use
-.PN IceReadPad .
-A maximum of 7 pad bytes can be specified.
-.sM
-.FD 0
-IceReadPad\^(\^\fIice_conn\fP, \fIbytes\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- int \fIbytes\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fIbytes\fP 1i
-The number of pad bytes.
-.LP
-.eM
-.NH 1
-Error Handling
-.XS
-\*(SN Error Handling
-.XE
-.LP
-There are two default error handlers in ICElib:
-.IP \(bu 5
-One to handle typically fatal conditions (for example,
-a connection dying because a machine crashed)
-.IP \(bu 5
-One to handle ICE-specific protocol errors
-.LP
-These error handlers can be changed to user-supplied routines if you
-prefer your own error handling and can be changed as often as you like.
-.sp
-.LP
-To set the ICE error handler, use
-.PN IceSetErrorHandler .
-.sM
-.FD 0
-IceErrorHandler IceSetErrorHandler\^(\^\fIhandler\fP\^)
-.br
- IceErrorHandler \fIhandler\fP\^;
-.FN
-.IP \fIhandler\fP 1i
-The ICE error handler.
-You should pass NULL to restore the default handler.
-.LP
-.eM
-.PN IceSetErrorHandler
-returns the previous error handler.
-.LP
-The ICE error handler is invoked when an unexpected ICE protocol
-error (major opcode 0) is encountered. The action of the default
-handler is to print an explanatory message to
-.PN stderr
-and if the severity is fatal, call
-.PN exit
-with a nonzero value. If exiting
-is undesirable, the application should register its own error handler.
-.LP
-Note that errors in other protocol
-domains should be handled by their respective libraries (these libraries
-should have their own error handlers).
-.LP
-An ICE error handler has the type of
-.PN IceErrorHandler .
-.sM
-.FD 0
-typedef void (*IceErrorHandler)();
-
-void ErrorHandler\^(\^\fIice_conn\fP, \fIswap\fP\^, \fIoffending_minor_opcode\fP\^, \fIoffending_sequence_num\fP\^, \fIerror_class\fP\^,
-.br
- \fIseverity\fP\^, \fIvalues\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- Bool \fIswap\fP\^;
-.br
- int \fIoffending_minor_opcode\fP\^;
-.br
- unsigned long \fIoffending_sequence_num\fP\^;
-.br
- int \fIerror_class\fP\^;
-.br
- int \fIseverity\fP\^;
-.br
- IcePointer \fIvalues\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-The ICE connection object.
-.IP \fIswap\fP 1i
-A flag that indicates if the values need byte swapping.
-.IP \fIoffending_minor_opcode\fP 1i
-The ICE minor opcode of the offending message.
-.IP \fIoffending_sequence_num\fP 1i
-The sequence number of the offending message.
-.IP \fIerror_class\fP 1i
-The error class of the offending message.
-.IP \fIseverity\fP 1i
-.PN IceCanContinue ,
-.PN IceFatalToProtocol ,
-or
-.PN IceFatalToConnection .
-.IP \fIvalues\fP 1i
-Any additional error values specific to the minor opcode and class.
-.LP
-.eM
-The following error classes are defined at the ICE level:
-.LP
-.Ds 0
-.PN IceBadMinor
-.PN IceBadState
-.PN IceBadLength
-.PN IceBadValue
-.PN IceBadMajor
-.PN IceNoAuth
-.PN IceNoVersion
-.PN IceSetupFailed
-.PN IceAuthRejected
-.PN IceAuthFailed
-.PN IceProtocolDuplicate
-.PN IceMajorOpcodeDuplicate
-.PN IceUnknownProtocol
-.De
-.LP
-For further information, see
-the \fIInter-Client Exchange Protocol\fP\^ standard.
-.sp
-.LP
-To handle fatal I/O errors, use
-.PN IceSetIOErrorHandler .
-.LP
-.sM
-.FD 0
-IceIOErrorHandler IceSetIOErrorHandler\^(\^\fIhandler\fP\^)
-.br
- IceIOErrorHandler \fIhandler\fP\^;
-.FN
-.IP \fIhandler\fP 1i
-The I/O error handler.
-You should pass NULL to restore the default handler.
-.LP
-.eM
-.PN IceSetIOErrorHandler
-returns the previous IO error handler.
-.LP
-An ICE I/O error handler has the type of
-.PN IceIOErrorHandler .
-.LP
-.sM
-.FD 0
-typedef void (*IceIOErrorHandler)();
-
-void IOErrorHandler\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-The ICE connection object.
-.LP
-.eM
-There are two ways of handling IO errors in ICElib:
-.IP \(bu 5
-In the first, the IO error handler does whatever is necessary
-to respond to the IO error and then returns, but it does not call
-.PN IceCloseConnection .
-The ICE connection is given a ``bad IO'' status, and all future reads
-and writes to the connection are ignored. The next time
-.PN IceProcessMessages
-is called it will return a status of
-.PN IceProcessMessagesIOError .
-At that time, the application should call
-.PN IceCloseConnection .
-.IP \(bu 5
-In the second, the IO error handler does call
-.PN IceCloseConnection ,
-and then uses the
-.PN longjmp
-call to get back to the application's main event loop.
-The
-.PN setjmp
-and
-.PN longjmp
-calls may not work properly on all platforms,
-and special care must be taken to avoid memory leaks.
-Therefore, this second model is less desirable.
-.LP
-Before the application I/O error handler is invoked, protocol libraries
-that were interested in being notified of I/O errors will have their
-.PN IceIOErrorProc
-handlers invoked. This handler is set up in the protocol registration
-functions (see
-.PN IceRegisterForProtocolSetup
-and
-.PN IceRegisterForProtocolReply )
-and could be used to clean up
-state specific to the protocol.
-.sp
-.LP
-.sM
-typedef void (*IceIOErrorProc)();
-.LP
-.FD 0
-void IOErrorProc\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-The ICE connection object.
-.LP
-.eM
-Note that every
-.PN IceIOErrorProc
-callback must return. This is required
-because each active protocol must be notified of the broken connection,
-and the application IO error handler must be invoked afterwards.
-.NH 1
-Multi-Threading Support
-.XS
-\*(SN Multi-Threading Support
-.XE
-.LP
-To declare that multiple threads in an application will be using the ICE
-library, use
-.PN IceInitThreads .
-.LP
-.sM
-.FD 0
-Status IceInitThreads\^()
-.FN
-.LP
-.eM
-The
-.PN IceInitThreads
-function must be the first ICElib function a
-multi-threaded program calls. It must complete before any other ICElib
-call is made.
-.PN IceInitThreads
-returns a nonzero status if and only if it was able
-to initialize the threads package successfully.
-It is safe to call
-.PN IceInitThreads
-more than once, although the threads package will only be initialized once.
-.LP
-Protocol libraries layered on top of ICElib will have to lock critical
-sections of code that access an ICE connection (for example, when
-generating messages). Two calls, which are generally implemented as
-macros, are provided:
-.sM
-.FD 0
-IceLockConn\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
-.sp
-IceUnlockConn\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-The ICE connection.
-.LP
-.eM
-.sp
-To keep an ICE connection locked across several ICElib calls, applications use
-.PN IceAppLockConn
-and
-.PN IceAppUnlockConn .
-.sM
-.FD 0
-void IceAppLockConn\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-The ICE connection to lock.
-.LP
-.eM
-The
-.PN IceAppLockConn
-function completely locks out other threads using the connection
-until
-.PN IceAppUnlockConn
-is called. Other threads attempting to use ICElib
-calls on the connection will block.
-If the program has not previously called
-.PN IceInitThreads ,
-.PN IceAppLockConn
-has no effect.
-.LP
-.sM
-.FD 0
-void IceAppUnlockConn\^(\^\fIice_conn\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-The ICE connection to unlock.
-.LP
-.eM
-The
-.PN IceAppUnlockConn
-function allows other threads to complete ICElib
-calls on the connection that were blocked by a previous call to
-.PN IceAppLockConn
-from this thread. If the program has not previously called
-.PN IceInitThreads ,
-.PN IceAppUnlockConn
-has no effect.
-.NH 1
-Miscellaneous Functions
-.XS
-\*(SN Miscellaneous Functions
-.XE
-.LP
-To allocate scratch space (for example, when generating
-messages with variable data), use
-.PN IceAllocScratch .
-Each ICE connection has one scratch space associated with it.
-The scratch space starts off as empty and grows as needed.
-The contents of the scratch space is not guaranteed to be preserved
-after any ICElib function is called.
-.LP
-.sM
-.FD 0
-char *IceAllocScratch\^(\^\fIice_conn\fP, \fIsize\fP\^)
-.br
- IceConn \fIice_conn\fP\^;
-.br
- unsigned long \fIsize\fP\^;
-.FN
-.IP \fIice_conn\fP 1i
-A valid ICE connection object.
-.IP \fIsize\fP 1i
-The number of bytes required.
-.LP
-.eM
-Note that the memory returned by
-.PN IceAllocScratch
-should not be freed by the caller.
-The ICE library will free the memory when the ICE connection is closed.
-.NH 1
-Acknowledgements
-.XS
-\*(SN Acknowledgements
-.XE
-.LP
-Thanks to Bob Scheifler for his thoughtful input on the design
-of the ICE library. Thanks also to Jordan Brown, Larry Cable, Donna Converse,
-Clive Feather, Stephen Gildea, Vania Joloboff, Kaleb Keithley,
-Stuart Marks, Hiro Miyamoto, Ralph Swick, Jim VanGilder, and Mike Wexler.
-.bp
-.XS
-Appendix A \- Authentication Utility Functions
-.XE
-.ce 10
-.sp 5
-\s+2\fBAppendix A\fP\s-2
-.sp
-\s+1\fBAuthentication Utility Functions\fP\s-1
-.ce 0
-.sp
-.LP
-As discussed in this document, the means by which authentication data
-is obtained by the ICE library (for
-.PN ConnectionSetup
-messages or
-.PN ProtocolSetup
-messages) is implementation-dependent.\(dg
-.FS \(dg
-The X Consortium's ICElib implementation assumes the presence of an
-ICE authority file.
-.FE
-.LP
-This appendix describes some utility functions that manipulate an
-ICE authority file. The authority file can be used to pass authentication
-data between clients.
-.LP
-The basic operations on the \&.ICEauthority file are:
-.IP \(bu 5
-Get file name
-.IP \(bu 5
-Lock
-.IP \(bu 5
-Unlock
-.IP \(bu 5
-Read entry
-.IP \(bu 5
-Write entry
-.IP \(bu 5
-Search for entry
-.LP
-These are fairly low-level operations, and it is expected that a program,
-like "iceauth", would
-exist to add, remove, and display entries in the file.
-.LP
-In order to use these utility functions, the
-.Pn < X11/ICE/ICEutil.h >
-header file must be included.
-.LP
-An entry in the \&.ICEauthority file is defined by the following data structure:
-.LP
-.sM
-.Ds 0
-.TA .5i
-.ta .5i
-typedef struct {
- char *protocol_name;
- unsigned short protocol_data_length;
- char *protocol_data;
- char *network_id;
- char *auth_name;
- unsigned short auth_data_length;
- char *auth_data;
-} IceAuthFileEntry;
-.De
-.LP
-.eM
-The protocol_name member is either ``ICE'' for connection setup authentication
-or the subprotocol name, such as ``XSMP''. For each entry, protocol specific
-data can be specified in the protocol_data member. This can be used
-to search for old entries that need to be removed from the file.
-.LP
-The network_id member is the network ID of the client accepting authentication
-(for example, the network ID of a session manager).
-A network ID has the following form:
-.TS
-lw(0.25i) lw(2.5i) lw(1i).
- tcp/<hostname>:<portnumber> or
- decnet/<hostname>::<objname> or
- local/<hostname>:<path>
-.TE
-.LP
-The auth_name member is the name of the authentication method.
-The auth_data member is the actual authentication data,
-and the auth_data_length member is the number of bytes in the data.
-.sp
-.LP
-To obtain the default authorization file name, use
-.PN IceAuthFileName .
-.sM
-.FD 0
-char *IceAuthFileName\^()
-.FN
-.LP
-.eM
-If the ICEAUTHORITY environment variable if set, this value is returned.
-Otherwise, the default authorization file name is $HOME/\&.ICEauthority.
-This name is statically allocated and should not be freed.
-.LP
-To synchronously update the authorization file, the file must
-be locked with a call to
-.PN IceLockAuthFile .
-This function takes advantage of the fact that the
-.PN link
-system call will fail if the name of the new link already exists.
-.sM
-.FD 0
-int IceLockAuthFile\^(\^\fIfile_name\fP, \fIretries\fP\^, \fItimeout\fP\^, \fIdead\fP\^)
-.br
- char *\fIfile_name\fP\^;
-.br
- int \fIretries\fP\^;
-.br
- int \fItimeout\fP\^;
-.br
- long \fIdead\fP\^;
-.FN
-.IP \fIfile_name\fP 1i
-The authorization file to lock.
-.IP \fIretries\fP 1i
-The number of retries.
-.IP \fItimeout\fP 1i
-The number of seconds before each retry.
-.IP \fIdead\fP 1i
-If a lock already exists that is the specified dead seconds old,
-it is broken.
-A value of zero is used to unconditionally break an old lock.
-.LP
-.eM
-One of three values is returned:
-.IP \(bu 5
-.PN IceAuthLockSuccess
-\- the lock succeeded.
-.IP \(bu 5
-.PN IceAuthLockError
-\- a system error occurred, and
-.PN errno
-may prove useful.
-.IP \(bu 5
-.PN IceAuthLockTimeout
-\- the specified number of retries failed.
-.LP
-.sp
-To unlock an authorization file, use
-.PN IceUnlockAuthFile .
-.sM
-.FD 0
-void IceUnlockAuthFile\^(\^\fIfile_name\fP\^)
-.br
- char *\fIfile_name\fP\^;
-.FN
-.IP \fIfile_name\fP 1i
-The authorization file to unlock.
-.LP
-.eM
-.LP
-To read the next entry in an authorization file, use
-.PN IceReadAuthFileEntry .
-.sM
-.FD 0
-IceAuthFileEntry *IceReadAuthFileEntry\^(\^\fIauth_file\fP\^)
-.br
- FILE *\fIauth_file\fP\^;
-.FN
-.IP \fIauth_file\fP 1i
-The authorization file.
-.LP
-.eM
-Note that it is the responsibility of the application to open the file
-for reading before calling this function. If an error is encountered,
-or there are no more entries to read, NULL is returned.
-.LP
-Entries should be free with a call to
-.PN IceFreeAuthFileEntry .
-.LP
-.sp
-To write an entry in an authorization file, use
-.PN IceWriteAuthFileEntry .
-.sM
-.FD 0
-Status IceWriteAuthFileEntry\^(\^\fIauth_file\fP, \fIentry\fP\^)
-.br
- FILE *\fIauth_file\fP\^;
-.br
- IceAuthFileEntry *\fIentry\fP\^;
-.FN
-.IP \fIauth_file\fP 1i
-The authorization file.
-.IP \fIentry\fP 1i
-The entry to write.
-.LP
-.eM
-Note that it is the responsibility of the application to open the file
-for writing before calling this function. The function returns a nonzero
-status if the operation was successful.
-.LP
-.sp
-To search the default authorization file for an entry that matches a given
-protocol_name/network_id/auth_name tuple, use
-.PN IceGetAuthFileEntry .
-.sM
-.FD 0
-IceAuthFileEntry *IceGetAuthFileEntry\^(\^\fIprotocol_name\fP, \fInetwork_id\fP\^, \fIauth_name\fP\^)
-.br
- char *\fIprotocol_name\fP\^;
-.br
- char *\fInetwork_id\fP\^;
-.br
- char *\fIauth_name\fP\^;
-.FN
-.IP \fIprotocol_name\fP 1i
-The name of the protocol to search on.
-.IP \fInetwork_id\fP 1i
-The network ID to search on.
-.IP \fIauth_name\fP 1i
-The authentication method to search on.
-.LP
-.eM
-If
-.PN IceGetAuthFileEntry
-fails to find such an entry, NULL is returned.
-.LP
-.sp
-To free an entry returned by
-.PN IceReadAuthFileEntry
-or
-.PN IceGetAuthFileEntry ,
-use
-.PN IceFreeAuthFileEntry .
-.sM
-.FD 0
-void IceFreeAuthFileEntry\^(\^\fIentry\fP\^)
-.br
- IceAuthFileEntry *\fIentry\fP\^;
-.FN
-.IP \fIentry\fP 1i
-The entry to free.
-.LP
-.eM
-.bp
-.XS
-Appendix B \- MIT-MAGIC-COOKIE-1 Authentication
-.XE
-.ce 10
-.sp 5
-\s+2\fBAppendix B\fP\s-2
-.sp
-\s+1\fBMIT-MAGIC-COOKIE-1 Authentication\fP\s-1
-.ce 0
-.sp
-.LP
-The X Consortium's ICElib implementation supports a simple
-MIT-MAGIC-COOKIE-1 authentication scheme using the authority file utilities
-described in Appendix A.
-.LP
-In this model, an application, such as a session manager, obtains a
-magic cookie by calling
-.PN IceGenerateMagicCookie ,
-and then stores it in the user's local \&.ICEauthority file
-so that local clients can connect. In order to allow remote clients to
-connect, some remote execution mechanism should be used to store the
-magic cookie in the user's \&.ICEauthority file on a remote machine.
-.LP
-In addition to storing the magic cookie in the \&.ICEauthority file, the
-application needs to call the
-.PN IceSetPaAuthData
-function in order to store the magic cookie in memory. When it comes time
-for the MIT-MAGIC-COOKIE-1 authentication procedure to accept or reject the
-connection, it will compare the magic cookie presented by the requestor to
-the magic cookie in memory.
-.LP
-.sM
-.FD 0
-char *IceGenerateMagicCookie\^(\^\fIlength\fP\^)
-.br
- int \fIlength\fP\^;
-.FN
-.IP \fIlength\fP 1i
-The desired length of the magic cookie.
-.LP
-.eM
-.LP
-The magic cookie returned will be null-terminated. If memory can not be
-allocated for the magic cookie, the function will return NULL.
-Otherwise, the magic cookie should be freed with a call to
-.PN free .
-.LP
-.sp
-To store the authentication data in memory, use
-.PN IceSetPaAuthData .
-Currently, this function is only used for MIT-MAGIC-COOKIE-1
-authentication, but it may be used for additional authentication
-methods in the future.
-.sM
-.FD 0
-void IceSetPaAuthData\^(\^\fInum_entries\fP, \fIentries\fP\^)
-.br
- int \fInum_entries\fP\^;
-.br
- IceAuthDataEntry *\fIentries\fP\^;
-.FN
-.IP \fInum_entries\fP 1i
-The number of authentication data entries.
-.IP \fIentries\fP 1i
-The list of authentication data entries.
-.LP
-.eM
-Each entry has associated with it a protocol name
-(for example, ``ICE'' for ICE connection setup authentication,
-``XSMP'' for session management authentication), a network ID for the
-``accepting'' client, an authentication name (for example, MIT-MAGIC-COOKIE-1),
-and authentication data. The ICE library
-will merge these entries with previously set entries, based on the
-(protocol_name, network_id, auth_name) tuple.
-.LP
-.sM
-.Ds 0
-.TA .5i
-.ta .5i
-typedef struct {
- char *protocol_name;
- char *network_id;
- char *auth_name;
- unsigned short auth_data_length;
- char *auth_data;
-} IceAuthDataEntry;
-.De
-.LP
-.eM
-.EH ''''
-.OH ''''
-.YZ 3
diff --git a/doc/ICElib.xml b/doc/ICElib.xml
new file mode 100644
index 0000000..27f3f0d
--- /dev/null
+++ b/doc/ICElib.xml
@@ -0,0 +1,4588 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+<!DOCTYPE book PUBLIC "-//OASIS//DTD DocBook XML V4.1.2//EN"
+ "http://www.oasis-open.org/docbook/xml/4.1.2/docbookx.dtd">
+
+
+
+<book id="icelib">
+
+<bookinfo>
+ <title>Inter-Client Exchange Library</title>
+ <subtitle>X Consortium Standard</subtitle>
+ <releaseinfo>X Version 11, Release 6.4</releaseinfo>
+ <authorgroup>
+ <author>
+ <firstname>Ralph</firstname><surname>Mor</surname>
+ <affiliation><orgname>X Consortium</orgname></affiliation>
+ </author>
+ </authorgroup>
+ <corpname>X Consortium Standard</corpname>
+ <copyright><year>1993</year><holder>X Consortium</holder></copyright>
+ <copyright><year>1994</year><holder>X Consortium</holder></copyright>
+ <copyright><year>1996</year><holder>X Consortium</holder></copyright>
+ <revhistory><revision><revnumber>1.0</revnumber><date></date></revision></revhistory>
+
+<legalnotice>
+<para>
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction,
+including without limitation the rights to use, copy, modify, merge,
+publish, distribute, sublicense, and/or sell copies of the Software, and
+to permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+</para>
+
+<para>The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+</para>
+
+<para>
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+</para>
+
+<para>
+Except as contained in this notice, the name of the X Consortium shall not be
+used in advertising or otherwise to promote the sale, use or other dealings
+in this Software without prior written authorization from the X Consortium.
+</para>
+
+</legalnotice>
+</bookinfo>
+
+<chapter id='overview_of_ice'>
+<title>Overview of ICE</title>
+
+<para>
+There are numerous possible inter-client protocols, with many similarities
+and common needs - authentication, version negotiation, byte
+order negotiation, and so on.
+The Inter-Client Exchange (ICE) protocol is intended to provide a framework
+for building such protocols, allowing them to make use of common negotiation
+mechanisms and to be multiplexed over a single transport connection.
+</para>
+</chapter>
+
+<chapter id='the_ice_library__c_language_interface_to'>
+<title>The ICE Library - C Language Interface to ICE</title>
+
+<para>
+A client that wishes to utilize ICE must first register the protocols it
+understands with the ICE library. Each protocol is dynamically assigned
+a major opcode ranging from 1-255 (two clients can use different
+major opcodes for the same protocol). The next step for the client is either
+to open a connection with another client or to wait for connections made
+by other clients. Authentication may be required. A client can both
+initiate connections with other clients and be
+waiting for clients to connect to itself (a nested session manager is an
+example). Once an ICE connection is established between the two clients, one
+of the clients needs to initiate a
+<function>ProtocolSetup</function>
+in order to
+"activate" a given protocol. Once the other client accepts the
+<function>ProtocolSetup</function>
+(once again, authentication may be required), the
+two clients are ready to start passing messages specific to that protocol to
+each other. Multiple protocols may be active on a single ICE connection.
+Clients are responsible for notifying the ICE library when a protocol is no
+longer active on an ICE connection, although ICE does not define how each
+subprotocol triggers a protocol shutdown.
+</para>
+
+<para>
+The ICE library utilizes callbacks to process incoming messages. Using
+callbacks allows
+<function>ProtocolSetup</function>
+messages and authentication to happen
+behind the scenes. An additional benefit is that messages never need
+to be buffered up by the library when the client blocks waiting for a
+particular message.
+</para>
+</chapter>
+
+<chapter id='intended_audience'>
+<title>Intended Audience</title>
+
+<para>This document is intended primarily for implementors of protocol libraries
+layered on top of ICE. Typically, applications that wish to utilize ICE
+will make calls into individual protocol libraries rather than directly
+make calls into the ICE library. However, some applications will have to
+make some initial calls into the ICE library in order to accept ICE
+connections (for example, a session manager accepting connections from
+clients). But in general, protocol libraries should be designed to hide
+the inner details of ICE from applications.</para>
+</chapter>
+
+<chapter id='header_files_and_library_name'>
+<title>Header Files and Library Name</title>
+
+
+<para>The header file
+&lt;<symbol role='Pn'>X11/ICE/ICElib.h</symbol>&gt;
+defines all of the ICElib data structures and function prototypes.
+<function>ICElib.h</function>
+includes the header file
+&lt;<symbol role='Pn'>X11/ICE/ICE.h</symbol>&gt;,
+which defines all of the ICElib constants.
+Protocol libraries that need to read and write messages should include
+the header file
+&lt;<symbol role='Pn'>X11/ICE/ICEmsg.h</symbol>&gt;.</para>
+
+<para>Applications should link against ICElib using -lICE.</para>
+</chapter>
+
+<chapter id='note_on_prefixes'>
+<title>Note on Prefixes</title>
+
+
+<para>The following name prefixes are used in the library to distinguish between
+a client that initiates a
+<function>ProtocolSetup</function>
+and a client that
+responds with a
+<function>ProtocolReply</function></para>
+
+<itemizedlist>
+ <listitem>
+<para><function>IcePo</function>
+- Ice Protocol Originator</para>
+ </listitem>
+ <listitem>
+<para><function>IcePa</function>
+- Ice Protocol Acceptor</para>
+ </listitem>
+</itemizedlist>
+</chapter>
+
+<chapter id='protocol_registration'>
+<title>Protocol Registration</title>
+
+<para>
+In order for two clients to exchange messages for a given protocol, each
+side must register the protocol with the ICE library. The purpose of
+registration is for each side to obtain a major opcode for the protocol
+and to provide callbacks for processing messages and handling authentication.
+There are two separate registration functions:
+</para>
+
+<itemizedlist>
+ <listitem>
+ <para>
+One to handle the side that does a
+<function>ProtocolSetup</function>
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+One to handle the side that responds with a
+<function>ProtocolReply</function>
+ </para>
+ </listitem>
+</itemizedlist>
+
+<para>
+It is recommended that protocol registration occur before the two clients
+establish an ICE connection. If protocol registration occurs after an
+ICE connection is created, there can be a brief interval of time in which a
+<function>ProtocolSetup</function>
+is received, but the protocol is not registered.
+If it is not possible to register a protocol before the creation of an
+ICE connection, proper precautions should be taken to avoid the above race
+condition.
+</para>
+
+
+<para>
+The <function>IceRegisterForProtocolSetup</function>
+function should be called for the client that initiates a
+<function>ProtocolSetup</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>int <function>IceRegisterForProtocolSetup</function></funcdef>
+ <paramdef>char<parameter> *protocol_name</parameter></paramdef>
+ <paramdef>char<parameter> *vendor</parameter></paramdef>
+ <paramdef>char<parameter> *release</parameter></paramdef>
+ <paramdef>int<parameter> *version_count</parameter></paramdef>
+ <paramdef>int<parameter> *version_count</parameter></paramdef>
+ <paramdef>IcePoVersionRec<parameter> *version_recs</parameter></paramdef>
+ <paramdef>int<parameter> auth_names</parameter></paramdef>
+ <paramdef>char<parameter> **auth_names</parameter></paramdef>
+ <paramdef>IcePoAuthProc<parameter> *auth_procs</parameter></paramdef>
+ <paramdef>IceIOErrorProc<parameter> *io_error_proc</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>protocol_name</emphasis></term>
+ <listitem>
+ <para>
+A string specifying the name of the protocol to register.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>vendor</emphasis></term>
+ <listitem>
+ <para>A vendor string with semantics specified by the protocol.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>release</emphasis></term>
+ <listitem>
+ <para>A release string with semantics specified by the protocol.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>version_count</emphasis></term>
+ <listitem>
+ <para>The number of different versions of the protocol supported.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>version_recs</emphasis></term>
+ <listitem>
+ <para>List of versions and associated callbacks.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>auth_count</emphasis></term>
+ <listitem>
+ <para>The number of authentication methods supported.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>auth_names</emphasis></term>
+ <listitem>
+ <para>The list of authentication methods supported.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>auth_procs</emphasis></term>
+ <listitem>
+ <para>
+The list of authentication callbacks, one for each authentication method.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>io_error_proc</emphasis></term>
+ <listitem>
+ <para>IO error handler, or NULL.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>
+<function>IceRegisterForProtocolSetup</function> returns the major
+opcode reserved or -1 if an error occurred. In order to actually activate
+the protocol, the <function>IceProtocolSetup</function>
+function needs to be called with this major opcode. Once the protocol is
+activated, all messages for the protocol should be sent using this major
+opcode.
+</para>
+
+<para>
+A protocol library may support multiple versions of the same protocol.
+The version_recs argument specifies a list of supported versions of the
+protocol, which are prioritized in decreasing order of preference.
+Each version record consists of a major and minor version of the protocol
+as well as a callback to be used for processing incoming messages.
+</para>
+
+
+<literallayout remap='Ds'>
+typedef struct {
+ int major_version;
+ int minor_version;
+ IcePoProcessMsgProc process_msg_proc;
+} IcePoVersionRec;
+</literallayout>
+
+<para>The
+<function>IcePoProcessMsgProc</function>
+callback is responsible for processing the set of messages that can be
+received by the client that initiated the
+<function>ProtocolSetup</function>
+For further information,
+see
+<link linkend="callbacks_for_processing_messages">
+<xref linkend="callbacks_for_processing_messages"></xref></link>.</para>
+
+<para>Authentication may be required before the protocol can become active.
+The protocol library must register the authentication methods that it
+supports with the ICE library.
+The auth_names and auth_procs arguments are a list of authentication names
+and callbacks that are prioritized in decreasing order of preference.
+For information on the
+<function>IcePoAuthProc</function>
+callback, see
+<link linkend="authentication_methods">
+<xref linkend="authentication_methods"></xref></link>
+</para>
+
+<para>The
+<function>IceIOErrorProc</function>
+callback is invoked if the ICE connection unexpectedly breaks.
+You should pass NULL for io_error_proc if not interested in being notified.
+For further information,
+<link linkend="error_handling">
+<xref linkend="error_handling"></xref></link>
+</para>
+
+
+<para>The
+<function>IceRegisterForProtocolReply</function>
+function should be called for the client that responds to a
+<function>ProtocolSetup</function>
+with a
+<function>ProtocolReply</function></para>
+
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>Bool <function>IceRegisterForProtocolReply</function></funcdef>
+ <paramdef>char<parameter> *host_name</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>protocol_name</emphasis></term>
+ <listitem><para>A string specifying the name of the protocol to register.</para></listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>vendor</emphasis></term>
+ <listitem>
+<para>A vendor string with semantics specified by the protocol.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>release</emphasis></term>
+ <listitem>
+<para>A release string with semantics specified by the protocol.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>version_count</emphasis></term>
+ <listitem>
+<para>The number of different versions of the protocol supported.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>version_recs</emphasis></term>
+ <listitem>
+<para>List of versions and associated callbacks.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>auth_count</emphasis></term>
+ <listitem>
+<para>The number of authentication methods supported.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>auth_names</emphasis></term>
+ <listitem>
+<para>The list of authentication methods supported.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>auth_procs</emphasis></term>
+ <listitem>
+<para>The list of authentication callbacks, one for each authentication method.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>host_based_auth_proc</emphasis></term>
+ <listitem>
+<para>Host based authentication callback.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>protocol_setup_proc</emphasis></term>
+ <listitem>
+<para>A callback to be invoked when authentication has succeeded for a
+<function>ProtocolSetup</function>
+but before the
+<function>ProtocolReply</function>
+is sent.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>protocol_activate_proc</emphasis></term>
+ <listitem>
+<para>A callback to be invoked after the
+<function>ProtocolReply</function>
+is sent.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>io_error_proc</emphasis></term>
+ <listitem>
+<para>IO error handler, or NULL.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para><function>IceRegisterForProtocolReply</function>
+returns the major opcode reserved or -1 if an error occurred. The major
+opcode should be used in all subsequent messages sent for this protocol.</para>
+
+<para>A protocol library may support multiple versions of the same protocol.
+The version_recs argument specifies a list of supported versions of the protocol,
+which are prioritized in decreasing order of preference.
+Each version record consists of a major and minor version of the protocol
+as well as a callback to be used for processing incoming messages.</para>
+
+
+<literallayout remap='Ds'>
+typedef struct {
+ int major_version;
+ int minor_version;
+ IcePaProcessMsgProc process_msg_proc;
+} IcePaVersionRec;
+</literallayout>
+
+
+<para>The
+<function>IcePaProcessMsgProc</function>
+callback is responsible for processing the set of messages that can be
+received by the client that accepted the
+<function>ProtocolSetup</function>
+For further information,
+see
+<link linkend="callbacks_for_processing_messages">
+<xref linkend="callbacks_for_processing_messages"></xref></link>
+</para>
+
+<para>Authentication may be required before the protocol can become active.
+The protocol library must register the authentication methods that it
+supports with the ICE library.
+The auth_names and auth_procs arguments are a list of authentication names
+and callbacks that are prioritized in decreasing order of preference.
+For information on the
+<function>IcePaAuthProc</function>,
+See
+<link linkend="authentication_methods">
+<xref linkend="authentication_methods"></xref></link>
+
+</para>
+
+<para>If authentication fails and the client attempting to initiate
+the
+<function>ProtocolSetup</function>
+has not required authentication, the
+<function>IceHostBasedAuthProc</function>
+callback is invoked with the host name of the originating client.
+If the callback returns
+<function>True</function>
+the
+<function>ProtocolSetup</function>
+will succeed, even though the original
+authentication failed.
+Note that authentication can effectively be disabled by registering an
+<function>IceHostBasedAuthProc</function>
+which always returns
+<function>True</function>
+If no host based
+authentication is allowed, you should pass NULL for host_based_auth_proc.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>Bool <function>HostBasedAuthProc</function></funcdef>
+ <paramdef>char<parameter> *host_name</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>protocol_name</emphasis></term>
+ <listitem><para>The host name of the client that sent the <function>ProtocolSetup</function></para></listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>The host_name argument is a string of the form <emphasis remap='I'>protocol</emphasis>/<emphasis remap='I'>hostname</emphasis>,
+where <emphasis remap='I'>protocol</emphasis> is one of {tcp, decnet, local}.</para>
+
+<para>Because
+<function>ProtocolSetup</function>
+messages and authentication happen behind the scenes
+via callbacks, the protocol library needs some way of being notified when the
+<function>ProtocolSetup</function>
+has completed.
+This occurs in two phases.
+In the first phase, the
+<function>IceProtocolSetupProc</function>
+callback is invoked after authentication has
+successfully completed but before the ICE library sends a
+<function>ProtocolReply</function>
+Any resources required for this protocol should be allocated at this time.
+If the
+<function>IceProtocolSetupProc</function>
+returns a successful status, the ICE library will
+send the
+<function>ProtocolReply</function>
+and then invoke the
+<function>IceProtocolActivateProc</function>
+callback. Otherwise, an error will be sent to the
+other client in response to the
+<function>ProtocolSetup</function></para>
+
+<para>The
+<function>IceProtocolActivateProc</function>
+is an optional callback and should be registered only if the protocol
+library intends to generate a message immediately following the
+<function>ProtocolReply</function>
+You should pass NULL for protocol_activate_proc if not interested
+in this callback.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>Status <function>ProtocolSetupProc</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> major_version</parameter></paramdef>
+ <paramdef>int<parameter> minor_version</parameter></paramdef>
+ <paramdef>char<parameter> *vendor</parameter></paramdef>
+ <paramdef>char<parameter> *release</parameter></paramdef>
+ <paramdef>IcePointer<parameter> *client_data_ret</parameter></paramdef>
+ <paramdef>char<parameter> **failure_reason_ret</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>protocol_name</emphasis></term>
+ <listitem>
+<para>The ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>major_version</emphasis></term>
+ <listitem>
+<para>The major version of the protocol.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>minor_version</emphasis></term>
+ <listitem>
+<para>The minor version of the protocol.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>vendor</emphasis></term>
+ <listitem>
+<para>The vendor string registered by the protocol originator.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>release</emphasis></term>
+ <listitem>
+<para>The release string registered by the protocol originator.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>client_data_ret</emphasis></term>
+ <listitem>
+<para>Client data to be set by callback.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>failure_reason_ret</emphasis></term>
+ <listitem>
+<para>Failure reason returned.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>The pointer stored in the client_data_ret argument will be passed
+to the
+<function>IcePaProcessMsgProc</function>
+callback whenever a message has arrived for this protocol on the
+ICE connection.</para>
+
+<para>The vendor and release strings should be freed with
+<function>free</function>
+when they are no longer needed.</para>
+
+<para>If a failure occurs, the
+<function>IceProtocolSetupProc</function>
+should return a zero status as well as allocate and return a failure
+reason string in failure_reason_ret.
+The ICE library will be responsible for freeing this memory.</para>
+
+<para>The
+<function>IceProtocolActivateProc</function>
+callback is defined as follows:</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void <function>ProtocolActivateProc</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>IcePointer<parameter> client_data</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem><para>The ICE connection object.</para></listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>client_data</emphasis></term>
+ <listitem>
+ <para>
+The client data set in the <function>IceProtocolSetupProc</function> callback.
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>The
+<function>IceIOErrorProc</function>
+callback is invoked if the ICE connection unexpectedly breaks.
+You should pass NULL for io_error_proc if not interested in being notified.
+For further information,
+see
+<link linkend="error_handling">
+<xref linkend="error_handling"></xref></link>
+</para>
+
+<sect1 id='callbacks_for_processing_messages'>
+<title>Callbacks for Processing Messages</title>
+
+<para>When an application detects that there is new data to read on an ICE
+connection (via
+<function>select</function>
+it calls the
+<function>IceProcessMessages</function>
+function
+<link linkend="processing_messages">
+<xref linkend="processing_messages"></xref></link>.
+
+When
+<function>IceProcessMessages</function>
+reads an ICE message header with a major opcode other than
+zero (reserved for the ICE protocol), it needs to call a function that will
+read the rest of the message, unpack it, and process it accordingly.</para>
+
+<para>If the message arrives at the client that initiated the
+<function>ProtocolSetup</function>
+the
+<function>IcePoProcessMsgProc</function>
+callback is invoked.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void <function>PoProcessMsgProc</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>IcePointer<parameter> client_data</parameter></paramdef>
+ <paramdef>int<parameter> opcode</parameter></paramdef>
+ <paramdef>unsigned long<parameter> length</parameter></paramdef>
+ <paramdef>Bool<parameter> swap</parameter></paramdef>
+ <paramdef>IceReplyWaitInfo<parameter> *reply_wait</parameter></paramdef>
+ <paramdef>Bool<parameter> *reply_ready_ret</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem><para>The ICE connection object.</para></listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>client_data</emphasis></term>
+ <listitem>
+<para>Client data associated with this protocol on the ICE connection.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>opcode</emphasis></term>
+ <listitem>
+<para>The minor opcode of the message.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>length</emphasis></term>
+ <listitem>
+<para>The length (in 8-byte units) of the message beyond the ICE header.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>swap</emphasis></term>
+ <listitem>
+<para>A flag that indicates if byte swapping is necessary.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>reply_wait</emphasis></term>
+ <listitem>
+<para>Indicates if the invoking client is waiting for a reply.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>reply_ready_ret</emphasis></term>
+ <listitem>
+<para>If set to
+<function>True</function>
+a reply is ready.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>If the message arrives at the client that accepted the
+<function>ProtocolSetup</function>
+the
+<function>IcePaProcessMsgProc</function>
+callback is invoked.</para>
+
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void <function>IcePaProcessMsgProc</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>IcePointer<parameter> client_data</parameter></paramdef>
+ <paramdef>int<parameter> opcode</parameter></paramdef>
+ <paramdef>unsigned long<parameter> length</parameter></paramdef>
+ <paramdef>Bool<parameter> swap</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem><para>The ICE connection object.</para></listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>client_data</emphasis></term>
+ <listitem>
+<para>Client data associated with this protocol on the ICE connection.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>opcode</emphasis></term>
+ <listitem>
+<para>The minor opcode of the message.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>length</emphasis></term>
+ <listitem>
+<para>The length (in 8-byte units) of the message beyond the ICE header.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>swap</emphasis></term>
+ <listitem>
+<para>A flag that indicates if byte swapping is necessary.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>In order to read the message, both of these callbacks should use the
+macros defined for this purpose (see
+<link linkend="reading_ice_messages">
+<xref linkend="reading_ice_messages"></xref></link>.).
+Note that byte swapping may be necessary.
+As a convenience, the length field in the ICE header will be swapped by ICElib
+if necessary.</para>
+
+<para>In both of these callbacks, the client_data argument is a pointer to client
+data that was registered at
+<function>ProtocolSetup</function>
+time.
+In the case of
+<function>IcePoProcessMsgProc</function>
+the client data was set in the call to
+<function>IceProtocolSetup</function>
+In the case of
+<function>IcePaProcessMsgProc</function>
+the client data was set in the
+<function>IceProtocolSetupProc</function>
+callback.</para>
+
+<para>The
+<function>IcePoProcessMsgProc</function>
+callback needs to check the reply_wait argument.
+If reply_wait is NULL ,
+the ICE library expects the function to
+pass the message to the client via a callback.
+For example, if this is a Session Management "Save Yourself" message,
+this function should notify the client of the "Save Yourself" via a callback.
+The details of how such a callback would be defined
+are implementation-dependent.</para>
+
+<para>However, if reply_wait is not NULL ,
+then the client is waiting for
+a reply or an error for a message it previously sent.
+The reply_wait is of type
+<function>IceReplyWaitInfo</function></para>
+
+
+<literallayout remap='Ds'>
+typedef struct {
+ unsigned long sequence_of_request;
+ int major_opcode_of_request;
+ int minor_opcode_of_request;
+ IcePointer reply;
+} IceReplyWaitInfo;
+</literallayout>
+
+<para><function>IceReplyWaitInfo</function>
+contains the major/minor opcodes and sequence number of
+the message for which a reply is being awaited.
+It also contains a pointer to the reply message to be filled in
+(the protocol library should cast this
+<function>IcePointer</function>
+to the appropriate reply type).
+In most cases, the reply will have some fixed-size part, and the client waiting
+for the reply will have provided a pointer to a structure to hold
+this fixed-size data. If there is variable-length data, it would be
+expected that the
+<function>IcePoProcessMsgProc</function>
+callback will have to allocate additional
+memory and store pointer(s) to that memory in the fixed-size
+structure. If the entire data is variable length (for example., a single
+variable-length string), then the client waiting for the reply would probably
+just pass a pointer to fixed-size space to hold a pointer, and the
+<function>IcePoProcessMsgProc</function>
+callback would allocate the storage and store the pointer.
+It is the responsibility of the client receiving the reply to
+free any memory allocated on its behalf.</para>
+
+<para>If reply_wait is not NULL and
+<function>IcePoProcessMsgProc</function>
+has a reply or error to return in response to this reply_wait
+(that is, no callback was generated), then the reply_ready_ret argument
+should be set to
+<function>True</function>
+Note that an error should only be returned
+if it corresponds to the reply being waited for. Otherwise, the
+<function>IcePoProcessMsgProc</function>
+should either handle the error internally or invoke an error handler
+for its library.</para>
+
+<para>If reply_wait is NULL,
+then care must be taken not to store any value in reply_ready_ret,
+because this pointer may also be NULL.</para>
+
+<para>The
+<function>IcePaProcessMsgProc</function>
+callback, on the other hand, should always pass
+the message to the client via a callback. For example, if this is a Session
+Management "Interact Request" message, this function should notify the
+client of the "Interact Request" via a callback.</para>
+
+<para>The reason the
+<function>IcePaProcessMsgProc</function>
+callback does not have a reply_wait, like
+<function>IcePoProcessMsgProc</function>
+does, is because a process that is acting as
+a server should never block for a reply (infinite blocking can
+occur if the connecting client does not act properly, denying access
+to other clients).</para>
+</sect1>
+
+<sect1 id='authentication_methods'>
+<title>Authentication Methods</title>
+
+<para>As already stated, a protocol library must register the authentication
+methods that it supports with the ICE library. For each authentication
+method, there are two callbacks that may be registered:</para>
+<itemizedlist>
+ <listitem>
+ <para>
+One to handle the side that initiates a <function>ProtocolSetup</function>
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+One to handle the side that accepts or rejects this request
+ </para>
+ </listitem>
+</itemizedlist>
+
+<para><function>IcePoAuthProc</function>
+is the callback invoked for the client that initiated the
+<function>ProtocolSetup</function>
+This callback must be able to respond
+to the initial "Authentication Required" message or subsequent
+"Authentication Next Phase" messages sent by the other client.</para>
+
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>IcePoAuthStatus <function>IcePoAuthStatus </function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>IcePointer<parameter> client_data</parameter></paramdef>
+ <paramdef>int<parameter> opcode</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem><para>The ICE connection object.</para></listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>auth_state_ptr</emphasis></term>
+ <listitem>
+<para>A pointer to state for use by the authentication callback procedure.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>clean_up</emphasis></term>
+ <listitem>
+<para>If
+<function>True</function>
+authentication is over, and the function
+should clean up any state it was maintaining. The
+last 6 arguments should be ignored.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>swap</emphasis></term>
+ <listitem>
+<para>If
+<function>True</function>
+the auth_data may have to be byte swapped
+(depending on its contents).</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>auth_datalen</emphasis></term>
+ <listitem>
+<para>The length (in bytes) of the authenticator data.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>auth_data</emphasis></term>
+ <listitem>
+<para>The data from the authenticator.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>reply_datalen_ret</emphasis></term>
+ <listitem>
+<para>The length (in bytes) of the reply data returned.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>reply_data_ret</emphasis></term>
+ <listitem>
+<para>The reply data returned.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>error_string_ret</emphasis></term>
+ <listitem>
+<para>If the authentication procedure encounters an error during
+authentication, it should allocate and return
+an error string.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>Authentication may require several phases, depending on the authentication
+method. As a result, the
+<function>IcePoAuthProc</function>
+may be called more than once when authenticating a client, and
+some state will have to be maintained between each invocation.
+At the start of each
+<function>ProtocolSetup</function>
+*auth_state_ptr is NULL,
+and the function should initialize its state and set
+this pointer. In subsequent invocations of the callback, the pointer
+should be used to get at any state previously stored by the callback.</para>
+
+<para>If needed, the network ID of the client accepting the
+<function>ProtocolSetup</function>
+can be obtained by calling the
+<function>IceConnectionString</function>
+function.</para>
+
+<para>ICElib will be responsible for freeing the reply_data_ret and
+error_string_ret pointers with
+<function>free</function></para>
+
+<para>The auth_data pointer may point to a volatile block of memory.
+If the data must be kept beyond this invocation of the callback, be sure
+to make a copy of it.</para>
+
+<para>The
+<function>IcePoAuthProc</function>
+should return one of four values:</para>
+<itemizedlist>
+ <listitem>
+<para><function>IcePoAuthHaveReply</function>
+- a reply is available.</para>
+ </listitem>
+ <listitem>
+<para><function>IcePoAuthRejected</function>
+- authentication rejected.</para>
+ </listitem>
+ <listitem>
+<para><function>IcePoAuthFailed</function>
+- authentication failed.</para>
+ </listitem>
+ <listitem>
+<para><function>IcePoAuthDoneCleanup</function>
+- done cleaning up.</para>
+ </listitem>
+</itemizedlist>
+
+<para><function>IcePaAuthProc</function>
+is the callback invoked for the client that received the
+<function>ProtocolSetup</function></para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>IcePoAuthStatus <function>PoAuthStatus </function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>IcePointer<parameter> *auth_state_ptr</parameter></paramdef>
+ <paramdef>Bool<parameter> swap</parameter></paramdef>
+ <paramdef>int<parameter> auth_datalen</parameter></paramdef>
+ <paramdef>IcePointer<parameter> auth_data</parameter></paramdef>
+ <paramdef>int<parameter> *reply_datalen_ret</parameter></paramdef>
+ <paramdef>IcePointer<parameter> *reply_data_ret</parameter></paramdef>
+ <paramdef>char<parameter> **error_string_ret</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem><para>The ICE connection object.</para></listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>auth_state_ptr</emphasis></term>
+ <listitem>
+<para>A pointer to state for use by the authentication callback procedure.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>swap</emphasis></term>
+ <listitem>
+<para>If
+<function>True</function>
+auth_data may have to be byte swapped
+(depending on its contents).</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>auth_datalen</emphasis></term>
+ <listitem>
+<para>The length (in bytes) of the protocol originator authentication data.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>auth_data</emphasis></term>
+ <listitem>
+<para>The authentication data from the protocol originator.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>reply_datalen_ret</emphasis></term>
+ <listitem>
+<para>The length of the authentication data returned.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>reply_data_ret</emphasis></term>
+ <listitem>
+<para>The authentication data returned.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>error_string_ret</emphasis></term>
+ <listitem>
+<para>If authentication is rejected or fails, an error
+string is returned.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>Authentication may require several phases, depending on the authentication
+method. As a result, the
+<function>IcePaAuthProc</function>
+may be called more than once when authenticating a client, and
+some state will have to be maintained between each invocation.
+At the start of each
+<function>ProtocolSetup</function>
+auth_datalen is zero,
+*auth_state_ptr is NULL,
+and the function should initialize its state and set
+this pointer. In subsequent invocations of the callback, the pointer
+should be used to get at any state previously stored by the callback.</para>
+
+<para>If needed, the network ID of the client accepting the
+<function>ProtocolSetup</function>
+can be obtained by calling the
+<function>IceConnectionString</function>
+function.</para>
+
+<para>The auth_data pointer may point to a volatile block of memory.
+If the data must be kept beyond this invocation of the callback, be sure
+to make a copy of it.</para>
+
+<para>ICElib will be responsible for transmitting and freeing the reply_data_ret and
+error_string_ret pointers with
+<function>free</function></para>
+
+<para>
+The <function>IcePaAuthProc</function> should return one of four values:
+</para>
+
+
+<itemizedlist>
+ <listitem>
+ <para>
+<function>IcePaAuthContinue</function> - continue (or start) authentication.
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+<function>IcePaAuthAccepted</function> - authentication accepted.
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+<function>IcePaAuthRejected</function> - authentication rejected.
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+<function>IcePaAuthFailed</function> - authentication failed.
+ </para>
+ </listitem>
+</itemizedlist>
+</sect1>
+
+</chapter>
+
+<chapter id='ice_connections'>
+<title>ICE Connections</title>
+
+<para>
+In order for two clients to establish an ICE connection, one client has to be
+waiting for connections, and the other client has to initiate the connection.
+Most clients will initiate connections, so we discuss that first.
+</para>
+
+<sect1 id='opening_an_ice_connection'>
+<title>Opening an ICE Connection</title>
+
+
+<para>
+To open an ICE connection with another client (that is, waiting
+for connections), use <function>IceOpenConnection</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>IceConn <function>IceOpenConnection</function></funcdef>
+ <paramdef>char<parameter> *network_ids_list</parameter></paramdef>
+ <paramdef>IcePointer<parameter> context</parameter></paramdef>
+ <paramdef>Bool<parameter> must_authenticate</parameter></paramdef>
+ <paramdef>int<parameter> major_opcode_check</parameter></paramdef>
+ <paramdef>int<parameter> error_length</parameter></paramdef>
+ <paramdef>char<parameter> *error_string_ret</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>network_ids_list</emphasis></term>
+ <listitem>
+ <para>
+Specifies the network ID(s) of the other client.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>context</emphasis></term>
+ <listitem>
+ <para>
+A pointer to an opaque object or NULL. Used to determine if an
+ICE connection can be shared (see below).
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>must_authenticate</emphasis></term>
+ <listitem>
+ <para>
+If <function>True</function> the other client may not bypass authentication.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>major_opcode_check</emphasis></term>
+ <listitem>
+ <para>
+Used to force a new ICE connection to be created (see below).
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>error_length</emphasis></term>
+ <listitem>
+ <para>Length of the error_string_ret argument passed in.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>error_string_ret</emphasis></term>
+ <listitem>
+ <para>
+Returns a null-terminated error message, if any. The error_string_ret
+argument points to user supplied memory. No more than error_length bytes
+are used.
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>
+<function>IceOpenConnection</function>
+returns an opaque ICE connection object if it succeeds;
+otherwise, it returns NULL.
+</para>
+
+<para>
+The network_ids_list argument contains a list of network IDs separated
+by commas. An attempt will be made to use the first network ID. If
+that fails, an attempt will be made using the second network ID, and so on.
+Each network ID has the following format:
+</para>
+
+<informaltable pgwide='0' frame='none'>
+ <tgroup cols='3' align='center'>
+ <colspec colname='c1'/>
+ <colspec colname='c2'/>
+ <colspec colname='c3'/>
+ <tbody>
+ <row>
+ <entry align='left'></entry>
+ <entry align='left'>tcp/&lt;hostname&gt;:&lt;portnumber&gt;</entry>
+ <entry align='left'>or</entry>
+ </row>
+ <row>
+ <entry align='left'></entry>
+ <entry align='left'>decnet/&lt;hostname&gt;::&lt;objname&gt;</entry>
+ <entry align='left'>or</entry>
+ </row>
+ <row>
+ <entry align='left'></entry>
+ <entry align='left'>local/&lt;hostname&gt;:&lt;path&gt;</entry>
+ <entry align='left'></entry>
+ </row>
+ </tbody>
+ </tgroup>
+</informaltable>
+
+
+<para>Most protocol libraries will have some sort of open function that should
+internally make a call into
+<function>IceOpenConnection</function>
+When
+<function>IceOpenConnection</function>
+is called, it may be possible to use a previously opened ICE connection (if
+the target client is the same). However, there are cases in which shared
+ICE connections are not desired.</para>
+
+<para>The context argument is used to determine if an ICE connection can
+be shared.
+If context is NULL,
+then the caller is always willing to share the connection.
+If context is not NULL,
+then the caller is not willing to use a previously opened ICE connection
+that has a different non-NULL context associated with it.</para>
+
+<para>In addition, if major_opcode_check contains a nonzero major opcode value,
+a previously created ICE connection will be used only if the major opcode
+is not active on the connection. This can be used to force multiple ICE
+connections between two clients for the same protocol.</para>
+
+<para>Any authentication requirements are handled internally by the ICE library.
+The method by which the authentication data is obtained
+is implementation-dependent.
+ <footnote remap='FS'>
+<para>The X Consortium's ICElib implementation uses an .ICEauthority file (see
+Appendix A).
+ </para></footnote> </para>
+
+<para>After
+<function>IceOpenConnection</function>
+is called, the client is ready to send a
+<function>ProtocolSetup</function>
+(provided that
+<function>IceRegisterForProtocolSetup</function>
+was called) or receive a
+<function>ProtocolSetup</function>
+(provided that
+<function>IceRegisterForProtocolReply</function>
+was called).</para>
+</sect1>
+
+<sect1 id='listening_for_ice_connections'>
+<title>Listening for ICE Connections</title>
+
+<para>Clients wishing to accept ICE connections must first call
+<function>IceListenForConnections</function>
+or
+<function>IceListenForWellKnownConnections</function>
+so that they can listen for connections. A list of opaque "listen" objects are
+returned, one for each type of transport method that is available
+(for example, Unix Domain, TCP, DECnet, and so on).</para>
+
+<para>Normally clients will let ICElib allocate an available name in each
+transport and return listen objects. Such a client will then use
+<function>IceComposeNetworkIdList</function>
+to extract the chosen names and make them
+available to other clients for opening the connection. In certain
+cases it may be necessary for a client to listen for connections
+on pre-arranged transport object names. Such a client may use
+<function>IceListenForWellKnownConnections</function>
+to specify the names for the listen objects.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>Status <function>IceListenForConnections</function></funcdef>
+ <paramdef>int<parameter> *count_ret</parameter></paramdef>
+ <paramdef>IceListenObj<parameter> **listen_objs_ret</parameter></paramdef>
+ <paramdef>int<parameter> error_length</parameter></paramdef>
+ <paramdef>char<parameter> *error_string_ret</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>count_ret</emphasis></term>
+ <listitem><para>Returns the number of listen objects created.</para></listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>listen_objs_ret</emphasis></term>
+ <listitem><para>Returns a list of pointers to opaque listen objects.</para></listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>error_length</emphasis></term>
+ <listitem>
+<para>The length of the error_string_ret argument passed in.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>error_string_ret</emphasis></term>
+ <listitem>
+<para>Returns a null-terminated error message, if any.
+The error_string_ret points to user supplied memory.
+No more than error_length bytes are used.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>The return value of
+<function>IceListenForConnections</function>
+is zero for failure and a positive value for success.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>Status <function>IceListenForWellKnownConnections</function></funcdef>
+ <paramdef>char<parameter> *port_id</parameter></paramdef>
+ <paramdef>int<parameter> *count_ret</parameter></paramdef>
+ <paramdef>IceListenObj<parameter> **listen_objs_ret</parameter></paramdef>
+ <paramdef>int<parameter> error_length</parameter></paramdef>
+ <paramdef>char<parameter> *error_string_ret</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>port_id</emphasis></term>
+ <listitem>
+ <para>
+Specifies the port identification for the address(es) to be opened. The
+value must not contain the slash ("/"> or comma (".") character; thse are
+reserved for future use.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>count_ret</emphasis></term>
+ <listitem>
+ <para>Returns the number of listen objects created.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>listen_objs_ret</emphasis></term>
+ <listitem>
+ <para>
+Returns a list of pointers to opaque listen objects.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>listen_objs_ret</emphasis></term>
+ <listitem>
+ <para>
+Returns a list of pointers to opaque listen objects.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>error_length</emphasis></term>
+ <listitem>
+ <para>
+The length of the error_string_ret argument passed in.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>error_string_ret</emphasis></term>
+ <listitem>
+ <para>
+Returns a null-terminated error message, if any. The error_string_ret
+points to user supplied memory. No more than error_length bytes are used.
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+<function>IceListenForWellKnownConnections</function> constructs a list
+of network IDs by prepending each known transport to port_id and then
+attempts to create listen objects for the result. Port_id is the portnumber,
+objname, or path portion of the ICE network ID. If a listen object for
+a particular network ID cannot be created the network ID is ignored.
+If no listen objects are created
+<function>IceListenForWellKnownConnections</function>
+returns failure.
+</para>
+
+<para>
+The return value of <function>IceListenForWellKnownConnections</function>
+is zero for failure and a positive value for success.
+</para>
+
+<para>
+To close and free the listen objects, use
+<function>IceFreeListenObjs</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void <function>IceFreeListenObjs</function></funcdef>
+ <paramdef>int<parameter> count</parameter></paramdef>
+ <paramdef>IceListenObj<parameter> *listen_objs</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>count</emphasis></term>
+ <listitem>
+ <para>The number of listen objects.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>listen_objs</emphasis></term>
+ <listitem>
+ <para>The listen objects.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>
+To detect a new connection on a listen object, use
+<function>select</function> on the descriptor associated with
+the listen object.
+</para>
+
+<para>
+To obtain the descriptor, use
+<function>IceGetListenConnectionNumber</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>int <function>IceGetListenConnectionNumber</function></funcdef>
+ <paramdef>IceListenObj<parameter> *listen_objs</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>listen_obj</emphasis></term>
+ <listitem>
+ <para>The listen objects.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+To obtain the network ID string associated with a listen object, use
+<function>IceGetListenConnectionString</function>
+</para>
+
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>char <function>IceGetListenConnectionString</function></funcdef>
+ <paramdef>IceListenObj<parameter> listen_obj</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>listen_obj</emphasis></term>
+ <listitem>
+ <para>The listen objects.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>A network ID has the following format:</para>
+
+<informaltable pgwide='0' frame='none'>
+ <tgroup cols='3' align='center'>
+ <colspec colname='c1'/>
+ <colspec colname='c2'/>
+ <colspec colname='c3'/>
+ <tbody>
+ <row>
+ <entry align='left'></entry>
+ <entry align='left'>tcp/&lt;hostname&gt;:&lt;portnumber&gt;</entry>
+ <entry align='left'>or</entry>
+ </row>
+ <row>
+ <entry align='left'></entry>
+ <entry align='left'>decnet/&lt;hostname&gt;::&lt;objname&gt;</entry>
+ <entry align='left'>or</entry>
+ </row>
+ <row>
+ <entry align='left'></entry>
+ <entry align='left'>local/&lt;hostname&gt;:&lt;path&gt;</entry>
+ <entry align='left'></entry>
+ </row>
+ </tbody>
+ </tgroup>
+</informaltable>
+
+<para>
+To compose a string containing a list of network IDs separated by commas
+(the format recognized by <function>IceOpenConnection</function>
+use <function>IceComposeNetworkIdList</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>char <function>IceComposeNetworkIdList</function></funcdef>
+ <paramdef>int<parameter> count</parameter></paramdef>
+ <paramdef>IceListenObj<parameter> *listen_objs</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>count</emphasis></term>
+ <listitem>
+ <para>The number of listen objects.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>listen_objs</emphasis></term>
+ <listitem>
+ <para>The listen objects.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+</sect1>
+
+<sect1 id='host_based_authentication_for_ice_connec'>
+<title>Host Based Authentication for ICE Connections</title>
+
+<para>
+If authentication fails when a client attempts to open an
+ICE connection and the initiating client has not required authentication,
+a host based authentication procedure may be invoked to provide
+a last chance for the client to connect. Each listen object has such a
+callback associated with it, and this callback is set using the
+<function>IceSetHostBasedAuthProc</function>
+function.
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void <function>IceSetHostBasedAuthProc</function></funcdef>
+ <paramdef>IceListenObj<parameter> listen_obj</parameter></paramdef>
+ <paramdef>IceHostBasedAuthProc<parameter> host_based_auth_proc</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>IceListenObj</emphasis></term>
+ <listitem>
+ <para>The listen object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>host_based_auth_proc</emphasis></term>
+ <listitem>
+ <para>The host based authentication procedure.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>
+By default, each listen object has no host based authentication procedure
+associated with it. Passing NULL for host_based_auth_proc turns off
+host based authentication if it was previously set.
+</para>
+
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>Bool <function>HostBasedAuthProc</function></funcdef>
+ <paramdef>char<parameter> *host_name</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>host_name</emphasis></term>
+ <listitem>
+ <para>
+The host name of the client that tried to open an ICE connection.
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>
+The host_name argument is a string in the form
+<emphasis remap='I'>protocol</emphasis>/
+<emphasis remap='I'>hostname</emphasis>,
+where <emphasis remap='I'>protocol</emphasis> is one of
+{tcp, decnet, local}.
+</para>
+
+<para>
+If <function>IceHostBasedAuthProc</function> returns
+<function>True</function>
+access will be granted, even though the original authentication failed.
+Note that authentication can effectively be disabled by registering an
+<function>IceHostBasedAuthProc</function>
+which always returns <function>True</function>
+</para>
+
+<para>
+Host based authentication is also allowed at
+<function>ProtocolSetup</function> time.
+The callback is specified in the
+<function>IceRegisterForProtocolReply</function>
+function (see
+<link linkend="protocol_registration">
+<xref linkend="protocol_registration"></xref></link>).
+</para>
+</sect1>
+
+<sect1 id='accepting_ice_connections'>
+<title>Accepting ICE Connections</title>
+
+
+<para>
+After a connection attempt is detected on a listen object returned by
+<function>IceListenForConnections</function>
+you should call <function>IceAcceptConnection</function>
+This returns a new opaque ICE connection object.
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>IceConn <function>IceAcceptConnection</function></funcdef>
+ <paramdef>IceListenObj<parameter> listen_obj</parameter></paramdef>
+ <paramdef>IceAcceptStatus<parameter> *status_ret</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>listen_obj</emphasis></term>
+ <listitem>
+<para>The listen object on which a new connection was detected.</para>
+ </listitem>
+ </varlistentry>
+ </variablelist>
+ <variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>status_ret</emphasis></term>
+ <listitem>
+<para>Return status information.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>The status_ret argument is set to one of the following values:</para>
+<itemizedlist>
+ <listitem>
+<para><function>IceAcceptSuccess</function>
+- the accept operation succeeded,
+and the function returns a new connection object.</para>
+ </listitem>
+ <listitem>
+<para><function>IceAcceptFailure</function>
+- the accept operation failed, and the function returns NULL.</para>
+ </listitem>
+ <listitem>
+<para><function>IceAcceptBadMalloc</function>
+- a memory allocation failed, and the function returns NULL.</para>
+ </listitem>
+</itemizedlist>
+
+<para>In general, to detect new connections, you should call
+<function>select</function>
+on the file descriptors associated with the listen objects.
+When a new connection is detected, the
+<function>IceAcceptConnection</function>
+function should be called.
+<function>IceAcceptConnection</function>
+may return a new ICE connection that is in a pending state. This is because
+before the connection can become valid, authentication may be necessary.
+Because the ICE library cannot block and wait for the connection to
+become valid (infinite blocking can occur if the connecting client
+does not act properly), the application must wait for the connection status
+to become valid.</para>
+
+<para>The following pseudo-code demonstrates how connections are accepted:</para>
+
+<literallayout class="monospaced">
+new_ice_conn = IceAcceptConnection (listen_obj, &amp;accept_status);
+if (accept_status != IceAcceptSuccess)
+{
+ close the file descriptor and return
+}
+
+status = IceConnectionStatus (new_ice_conn);
+time_start = time_now;
+
+while (status == IceConnectPending)
+{
+ select() on {new_ice_conn, all open connections}
+
+ for (each ice_conn in the list of open connections)
+ if (data ready on ice_conn)
+ {
+ status = IceProcessMessages (ice_conn, NULL, NULL);
+ if (status == IceProcessMessagesIOError)
+ IceCloseConnection(ice_conn);
+ }
+ if data ready on new_ice_conn
+ {
+ /*
+ * IceProcessMessages is called until the connection
+ * is non-pending. Doing so handles the connection
+ * setup request and any authentication requirements.
+ */
+
+ IceProcessMessages ( new_ice_conn, NULL, NULL);
+ status = IceConnectionStatus (new_ice_conn);
+ }
+ else
+ {
+ if (time_now - time_start &gt; MAX_WAIT_TIME)
+ status = IceConnectRejected;
+ }
+}
+
+if (status == IceConnectAccepted)
+{
+ Add new_ice_conn to the list of open connections
+}
+else
+{
+ IceCloseConnection
+ new_ice_conn
+}
+</literallayout>
+
+<para>After
+<function>IceAcceptConnection</function>
+is called and the connection has been
+validated, the client is ready to receive a
+<function>ProtocolSetup</function>
+(provided
+that
+<function>IceRegisterForProtocolReply</function>
+was called) or send a
+<function>ProtocolSetup</function>
+(provided that
+<function>IceRegisterForProtocolSetup</function>
+was called).</para>
+</sect1>
+
+<sect1 id='closing_ice_connections'>
+<title>Closing ICE Connections</title>
+
+<para>To close an ICE connection created with
+<function>IceOpenConnection</function>
+or
+<function>IceAcceptConnection</function>
+use
+<function>IceCloseConnection</function></para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>IceCloseStatus <function>IceCloseConnection</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>The ICE connection to close.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>To actually close an ICE connection, the following conditions
+must be met:</para>
+
+<itemizedlist>
+ <listitem>
+<para>The <emphasis remap='I'>open reference count</emphasis> must have reached zero on this ICE connection.
+When
+<function>IceOpenConnection</function>
+is called, it tries to use a previously opened
+ICE connection. If it is able to use an existing connection, it increments
+the open reference count on the connection by one.
+So, to close an ICE connection, each call to
+<function>IceOpenConnection</function>
+must be matched with a call to
+<function>IceCloseConnection</function>
+The connection can be closed only
+on the last call to
+<function>IceCloseConnection</function></para>
+ </listitem>
+ <listitem>
+<para>The <emphasis remap='I'>active protocol count</emphasis> must have reached zero. Each time a
+<function>ProtocolSetup</function>
+succeeds on the connection, the active protocol count
+is incremented by one. When the client no longer expects to use the
+protocol on the connection, the
+<function>IceProtocolShutdown</function>
+function should be called, which decrements the active protocol count
+by one (see
+<link linkend="protocol_setup_and_shutdown">
+<xref linkend="protocol_setup_and_shutdown"></xref></link>).
+</para>
+ </listitem>
+ <listitem>
+<para>If shutdown negotiation is enabled on the connection, the client on the other
+side of the ICE connection must agree to have the connection closed.</para>
+
+<para><function>IceCloseConnection</function>
+returns one of the following values:</para>
+ </listitem>
+ <listitem>
+<para><function>IceClosedNow</function>
+- the ICE connection was closed at this time. The watch procedures were
+invoked and the connection was freed.</para>
+ </listitem>
+ <listitem>
+<para><function>IceClosedASAP</function>
+- an IO error had occurred on the connection, but
+<function>IceCloseConnection</function>
+is being called within a nested
+<function>IceProcessMessages</function>
+The watch procedures have been invoked at this time, but the connection
+will be freed as soon as possible (when the nesting level reaches zero and
+<function>IceProcessMessages</function>
+returns a status of
+<function>IceProcessMessagesConnectionClosed</function></para>
+ </listitem>
+ <listitem>
+<para><function>IceConnectionInUse</function>
+- the connection was not closed at this time, because it is being used by
+other active protocols.</para>
+ </listitem>
+ <listitem>
+<para><function>IceStartedShutdownNegotiation</function>
+- the connection was not closed at this time and shutdown negotiation started
+with the client on the other side of the ICE connection. When the connection
+is actually closed,
+<function>IceProcessMessages</function>
+will return a status of
+<function>IceProcessMessagesConnectionClosed</function></para>
+ </listitem>
+</itemizedlist>
+
+<para>When it is known that the client on the other side of the ICE connection
+has terminated the connection without initiating shutdown negotiation, the
+<function>IceSetShutdownNegotiation</function>
+function should be called to turn off shutdown negotiation. This will prevent
+<function>IceCloseConnection</function>
+from writing to a broken connection.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void <function>IceSetShutdownNegotiation</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>Bool<parameter> negotiate</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>negotiate</emphasis></term>
+ <listitem>
+<para>If
+<function>False</function>
+shutdown negotiating will be turned off.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>To check the shutdown negotiation status of an ICE connection, use
+<function>IceCheckShutdownNegotiation</function></para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>Bool <function>IceCheckShutdownNegotiation</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para><function>IceCheckShutdownNegotiation</function>
+returns
+<function>True</function>
+if shutdown negotiation will take place on the connection;
+otherwise, it returns
+<function>False</function>
+Negotiation is on by default for a connection. It
+can only be changed with the
+<function>IceSetShutdownNegotiation</function>
+function.</para>
+</sect1>
+
+<sect1 id='connection_watch_procedures'>
+<title>Connection Watch Procedures</title>
+
+<para>To add a watch procedure that will be called
+each time ICElib opens a new connection via
+<function>IceOpenConnection</function>
+or
+<function>IceAcceptConnection</function>
+or closes a connection via
+<function>IceCloseConnection</function>
+use
+<function>IceAddConnectionWatch</function></para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>Status <function>IceAddConnectionWatch</function></funcdef>
+ <paramdef>IceWatchProc<parameter> watch_proc</parameter></paramdef>
+ <paramdef>IcePointer<parameter> client_data</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>watch_proc</emphasis></term>
+ <listitem>
+ <para>
+The watch procedure to invoke when ICElib opens or closes a connection.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>client_data</emphasis></term>
+ <listitem>
+ <para>This pointer will be passed to the watch procedure.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>
+The return value of <function>IceAddConnectionWatch</function>
+is zero for failure, and a positive value for success.
+</para>
+
+<para>
+Note that several calls to <function>IceOpenConnection</function>
+might share the same ICE connection. In such a case, the watch procedure
+is only invoked when the connection is first created (after authentication
+succeeds). Similarly, because connections might be shared, the
+watch procedure is called only if <function>IceCloseConnection</function>
+actually closes the connection (right before the IceConn is freed).
+</para>
+
+<para>
+The watch procedures are very useful for applications that
+need to add a file descriptor to a select mask when a new connection
+is created and remove the file descriptor when the connection is destroyed.
+Because connections are shared, knowing when to add and remove the file
+descriptor from the select mask would be difficult without the watch
+procedures.
+</para>
+
+<para>
+Multiple watch procedures may be registered with the ICE library.
+No assumptions should be made about their order of invocation.
+</para>
+
+<para>
+If one or more ICE connections were already created by the ICE library at the
+time the watch procedure is registered, the watch procedure will instantly
+be invoked for each of these ICE connections (with the opening argument
+set to <function>True</function>
+</para>
+
+<para>
+The watch procedure is of type <function>IceWatchProc</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void <function>WatchProc</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>IcePointer<parameter> client_data</parameter></paramdef>
+ <paramdef>Bool<parameter> opening</parameter></paramdef>
+ <paramdef>IcePointer<parameter> *watch_data</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>
+The opened or closed ICE connection. Call
+<function>IceConnectionNumber</function>
+to get the file descriptor associated with this connection.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>client_data</emphasis></term>
+ <listitem>
+ <para>
+Client data specified in the call to
+<function>IceAddConnectionWatch</function>
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>opening</emphasis></term>
+ <listitem>
+ <para>
+If <function>True</function> the connection is being opened. If
+<function>False</function> the connection is being closed.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>watch_data</emphasis></term>
+ <listitem>
+ <para>Can be used to save a pointer to client data.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+If opening is <function>True</function> the client should set the
+*watch_data pointer to any data it may need to save until the connection
+is closed and the watch procedure is invoked again with opening set to
+<function>False</function>
+</para>
+
+<para>
+To remove a watch procedure, use
+<function>IceRemoveConnectionWatch</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void <function>IceRemoveConnectionWatch</function></funcdef>
+ <paramdef>IceWatchProc<parameter> watch_proc</parameter></paramdef>
+ <paramdef>IcePointer<parameter> client_data</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>watch_proc</emphasis></term>
+ <listitem>
+ <para>
+The watch procedure that was passed to
+<function>IceAddConnectionWatch</function>
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>client_data</emphasis></term>
+ <listitem>
+ <para>
+The client_data pointer that was passed to
+<function>IceAddConnectionWatch</function>
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+</sect1>
+</chapter>
+
+<chapter id='protocol_setup_and_shutdown'>
+<title>Protocol Setup and Shutdown</title>
+
+<para>
+To activate a protocol on a given ICE connection, use
+<function>IceProtocolSetup</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>IceProtocolSetupStatus <function>IceProtocolSetup</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> my_opcode</parameter></paramdef>
+ <paramdef>IcePointer<parameter> client_data</parameter></paramdef>
+ <paramdef>Bool<parameter> must_authenticate</parameter></paramdef>
+ <paramdef>int<parameter> *major_version_ret</parameter></paramdef>
+ <paramdef>int<parameter> *minor_version_ret</parameter></paramdef>
+ <paramdef>char<parameter> **vendor_ret</parameter></paramdef>
+ <paramdef>char<parameter> **release_ret</parameter></paramdef>
+ <paramdef>int<parameter> error_length</parameter></paramdef>
+ <paramdef>char<parameter> *error_string_ret</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>my_opcode</emphasis></term>
+ <listitem>
+ <para>
+The major opcode of the protocol to be set up, as returned by
+<function>IceRegisterForProtocolSetup</function>
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>client_data</emphasis></term>
+ <listitem>
+ <para>
+The client data stored in this pointer will be passed to the
+<function>IcePoProcessMsgProc</function> callback.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>must_authenticate</emphasis></term>
+ <listitem>
+ <para>
+If <function>True</function> the other client may
+not bypass authentication.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>major_version_ret</emphasis></term>
+ <listitem>
+ <para>The major version of the protocol to be used is returned.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>minor_version_ret</emphasis></term>
+ <listitem>
+ <para>The minor version of the protocol to be used is returned.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>vendor_ret</emphasis></term>
+ <listitem>
+ <para>The vendor string specified by the protocol acceptor.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>release_ret</emphasis></term>
+ <listitem>
+ <para>The release string specified by the protocol acceptor.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>error_length</emphasis></term>
+ <listitem>
+ <para>
+Specifies the length of the error_string_ret argument passed in.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>error_string_ret</emphasis></term>
+ <listitem>
+ <para>
+Returns a null-terminated error message, if any.
+The error_string_ret argument points to user supplied memory.
+No more than error_length bytes are used.
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+The vendor_ret and release_ret strings should be freed with
+<function>free</function> when no longer needed.
+</para>
+
+<para>
+<function>IceProtocolSetup</function> returns one of the following values:
+</para>
+
+<itemizedlist>
+ <listitem>
+ <para>
+<function>IceProtocolSetupSuccess</function> - the major_version_ret,
+minor_version_ret, vendor_ret, release_ret are set.
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+<function>IceProtocolSetupFailure</function> or
+<function>IceProtocolSetupIOError</function>
+- check error_string_ret for failure reason. The major_version_ret,
+minor_version_ret, vendor_ret, release_ret are not set.
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+<function>IceProtocolAlreadyActive</function>
+- this protocol is already active on this connection.
+The major_version_ret, minor_version_ret, vendor_ret, release_ret
+are not set.
+ </para>
+ </listitem>
+</itemizedlist>
+
+<para>
+To notify the ICE library when a given protocol will no longer be used
+on an ICE connection, use <function>IceProtocolShutdown</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>Status <function>IceProtocolShutdown</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> major_opcode</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>major_opcode</emphasis></term>
+ <listitem>
+ <para>The major opcode of the protocol to shut down.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>
+The return value of <function>IceProtocolShutdown</function>
+is zero for failure and a positive value for success.
+</para>
+
+<para>
+Failure will occur if the major opcode was never registered OR the protocol
+of the major opcode was never activated on the connection. By activated,
+we mean that a <function>ProtocolSetup</function> succeeded on the connection.
+Note that ICE does not define how each sub-protocol triggers a
+protocol shutdown.
+</para>
+</chapter>
+
+<chapter id='processing_messages'>
+<title>Processing Messages</title>
+
+
+<para>To process incoming messages on an ICE connection, use
+<function>IceProcessMessages</function></para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>IceProcessMessagesStatus <function>IceProcessMessages</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>IceReplyWaitInfo<parameter> *reply_wait</parameter></paramdef>
+ <paramdef>Bool<parameter> *reply_ready_ret</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>reply_wait</emphasis></term>
+ <listitem>
+ <para>Indicates if a reply is being waited for.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>reply_ready_ret</emphasis></term>
+ <listitem>
+ <para>
+If set to <function>True</function> on return, a reply is ready.
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+<function>IceProcessMessages</function> is used in two ways:
+</para>
+
+<itemizedlist>
+ <listitem>
+ <para>
+In the first, a client may generate a message and block by calling
+<function>IceProcessMessages</function> repeatedly until it gets its reply.
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+In the second, a client calls <function>IceProcessMessages</function>
+with reply_wait set to NULL in response to <function>select</function>
+showing that there is data to read on the ICE connection.
+The ICE library may process zero or more complete messages.
+Note that messages that are not blocked for are always processed by
+invoking callbacks.
+ </para>
+ </listitem>
+</itemizedlist>
+
+<para>
+<function>IceReplyWaitInfo</function> contains the major/minor opcodes
+and sequence number of the message for which a reply is being awaited.
+It also contains a pointer to the reply message to be filled in (the
+protocol library should cast this <function>IcePointer</function>
+to the appropriate reply type). In most
+cases, the reply will have some fixed-size part, and the client waiting
+for the reply will have provided a pointer to a structure to hold
+this fixed-size data. If there is variable-length data, it would be
+expected that the
+<function>IcePoProcessMsgProc</function>
+callback will have to allocate additional
+memory and store pointer(s) to that memory in the fixed-size
+structure. If the entire data is variable length (for example, a single
+variable-length string), then the client waiting for the reply would probably
+just pass a pointer to fixed-size space to hold a pointer, and the
+<function>IcePoProcessMsgProc</function>
+callback would allocate the storage and store the pointer.
+It is the responsibility of the client receiving the reply to
+free up any memory allocated on its behalf.
+</para>
+
+<literallayout class="monospaced">
+typedef struct {
+ unsigned long sequence_of_request;
+ int major_opcode_of_request;
+ int minor_opcode_of_request;
+ IcePointer reply;
+} IceReplyWaitInfo;
+</literallayout>
+
+<para>
+If reply_wait is not NULL and
+<function>IceProcessMessages</function>
+has a reply or error to return in response to this reply_wait
+(that is, no callback was generated), then the reply_ready_ret argument
+will be set to <function>True</function>
+</para>
+
+<para>
+If reply_wait is NULL, then the caller may also pass NULL for
+reply_ready_ret and be guaranteed that no value will be stored in
+this pointer.
+</para>
+
+<para>
+<function>IceProcessMessages</function> returns one of the following values:
+</para>
+
+<itemizedlist>
+ <listitem>
+ <para>
+<function>IceProcessMessagesSuccess</function> - no error occurred.
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+<function>IceProcessMessagesIOError</function> - an IO error occurred,
+and the caller must explicitly close the connection by calling
+<function>IceCloseConnection</function>
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+<function>IceProcessMessagesConnectionClosed</function>
+- the ICE connection has been closed (closing of the connection was deferred
+because of shutdown negotiation, or because the
+<function>IceProcessMessages</function>
+nesting level was not zero). Do not attempt
+to access the ICE connection at this point, since it has been freed.
+ </para>
+ </listitem>
+</itemizedlist>
+
+</chapter>
+
+<chapter id='ping'>
+<title>Ping</title>
+
+<para>
+To send a "Ping" message to the client on the other side of the
+ICE connection, use <function>IcePing</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>Status <function>IcePing</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>IcePingReplyProc<parameter> ping_reply_proc</parameter></paramdef>
+ <paramdef>IcePointer<parameter> client_data</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>ping_reply_proc</emphasis></term>
+ <listitem>
+ <para>The callback to invoke when the Ping reply arrives.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>client_data</emphasis></term>
+ <listitem>
+ <para>
+This pointer will be passed to the <function>IcePingReplyProc</function>
+callback.
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para><function>IcePing</function>
+returns zero for failure and a positive value for success.</para>
+
+<para>When
+<function>IceProcessMessages</function>
+processes the Ping reply, it will invoke the
+<function>IcePingReplyProc</function>
+callback.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void <function>PingReplyProc</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>IcePointer<parameter> client_data</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+<para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>client_data</emphasis></term>
+ <listitem>
+<para>The client data specified in the call to
+<function>IcePing</function></para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+</chapter>
+
+<chapter id='using_icelib_informational_functions'>
+<title>Using ICElib Informational Functions</title>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>IceConnectStatus <function>IceConnectionStatus</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<para><function>IceConnectionStatus</function>
+returns the status of an ICE connection. The possible return values are:</para>
+
+<itemizedlist>
+ <listitem>
+<para><function>IceConnectPending</function>
+- the connection is not valid yet (that is, authentication is taking place).
+This is only relevant to connections created by
+<function>IceAcceptConnection</function></para>
+ </listitem>
+ <listitem>
+<para><function>IceConnectAccepted</function>
+- the connection has been accepted.
+This is only relevant to connections created by
+<function>IceAcceptConnection</function></para>
+ </listitem>
+ <listitem>
+<para><function>IceConnectRejected</function>
+- the connection had been rejected (that is, authentication failed).
+This is only relevant to connections created by
+<function>IceAcceptConnection</function></para>
+ </listitem>
+ <listitem>
+<para><function>IceConnectIOError</function>
+- an IO error has occurred on the connection.</para>
+ </listitem>
+</itemizedlist>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>char <function> *IceVendor</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<para><function>IceVendor</function>
+returns the ICE library vendor identification
+for the other side of the connection.
+The string should be freed with a call to
+<function>free</function>
+when no longer needed.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>char <function> *IceRelease</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<para><function>IceRelease</function>
+returns the release identification of the ICE library
+on the other side of the connection.
+The string should be freed with a call to
+<function>free</function>
+when no longer needed.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>int <function> IceProtocolVersion</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<para><function>IceProtocolVersion</function>
+returns the major version of the ICE protocol on this connection.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>int <function> IceProtocolRevision</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+
+<para><function>IceProtocolRevision</function>
+returns the minor version of the ICE protocol on this connection.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>int <function> IceConnectionNumber</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+
+<para><function>IceConnectionNumber</function>
+returns the file descriptor of this ICE connection.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>char <function> *IceConnectionString</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<para><function>IceConnectionString</function>
+returns the network ID of the client that
+accepted this connection. The string should be freed with a call to
+<function>free</function>
+when no longer needed.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>unsigned long <function> IceLastSentSequenceNumber</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+
+<para><function>IceLastSentSequenceNumber</function>
+returns the sequence number of the last message sent on this ICE connection.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>unsigned long <function> IceLastReceivedSequenceNumber</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<para><function>IceLastReceivedSequenceNumber</function>
+returns the sequence number of the last message received on this
+ICE connection.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>Bool <function> IceSwapping</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+
+<para><function>IceSwapping</function>
+returns
+<function>True</function>
+if byte swapping is necessary when reading messages on the ICE connection.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>IcePointer <function> IceGetContext</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<para><function>IceGetContext</function>
+returns the context associated with a connection created by
+<function>IceOpenConnection</function></para>
+</chapter>
+
+<chapter id='ice_messages'>
+<title>ICE Messages</title>
+
+<para>
+All ICE messages have a standard 8-byte header. The ICElib macros that
+read and write messages rely on the following naming convention for message
+headers:
+</para>
+
+<literallayout class='monospaced'>
+ CARD8 major_opcode;
+ CARD8 minor_opcode;
+ CARD8 data[2];
+ CARD32 length B32;
+</literallayout>
+
+<para>
+The 3rd and 4th bytes of the message header can be used as needed.
+The length field is specified in units of 8 bytes.
+</para>
+
+<sect1 id='sending_ice_messages'>
+<title>Sending ICE Messages</title>
+
+<para>
+The ICE library maintains an output buffer used for generating messages.
+Protocol libraries layered on top of ICE may choose to batch messages
+together and flush the output buffer at appropriate times.
+</para>
+
+<para>
+If an IO error has occurred on an ICE connection, all write operations
+will be ignored. For further information, see
+<link linkend="error_handling">
+<xref linkend="error_handling"></xref></link>.
+</para>
+
+
+<para>
+To get the size of the ICE output buffer, use
+<function>IceGetOutBufSize</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>int <function> IceGetOutBufSize</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>
+To flush the ICE output buffer, use <function>IceFlush</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>int <function> IceFlush</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+Note that the output buffer may be implicitly flushed if there is
+insufficient space to generate a message.
+</para>
+
+<para>The following macros can be used to generate ICE messages:</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceGetHeader</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> major_opcode</parameter></paramdef>
+ <paramdef>int<parameter> minor_opcode</parameter></paramdef>
+ <paramdef>int<parameter> header_size</parameter></paramdef>
+ <paramdef>&lt;C_data_type&gt;<parameter> *pmsg</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>major_opcode</emphasis></term>
+ <listitem>
+ <para>The major opcode of the message.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>minor_opcode</emphasis></term>
+ <listitem>
+ <para>The minor opcode of the message.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>header_size</emphasis></term>
+ <listitem>
+ <para>The size of the message header (in bytes).</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>&lt;C_data_type&gt;</emphasis></term>
+ <listitem>
+ <para>The actual C data type of the message header.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>pmsg</emphasis></term>
+ <listitem>
+ <para>
+The message header pointer. After this macro is called, the
+library can store data in the message header.
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>
+<function>IceGetHeader</function>
+is used to set up a message header on an ICE connection.
+It sets the major and minor opcodes of the message, and initializes
+the message's length to the length of the header. If additional
+variable length data follows, the message's length field should be
+updated.
+</para>
+
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceGetHeaderExtra</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> major_opcode</parameter></paramdef>
+ <paramdef>int<parameter> minor_opcode</parameter></paramdef>
+ <paramdef>int<parameter> header_size</parameter></paramdef>
+ <paramdef>int<parameter> extra</parameter></paramdef>
+ <paramdef>&lt;C_data_type&gt;<parameter> *pmsg</parameter></paramdef>
+ <paramdef>char<parameter> *pdata</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>major_opcode</emphasis></term>
+ <listitem>
+ <para>The major opcode of the message.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>minor_opcode</emphasis></term>
+ <listitem>
+ <para>The minor opcode of the message.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>header_size</emphasis></term>
+ <listitem>
+ <para>The size of the message header (in bytes).</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>extra</emphasis></term>
+ <listitem>
+ <para>
+The size of the extra data beyond the header (in 8-byte units).
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>&lt;C_data_type&gt;</emphasis></term>
+ <listitem>
+ <para>The actual C data type of the message header.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>pmsg</emphasis></term>
+ <listitem>
+ <para>
+The message header pointer. After this macro is called, the
+library can store data in the message header.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>pdata</emphasis></term>
+ <listitem>
+ <para>
+Returns a pointer to the ICE output buffer that points
+immediately after the message header. The variable length
+data should be stored here. If there was not enough room
+in the ICE output buffer, pdata is set to NULL.
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>
+<function>IceGetHeaderExtra</function>
+is used to generate a message with a fixed (and relatively small) amount
+of variable length data. The complete message must fit in the ICE output
+buffer.
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceSimpleMessage</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> major_opcode</parameter></paramdef>
+ <paramdef>int<parameter> minor_opcode</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>major_opcode</emphasis></term>
+ <listitem>
+ <para>The major opcode of the message.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>minor_opcode</emphasis></term>
+ <listitem>
+ <para>The minor opcode of the message.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+<function>IceSimpleMessage</function>
+is used to generate a message that is identical
+in size to the ICE header message, and has no additional data.
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceErrorHeader</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> offending_major_opcode</parameter></paramdef>
+ <paramdef>int<parameter> offending_minor_opcode</parameter></paramdef>
+ <paramdef>int<parameter> offending_sequence_num</parameter></paramdef>
+ <paramdef>int<parameter> severity</parameter></paramdef>
+ <paramdef>int<parameter> error_class</parameter></paramdef>
+ <paramdef>int<parameter> data_length</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>offending_major_opcode</emphasis></term>
+ <listitem>
+ <para>
+The major opcode of the protocol in which an error was detected.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>offending_minor_opcode</emphasis></term>
+ <listitem>
+ <para>
+The minor opcode of the protocol in which an error was detected.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>offending_sequence_num</emphasis></term>
+ <listitem>
+ <para>The sequence number of the message that caused the error.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>severity</emphasis></term>
+ <listitem>
+ <para>
+<function>IceCanContinue</function>
+<function>IceFatalToProtocol</function>
+or
+<function>IceFatalToConnection</function>
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>error_class</emphasis></term>
+ <listitem>
+ <para>The error class.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>data_length</emphasis></term>
+ <listitem>
+ <para>
+Length of data (in 8-byte units) to be written after the header.
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+<function>IceErrorHeader</function> sets up an error message header.
+</para>
+
+<para>
+Note that the two clients connected by ICE may be using different
+major opcodes for a given protocol. The offending_major_opcode passed
+to this macro is the major opcode of the protocol for the client
+sending the error message.
+</para>
+
+<para>
+Generic errors, which are common to all protocols, have classes
+in the range 0x8000..0xFFFF.
+See the <emphasis remap='I'>Inter-Client Exchange Protocol</emphasis>
+standard for more details.
+</para>
+
+<informaltable pgwide='0' frame='none'>
+ <tgroup cols='2' align='center'>
+ <colspec colname='c1'/>
+ <colspec colname='c2'/>
+ <tbody>
+ <row>
+ <entry align='left'>IceBadMinor</entry>
+ <entry align='left'>0x8000</entry>
+ </row>
+ <row>
+ <entry align='left'>IceBadState</entry>
+ <entry align='left'>0x8001</entry>
+ </row>
+ <row>
+ <entry align='left'>IceBadLength</entry>
+ <entry align='left'>0x8002</entry>
+ </row>
+ <row>
+ <entry align='left'>IceBadValue</entry>
+ <entry align='left'>0x8003</entry>
+ </row>
+ </tbody>
+ </tgroup>
+</informaltable>
+
+<para>Per-protocol errors have classes in the range 0x0000-0x7fff.</para>
+
+<para>
+To write data to an ICE connection, use the
+<function>IceWriteData</function> macro. If the data fits into the
+ICE output buffer, it is copied there. Otherwise, the ICE output buffer
+is flushed and the data is directly sent.
+</para>
+
+<para>
+This macro is used in conjunction with
+<function>IceGetHeader</function> and
+<function>IceErrorHeader</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceWriteData</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> bytes</parameter></paramdef>
+ <paramdef>char<parameter> *data</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>bytes</emphasis></term>
+ <listitem>
+ <para>The number of bytes to write.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>data</emphasis></term>
+ <listitem>
+ <para>The data to write.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>
+To write data as 16-bit quantities, use <function>IceWriteData16</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceWriteData16</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> bytes</parameter></paramdef>
+ <paramdef>char<parameter> *data</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>bytes</emphasis></term>
+ <listitem>
+ <para>The number of bytes to write.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>data</emphasis></term>
+ <listitem>
+ <para>The data to write.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+To write data as 32-bit quantities, use <function>IceWriteData32</function>
+</para>
+
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceWriteData32</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> bytes</parameter></paramdef>
+ <paramdef>char<parameter> *data</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>bytes</emphasis></term>
+ <listitem>
+ <para>The number of bytes to write.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>data</emphasis></term>
+ <listitem>
+ <para>The data to write.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+To write data as 32-bit quantities, use <function>IceWriteData32</function>
+</para>
+
+<para>
+To bypass copying data to the ICE output buffer, use
+<function>IceSendData</function> to directly send data over the network
+connection. If necessary, the ICE output buffer is first flushed.
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceSendData</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> bytes</parameter></paramdef>
+ <paramdef>char<parameter> *data</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>bytes</emphasis></term>
+ <listitem>
+ <para>The number of bytes to send.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>data</emphasis></term>
+ <listitem>
+ <para>The data to send.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>
+To force 32-bit or 64-bit alignment, use <function>IceWritePad</function>
+A maximum of 7 pad bytes can be specified.
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceWritePad</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> bytes</parameter></paramdef>
+ <paramdef>char<parameter> *data</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>bytes</emphasis></term>
+ <listitem>
+ <para>The number of bytes to write.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>data</emphasis></term>
+ <listitem>
+ <para>The number of pad bytes to write.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+</sect1>
+
+<sect1 id='reading_ice_messages'>
+<title>Reading ICE Messages</title>
+
+
+<para>
+The ICE library maintains an input buffer used for reading messages.
+If the ICE library chooses to perform nonblocking reads (this is
+implementation-dependent), then for every read operation that it makes,
+zero or more complete messages may be read into the input buffer. As
+a result, for all of the macros described in this section that read
+messages, an actual read operation will occur on the connection only if
+the data is not already present in the input buffer.
+</para>
+
+
+<para>
+To get the size of the ICE input buffer, use
+<function>IceGetInBufSize</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>int<function> IceGetInBufSize</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+When reading messages, care must be taken to check for IO errors. If
+any IO error occurs in reading any part of a message, the message should
+be thrown out. After using any of the macros described below for reading
+messages, the <function>IceValidIO</function>
+macro can be used to check if an IO error occurred on the
+connection. After an IO error has occurred on an ICE connection, all
+read operations will be ignored. For further information, see
+<link linkend="error_handling">
+<xref linkend="error_handling"></xref></link>.
+</para>
+
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>Bool<function> IceValidIO</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>The following macros can be used to read ICE messages.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceReadSimpleMessage</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>&lt;C_data_type&gt;<parameter> *pmsg</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>&lt;C_data_type&gt;</emphasis></term>
+ <listitem>
+ <para>The actual C data type of the message header.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>pmsg</emphasis></term>
+ <listitem>
+ <para>This pointer is set to the message header.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+<function>IceReadSimpleMessage</function>
+is used for messages that are identical in size to the 8-byte ICE header, but
+use the spare 2 bytes in the header to encode additional data. Note that the
+ICE library always reads in these first 8 bytes, so it can obtain the major
+opcode of the message. <function>IceReadSimpleMessage</function>
+simply returns a pointer to these 8 bytes; it does not actually read any data
+into the input buffer.
+</para>
+
+<para>
+For a message with variable length data, there are two ways of reading
+the message. One method involves reading the complete message in one
+pass using <function>IceReadCompleteMessage</function>
+The second method involves reading the message header (note that this may
+be larger than the 8-byte ICE header), then reading
+the variable length data in chunks (see
+<function>IceReadMessageHeader</function> and
+<function>IceReadData</function>
+</para>
+
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceReadCompleteMessage</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> header_size</parameter></paramdef>
+ <paramdef>&lt;C_data_type&gt;<parameter> *pmsg</parameter></paramdef>
+ <paramdef>char<parameter> *pdata</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>header_size</emphasis></term>
+ <listitem>
+ <para>The size of the message header (in bytes).</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>&lt;C_data_type&gt;</emphasis></term>
+ <listitem>
+ <para>The actual C data type of the message header.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>pmsg</emphasis></term>
+ <listitem>
+ <para>This pointer is set to the message header.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>pdata</emphasis></term>
+ <listitem>
+ <para>
+This pointer is set to the variable length data of the message.
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+If the ICE input buffer has sufficient space,
+<function>IceReadCompleteMessage</function>
+will read the complete message into the
+ICE input buffer. Otherwise, a buffer will be allocated to hold the
+variable length data. After the call, the pdata argument should
+be checked against NULL to make sure that there was sufficient memory
+to allocate the buffer.
+</para>
+
+<para>
+After calling <function>IceReadCompleteMessage</function>
+and processing the message, <function>IceDisposeCompleteMessage</function>
+should be called.
+</para>
+
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceDisposeCompleteMessage</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>char<parameter> *pdata</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>pdata</emphasis></term>
+ <listitem>
+ <para>
+The pointer to the variable length data returned in
+<function>IceReadCompleteMessage</function>
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+If a buffer had to be allocated to hold the variable length data (because
+it did not fit in the ICE input buffer), it is freed here by ICElib.
+</para>
+
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceReadMessageHeader</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> header_size</parameter></paramdef>
+ <paramdef>&lt;C_data_type&gt;<parameter> *pmsg</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>header_size</emphasis></term>
+ <listitem>
+ <para>The size of the message header (in bytes).</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>&lt;C_data_type&gt;</emphasis></term>
+ <listitem>
+ <para>The actual C data type of the message header.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>pmsg</emphasis></term>
+ <listitem>
+ <para>This pointer is set to the message header.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+<function>IceReadMessageHeader</function> reads just the message header.
+The rest of the data should be read with the
+<function>IceReadData</function>
+family of macros. This method of reading a message should be used when the
+variable length data must be read in chunks.
+</para>
+
+
+<para>
+To read data directly into a user supplied buffer, use
+<function>IceReadData</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceReadData</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> bytes</parameter></paramdef>
+ <paramdef>char<parameter> *pdata</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>bytes</emphasis></term>
+ <listitem>
+ <para>The number of bytes to read.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>pdata</emphasis></term>
+ <listitem>
+ <para>The data is read into this user supplied buffer.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>
+To read data as 16-bit quantities, use <function>IceReadData16</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceReadData16</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>Bool<parameter> swap</parameter></paramdef>
+ <paramdef>int<parameter> bytes</parameter></paramdef>
+ <paramdef>char<parameter> *pdata</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>swap</emphasis></term>
+ <listitem>
+ <para>
+If <function>True,</function> the values will be byte swapped.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>bytes</emphasis></term>
+ <listitem>
+ <para>The number of bytes to read.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>pdata</emphasis></term>
+ <listitem>
+ <para>The data is read into this user supplied buffer.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>
+To read data as 32-bit quantities, use <function>IceReadData32</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceReadData32</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>Bool<parameter> swap</parameter></paramdef>
+ <paramdef>int<parameter> bytes</parameter></paramdef>
+ <paramdef>char<parameter> *pdata</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>swap</emphasis></term>
+ <listitem>
+ <para>
+If <function>True,</function> the values will be byte swapped.
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>bytes</emphasis></term>
+ <listitem>
+ <para>The number of bytes to read.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>pdata</emphasis></term>
+ <listitem>
+ <para>The data is read into this user supplied buffer.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>To force 32-bit or 64-bit alignment, use
+<function>IceReadPad</function>
+A maximum of 7 pad bytes can be specified.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceReadPad</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> bytes</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem>
+ <para>A valid ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>bytes</emphasis></term>
+ <listitem>
+ <para>The number of pad bytes.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+</sect1>
+</chapter>
+
+<chapter id='error_handling'>
+<title>Error Handling</title>
+
+
+<para>There are two default error handlers in ICElib:</para>
+
+<itemizedlist>
+ <listitem>
+ <para>
+One to handle typically fatal conditions (for example,
+a connection dying because a machine crashed)
+ </para>
+ </listitem>
+ <listitem>
+ <para>One to handle ICE-specific protocol errors</para>
+ </listitem>
+</itemizedlist>
+
+<para>
+These error handlers can be changed to user-supplied routines if you
+prefer your own error handling and can be changed as often as you like.
+</para>
+
+
+<para>
+To set the ICE error handler, use <function>IceSetErrorHandler</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef><function> IceSetErrorHandler</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>int<parameter> bytes</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>handler</emphasis></term>
+ <listitem>
+ <para>
+The ICE error handler. You should pass NULL to restore the default handler.
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+<function>IceSetErrorHandler</function> returns the previous error handler.
+</para>
+
+<para>
+The ICE error handler is invoked when an unexpected ICE protocol
+error (major opcode 0) is encountered. The action of the default
+handler is to print an explanatory message to
+<function>stderr</function>
+and if the severity is fatal, call
+<function>exit</function>
+with a nonzero value. If exiting
+is undesirable, the application should register its own error handler.
+</para>
+
+<para>
+Note that errors in other protocol
+domains should be handled by their respective libraries (these libraries
+should have their own error handlers).
+</para>
+
+<para>
+An ICE error handler has the type of <function>IceErrorHandler</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void<function> IceErrorHandler</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>Bool<parameter> swap</parameter></paramdef>
+ <paramdef>int<parameter> offending_minor_opcode</parameter></paramdef>
+ <paramdef>unsigned long<parameter> offending_sequence_num</parameter></paramdef>
+ <paramdef>int<parameter> error_class</parameter></paramdef>
+ <paramdef>int<parameter> severity</parameter></paramdef>
+ <paramdef>IcePointer<parameter> values</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>handler</emphasis></term>
+ <listitem>
+ <para>The ICE connection object.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>swap</emphasis></term>
+ <listitem>
+ <para>A flag that indicates if the values need byte swapping.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>offending_minor_opcode</emphasis></term>
+ <listitem>
+ <para>The ICE minor opcode of the offending message.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>offending_sequence_num</emphasis></term>
+ <listitem>
+ <para>The sequence number of the offending message.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>error_class</emphasis></term>
+ <listitem>
+ <para>The error class of the offending message.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>severity</emphasis></term>
+ <listitem>
+ <para>
+<function>IceCanContinue</function>
+<function>IceFatalToProtocol</function>
+or
+<function>IceFatalToConnection</function>
+ </para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>values</emphasis></term>
+ <listitem>
+ <para>
+Any additional error values specific to the minor opcode and class.
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>The following error classes are defined at the ICE level:</para>
+
+<literallayout remap='Ds'>
+<function>IceBadMinor</function>
+<function>IceBadState</function>
+<function>IceBadLength</function>
+<function>IceBadValue</function>
+<function>IceBadMajor</function>
+<function>IceNoAuth</function>
+<function>IceNoVersion</function>
+<function>IceSetupFailed</function>
+<function>IceAuthRejected</function>
+<function>IceAuthFailed</function>
+<function>IceProtocolDuplicate</function>
+<function>IceMajorOpcodeDuplicate</function>
+<function>IceUnknownProtocol</function>
+</literallayout>
+
+<para>
+For further information, see
+the <emphasis remap='I'>Inter-Client Exchange Protocol</emphasis> standard.
+</para>
+
+
+<para>
+To handle fatal I/O errors, use <function>IceSetIOErrorHandler</function>
+</para>
+
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>IceIOErrorHandler<function> IceSetIOErrorHandler</function></funcdef>
+ <paramdef>IceIOErrorHandler<parameter> handler</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>handler</emphasis></term>
+ <listitem>
+ <para>
+The I/O error handler. You should pass NULL to restore the default handler.
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+<function>IceSetIOErrorHandler</function> returns the previous
+IO error handler.
+</para>
+
+<para>
+An ICE I/O error handler has the type of
+<function>IceIOErrorHandler</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void<function> IceIOErrorHandler</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem><para>The ICE connection object.</para></listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para> There are two ways of handling IO errors in ICElib:</para>
+
+<itemizedlist>
+ <listitem>
+ <para>
+In the first, the IO error handler does whatever is necessary
+to respond to the IO error and then returns, but it does not call
+<function>IceCloseConnection</function>
+The ICE connection is given a "bad IO" status, and all future reads
+and writes to the connection are ignored. The next time
+<function>IceProcessMessages</function>
+is called it will return a status of
+<function>IceProcessMessagesIOError</function>
+At that time, the application should call
+<function>IceCloseConnection</function>
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+In the second, the IO error handler does call
+<function>IceCloseConnection</function>
+and then uses the <function>longjmp</function>
+call to get back to the application's main event loop. The
+<function>setjmp</function> and
+<function>longjmp</function>
+calls may not work properly on all platforms,
+and special care must be taken to avoid memory leaks.
+Therefore, this second model is less desirable.
+ </para>
+ </listitem>
+</itemizedlist>
+
+<para>
+Before the application I/O error handler is invoked, protocol libraries
+that were interested in being notified of I/O errors will have their
+<function>IceIOErrorProc</function>
+handlers invoked. This handler is set up in the protocol registration
+functions (see <function>IceRegisterForProtocolSetup</function> and
+<function>IceRegisterForProtocolReply</function>
+and could be used to clean up state specific to the protocol.
+</para>
+
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void<function> IceIOErrorProc</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem><para>The ICE connection object.</para></listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+Note that every <function>IceIOErrorProc</function>
+callback must return. This is required
+because each active protocol must be notified of the broken connection,
+and the application IO error handler must be invoked afterwards.
+</para>
+</chapter>
+
+<chapter id='multithreading_support'>
+<title>Multi-Threading Support</title>
+
+
+<para>To declare that multiple threads in an application will be using the ICE
+library, use
+<function>IceInitThreads</function></para>
+
+<literallayout remap='FD'>
+Status IceInitThreads()
+</literallayout>
+
+
+<para>The
+<function>IceInitThreads</function>
+function must be the first ICElib function a
+multi-threaded program calls. It must complete before any other ICElib
+call is made.
+<function>IceInitThreads</function>
+returns a nonzero status if and only if it was able
+to initialize the threads package successfully.
+It is safe to call
+<function>IceInitThreads</function>
+more than once, although the threads package will only be initialized once.</para>
+
+<para>Protocol libraries layered on top of ICElib will have to lock critical
+sections of code that access an ICE connection (for example, when
+generating messages). Two calls, which are generally implemented as
+macros, are provided:</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void<function> IceLockConn</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void<function> IceUnlockConn</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem><para>The ICE connection object.</para></listitem>
+ </varlistentry>
+</variablelist>
+
+<para>To keep an ICE connection locked across several ICElib calls, applications use
+<function>IceAppLockConn</function>
+and
+<function>IceAppUnlockConn</function></para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void<function> IceAppLockConn</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem><para>The ICE connection object.</para></listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>The
+<function>IceAppLockConn</function>
+function completely locks out other threads using the connection
+until
+<function>IceAppUnlockConn</function>
+is called. Other threads attempting to use ICElib
+calls on the connection will block.
+If the program has not previously called
+<function>IceInitThreads</function>
+<function>IceAppLockConn</function>
+has no effect.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void<function> IceAppUnlockConn</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem><para>The ICE connection object.</para></listitem>
+ </varlistentry>
+</variablelist>
+
+<para>The
+<function>IceAppUnlockConn</function>
+function allows other threads to complete ICElib
+calls on the connection that were blocked by a previous call to
+<function>IceAppLockConn</function>
+from this thread. If the program has not previously called
+<function>IceInitThreads</function>
+<function>IceAppUnlockConn</function>
+has no effect.</para>
+</chapter>
+
+<chapter id='miscellaneous_functions'>
+<title>Miscellaneous Functions</title>
+
+
+
+
+<para>To allocate scratch space (for example, when generating
+messages with variable data), use
+<function>IceAllocScratch</function>
+Each ICE connection has one scratch space associated with it.
+The scratch space starts off as empty and grows as needed.
+The contents of the scratch space is not guaranteed to be preserved
+after any ICElib function is called.</para>
+
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>char<function> *IceAllocScratch</function></funcdef>
+ <paramdef>IceConn<parameter> ice_conn</parameter></paramdef>
+ <paramdef>unsigned long<parameter> size</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>ice_conn</emphasis></term>
+ <listitem><para>The ICE connection object.</para></listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>size</emphasis></term>
+ <listitem><para>The number of bytes required.</para></listitem>
+ </varlistentry>
+</variablelist>
+
+<para>Note that the memory returned by
+<function>IceAllocScratch</function>
+should not be freed by the caller.
+The ICE library will free the memory when the ICE connection is closed.</para>
+</chapter>
+
+<chapter id='acknowledgements'>
+<title>Acknowledgements</title>
+
+
+<para>
+Thanks to Bob Scheifler for his thoughtful input on the design
+of the ICE library. Thanks also to Jordan Brown, Larry Cable, Donna Converse,
+Clive Feather, Stephen Gildea, Vania Joloboff, Kaleb Keithley,
+Stuart Marks, Hiro Miyamoto, Ralph Swick, Jim VanGilder, and Mike Wexler.
+</para>
+</chapter>
+
+<appendix id="authentication_utility_functions">
+<title>Authentication Utility Functions</title>
+
+
+<para>
+As discussed in this document, the means by which authentication data
+is obtained by the ICE library (for
+<function>ConnectionSetup</function>
+messages or
+<function>ProtocolSetup</function>
+messages) is implementation-dependent.&dagger;
+<footnote remap='FS'>
+<para>The X Consortium's ICElib implementation assumes the presence of an
+ICE authority file.
+</para></footnote>
+</para>
+
+<para>
+This appendix describes some utility functions that manipulate an
+ICE authority file. The authority file can be used to pass authentication
+data between clients.
+</para>
+
+<para>The basic operations on the .ICEauthority file are:</para>
+
+<itemizedlist>
+ <listitem>
+ <para>Get file name</para>
+ </listitem>
+ <listitem>
+ <para>Lock</para>
+ </listitem>
+ <listitem>
+ <para>Unlock</para>
+ </listitem>
+ <listitem>
+ <para>Read entry</para>
+ </listitem>
+ <listitem>
+ <para>Write entry</para>
+ </listitem>
+ <listitem>
+ <para>Search for entry</para>
+ </listitem>
+</itemizedlist>
+
+<para>
+These are fairly low-level operations, and it is expected that a program,
+like "iceauth", would exist to add, remove, and display entries in the file.
+</para>
+
+<para>
+In order to use these utility functions, the
+&lt;<symbol role='Pn'>X11/ICE/ICEutil.h</symbol>&gt;
+header file must be included.
+</para>
+
+<para>
+An entry in the .ICEauthority file is defined by the following data structure:
+</para>
+
+
+<literallayout class="monospaced">
+typedef struct {
+ char *protocol_name;
+ unsigned short protocol_data_length;
+ char *protocol_data;
+ char *network_id;
+ char *auth_name;
+ unsigned short auth_data_length;
+ char *auth_data;
+} IceAuthFileEntry;
+</literallayout>
+
+
+<para>
+The protocol_name member is either "ICE" for connection setup authentication
+or the subprotocol name, such as "XSMP". For each entry, protocol specific
+data can be specified in the protocol_data member. This can be used
+to search for old entries that need to be removed from the file.
+</para>
+
+<para>
+The network_id member is the network ID of the client accepting
+authentication (for example, the network ID of a session manager).
+A network ID has the following form:
+</para>
+
+<informaltable pgwide='0' frame='none'>
+ <tgroup cols='3' align='center'>
+ <colspec colname='c1'/>
+ <colspec colname='c2'/>
+ <colspec colname='c3'/>
+ <tbody>
+ <row>
+ <entry align='left'></entry>
+ <entry align='left'>tcp/&lt;hostname&gt;:&lt;portnumber&gt;</entry>
+ <entry align='left'>or</entry>
+ </row>
+ <row>
+ <entry align='left'></entry>
+ <entry align='left'>decnet/&lt;hostname&gt;::&lt;objname&gt;</entry>
+ <entry align='left'>or</entry>
+ </row>
+ <row>
+ <entry align='left'></entry>
+ <entry align='left'>local/&lt;hostname&gt;:&lt;path&gt;</entry>
+ <entry align='left'></entry>
+ </row>
+ </tbody>
+ </tgroup>
+</informaltable>
+
+<para>
+The auth_name member is the name of the authentication method.
+The auth_data member is the actual authentication data,
+and the auth_data_length member is the number of bytes in the data.
+</para>
+
+<para>
+To obtain the default authorization file name, use
+<function>IceAuthFileName</function>
+</para>
+
+<literallayout remap='FD'>
+char *IceAuthFileName()
+</literallayout>
+
+<para>
+If the ICEAUTHORITY environment variable if set, this value is returned.
+Otherwise, the default authorization file name is $HOME/.ICEauthority.
+This name is statically allocated and should not be freed.
+</para>
+
+<para>
+To synchronously update the authorization file, the file must
+be locked with a call to
+<function>IceLockAuthFile</function>
+This function takes advantage of the fact that the
+<function>link</function>
+system call will fail if the name of the new link already exists.
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>int<function> IceLockAuthFile</function></funcdef>
+ <paramdef>char<parameter> *file_name</parameter></paramdef>
+ <paramdef>int<parameter> retries</parameter></paramdef>
+ <paramdef>int<parameter> timeout</parameter></paramdef>
+ <paramdef>long<parameter> dead</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>file_name</emphasis></term>
+ <listitem><para>The authorization file to lock.</para></listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>retries</emphasis></term>
+ <listitem>
+ <para>The number of retries.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>timeout</emphasis></term>
+ <listitem>
+ <para>The number of seconds before each retry.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>dead</emphasis></term>
+ <listitem>
+ <para>
+If a lock already exists that is the specified dead seconds old,
+it is broken.
+A value of zero is used to unconditionally break an old lock.
+ </para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>One of three values is returned:</para>
+
+<itemizedlist>
+ <listitem>
+ <para>
+<function>IceAuthLockSuccess</function> - the lock succeeded.
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+<function>IceAuthLockError</function> - a system error occurred, and
+<function>errno</function> may prove useful.
+ </para>
+ </listitem>
+ <listitem>
+ <para>
+<function>IceAuthLockTimeout</function> - the specified number of
+retries failed.
+ </para>
+ </listitem>
+</itemizedlist>
+
+<para>
+To unlock an authorization file, use <function>IceUnlockAuthFile</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>int<function> IceUnlockAuthFile</function></funcdef>
+ <paramdef>char<parameter> *file_name</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>file_name</emphasis></term>
+ <listitem><para>The authorization file to unlock.</para></listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+To read the next entry in an authorization file, use
+<function>IceReadAuthFileEntry</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>IceAuthFileEntry<function> *IceReadAuthFileEntry</function></funcdef>
+ <paramdef>FILE<parameter> *auth_file</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>auth_file</emphasis></term>
+ <listitem><para>The authorization file.</para></listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+Note that it is the responsibility of the application to open the file
+for reading before calling this function. If an error is encountered,
+or there are no more entries to read, NULL is returned.
+</para>
+
+<para>
+Entries should be free with a call to
+<function>IceFreeAuthFileEntry</function>
+</para>
+
+<para>
+To write an entry in an authorization file, use
+<function>IceWriteAuthFileEntry</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>Status<function> IceWriteAuthFileEntry</function></funcdef>
+ <paramdef>FILE<parameter> *auth_file</parameter></paramdef>
+ <paramdef>IceAuthFileEntry<parameter> *entry</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>auth_file</emphasis></term>
+ <listitem><para>The authorization file.</para></listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>entry</emphasis></term>
+ <listitem><para>The entry to write.</para></listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+Note that it is the responsibility of the application to open the file
+for writing before calling this function. The function returns a nonzero
+status if the operation was successful.
+</para>
+
+
+<para>
+To search the default authorization file for an entry that matches a given
+protocol_name/network_id/auth_name tuple, use
+<function>IceGetAuthFileEntry</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>IceAuthFileEntry<function> *IceGetAuthFileEntry</function></funcdef>
+ <paramdef>char<parameter> *protocol_name</parameter></paramdef>
+ <paramdef>char<parameter> *network_id</parameter></paramdef>
+ <paramdef>char<parameter> *auth_name</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>auth_file</emphasis></term>
+ <listitem><para>The name of the protocol to search on.</para></listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>network_id</emphasis></term>
+ <listitem>
+ <para>The network ID to search on.</para>
+ </listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>auth_name</emphasis></term>
+ <listitem>
+ <para>The authentication method to search on.</para>
+ </listitem>
+ </varlistentry>
+</variablelist>
+
+<para>
+If <function>IceGetAuthFileEntry</function>
+fails to find such an entry, NULL is returned.
+</para>
+
+
+<para>
+To free an entry returned by
+<function>IceReadAuthFileEntry</function> or
+<function>IceGetAuthFileEntry</function> use
+<function>IceFreeAuthFileEntry</function>
+</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void<function> IceFreeAuthFileEntry</function></funcdef>
+ <paramdef>IceAuthFileEntry<parameter> *entry</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>entry</emphasis></term>
+ <listitem><para>The entry to free.</para></listitem>
+ </varlistentry>
+</variablelist>
+
+</appendix>
+
+<appendix id="mit_magic_cookie_1_authentication">
+<title>MIT-MAGIC-COOKIE-1 Authentication</title>
+
+
+<para>The X Consortium's ICElib implementation supports a simple
+MIT-MAGIC-COOKIE-1 authentication scheme using the authority file utilities
+described in Appendix A.</para>
+
+<para>In this model, an application, such as a session manager, obtains a
+magic cookie by calling
+<function>IceGenerateMagicCookie</function>
+and then stores it in the user's local .ICEauthority file
+so that local clients can connect. In order to allow remote clients to
+connect, some remote execution mechanism should be used to store the
+magic cookie in the user's .ICEauthority file on a remote machine.</para>
+
+<para>In addition to storing the magic cookie in the .ICEauthority file, the
+application needs to call the
+<function>IceSetPaAuthData</function>
+function in order to store the magic cookie in memory. When it comes time
+for the MIT-MAGIC-COOKIE-1 authentication procedure to accept or reject the
+connection, it will compare the magic cookie presented by the requestor to
+the magic cookie in memory.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>char<function> *IceGenerateMagicCookie</function></funcdef>
+ <paramdef>int<parameter> length</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>length</emphasis></term>
+ <listitem><para>The desired length of the magic cookie.</para></listitem>
+ </varlistentry>
+</variablelist>
+
+
+<para>The magic cookie returned will be null-terminated. If memory can not be
+allocated for the magic cookie, the function will return NULL.
+Otherwise, the magic cookie should be freed with a call to
+<function>free</function></para>
+
+
+<para>To store the authentication data in memory, use
+<function>IceSetPaAuthData</function>
+Currently, this function is only used for MIT-MAGIC-COOKIE-1
+authentication, but it may be used for additional authentication
+methods in the future.</para>
+
+<funcsynopsis>
+<funcprototype>
+ <funcdef>void<function> IceSetPaAuthData</function></funcdef>
+ <paramdef>int<parameter> num_entries</parameter></paramdef>
+ <paramdef>IceAuthDataEntry<parameter> *entries</parameter></paramdef>
+</funcprototype>
+</funcsynopsis>
+
+<variablelist remap='IP'>
+ <varlistentry>
+ <term><emphasis remap='I'>num_entries</emphasis></term>
+ <listitem><para>The number of authentication data entries.</para></listitem>
+ </varlistentry>
+ <varlistentry>
+ <term><emphasis remap='I'>entries</emphasis></term>
+ <listitem><para>The list of authentication data entries.</para></listitem>
+ </varlistentry>
+</variablelist>
+
+<para>Each entry has associated with it a protocol name
+(for example, "ICE" for ICE connection setup authentication,
+"XSMP" for session management authentication), a network ID for the
+"accepting" client, an authentication name (for example, MIT-MAGIC-COOKIE-1),
+and authentication data. The ICE library
+will merge these entries with previously set entries, based on the
+(protocol_name, network_id, auth_name) tuple.</para>
+
+
+
+<literallayout class="monospaced">
+typedef struct {
+ char *protocol_name;
+ char *network_id;
+ char *auth_name;
+ unsigned short auth_data_length;
+ char *auth_data;
+} IceAuthDataEntry;
+</literallayout>
+
+</appendix>
+</book>
+
diff --git a/doc/Makefile.am b/doc/Makefile.am
index e3cbc9d..23ed84a 100644
--- a/doc/Makefile.am
+++ b/doc/Makefile.am
@@ -1 +1,64 @@
-EXTRA_DIST = ice.ms ICElib.ms
+#
+# Copyright (c) 2010, Oracle and/or its affiliates. All rights reserved.
+#
+# Permission is hereby granted, free of charge, to any person obtaining a
+# copy of this software and associated documentation files (the "Software"),
+# to deal in the Software without restriction, including without limitation
+# the rights to use, copy, modify, merge, publish, distribute, sublicense,
+# and/or sell copies of the Software, and to permit persons to whom the
+# Software is furnished to do so, subject to the following conditions:
+#
+# The above copyright notice and this permission notice (including the next
+# paragraph) shall be included in all copies or substantial portions of the
+# Software.
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+# THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+# DEALINGS IN THE SOFTWARE.
+#
+
+if ENABLE_DOCS
+doc_sources = ICElib.xml
+dist_doc_DATA = $(doc_sources)
+
+if HAVE_XMLTO
+doc_DATA = $(doc_sources:.xml=.html)
+
+if HAVE_FOP
+doc_DATA += $(doc_sources:.xml=.ps) $(doc_sources:.xml=.pdf)
+endif
+
+if HAVE_XMLTO_TEXT
+doc_DATA += $(doc_sources:.xml=.txt)
+endif
+
+if HAVE_STYLESHEETS
+XMLTO_FLAGS = -m $(XSL_STYLESHEET)
+
+doc_DATA += xorg.css
+xorg.css: $(STYLESHEET_SRCDIR)/xorg.css
+ $(AM_V_GEN)cp -pf $(STYLESHEET_SRCDIR)/xorg.css $@
+endif
+
+CLEANFILES = $(doc_DATA)
+
+SUFFIXES = .xml .ps .pdf .txt .html
+
+.xml.txt:
+ $(AM_V_GEN)$(XMLTO) $(XMLTO_FLAGS) txt $<
+
+.xml.html:
+ $(AM_V_GEN)$(XMLTO) $(XMLTO_FLAGS) xhtml-nochunks $<
+
+.xml.pdf:
+ $(AM_V_GEN)$(XMLTO) $(XMLTO_FLAGS) --with-fop pdf $<
+
+.xml.ps:
+ $(AM_V_GEN)$(XMLTO) $(XMLTO_FLAGS) --with-fop ps $<
+
+endif HAVE_XMLTO
+endif ENABLE_DOCS
diff --git a/doc/ice.ms b/doc/ice.ms
deleted file mode 100644
index 7d31ea6..0000000
--- a/doc/ice.ms
+++ /dev/null
@@ -1,1878 +0,0 @@
-.\" Use tbl macros.t ice.ms | troff -ms
-.\" $XdotOrg: xc/doc/specs/ICE/ice.ms,v 1.2 2004/04/23 18:42:16 eich Exp $
-.\"
-.\" TODO:
-.\" Think about connector/listener originator/answerer terminology.
-.EH ''''
-.OH ''''
-.EF ''''
-.OF ''''
-.\"
-.\" Disable hyphenation. I hate it.
-.hy 0
-.de hy
-..
-.\" A couple of macros to standardize things and make them
-.\" easy to type.
-.de Ss \" Begin state - .Ss <state name>
-.KS
-.LP
-\fC\\$1\fP\^:
-.br
-..
-.de St \" Transition - .St "condition" message <new state>
-.RS
-\\$1
-.PN \\$2
-\(-> \fC\\$3\fP
-.RE
-..
-.de Se \" End state - .Se
-.LP
-.KE
-..
-.de Ms \" Start message header - .Ms messagename
-.sM
-.PN \\$1
-.RS
-..
-.de Mf \" Field in message - .Mf name; types follow on separate line(s)
-.\".br
-.IP "\fI\\$1\fP\^:" "\w'\fI\\$1\fP\^:'u+1"
-..
-.de Mc \" Field Continuation - .Mc; description follows on separate line(s)
-.br
-.\" \h'1i'
-..
-.de Ma \" Message addendum - .Ma title; contents follow
-.IP "\\$1:" "\w'\\$1:'u+1"
-..
-.de Me \" End of message header - .Me
-.RE
-.LP
-.eM
-..
-.de Es \" Start Encoding - .Es messagename
-.KS
-.LP
-.nf
-.PN \\$1
-.ta .2i .5i 2.0i
-..
-.de Ee \" End Encoding - .Ee
-.fi
-.LP
-.KE
-..
-.\"
-.\" --- cT --- centered title; centers $1, adds TOC entry unless $2 is "no"
-.\"
-.de cT
-\\& \" filler so that the following .sp really leaves a space
-.sp 1
-.ce 1
-\\s+1\\fB\\$1\\fP\\s-1
-.sp 1
-.if !'\\$2'no' \{\
-.XS \\n(PN
-\\$1
-.XE
-\}
-..
-.ps 10
-.nr PS 10
-\&
-.TL
-\s+2\fBInter-Client Exchange (ICE) Protocol\fP\s-2
-.sp
-Version 1.1
-.sp
-X Consortium Standard
-.sp
-X Version 11, Release 6.8
-
-
-
-.AU
-Robert Scheifler
-.AI
-X Consortium, Inc.
-.AU
-Jordan Brown
-.AI
-Quarterdeck Office Systems
-
-
-
-.AB
-.LP
-There are numerous possible protocols that can be used for communication
-among clients. They have many similarities and common needs, including
-authentication,
-version negotiation,
-data typing, and
-connection management. The
-.I
-Inter-Client Exchange
-.R
-(ICE) protocol is intended to provide a framework for building such
-protocols. Using ICE reduces the complexity of designing new protocols and
-allows the sharing of many aspects of the implementation.
-.AE
-.LP
-.bp
-\&
-.sp 8
-.LP
-.DS C
-.if n Copyright (c) 1993, 1994 X Consortium
-.if t Copyright \(co 1993, 1994 X Consortium
-.DE
-.sp 3
-.LP
-Permission is hereby granted, free of charge, to any person obtaining a copy
-of this software and associated documentation files (the ``Software''), to deal
-in the Software without restriction, including without limitation the rights
-to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
-copies of the Software, and to permit persons to whom the Software is
-furnished to do so, subject to the following conditions:
-.LP
-The above copyright notice and this permission notice shall be included in
-all copies or substantial portions of the Software.
-.LP
-THE SOFTWARE IS PROVIDED ``AS IS'', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
-AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
-CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-.LP
-Except as contained in this notice, the name of the X Consortium shall not be
-used in advertising or otherwise to promote the sale, use or other dealings
-in this Software without prior written authorization from the X Consortium.
-.sp 5
-X Window System is a trademark of The Open Group.
-.EH '\fBInter-Client Exchange Protocol\fP''\fBX11, Release 6.8\fP'
-.OH '\fBInter-Client Exchange Protocol\fP''\fBX11, Release 6.8\fP'
-.bp 1
-.EF ''\fB % \fP''
-.OF ''\fB % \fP''
-.nH 1 "Purpose and Goals"
-.LP
-In discussing a variety of protocols \(em existing, under development, and
-hypothetical \(em it was noted that they have many elements in common. Most
-protocols need mechanisms for authentication, for
-version negotiation,
-and for setting up and taking down connections. There are also
-cases where the same two parties need to talk to each other using multiple
-protocols. For example, an embedding relationship between two parties is
-likely to require the simultaneous use of session management, data transfer,
-focus negotiation, and command notification protocols. While these are
-logically separate protocols, it is desirable for them to share as many
-pieces of implementation as possible.
-.LP
-The
-.I
-Inter-Client Exchange
-.R
-(ICE) protocol provides a generic framework for building protocols on top of
-reliable, byte-stream transport connections. It provides basic mechanisms
-for setting up and shutting down connections, for performing authentication,
-for negotiating
-versions,
-and for reporting errors. The
-protocols running within an ICE connection are referred to here as
-.I subprotocols.
-ICE provides facilities for each subprotocol to do its own version
-negotiation, authentication, and error reporting. In addition, if two
-parties are communicating using several different subprotocols, ICE will
-allow them to share the same transport layer connection.
-.nH 1 "Overview of the protocol"
-.LP
-Through some mechanism outside ICE, two parties make themselves known to
-each other and agree that they would like to communicate using an ICE
-subprotocol. ICE assumes that this negotation includes some notion by which
-the parties will decide which is the \*Qoriginating\*U party and which is
-the \*Qanswering\*U party. The negotiation will also need to provide the
-originating party with a name or address of the answering party. Examples
-of mechanisms by which parties can make themselves known to each other are
-the X selection mechanism, environment
-variables, and shared files.
-.LP
-The originating party first determines whether there is an existing ICE
-connection between the two parties. If there is, it can re-use the existing
-connection and move directly to the setup of the subprotocol. If no ICE
-connection exists, the originating party will open a transport connection to
-the answering party and will start ICE connection setup.
-.LP
-The ICE connection setup dialog consists of three major parts: byte order
-exchange, authentication, and connection information exchange. The first
-message in each direction is a
-.PN ByteOrder
-message telling which byte order will be used by the sending party in
-messages that it sends. After that, the originating party sends a
-.PN ConnectionSetup
-message giving information about itself (vendor name and release number) and
-giving a list of ICE version numbers it is capable of supporting and a list
-of authentication schemes it is willing to accept. Authentication is
-optional. If no authentication is required, the answering party responds
-with a
-.PN ConnectionReply
-message giving information about itself, and the connection setup is complete.
-.LP
-If the connection setup is to be authenticated, the answering party will
-respond with an
-.PN AuthenticationRequired
-message instead of a
-.PN ConnectionReply
-message. The parties then exchange
-.PN AuthenticationReply
-and
-.PN AuthenticationNextPhase
-messages until authentication is complete, at which time the answering party
-finally sends its
-.PN ConnectionReply
-message.
-.LP
-Once an ICE connection is established (or an existing connection reused),
-the originating party starts subprotocol negotiation by sending a
-.PN ProtocolSetup
-message. This message gives the name of the subprotocol that the parties
-have agreed to use, along with the ICE major opcode that the originating
-party has assigned to that subprotocol. Authentication can also occur for
-the subprotocol, independently of authentication for the connection.
-Subprotocol authentication is optional. If there is no subprotocol
-authentication, the answering party responds with a
-.PN ProtocolReply
-message, giving the ICE major opcode that it has assigned
-for the subprotocol.
-.LP
-Subprotocols are authenticated independently of each other, because they may
-have differing security requirements. If there is authentication for this
-particular subprotocol, it takes place before the answering party emits the
-.PN ProtocolReply
-message, and it uses the
-.PN AuthenticationRequired ,
-.PN AuthenticationReply ,
-and
-.PN AuthenticationNextPhase
-messages, just as for the connection authentication. Only when subprotocol
-authentication is complete does the answering party send its
-.PN ProtocolReply
-message.
-.LP
-When a subprotocol has been set up and authenticated, the two parties can
-communicate using messages defined by the subprotocol. Each message has two
-opcodes: a major opcode and a minor opcode. Each party will send messages
-using the major opcode it has assigned in its
-.PN ProtocolSetup
-or
-.PN ProtocolReply
-message. These opcodes will, in general, not be the same. For a particular
-subprotocol, each party will need to keep track of two major opcodes: the
-major opcode it uses when it sends messages, and the major opcode it expects
-to see in messages it receives. The minor opcode values and semantics are
-defined by each individual subprotocol.
-.LP
-Each subprotocol will have one or more messages whose semantics are that the
-subprotocol is to be shut down. Whether this is done unilaterally or is
-performed through negotiation is defined by each subprotocol. Once a
-subprotocol is shut down, its major opcodes are removed from
-use; no further messages on this subprotocol should be sent until the
-opcode is reestablished with
-.PN ProtocolSetup .
-.LP
-ICE has a facility to negotiate the closing of the connection when there are
-no longer any active subprotocols. When either party decides that no
-subprotocols are active, it can send a
-.PN WantToClose
-message. If the other party agrees to close the connection, it can simply
-do so. If the other party wants to keep the connection open, it can
-indicate its desire by replying with a
-.PN NoClose
-message.
-.\" XXX - Note that it's likely that both parties will WantToClose at once.
-.LP
-It should be noted that the party that initiates the connection isn't
-necessarily the same as the one that initiates setting up a subprotocol.
-For example, suppose party A connects to party B. Party A will issue the
-.PN ConnectionSetup
-message and party B will respond with a
-.PN ConnectionReply
-message. (The authentication steps are omitted here for brevity.)
-Typically, party A will also issue the
-.PN ProtocolSetup
-message and expect a
-.PN ProtocolReply
-from party B. Once the connection is established, however, either party may
-initiate the negotiation of a subprotocol. Continuing this example, party B
-may decide that it needs to set up a subprotocol for communication with
-party A. Party B would issue the
-.PN ProtocolSetup
-message and expect a
-.PN ProtocolReply
-from party A.
-.nH 1 "Data Types"
-.LP
-ICE messages contain several types of data. Byte order is negotiated in
-the initial connection messages; in general data is sent in the sender's
-byte order and the receiver is required to swap it appropriately.
-In order to support 64-bit machines, ICE messages
-are padded to multiples of 8 bytes. All messages are designed so that
-fields are \*Qnaturally\*U aligned on 16-, 32-, and 64-bit boundaries.
-The following formula gives the number of bytes necessary
-to pad \fIE\fP bytes to the next multiple of \fIb\fP\^:
-.DS
-pad(\fIE\fP, \fIb\fP\^) = (\fIb\fP \- (\fIE\fP mod \fIb\fP\^)) mod \fIb\fP
-.DE
-.nH 2 "Primitive Types"
-.LP
-.TS H
-expand;
-lB lB
-l lw(3.5i).
-_
-.sp 6p
-Type Name Description
-.sp 6p
-_
-.sp 6p
-.TH
-.R
-CARD8 8-bit unsigned integer
-CARD16 16-bit unsigned integer
-CARD32 32-bit unsigned integer
-BOOL T{
-.PN False
-or
-.PN True
-T}
-LPCE T{
-A character from the X Portable Character Set in Latin Portable Character
-Encoding
-T}
-.sp 6p
-_
-.TE
-.KS
-.nH 2 "Complex Types"
-.LP
-.TS H
-expand;
-lB lB
-l lw(3.5i).
-_
-.sp 6p
-Type Name Type
-.sp 6p
-_
-.sp 6p
-.TH
-.R
-VERSION [Major, minor: CARD16]
-STRING LISTofLPCE
-.sp 6p
-_
-.TE
-.KE
-LISTof<type> denotes a counted collection of <type>. The exact encoding
-varies depending on the context; see the encoding section.
-.nH 1 "Message Format"
-.LP
-All ICE messages include the following information:
-.TS H
-expand;
-cB lB
-
-l lw(3.5i).
-_
-.sp 6p
-Field Type Description
-.sp 6p
-_
-.sp 6p
-.TH
-CARD8 protocol major opcode
-CARD8 protocol minor opcode
-CARD32 length of remaining data in 8-byte units
-.sp 6p
-_
-.TE
-.LP
-The fields are as follows:
-.LP
-Protocol major opcode
-.RS
-This specifies what subprotocol the message is intended for. Major opcode
-0 is reserved for ICE control messages. The major opcodes of other
-subprotocols are dynamically assigned and exchanged at protocol
-negotiation time.
-.RE
-.LP
-Protocol minor opcode
-.RS
-This specifies what protocol-specific operation is to be performed.
-Minor opcode 0 is reserved for Errors; other values are protocol-specific.
-.RE
-.LP
-Length of data in 8-byte units
-.RS
-This specifies the length of the information following the first 8 bytes.
-Each message-type has a different format, and will need to be separately
-length-checked against this value. As every data item has either an
-explicit length, or an implicit length, this can be easily accomplished.
-Messages that have too little or too much data indicate a serious
-protocol failure, and should result in a
-.PN BadLength
-error.
-.RE
-.nH 1 "Overall Protocol Description"
-.LP
-Every message sent in a given direction has an implicit sequence number,
-starting with 1. Sequence numbers are global to the connection; independent
-sequence numbers are \fInot\fP maintained for each protocol.
-.LP
-Messages of a given major-opcode (i.e., of a given protocol) must be
-responded to (if a response is called for) in order by the receiving party.
-Messages from different protocols can be responded to in arbitrary order.
-.LP
-Minor opcode 0 in every protocol is for reporting errors. At most one error
-is generated per request. If more than one error condition is encountered
-in processing a request, the choice of which error is returned is
-implementation-dependent.
-.Ms Error
-.Mf offending-minor-opcode
-CARD8
-.Mf severity
-.Pn { CanContinue ,
-.PN FatalToProtocol ,
-.PN FatalToConnection }
-.Mf sequence-number
-CARD32
-.Mf class
-CARD16
-.Mf value(s)
-<dependent on major/minor opcode and class>
-.Me
-This message is sent to report an error in response to a message
-from any protocol.
-The
-.PN Error
-message
-exists in all protocol major-opcode spaces; it
-is minor-opcode zero in every protocol. The minor opcode of the
-message that caused the error is reported, as well as the sequence
-number of that message.
-The severity indicates the sender's behavior following
-the identification of the error.
-.PN CanContinue
-indicates the sender is willing to accept additional messages for this
-protocol.
-.PN FatalToProcotol
-indicates the sender is unwilling to accept further messages for this
-protocol but that messages for other protocols may be accepted.
-.PN FatalToConnection
-indicates the sender is unwilling to accept any further
-messages for any protocols on the connection. The sender
-is required to conform to specified severity conditions
-for generic and ICE (major opcode 0) errors; see Sections 6.1
-and 6.2.
-The class defines the generic class of
-error. Classes are specified separately for each protocol (numeric
-values can mean different things in different protocols). The error
-values, if any, and their types vary with the specific error class
-for the protocol.
-.LP
-.\" XXX
-.\" (Asynchronous errors \(em errors not associated with a previous
-.\" message??? If so, offending-minor and sequence = 0.)
-.nH 1 "ICE Control Subprotocol \(em Major Opcode 0"
-.LP
-Each of the ICE control opcodes is described below.
-Most of the messages have additional information included beyond the
-description above. The additional information is appended to the message
-header and
-the length field is computed accordingly.
-.LP
-In the following message descriptions, \*QExpected errors\*U indicates
-errors that may occur in the normal course of events. Other errors
-(in particular
-.PN BadMajor ,
-.PN BadMinor ,
-.PN BadState ,
-.PN BadLength ,
-.PN BadValue ,
-.PN ProtocolDuplicate ,
-and
-.PN MajorOpcodeDuplicate )
-might occur, but generally indicate a serious implementation failure on
-the part of the
-errant
-peer.
-.Ms ByteOrder
-.Mf byte-order
-.Pn { MSBfirst ,
-.PN LSBfirst }
-.Me
-Both parties must send this message before sending any other,
-including errors. This message specifies the byte order that
-will be used on subsequent messages sent by this party.
-.LP
-Note: If the receiver detects an error in this message,
-it must be sure to send its own
-.PN ByteOrder
-message before sending the
-.PN Error .
-.Ms ConnectionSetup
-.Mf versions
-LISTofVERSION
-.Mf must-authenticate
-BOOL
-.Mf authentication-protocol-names
-LISTofSTRING
-.Mf vendor
-STRING
-.Mf release
-STRING
-.LP
-.Ma "Responses"
-.PN ConnectionReply ,
-.PN AuthenticationRequired .
-(See note)
-.Ma "Expected errors"
-.PN NoVersion ,
-.PN SetupFailed ,
-.PN NoAuthentication ,
-.PN AuthenticationRejected ,
-.Mc
-.PN AuthenticationFailed .
-.Me
-The party that initiates the connection
-(the
-one that does the \*Qconnect()\*U)
-must send this
-message
-as the second message (after
-.PN ByteOrder )
-on startup.
-.LP
-Versions gives a list, in decreasing order of preference, of the
-protocol versions this party is capable of speaking. This document
-specifies major version 1, minor version 0.
-.LP
-If must-authenticate is
-.PN True ,
-the initiating party demands authentication; the accepting party \fImust\fP
-pick an authentication scheme and use it. In this case, the only valid
-response is
-.PN AuthenticationRequired .
-.LP
-If must-authenticate is
-.PN False ,
-the accepting party may choose an authentication mechanism, use a
-host-address-based authentication scheme, or skip authentication.
-When must-authenticate is
-.PN False ,
-.PN ConnectionReply
-and
-.PN AuthenticationRequired
-are both valid responses. If a host-address-based authentication scheme is
-used,
-.PN AuthenticationRejected
-and
-.PN AuthenticationFailed
-errors are possible.
-.LP
-Authentication-protocol-names specifies a (possibly null, if
-must-authenticate is
-.PN False )
-list of authentication protocols the party is willing to perform. If
-must-authenticate is
-.PN True ,
-presumably the party will offer only authentication mechanisms
-allowing mutual authentication.
-.LP
-Vendor gives the name of the vendor of this ICE implementation.
-.LP
-Release gives the release identifier of this ICE implementation.
-.LP
-.Ms AuthenticationRequired
-.Mf authentication-protocol-index
-CARD8
-.Mf data
-<specific to authentication protocol>
-.LP
-.Ma "Response"
-.PN AuthenticationReply .
-.Ma "Expected errors"
-.PN AuthenticationRejected ,
-.PN AuthenticationFailed .
-.Me
-This message is sent in response to a
-.PN ConnectionSetup
-or
-.PN ProtocolSetup
-message to specify that authentication is to be done and what authentication
-mechanism is to be used.
-.LP
-The authentication protocol is specified by a 0-based index into the list
-of names given in the
-.PN ConnectionSetup
-or
-.PN ProtocolSetup .
-Any protocol-specific data that might be required is also sent.
-.Ms AuthenticationReply
-.Mf data
-<specific to authentication protocol>
-.LP
-.Ma "Responses"
-.PN AuthenticationNextPhase ,
-.PN ConnectionReply ,
-.PN ProtocolReply .
-.Ma "Expected errors"
-.PN AuthenticationRejected ,
-.PN AuthenticationFailed ,
-.PN SetupFailed .
-.Me
-This message is sent in response to an
-.PN AuthenticationRequired
-or
-.PN AuthenticationNextPhase
-message, to
-supply authentication data as defined by the authentication protocol
-being used.
-.LP
-Note that this message is sent by the party that initiated the current
-negotiation \(em the party that sent the
-.PN ConnectionSetup
-or
-.PN ProtocolSetup
-message.
-.LP
-.PN AuthenticationNextPhase
-indicates that more is to be done to complete the authentication.
-If the authentication is complete,
-.PN ConnectionReply
-is appropriate if the current authentication handshake is the result of a
-.PN ConnectionSetup ,
-and a
-.PN ProtocolReply
-is appropriate if it is the result of a
-.PN ProtocolSetup .
-.Ms AuthenticationNextPhase
-.Mf data
-<specific to authentication protocol>
-.LP
-.Ma "Response"
-.PN AuthenticationReply .
-.Ma "Expected errors"
-.PN AuthenticationRejected ,
-.PN AuthenticationFailed .
-.Me
-This message is sent in response to an
-.PN AuthenticationReply
-message, to supply authentication data as defined by the authentication
-protocol being used.
-.Ms ConnectionReply
-.Mf version-index
-CARD8
-.Mf vendor
-STRING
-.Mf release
-STRING
-.Me
-This message is sent in response to a
-.PN ConnectionSetup
-or
-.PN AuthenticationReply
-message to indicate that the authentication handshake is complete.
-.LP
-Version-index gives a 0-based index into the list of versions offered in
-the
-.PN ConnectionSetup
-message; it specifies the version of the ICE protocol that both parties
-should speak for the duration of the connection.
-.LP
-Vendor gives the name of the vendor of this ICE implementation.
-.LP
-Release gives the release identifier of this ICE implementation.
-.Ms ProtocolSetup
-.Mf protocol-name
-STRING
-.Mf major-opcode
-CARD8
-.Mf versions
-LISTofVERSION
-.Mf vendor
-STRING
-.Mf release
-STRING
-.Mf must-authenticate
-BOOL
-.Mf authentication-protocol-names
-LISTofSTRING
-.LP
-.Ma "Responses"
-.PN AuthenticationRequired ,
-.PN ProtocolReply .
-.Ma "Expected errors"
-.PN UnknownProtocol ,
-.PN NoVersion ,
-.PN SetupFailed ,
-.PN NoAuthentication ,
-.Mc
-.PN AuthenticationRejected ,
-.PN AuthenticationFailed .
-.Me
-This message is used to initiate negotiation of
-a protocol and establish any authentication
-specific to it.
-.LP
-Protocol-name gives the name of the protocol the party wishes
-to speak.
-.LP
-Major-opcode gives the opcode that the party will use in messages
-it sends.
-.LP
-Versions gives a list of version numbers, in decreasing order of
-preference, that the party is willing to speak.
-.LP
-Vendor and release are identification strings with semantics defined
-by the specific protocol being negotiated.
-.LP
-If must-authenticate is
-.PN True ,
-the initiating party demands authentication; the accepting party \fImust\fP
-pick an authentication scheme and use it. In this case, the only valid
-response is
-.PN AuthenticationRequired .
-.LP
-If must-authenticate is
-.PN False ,
-the accepting party may choose an authentication mechanism, use a
-host-address-based authentication scheme, or skip authentication.
-When must-authenticate is
-.PN False ,
-.PN ProtocolReply
-and
-.PN AuthenticationRequired
-are both valid responses. If a host-address-based authentication scheme is
-used,
-.PN AuthenticationRejected
-and
-.PN AuthenticationFailed
-errors are possible.
-.LP
-Authentication-protocol-names specifies a (possibly null, if
-must-authenticate is
-.PN False )
-list of authentication protocols the party is willing to perform. If
-must-authenticate is
-.PN True ,
-presumably the party will offer only authentication mechanisms
-allowing mutual authentication.
-.Ms ProtocolReply
-.Mf major-opcode
-CARD8
-.Mf version-index
-CARD8
-.Mf vendor
-STRING
-.Mf release
-STRING
-.Me
-This message is sent in response to a
-.PN ProtocolSetup
-or
-.PN AuthenticationReply
-message to indicate that the authentication handshake is complete.
-.LP
-Major-opcode gives the opcode that this party will use in
-messages that it sends.
-.LP
-Version-index gives a 0-based index into the list of versions offered in the
-.PN ProtocolSetup
-message; it specifies the version of the protocol that both
-parties should speak for the duration of the connection.
-.LP
-Vendor and release are identification strings with semantics defined
-by the specific protocol being negotiated.
-.LP
-.Ms Ping
-.Ma "Response"
-.PN PingReply .
-.Me
-This message is used to test if the connection is still functioning.
-.Ms PingReply
-.Me
-This message is sent in response to a
-.PN Ping
-message, indicating that the connection is still functioning.
-.Ms WantToClose
-.Ma "Responses"
-.PN WantToClose ,
-.PN NoClose ,
-.PN ProtocolSetup .
-.Me
-This message is used to initiate a possible close of the connection.
-The sending party has noticed that, as a result of mechanisms specific
-to each protocol, there are no active
-protocols
-left.
-There are
-four possible scenarios arising from this request:
-.IP (1) 5
-The receiving side noticed too, and has already sent a
-.PN WantToClose .
-On receiving a
-.PN WantToClose
-while already attempting to shut down, each party should simply close the
-connection.
-.IP (2)
-The receiving side hasn't noticed, but agrees. It closes
-the connection.
-.IP (3)
-The receiving side has a
-.PN ProtocolSetup
-\*Qin flight,\*U in which case it is to ignore
-.PN WantToClose
-and the party sending
-.PN WantToClose
-is to abandon the shutdown attempt when it receives the
-.PN ProtocolSetup .
-.IP (4)
-The receiving side wants the connection kept open for some
-reason not specified by the ICE protocol, in which case it
-sends
-.PN NoClose .
-.LP
-See the state transition diagram for additional information.
-.Ms NoClose
-.Me
-This message is sent in response to a
-.PN WantToClose
-message to indicate that the responding
-party does not want the connection closed at
-this time. The receiving party should not close the
-connection. Either party may again initiate
-.PN WantToClose
-at some future time.
-.nH 2 "Generic Error Classes"
-.LP
-These errors should be used by all protocols, as applicable.
-For ICE (major opcode 0),
-.PN FatalToProtocol
-should
-be interpreted as
-.PN FatalToConnection.
-.Ms BadMinor
-.Mf offending-minor-opcode
-<any>
-.Mf severity
-.PN FatalToProtocol
-or
-.PN CanContinue
-(protocol's discretion)
-.Mf values
-(none)
-.Me
-Received a message with an unknown minor opcode.
-.br
-.ne 9
-.Ms BadState
-.Mf offending-minor-opcode
-<any>
-.Mf severity
-.PN FatalToProtocol
-or
-.PN CanContinue
-(protocol's discretion)
-.Mf values
-(none)
-.Me
-Received a message with a valid minor opcode which is not appropriate
-for the current state of the protocol.
-.Ms BadLength
-.Mf offending-minor-opcode
-<any>
-.Mf severity
-.PN FatalToProtocol
-or
-.PN CanContinue
-(protocol's discretion)
-.Mf values
-(none)
-.Me
-Received a message with a bad length. The length of the message is
-longer or shorter than required to contain the data.
-.Ms BadValue
-.Mf offending-minor-opcode
-<any>
-.Mf severity
-.PN CanContinue
-.Mf values
-CARD32 Byte offset to offending value in offending message
-.Mc
-CARD32 Length of offending value
-.Mc
-<varies> Offending value
-.Me
-Received a message with a bad value specified.
-.nH 2 "ICE Error Classes"
-.LP
-These errors are all major opcode 0 errors.
-.Ms BadMajor
-.Mf offending-minor-opcode
-<any>
-.Mf severity
-.PN CanContinue
-.Mf values
-CARD8 Opcode
-.Me
-The opcode given is not one that has been registered.
-.Ms NoAuthentication
-.Mf offending-minor-opcode
-.PN ConnectionSetup ,
-.PN ProtocolSetup
-.Mf severity
-.PN ConnectionSetup
-\(->
-.PN FatalToConnection
-.Mc
-.PN ProtocolSetup
-\(->
-.PN FatalToProtocol
-.Mf values
-(none)
-.Me
-None of the authentication protocols offered are available.
-.Ms NoVersion
-.Mf offending-minor-opcode
-.PN ConnectionSetup ,
-.PN ProtocolSetup
-.Mf severity
-.PN ConnectionSetup
-\(->
-.PN FatalToConnection
-.Mc
-.PN ProtocolSetup
-\(->
-.PN FatalToProtocol
-.Mf values
-(none)
-.Me
-None of the protocol versions offered are available.
-.\" .Ms SetupFailed
-.sM
-.PN SetupFailed
-.RS
-.Mf offending-minor-opcode
-.PN ConnectionSetup ,
-.PN ProtocolSetup ,
-.PN AuthenticationReply
-.Mf severity
-.PN ConnectionSetup
-\(->
-.PN FatalToConnection
-.Mc
-.PN ProtocolSetup
-\(->
-.PN FatalToProtocol
-.Mc
-.PN AuthenticationReply
-\(->
-.PN FatalToConnection
-if authenticating a connection, otherwise
-.PN FatalToProtocol
-.Mf values
-STRING reason
-.Me
-The sending side is unable to accept the
-new connection or new protocol for a reason other than authentication
-failure. Typically this error will be a result of inability to allocate
-additional resources on the sending side. The reason field will give a
-human-interpretable message providing further detail on the type of failure.
-.br
-.Ms AuthenticationRejected
-.Mf offending-minor-opcode
-.PN AuthenticationReply ,
-.PN AuthenticationRequired ,
-.br
-.PN AuthenticationNextPhase
-.Mf severity
-.PN FatalToProtocol
-.Mf values
-STRING reason
-.Me
-Authentication rejected. The peer has failed to properly
-authenticate itself.
-The reason field will give a human-interpretable message
-providing further detail.
-.Ms AuthenticationFailed
-.Mf offending-minor-opcode
-.PN AuthenticationReply ,
-.PN AuthenticationRequired ,
-.br
-.PN AuthenticationNextPhase
-.Mf severity
-.PN FatalToProtocol
-.Mf values
-STRING reason
-.Me
-Authentication failed.
-.PN AuthenticationFailed
-does not imply that the authentication was rejected, as
-.PN AuthenticationRejected
-does. Instead it means that the sender was unable to complete
-the authentication for some other reason. (For instance, it
-may have been unable to contact an authentication server.)
-The reason field will give a human-interpretable message
-providing further detail.
-.br
-.ne 10
-.Ms ProtocolDuplicate
-.Mf offending-minor-opcode
-.PN ProtocolSetup
-.Mf severity
-.PN FatalToProtocol
-(but see note)
-.Mf values
-STRING protocol name
-.Me
-The protocol name was already registered. This is fatal to
-the \*Qnew\*U protocol being set up by
-.PN ProtocolSetup ,
-but it does not affect the existing registration.
-.Ms MajorOpcodeDuplicate
-.Mf offending-minor-opcode
-.PN ProtocolSetup
-.Mf severity
-.PN FatalToProtocol
-(but see note)
-.Mf values
-CARD8 opcode
-.Me
-The major opcode specified was already registered. This is
-fatal to the \*Qnew\*U protocol being set up by
-.PN ProtocolSetup ,
-but it does not affect the existing registration.
-.Ms UnknownProtocol
-.Mf offending-minor-opcode
-.PN ProtocolSetup
-.Mf severity
-.PN FatalToProtocol
-.Mf values
-STRING protocol name
-.Me
-The protocol specified is not supported.
-.nH 1 "State Diagrams"
-.LP
-Here are the state diagrams for the party that initiates the connection:
-.Ss start
-.\" .St "connect to other end, send" ConnectionSetup conn_wait
-.RS
-connect to other end, send
-.PN ByteOrder ,
-.PN ConnectionSetup
-\(-> \fCconn_wait\fP
-.RE
-.Se
-.Ss conn_wait
-.St "receive" ConnectionReply stasis
-.St "receive" AuthenticationRequired conn_auth1
-.St "receive" Error quit
-.St "receive <other>, send" Error quit
-.Se
-.Ss conn_auth1
-.St "if good auth data, send" AuthenticationReply conn_auth2
-.St "if bad auth data, send" Error quit
-.Se
-.Ss conn_auth2
-.St "receive" ConnectionReply stasis
-.St "receive" AuthenticationNextPhase conn_auth1
-.St "receive" Error quit
-.St "receive <other>, send" Error quit
-.Se
-.br
-.ne 22
-Here are top-level state transitions for the party that accepts connections.
-.Ss listener
-.\" .St "accept connection" "" init_wait
-.RS
-accept connection \(-> \fCinit_wait\fP
-.RE
-.Se
-.Ss init_wait
-.\" .St "receive ByteOrder, ConnectionSetup" auth_ask
-.RS
-receive
-.PN ByteOrder ,
-.PN ConnectionSetup
-\(-> \fCauth_ask\fP
-.RE
-.St "receive <other>, send" Error quit
-.Se
-.Ss auth_ask
-.\" .St "send ByteOrder, ConnectionReply" stasis
-.RS
-send
-.PN ByteOrder ,
-.PN ConnectionReply
-\(-> \fCstasis\fP
-.RE
-.St "send" AuthenticationRequired auth_wait
-.St "send" Error quit
-.Se
-.Ss auth_wait
-.St "receive" AuthenticationReply auth_check
-.St "receive <other>, send" Error quit
-.Se
-.Ss auth_check
-.St "if no more auth needed, send" ConnectionReply stasis
-.St "if good auth data, send" AuthenticationNextPhase auth_wait
-.St "if bad auth data, send" Error quit
-.Se
-.sp 1
-Here are the top-level state transitions for all parties after the initial
-connection establishment subprotocol.
-.LP
-Note: this is not quite the truth for branches out from stasis, in
-that multiple conversations can be interleaved on the connection.
-.Ss stasis
-.St "send" ProtocolSetup proto_wait
-.St "receive" ProtocolSetup proto_reply
-.St "send" Ping ping_wait
-.\" .St "receive Ping, send PingReply" stasis
-.RS
-receive
-.PN Ping ,
-send
-.PN PingReply
-\(-> \fCstasis\fP
-.RE
-.St "receive" WantToClose shutdown_attempt
-.St "receive <other>, send" Error stasis
-.St "all protocols shut down, send" WantToClose close_wait
-.Se
-.Ss proto_wait
-.St "receive" ProtocolReply stasis
-.St "receive" AuthenticationRequired give_auth1
-.\" .St "receive Error, give up on this protocol" stasis
-.RS
-receive
-.PN Error ,
-give up on this protocol \(-> \fCstasis\fP
-.RE
-.St "receive" WantToClose proto_wait
-.Se
-.Ss give_auth1
-.St "if good auth data, send" AuthenticationReply give_auth2
-.\" .St "if bad auth data, send Error, give up on this protocol" stasis
-.RS
-if bad auth data, send
-.PN Error ,
-give up on this protocol \(-> \fCstasis\fP
-.RE
-.St "receive" WantToClose give_auth1
-.Se
-.Ss give_auth2
-.St "receive" ProtocolReply stasis
-.St "receive" AuthenticationNextPhase give_auth1
-.\" .St "receive Error, give up on this protocol" stasis
-.RS
-receive
-.PN Error ,
-give up on this protocol \(-> \fCstasis\fP
-.RE
-.St "receive" WantToClose give_auth2
-.Se
-.Ss proto_reply
-.St "send" ProtocolReply stasis
-.St "send" AuthenticationRequired take_auth1
-.\" .St "send Error, give up on this protocol" stasis
-.RS
-send
-.PN Error ,
-give up on this protocol \(-> \fCstasis\fP
-.RE
-.Se
-.Ss take_auth1
-.St "receive" AuthenticationReply take_auth2
-.\" .St "receive Error, give up on this protocol" stasis
-.RS
-receive
-.PN Error ,
-give up on this protocol \(-> \fCstasis\fP
-.RE
-.Se
-.Ss take_auth2
-.\" .St "if good auth data" take_auth3
-.RS
-if good auth data \(-> \fCtake_auth3\fP
-.RE
-.\" .St "if bad auth data, send Error, give up on this protocol" stasis
-.RS
-if bad auth data, send
-.PN Error ,
-give up on this protocol \(-> \fCstasis\fP
-.RE
-.Se
-.Ss take_auth3
-.St "if no more auth needed, send" ProtocolReply stasis
-.St "if good auth data, send" AuthenticationNextPhase take_auth1
-.\" .St "if bad auth data, send Error, give up on this protocol" stasis
-.RS
-if bad auth data, send
-.PN Error ,
-give up on this protocol \(-> \fCstasis\fP
-.RE
-.Se
-.Ss ping_wait
-.St "receive" PingReply stasis
-.Se
-.Ss quit
-.RS
-\(-> close connection
-.RE
-.Se
-.sp 1
-Here are the state transitions for shutting down the connection:
-.Ss shutdown_attempt
-.St "if want to stay alive anyway, send" NoClose stasis
-.\" .St "else" quit
-.RS
-else \(-> \fCquit\fP
-.RE
-.Se
-.Ss close_wait
-.St "receive" ProtocolSetup proto_reply
-.St "receive" NoClose stasis
-.St "receive" WantToClose quit
-.\" .St "connection close" quit
-.RS
-connection close \(-> \fCquit\fP
-.RE
-.Se
-.nH 1 "Protocol Encoding"
-.LP
-In the encodings below, the first column is the number of bytes occupied.
-The second column is either the type (if the value is variable) or the
-actual value. The third column is the description of the value (e.g.,
-the parameter name). Receivers must ignore bytes that are designated
-as unused or pad bytes.
-.LP
-This document describes major version 1, minor version 0 of the ICE protocol.
-.LP
-LISTof<type> indicates some number of repetitions of <type>, with no
-additional padding. The number of repetitions must be specified elsewhere
-in the message.
-.KS
-.nH 2 "Primitive Types"
-.LP
-.TS H
-expand;
-lB lB lB
-l l lw(3.5i).
-_
-.sp 6p
-Type Name Length (bytes) Description
-.sp 6p
-_
-.sp 6p
-.TH
-.R
-CARD8 1 8-bit unsigned integer
-CARD16 2 16-bit unsigned integer
-CARD32 4 32-bit unsigned integer
-LPCE 1 T{
-A character from the X Portable Character Set in Latin Portable Character
-Encoding
-T}
-.sp 6p
-_
-.TE
-.KE
-.KS
-.nH 2 "Enumerations"
-.LP
-.TS H
-expand;
-lB lB lB
-l l lw(3.5i).
-_
-.sp 6p
-Type Name Value Description
-.sp 6p
-_
-.sp 6p
-.TH
-.R
-BOOL 0 T{
-.PN False
-T}
- 1 T{
-.PN True
-T}
-.sp 6p
-_
-.TE
-.KE
-.KS
-.nH 2 "Compound Types"
-.LP
-.TS H
-expand;
-lB lB lB lB
-l l l lw(3.5i).
-_
-.sp 6p
-Type Name Length (bytes) Type Description
-.sp 6p
-_
-.sp 6p
-.TH
-.R
-VERSION
- 2 CARD16 Major version number
- 2 CARD16 Minor version number
-STRING
- 2 CARD16 length of string in bytes
- n LISTofLPCE string
- p unused, p = pad(n+2, 4)
-.sp 6p
-_
-.TE
-.KE
-.ne 6
-.nH 2 "ICE Minor opcodes"
-.LP
-.RS
-.TS
-lB cB
-l n.
-_
-.sp 6p
-Message Name Encoding
-.sp 6p
-_
-.sp 6p
-Error 0
-ByteOrder 1
-ConnectionSetup 2
-AuthenticationRequired 3
-AuthenticationReply 4
-AuthenticationNextPhase 5
-ConnectionReply 6
-ProtocolSetup 7
-ProtocolReply 8
-Ping 9
-PingReply 10
-WantToClose 11
-NoClose 12
-.sp 6p
-_
-.TE
-.RE
-.\" XXX - This is hokey, but I don't think you can nest .KS/.KE.
-.ne 16
-.nH 2 "Message Encoding"
-.LP
-.Es Error
- 1 CARD8 major-opcode
- 1 0 Error
- 2 CARD16 class
- 4 (n+p)/8+1 length
- 1 CARD8 offending-minor-opcode
- 1 severity:
- 0 CanContinue
- 1 FatalToProtocol
- 2 FatalToConnection
- 2 unused
- 4 CARD32 sequence number of erroneous message
- n <varies> value(s)
- p pad, p = pad(n,8)
-.Ee
-.Es ByteOrder
- 1 0 ICE
- 1 1 ByteOrder
- 1 byte-order:
- 0 LSBfirst
- 1 MSBfirst
- 1 unused
- 4 0 length
-.Ee
-.Es ConnectionSetup
- 1 0 ICE
- 1 2 ConnectionSetup
- 1 CARD8 Number of versions offered
- 1 CARD8 Number of authentication protocol names offered
- 4 (i+j+k+m+p)/8+1 length
- 1 BOOL must-authenticate
- 7 unused
- i STRING vendor
- j STRING release
- k LISTofSTRING authentication-protocol-names
- m LISTofVERSION version-list
- p unused, p = pad(i+j+k+m,8)
-.Ee
-.Es AuthenticationRequired
- 1 0 ICE
- 1 3 AuthenticationRequired
- 1 CARD8 authentication-protocol-index
- 1 unused
- 4 (n+p)/8+1 length
- 2 n length of authentication data
- 6 unused
- n <varies> data
- p unused, p = pad(n,8)
-.Ee
-.Es AuthenticationReply
- 1 0 ICE
- 1 4 AuthenticationReply
- 2 unused
- 4 (n+p)/8+1 length
- 2 n length of authentication data
- 6 unused
- n <varies> data
- p unused, p = pad(n,8)
-.Ee
-.Es AuthenticationNextPhase
- 1 0 ICE
- 1 5 AuthenticationNextPhase
- 2 unused
- 4 (n+p)/8+1 length
- 2 n length of authentication data
- 6 unused
- n <varies> data
- p unused, p = pad(n,8)
-.Ee
-.Es ConnectionReply
- 1 0 ICE
- 1 6 ConnectionReply
- 1 CARD8 version-index
- 1 unused
- 4 (i+j+p)/8 length
- i STRING vendor
- j STRING release
- p unused, p = pad(i+j,8)
-.Ee
-.Es ProtocolSetup
- 1 0 ICE
- 1 7 ProtocolSetup
- 1 CARD8 major-opcode
- 1 BOOL must-authenticate
- 4 (i+j+k+m+n+p)/8+1 length
- 1 CARD8 Number of versions offered
- 1 CARD8 Number of authentication protocol names offered
- 6 unused
- i STRING protocol-name
- j STRING vendor
- k STRING release
- m LISTofSTRING authentication-protocol-names
- n LISTofVERSION version-list
- p unused, p = pad(i+j+k+m+n,8)
-.Ee
-.Es ProtocolReply
- 1 0 ICE
- 1 8 ProtocolReply
- 1 CARD8 version-index
- 1 CARD8 major-opcode
- 4 (i+j+p)/8 length
- i STRING vendor
- j STRING release
- p unused, p = pad(i+j, 8)
-.Ee
-.Es Ping
- 1 0 ICE
- 1 9 Ping
- 2 0 unused
- 4 0 length
-.Ee
-.Es PingReply
- 1 0 ICE
- 1 10 PingReply
- 2 0 unused
- 4 0 length
-.Ee
-.Es WantToClose
- 1 0 ICE
- 1 11 WantToClose
- 2 0 unused
- 4 0 length
-.Ee
-.Es NoClose
- 1 0 ICE
- 1 12 NoClose
- 2 0 unused
- 4 0 length
-.Ee
-.nH 2 "Error Class Encoding"
-.LP
-Generic errors have classes in the range 0x8000\-0xFFFF, and
-subprotocol-specific errors are in the range 0x0000\-0x7FFF.
-.nH 3 "Generic Error Class Encoding"
-.LP
-.TS
-lB cB
-l n.
-_
-.sp 6p
-Class Encoding
-.sp 6p
-_
-.sp 6p
-BadMinor 0x8000
-BadState 0x8001
-BadLength 0x8002
-BadValue 0x8003
-.sp 6p
-_
-.TE
-.nH 3 "ICE-specific Error Class Encoding"
-.LP
-.TS
-lB cB
-l n.
-_
-.sp 6p
-Class Encoding
-.sp 6p
-_
-.sp 6p
-BadMajor 0
-NoAuthentication 1
-NoVersion 2
-SetupFailed 3
-AuthenticationRejected 4
-AuthenticationFailed 5
-ProtocolDuplicate 6
-MajorOpcodeDuplicate 7
-UnknownProtocol 8
-.sp 6p
-_
-.TE
-.bp
-.\" Set registers to number the appendixes A.1, B.1, C.1, ...
-.nr H1 0
-.af H1 A
-.cT "Appendix A" no
-.nH 1 "Modification History"
-.nH 2 "Release 6 to Release 6.1"
-.LP
-Release 6.1 added the ICE X rendezvous protocol (Appendix B) and
-updated the document version to 1.1.
-.nH 2 "Release 6.1 to Release 6.3"
-.LP
-Release 6.3 added the listen on well known ports feature.
-.bp
-.cT "Appendix B" no
-.nH 1 "ICE X Rendezvous Protocol"
-.nH 2 "Introduction"
-.LP
-The ICE X rendezvous protocol is designed to answer the need posed
-in Section 2 for one mechanism by which two clients interested in
-communicating via ICE are able to exchange the necessary information.
-This protocol is appropriate for any two ICE clients who also have X
-connections to the same X server.
-.nH 2 "Overview of ICE X Rendezvous"
-.LP
-The ICE X Rendezvous Mechanism requires clients willing to act as ICE
-originating parties to pre-register the ICE subprotocols they support in an
-ICE_PROTOCOLS property on their top-level window. Clients willing to
-act as ICE answering parties then send an ICE_PROTOCOLS X
-.PN ClientMessage
-event to the ICE originating parties. This
-.PN ClientMessage
-event identifies
-the ICE network IDs of the ICE answering party as well as the ICE
-subprotocol it wishes to speak. Upon receipt of this message the ICE
-originating party uses the information to establish an ICE connection
-with the ICE answering party.
-.nH 2 "Registering Known Protocols"
-.LP
-Clients willing to act as ICE originating parties preregister
-the ICE subprotocols they support in a list of atoms held by an
-ICE_PROTOCOLS property on their top-level window. The name of each
-atom listed in ICE_PROTOCOLS must be of the form
-ICE_INITIATE_\fIpname\fP where \fIpname\fP is the name of the ICE
-subprotocol the ICE originating party is willing to speak, as would be
-specified in an ICE
-.PN ProtocolSetup
-message.
-.LP
-Clients with an ICE_INITIATE_\fIpname\fP atom in the ICE_PROTOCOLS property
-on their top-level windows must respond to
-.PN ClientMessage
-events of
-type ICE_PROTOCOLS specifying ICE_INITIATE_\fIpname\fP. If a client does not
-want to respond to these client message events, it should
-remove the ICE_INITIATE_\fIpname\fP atom from its ICE_PROTOCOLS property
-or remove the ICE_PROTOCOLS property entirely.
-.nH 2 "Initiating the Rendezvous"
-.LP
-To initiate the rendezvous a client acting as an ICE answering
-party sends an X
-.PN ClientMessage
-event of type ICE_PROTOCOLS to an ICE
-originating party. This ICE_PROTOCOLS client message contains the
-information the ICE originating party needs to identify the ICE
-subprotocol the two parties will use as well as the ICE network
-identification string of the ICE answering party.
-.LP
-Before the ICE answering party sends the client message event it must
-define a text property on one of its windows. This text property
-contains the ICE answering party's ICE network identification string
-and will be used by ICE originating parties to determine the ICE
-answering party's list of ICE network IDs.
-.LP
-The property name will normally be ICE_NETWORK_IDS, but may be any
-name of the ICE answering party's choosing. The format for this text
-property is as follows:
-.ne 7
-.TS
-lB lB
-lw(1.25i) lw(4i) .
-_
-.sp 6p
-Field Value
-.sp 6p
-_
-.sp 6p
-type XA_STRING
-format 8
-value comma-separated list of ICE network IDs
-.sp 6p
-_
-.TE
-.LP
-Once the ICE answering party has established this text property on one
-of its windows, it initiates the rendezvous by sending an
-ICE_PROTOCOLS
-.PN ClientMessage
-event to an ICE originating party's
-top-level window. This event has the following format
-and must only be sent to windows that have pre-registered the ICE
-subprotocol in an ICE_PROTOCOLS property on their top-level window.
-.ne 13
-.TS
-lB lB
-lw(1.25i) lw(4i) .
-_
-.sp 6p
-Field Value
-.sp 6p
-_
-.sp 6p
-message_type Atom = "ICE_PROTOCOLS"
-format 32
-data.l[0] Atom identifying the ICE subprotocol to speak
-data.l[1] Timestamp
-data.l[2] T{
-ICE answering party's window ID with
-ICE network IDs text property
-T}
-data.l[3] T{
-Atom naming text property containing the ICE
-answering party's ICE network IDs
-T}
-data.l[4] Reserved. Must be 0.
-.sp 6p
-_
-.TE
-The name of the atom in data.l[0] must be of the form
-ICE_INITIATE_\fIpname\fP, where \fIpname\fP is the name of the ICE
-subprotocol the ICE answering party wishes to speak.
-.LP
-When an ICE originating party receives a
-.PN ClientMessage
-event of type
-ICE_PROTOCOLS specifying ICE_INITIATE_\fIpname\fP it can initiate an ICE
-connection with the ICE answering party.
-To open this connection the client retrieves the ICE answering
-party's ICE network IDs from the window specified in data.l[2] using
-the text property specified in data.l[3].
-.LP
-If the connection attempt fails for any reason, the client must
-respond to the client message event by sending a return
-.PN ClientMessage
-event to the window specified in data.l[2]. This return
-event has the following format:
-.ne 13
-.TS
-lB lB
-lw(1.25i) lw(4i) .
-_
-.sp 6p
-Field Value
-.sp 6p
-_
-.sp 6p
-message_type Atom = "ICE_INITIATE_FAILED"
-format 32
-data.l[0] Atom identifying the ICE subprotocol requested
-data.l[1] Timestamp
-data.l[2] T{
-Initiating party's window ID
-(holding ICE_PROTOCOLS)
-T}
-data.l[3] int: reason for failure
-data.l[4] Reserved, must be 0
-.sp 6p
-_
-.TE
-The values of data.l[0] and data.l[1] are copied directly from the
-client message event the client received.
-.LP
-The value in data.l[2] is
-the id of the window to which the ICE_PROTOCOLS.ICE_INITIATE_\fIpname\fP
-client message event was sent.
-.LP
-Data.l[3] has one of the following values:
-.LP
-.ne 21
-.TS
-lB cBw(0.6i) lB
-l n lw(4i) .
-_
-.sp 6p
-Value Encoding Description
-.sp 6p
-_
-.sp 6p
-T{
-.PN OpenFailed
-T} 1 T{
-The client was unable to open the connection
-(e.g. a call to IceOpenConnection() failed). If the
-client is able to distinguish authentication or
-authorization errors from general errors, then
-the preferred reply is
-.PN AuthenticationFailed
-for authorization errors.
-T}
-.sp 4p
-T{
-.PN AuthenticationFailed
-T} 2 T{
-Authentication or authorization of the
-connection or protocol setup was refused.
-This reply will be given only if the client is
-able to distinguish it from
-.PN OpenFailed ;
-otherwise
-.PN OpenFailed
-will be returned.
-T}
-.sp 4p
-T{
-.PN SetupFailed
-T} 3 T{
-The client was unable to initiate the specified
-protocol on the connection (e.g. a call to
-IceProtocolSetup() failed).
-T}
-.sp 4p
-T{
-.PN UnknownProtocol
-T} 4 T{
-The client does not recognize the requested
-protocol. (This represents a semantic error
-on the part of the answering party.)
-T}
-.sp 4p
-T{
-.PN Refused
-T} 5 T{
-The client was in the process of removing
-ICE_INITIATE_\fIpname\fP from its ICE_PROTOCOLS list
-when the client message was sent; the client no
-longer is willing to establish the specified ICE
-communication.
-T}
-.sp 6p
-_
-.TE
-.sp
-.NT "Advice to Implementors"
-Clients willing to act as ICE originating parties must update the
-ICE_PROTOCOLS property on their top-level windows to include the
-ICE_INITIATE_\fIpname\fP atom(s) identifying the ICE subprotocols they
-speak. The method a client uses to update the ICE_PROTOCOLS property
-to include ICE_INITIATE_\fIpname\fP atoms is implementation dependent, but
-the client must ensure the integrity of the list to prevent the
-accidental omission of any atoms previously in the list.
-.LP
-When setting up the ICE network IDs text property on one of its
-windows, the ICE answering party can determine its comma-separated
-list of ICE network IDs by calling IceComposeNetworkIdList() after
-making a call to IceListenForConnections(). The method an ICE
-answering party uses to find the top-level windows of clients willing
-to act as ICE originating parties is dependent upon the nature of the
-answering party. Some may wish to use the approach of requiring the
-user to click on a client's window. Others wishing to find existing
-clients without requiring user interaction might use something similar
-to the XQueryTree() method used by several freely-available
-applications. In order for the ICE answering party to become
-automatically aware of new clients willing to originate ICE
-connections, the ICE answering party might register for
-SubstructureNotify events on the root window of the display. When it
-receives a SubstructureNotify event, the ICE answering party can check
-to see if it was the result of the creation of a new client top-level
-window with an ICE_PROTOCOLS property.
-.LP
-In any case, before attempting to use this ICE X Rendezvous Mechanism
-ICE answering parties wishing to speak ICE subprotocol \fIpname\fP should
-check for the ICE_INITIATE_\fIpname\fP atom in the ICE_PROTOCOLS property on
-a client's top-level window. A client that does not include an
-ICE_INITIATE_\fIpname\fP atom in a ICE_PROTOCOLS property on some top-level
-window should be assumed to ignore
-.PN ClientMessage
-events of type
-ICE_PROTOCOLS specifying ICE_INITIATE_\fIpname\fP for ICE subprotocol
-\fIpname\fP.
-.NE
-.nH 2 "ICE Subprotocol Versioning"
-.LP
-Although the version of the ICE subprotocol could be passed in the
-client message event, ICE provides more a flexible version negotiation
-mechanism than will fit within a single
-.PN ClientMessage
-event. Because
-of this, ICE subprotocol versioning is handled within the ICE protocol
-setup phase.
-.NT Example
-Clients wish to communicate with each other via an ICE subprotocol
-known as "RAP V1.0". In RAP terminology one party, the "agent",
-communicates with other RAP-enabled applications on demand. The
-user may direct the agent to establish communication with a specific
-application by clicking on the application's window, or the agent may
-watch for new application windows to be created and automatically
-establish communication.
-.LP
-During startup the ICE answering party (the agent) first calls
-IceRegisterForProtocolReply() with a list of
-the versions (i.e., 1.0) of RAP the agent can speak. The answering
-party then calls IceListenForConnections() followed by
-IceComposeNetworkIdList() and stores the resulting ICE network IDs
-string in a text property on one of its windows.
-.LP
-When the answering party (agent) finds a client with which it wishes to
-speak, it checks to see if the ICE_INITIATE_RAP atom is in the ICE_PROTOCOLS
-property on the client's top-level window. If it is present the agent
-sends the client's top-level window an ICE_PROTOCOLS client
-message event as described above. When the client receives the client
-message event and is willing to originate an ICE connection using RAP,
-it performs an IceRegisterForProtocolSetup() with a list of the
-versions of RAP the client can speak. The client then retrieves
-the agent's ICE network ID from the property and window specified by
-the agent in the client message event and calls IceOpenConnection().
-After this call succeeds the client calls IceProtocolSetup() specifying
-the RAP protocol. During this
-process, ICE calls the RAP protocol routines that handle the version
-negotiation.
-.LP
-Note that it is not necessary for purposes of this rendezvous that
-the client application call any ICElib functions prior to receipt
-of the client message event.
-.NE
-.YZ 1